ARTICLE DETAIL

资讯详情

深耕网站建设、视觉设计与SEO优化的一线实战洞察。

详解Unity Shader.PropertyToID

详解Unity Shader.PropertyToID 目录方法声明完整示例类执行过程为什么使用 Property IDMaterial常用Set方法速查表哪些 Set 方法不属于 Shader 属性传值参考资料方法声明public static int PropertyToID(string name);参数参数说明nameShader 属性名称例如_EdgeColor。返回值类型说明int该 Shader 属性名称在当前运行环境中的整数标识符。Shader.PropertyToID()用于获取 Shader 属性名称对应的整数 ID。相比在Material.SetColor()或MaterialPropertyBlock中反复传入字符串缓存并使用整数 ID 更适合需要频繁设置材质参数的场景。例如private static readonly int EdgeColorId Shader.PropertyToID(_EdgeColor);需要注意同一个属性名对应的 ID 在本次游戏运行期间保持不变但在不同运行过程或不同设备之间可能不同。因此该 ID 只能作为运行时标识使用不应进行持久化保存或通过网络发送。完整示例类using UnityEngine; public class ShaderPropertyIdExample : MonoBehaviour { [SerializeField] private Material material; [SerializeField] private Color edgeColor Color.red; // 把 Shader 属性名转换成整数 ID并缓存下来。 private static readonly int EdgeColorId Shader.PropertyToID(_EdgeColor); private void Update() { if (material null) return; // 找到 EdgeColorId 对应的 Shader 属性 // 将 edgeColor 的颜色数据写入该属性。 material.SetColor(EdgeColorId, edgeColor); } }Shader 中需要存在对应属性Properties { _EdgeColor (Edge Color, Color) (0, 0, 0, 1) }HLSL 中也需要声明CBUFFER_START(UnityPerMaterial) float4 _EdgeColor; CBUFFER_ENDColor包含RGBA四个分量因此在 HLSL 中使用float4接收。执行过程第一步把 Shader 属性名转换成整数 IDprivate static readonly int EdgeColorId Shader.PropertyToID(_EdgeColor);概念上相当于_EdgeColor → 属性编号 1234512345只是示例实际编号由 Unity 在运行时生成。第二步通过属性编号找到材质中的_EdgeColor并写入颜色material.SetColor(EdgeColorId, edgeColor);假设颜色为edgeColor Color.red;那么这行代码表达的是找到 EdgeColorId 对应的 Shader 属性 _EdgeColor 把红色写入这个属性它并不是把颜色赋给EdgeColorId这个整数变量。EdgeColorId只负责定位目标属性edgeColor才是真正需要传递的数据。为什么使用 Property ID字符串版本material.SetColor(_EdgeColor, edgeColor);每次调用都需要根据字符串确定目标 Shader 属性。Property ID 版本private static readonly int EdgeColorId Shader.PropertyToID(_EdgeColor); material.SetColor(EdgeColorId, edgeColor);类初始化时完成一次名称转换之后直接使用整数编号访问属性。这个过程与 DNS 的思路比较相似域名 → DNS 解析 → IP 地址对应到 Shader 属性属性名 → PropertyToID → 整数 ID主要优点包括避免在高频调用中反复处理属性名称。适合Update()和 Render Pass 等每帧执行的位置。属性名称集中定义减少代码中重复出现字符串。修改属性名时只需要调整一处。下面是两个小tip1. static readonly的含义private static readonly int EdgeColorId Shader.PropertyToID(_EdgeColor);其中private只允许当前类内部使用。static所有该类实例共享同一份 ID。readonly初始化完成后不能重新赋值。intProperty ID 使用整数表示。因此EdgeColorId适合作为类级别的只读属性编号。2. 注意属性名称必须一致C# 中的属性名称Shader.PropertyToID(_EdgeColor);必须与 Shader 中的名称完全一致float4 _EdgeColor;注意大小写HLSL会进行区分还可以在设置前检查材质是否包含该属性if (material ! null material.HasProperty(EdgeColorId)) { material.SetColor(EdgeColorId, edgeColor); }Material常用Set方法速查表C# 方法C# 数据类型常见 HLSL 类型主要用途SetFloatfloatfloat、half强度、速度、范围、阈值SetIntegerintint模式编号、数量、索引SetColorColorfloat4、half4基础色、描边色、雾颜色SetVectorVector4float4、half4方向、参数组合、坐标SetMatrixMatrix4x4float4x4空间变换矩阵SetTextureTextureTEXTURE2D等颜色贴图、遮罩、深度图SetBufferComputeBuffer或GraphicsBufferStructuredBuffer向 GPU 传递结构化数据SetConstantBufferComputeBuffer或GraphicsBuffercbuffer绑定常量缓冲区SetFloatArrayfloat[]或Listfloatfloat[]浮点数组SetColorArrayColor[]或ListColorfloat4[]颜色数组SetVectorArrayVector4[]或ListVector4float4[]向量数组SetMatrixArrayMatrix4x4[]或ListMatrix4x4float4x4[]矩阵数组SetTextureOffsetVector2对应纹理的_ST.zw设置纹理偏移SetTextureScaleVector2对应纹理的_ST.xy设置纹理缩放哪些 Set 方法不属于 Shader 属性传值Material还包含一些以Set开头的方法但用途不同方法用途SetPass激活材质中的某个 Shader PassSetShaderPassEnabled启用或禁用指定 PassSetOverrideTag修改材质的 Shader TagSetKeyword设置局部 Shader Keyword 状态SetPropertyLock控制材质属性锁定状态这些方法不是向某个 HLSL变量写入普通数据因此不应与SetFloat()、SetColor()混为一类。参考资料1. Shader-PropertyToID - Unity 脚本 API
返回列表