Shader Graph already provides some texture sampling nodes (e.g. Sample Texture 2D) for use in the graph. But it can be useful to sample inside a Custom Function, e.g. inside a loop, or to access sampling macros that don’t have built-in nodes. Macros In shader code online you might typically see sampler2D and tex2D() functions being used. This is the older DX9 syntax, but with Shader Graph we mostly use the newer DX11+ syntax which has separate objects for the texture and sampler. This isn’t supported in all platforms though (GLES2), so Unity provides a bunch of macros which can generate different code. These macros are defined in files found under render-pipelines.core/ShaderLibrary/API. Some important macros for sampling textures are listed below : Sample : Can be used in Fragment stage only SAMPLE_TEXTURE2D(textureName, samplerName, coord2) SAMPLE_TEXTURECUBE(textureName, samplerName, coord3) SAMPLE_TEXTURE3D(textureName, samplerName, coord3) SAMPLE_TEXTURE2D_ARRAY(textureName, samplerName, coord2, index) SAMPLE_TEXTURECUBE_ARRAY(textureName, samplerName, coord3, index) These macros would end up using tex.Sample(…) (on DX11+ type platforms) Sample Level (of Detail) : Provides lod input to specify the mip map level sampled. Can be used in both Vertex & Fragment stages SAMPLE_TEXTURE2D_LOD(textureName, samplerName, coord2, lod) SAMPLE_TEXTURECUBE_LOD(textureName, samplerName, coord3, lod) SAMPLE_TEXTURE3D_LOD(textureName, samplerName, coord3, lod) SAMPLE_TEXTURE2D_ARRAY_LOD(textureName, samplerName, coord2, index, lod) SAMPLE_TEXTURECUBE_ARRAY_LOD(textureName, samplerName, coord3, index, lod) These macros would end up using tex.SampleLevel(…) (on DX11+ type platforms) Sample Bias : Provides a bias to adjust the mip map level. Can be used in Fragment stage only. SAMPLE_TEXTURE2D_BIAS(textureName, samplerName, coord2, bias) SAMPLE_TEXTURECUBE_BIAS(textureName, samplerName, coord3, bias) SAMPLE_TEXTURE2D_ARRAY_BIAS(textureName, samplerName, coord2, index, bias) SAMPLE_TEXTURECUBE_ARRAY_BIAS(textureName, samplerName, coord3, index, bias) Doesn’t seem to be BIAS macros for Texture3D. May be able to use tex.SampleBias(…) function still (or tex3Dbias for GLES2) Sample Gradient : Provides inputs for partial derivatives. Can be used in both Vertex & Fragment stages. (Unless you use ddx()/ddy() functions to calculate those derivates as those are Fragment only). These are useful when the UV coords used for sampling aren’t continous, see Pixellation along seams question above. SAMPLE_TEXTURE2D_GRAD(textureName, samplerName, coord2, dpdx, dpdy) SAMPLE_TEXTURE2D_ARRAY_GRAD(textureName, samplerName, coord2, index, dpdx, dpdy) Doesn’t seem there is GRAD macros for other texture types. May be able to use tex.SampleGrad(…) function still (or texCUBEgrad/tex3Dgrad for GLES2) Shader Graph Texture Types In Shader Graph v10.3+ (Unity 2020.2.3f1+), structs were added which wrap textures and their associated samplers together, allowing them to both be passed into a Custom Function node in a single parameter. These types are defined in render-pipelines.core/ShaderLibrary/Texture.hlsl UnityTexture2D (“Texture 2D” in SG dropdown) UnityTexture2DArray (“Texture 2D Array” in SG dropdown) UnityTexture3D (“Texture 3D” in SG dropdown) UnityTextureCube (“Cubemap” in SG dropdown) UnitySamplerState (“Sampler State” in SG dropdown) The sampler state associated with the texture can be accessed using .samplerstate on the UnityTextureX object. UnityTexture2D also has access to the Texel Size (via .texelSize). Custom Function Example (v10.3+) If you aren’t familiar with the Custom Function node syntax see Intro to Shader Graph - Custom Functions and Custom Function docs page. Here is an example sampling a 3D Texture, using LOD version so it could be used in the vertex stage. This code would be put in a .hlsl file for use with Custom Function File mode. It would also work with String mode but then you would only want the body of the function (inside {}) and you need to match the names for inputs/outputs. 1 2 3 void Example_float(UnityTexture3D Tex, float3 UV, out float4 Out){ Out = SAMPLE_TEXTURE3D_LOD(Tex, Tex.samplerstate, UV, 0); } Inputs : “Texture 3D”, named “Tex” “Vector2”, named “UV” Outputs : “Vector4”, named “Out” Custom Function Example (Pre-v10.3) Earlier versions don’t have these UnityTextureX/UnitySamplerState types so instead need to use the HLSL texture objects, such as Texture3D and SamplerState. For example : 1 2 3 void Example_float(Texture3D Tex, SamplerState SS, float3 UV, out float4 Out){ Out = SAMPLE_TEXTURE3D_LOD(Tex, SS, UV, 0); } Inputs : “Texture 3D”, named “Tex” “SamplerState”, named “SS” “Vector2”, named “UV” Outputs : “Vector4”, named “Out” This could also be used in newer versions, by using the “Bare Texture 3D” and “Bare Sampler State” options on the input/output types. (Though this will likely error in GLES2 platforms, hence why the newer structs were introduced)