0x08.Shader函数tex2D
在 Unity Shader 中,tex2D
是最常用的纹理采样函数,用于从 2D 纹理中读取颜色值。它是实现纹理映射、法线贴图、遮罩效果等的核心工具。
1. 基本语法
fixed4 tex2D(sampler2D sampler, float2 uv);
sampler
:纹理采样器(如_MainTex
),需与Properties
块中声明的纹理关联。uv
:纹理坐标,通常是范围为[0, 1]
的二维向量。- 返回值:采样到的颜色值(
fixed4
或float4
,包含 RGBA 四个通道)。
2. 工作原理
- 纹理坐标:
uv
的(0,0)
对应纹理左下角,(1,1)
对应右上角。 - 采样方式:根据纹理的 Filter Mode(过滤模式)和 Wrap Mode(环绕模式)自动处理插值和边界行为。
3. 核心参数详解
3.1 纹理采样器 (sampler2D
)
sampler2D _MainTex; // 声明采样器
需在 Properties
块中关联纹理:
Properties {
_MainTex ("Texture", 2D) = "white" {} // 默认白色纹理
}
3.2 纹理坐标 (uv
)
- 范围:默认
[0, 1]
,超出范围的行为由纹理的 Wrap Mode 决定。 - 常见处理:
// 应用材质面板中的缩放和偏移 o.uv = TRANSFORM_TEX(v.uv, _MainTex); // 手动缩放纹理(例如重复4次) o.uv = v.uv * 4.0; // 镜像效果 o.uv = 1.0 - abs(o.uv * 2.0 - 1.0);
4. 纹理参数对采样的影响
4.1 Filter Mode(过滤模式)
控制纹理在缩放时的表现:
- Point:最近邻采样(像素风,硬边缘)。
- Bilinear:双线性插值(平滑过渡,默认)。
- Trilinear:三线性插值(考虑 mipmap,更平滑)。
4.2 Wrap Mode(环绕模式)
控制纹理坐标超出 [0, 1]
时的行为:
- Repeat:重复纹理(需配合
fract
或mod
使用)。 - Clamp:边缘像素延伸。
- Mirror:镜像重复。
5. 代码示例
5.1 基础纹理采样
fixed4 frag (v2f i) : SV_Target {
fixed4 col = tex2D(_MainTex, i.uv); // 采样纹理
return col;
}
5.2 纹理重复(4x4 平铺)
fixed4 frag (v2f i) : SV_Target {
float2 tiledUV = fract(i.uv * 4.0); // 使用fract确保坐标在[0,1]内
fixed4 col = tex2D(_MainTex, tiledUV);
return col;
}
5.3 带遮罩的纹理混合
sampler2D _MaskTex; // 遮罩纹理
fixed4 frag (v2f i) : SV_Target {
fixed4 baseCol = tex2D(_MainTex, i.uv); // 基础纹理
fixed4 maskCol = tex2D(_MaskTex, i.uv); // 遮罩纹理
fixed4 finalCol = lerp(baseCol, _Highlight, maskCol.r); // 根据遮罩值混合
return finalCol;
}
5.4 法线贴图采样
sampler2D _NormalMap; // 法线贴图
fixed4 frag (v2f i) : SV_Target {
fixed4 normalCol = tex2D(_NormalMap, i.uv); // 采样法线贴图
float3 normal = UnpackNormal(normalCol); // 解压法线向量
// 后续光照计算...
}
6. 高级变体函数
6.1 带 Mipmap 级别控制的采样
fixed4 tex2Dlod(sampler2D sampler, float4 uv_and_lod);
uv_and_lod.xy
:纹理坐标。uv_and_lod.w
:Mipmap 级别(0 表示最高精度)。
6.2 带导数计算的采样(用于抗锯齿)
fixed4 tex2Dgrad(sampler2D sampler, float2 uv, float2 ddx, float2 ddy);
ddx/ddy
:纹理坐标在屏幕空间的导数。
7. 性能与优化
- 减少采样次数:多次
tex2D
会显著降低性能。 - 使用压缩纹理:如 DXT、ETC 格式可减少内存占用。
- 合理设置 Mipmap:远距离物体启用 Mipmap 可提升性能。
总结
tex2D
是 Unity Shader 中纹理采样的核心函数,通过组合不同的纹理坐标处理和参数设置,你可以实现:
- 基础纹理映射
- 纹理重复与镜像
- 遮罩与混合效果
- 法线贴图与光照
- 高级渲染技术(如环境映射、后处理)
在 Unity Shader 中,除了基础的 tex2D
函数外,还有许多其他纹理采样函数,用于处理不同类型的纹理、实现特殊效果或优化性能。
1. 带 Mipmap 控制的采样
tex2Dlod
直接指定 Mipmap 级别,用于精细控制细节程度:
fixed4 tex2Dlod(sampler2D sampler, float4 uv_and_lod);
uv_and_lod.xy
:纹理坐标。uv_and_lod.w
:Mipmap 级别(0 表示最高精度,值越大越模糊)。
应用场景:程序化纹理、地形 LOD 过渡。
2. 带导数计算的采样
tex2Dgrad
手动提供纹理坐标的导数(用于屏幕空间变化率),优化抗锯齿:
fixed4 tex2Dgrad(sampler2D sampler, float2 uv, float2 ddx, float2 ddy);
ddx/ddy
:纹理坐标在屏幕空间 X/Y 方向的导数。
应用场景:快速移动对象的纹理采样、自定义过滤算法。
3. 3D 纹理采样
tex3D
用于采样体积纹理(如雾效、体积云):
fixed4 tex3D(sampler3D sampler, float3 uv);
uv
:三维纹理坐标。
应用场景:体积渲染、流体模拟、环境雾。
4. 立方体纹理采样
texCUBE
用于采样立方体贴图(如反射探针、天空盒):
fixed4 texCUBE(samplerCUBE sampler, float3 direction);
direction
:采样方向向量(从原点指向立方体表面)。
应用场景:反射、折射、环境光照。
5. 投影纹理采样
tex2Dproj
用于实现阴影映射或透视投影纹理:
fixed4 tex2Dproj(sampler2D sampler, float4 uv_proj);
uv_proj
:投影纹理坐标(通常是齐次坐标(u,v,w,q)
,采样时会自动执行(u/q, v/q)
)。
应用场景:阴影贴图、投影广告牌。
6. 双线性过滤的点采样
tex2Dbias
在采样时应用 Mipmap 偏移,实现更精细的控制:
fixed4 tex2Dbias(sampler2D sampler, float4 uv_bias);
uv_bias.xy
:纹理坐标。uv_bias.w
:Mipmap 偏移值(负值使纹理更清晰,正值使纹理更模糊)。
应用场景:选择性锐化或模糊特定区域。
7. 纹理数组采样
tex2Darray
用于采样纹理数组(一组相同尺寸的纹理):
fixed4 tex2Darray(sampler2DArray sampler, float3 uv);
uv.xy
:纹理坐标。uv.z
:纹理数组索引。
应用场景:多材质渲染、纹理动画序列。
8. 采样并比较(用于阴影)
tex2Dcmp
用于阴影采样,将采样值与比较值进行深度比较:
fixed tex2Dcmp(sampler2D sampler, float4 uv_compare);
uv_compare.xy
:纹理坐标。uv_compare.z
:用于比较的深度值。
应用场景:阴影贴图(与 UNITY_SAMPLE_TEXCUBE_COMPARE
配合使用)。
9. 特殊采样函数
UNITY_SAMPLE_TEXCUBE_LOD
Unity 专用的立方体贴图采样,带 LOD 控制:
fixed4 UNITY_SAMPLE_TEXCUBE_LOD(samplerCUBE sampler, float3 dir, float lod);
应用场景:带反射细节控制的 PBR 材质。
10. 内置宏与辅助函数
UNITY_SAMPLE_GI
采样全局光照(GI):
UNITY_SAMPLE_GI(lightColor, worldPos, worldNormal);
应用场景:间接光照计算。
总结
函数名 | 作用 | 应用场景 |
---|---|---|
tex2Dlod |
指定 Mipmap 级别采样 | 程序化纹理、地形 LOD |
tex2Dgrad |
手动提供导数 | 自定义过滤、抗锯齿 |
tex3D |
采样 3D 体积纹理 | 体积雾、流体模拟 |
texCUBE |
采样立方体贴图 | 反射、天空盒 |
tex2Dproj |
投影纹理采样 | 阴影映射、投影广告牌 |
tex2Darray |
采样纹理数组 | 多材质切换、纹理动画 |
tex2Dcmp |
采样并比较(阴影专用) | 阴影贴图 |
UNITY_SAMPLE_GI |
采样全局光照 | 间接光照计算 |