【问题标题】:How to define an array of floats in Shader properties?如何在 Shader 属性中定义浮点数组?
【发布时间】:2017-07-14 08:51:03
【问题描述】:

我想在我的着色器中定义一个浮点数组,如下所示:

Properties
{
    _TilesX ("Tiles X", Int) = 10
    _TilesY ("Tiles Y", Int) = 10

    _TileData1 ("Tile data", Float[]) = {} // THIS!!!

    _Texture1 ("Texture odd", 2D) = "white" {}
    _Texture2 ("Texture even", 2D) = "white" {}
}

我正在尝试创建一个将用作网格的平面,并且我想在运行时修改 _TileData1 以更改图块的 Y 偏移量。我正在使用 _TilesX 和 _TilesY 从一维数组中获取图块的二维位置。

为了清楚起见,我只想了解如何定义 float[] 的属性类型,因为我在 Unity 的手册页或论坛上找不到如何定义。

【问题讨论】:

    标签: unity3d shader


    【解决方案1】:

    您不能使用float[] 的属性。但是您可以将它们用作着色器中的变量并从脚本中设置它们:

    在你的着色器中:

    CGPROGRAM
    int _SegmentsCount = 0;
    float _Segments[1000];
    
    void surf (Input IN, inout SurfaceOutput o) {
        for (int i = 0; i < _SegmentsCount; i++) {
            // This is obsviously just an example,
            // avoid loops in shaders if you can help it.
        }
    }
    
    ENDCG
    

    然后在你的脚本中:

    float [] array = new float[] { 0.25f, 0.75f };
    material.SetFloatArray("_Segments", array);
    material.SetInt("_SegmentsCount", 2);
    
    renderer.material = material;
    

    【讨论】:

    • 所以 _Segments 必须有一个定义的长度? c#不能在运行时更改吗?
    • 它可以在你的 C# 代码中改变。但不在着色器中(因此将其超大到 1000 并需要在 _SegmentsCount 中传递长度)
    • 绝对的答案!谢谢
    【解决方案2】:

    显然不是。

    我不这么认为,因为我从未见过它,但我想我会四处搜索,然后我遇到了this thread,回答问题的人这样说(强调我的):

    从 5.4 开始,您可以使用 SetFloatArraySetVectorArraySetColorArray 从脚本中设置数组,但您不能在属性中定义数组。基本上这意味着 您仍然可以设置值并将其定义在要使用的 CGPROGRAM 块中,但它不会被序列化/由材质资产保存或显示在材质编辑器中。这是一个奇怪的遗漏,特别是因为纹理数组作为属性被支持(尽管纹理数组是一种特定类型的纹理采样器,而不是像颜色数组这样的纹理属性数组)。

    因此您可以在计算中使用它,但您只能通过 MonoBehaviour 脚本修改该值(并且需要)。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2013-01-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-03-24
      • 1970-01-01
      相关资源
      最近更新 更多