程序员Unity Shader分享unity3D技术分享

Unity 传递 Array 给 Shader

2017-04-06  本文已影响3896人  cdf02aaf6ae2

缘起

有时候我们需要传一组数据给我们的 Shader,以便实现一些特殊的效果。但 Unity 官方的 ShaderLab 貌似不提供这样的功能,我们能定义的属性只有有限的几种:纹理、数值等。

其实在底层,不管是 OpenGL 还是 Direct3D,其 Shader 都是支持传递任意数量数组数据的。Unity 虽然对 Shader 开发进行了一些简化封装,却并没有屏蔽这样的功能。而且在其 5.4+ 版本中,还通过增加的 API 提供了有限的引擎支持。

步骤

Shader

  1. 变量声明
uniform float4 _Points[100];  // 数组变量
uniform float _Points_Num;  // 数组长度变量
  1. 在 Surface Shaders 或 Vertex and Fragment Shaders 中使用
// 遍历
for (int j=0; j<_Points_Num; j++)
{
    float4 p4 = _Points[j]; // 索引取值
    // 自定义处理
}

Script

  1. 通过 Material 给 Shader 传递真正的数组数据
var points = new Vector4[60];
for (var i = 0; i < 60; i++)
{
    points[i] = new Vector4(some.x, some.y, some.z, some.w);
}

var render = GetComponentInChildren<MeshRenderer>();
foreach (var material in render.materials)
{
    material.SetInt("_Points_Num",points.Length);
    material.SetVectorArray("_Points",points);
}
  1. 通过 Shader 进行全局赋值
Shader.SetGlobalInt("_Points_Num",points.Length);
Shader.SetGlobalVectorArray("_Points",points);

限制

注意

参考

  1. Arrays & shaders: heatmaps in Unity
  2. Arrays & Shaders in Unity 5.4+
上一篇 下一篇

猜你喜欢

热点阅读