Eoi*_*Roe 2 shader modifier scenekit metal
我在将制服传递给场景套件的着色器修改器时遇到困难。这在使用 OpenGL 时似乎工作正常,但在使用 Metal 时则不然。
我之前曾成功使用过 SCNProgram,但想利用 SceneKit 的曲面细分器,而不是为曲面细分设置计算着色器。
但我想使用我已经用 Metal 编写的代码,而不是使用 OpenGL。
不幸的是,关于如何做到这一点的例子并不多。这个 Swift Playground 演示了如何在 OpenGL 中很好地做到这一点。
https://github.com/markpmlim/Twister/blob/master/Twister.playground/Contents.swift
//Geometry - Metal will translate the OpenGL code.
let geometryShaderModifier =
"uniform float twistFactor;\n" +
"mat4 rotationAroundX(float angle) {\n" +
"return mat4(1.0, 0.0, 0.0, 0.0,\n" +
" 0.0, cos(angle), -sin(angle), 0.0,\n" +
" 0.0, sin(angle), cos(angle), 0.0,\n" +
" 0.0, 0.0, 0.0, 1.0);\n" +
"}\n" +
"#pragma body\n" +
"float rotationAngle = _geometry.position.x * twistFactor;\n" +
"mat4 rotationMatrix = rotationAroundX(rotationAngle);\n" +
"_geometry.position *= rotationMatrix;\n" +
"vec4 twistedNormal = vec4(_geometry.normal, 1.0) * rotationMatrix;\n" +
"_geometry.normal = twistedNormal.xyz;\n"
Run Code Online (Sandbox Code Playgroud)
但是当我将其更改为 Metal 时,它不起作用:
let geometryShaderModifier =
"#pragma arguments \n" +
"float twistFactor;\n" +
"float4x4 rotationAroundX(float angle) {\n" +
"return float4x4(1.0, 0.0, 0.0, 0.0,\n" +
" 0.0, cos(angle), -sin(angle), 0.0,\n" +
" 0.0, sin(angle), cos(angle), 0.0,\n" +
" 0.0, 0.0, 0.0, 1.0);\n" +
"}\n" +
"#pragma body\n" +
"float rotationAngle = _geometry.position.x * twistFactor;\n" +
"float4x4 rotationMatrix = rotationAroundX(rotationAngle);\n" +
"_geometry.position *= rotationMatrix;\n" +
"float4 twistedNormal = float4(_geometry.normal, 1.0) * rotationMatrix;\n" +
"_geometry.normal = twistedNormal.xyz;\n"
Run Code Online (Sandbox Code Playgroud)
这就是我使用键值编码提供值的方式:
// The uniform "twistFactor" must be assigned a value.
torus.setValue(1.0, forKey: "twistFactor")
Run Code Online (Sandbox Code Playgroud)
我想我可以切换回使用 OpenGL 来解决这个问题,但有点令人沮丧的是,Apple 着色器修改器文档的前几行很难工作。
// For Metal, a pragma directive and one custom variable on each line:
#pragma arguments
float intensity;
Run Code Online (Sandbox Code Playgroud)
我看到不同论坛上流传着许多具有相同基本问题的帖子,如果他们能够为此提供更清晰的文档,那就太好了。
我收到以下错误消息:
程序源:2566:50:错误:使用未声明的标识符“twistFactor”
预先感谢您的任何帮助!
您可以使用#pragma declaration标记来帮助 SceneKit 区分着色器修改器参数和本地函数:
let geometryShaderModifier =
"#pragma arguments\n" +
"float twistFactor;\n" +
"#pragma declaration\n" + // HERE
"float4x4 rotationAroundX(float angle) {\n" +
"return float4x4(1.0, 0.0, 0.0, 0.0,\n" +
" 0.0, cos(angle), -sin(angle), 0.0,\n" +
" 0.0, sin(angle), cos(angle), 0.0,\n" +
" 0.0, 0.0, 0.0, 1.0);\n" +
"}\n" +
"#pragma body\n" +
"float rotationAngle = _geometry.position.x * twistFactor;\n" +
"float4x4 rotationMatrix = rotationAroundX(rotationAngle);\n" +
"_geometry.position *= rotationMatrix;\n" +
"float4 twistedNormal = float4(_geometry.normal, 1.0) * rotationMatrix;\n" +
"_geometry.normal = twistedNormal.xyz;\n"
Run Code Online (Sandbox Code Playgroud)