I was frustrated by an error when linking OpenGL es shader 3.0 program on iOS.
I have one vertex shader and one fragment shader and they are linked to generate a single program. There are shared uniforms and uniform blocks in both shaders. I understand that these uniforms must have exactly same type, precision and name, so that I even copy the uniform declaration from one shader to the other shader.
Here is the code of my vertex shader:
// Vertex shader #version 300 es precision highp float; // ........................... // Shared uniforms ... uniform mat4 viewMatrix; uniform mat4 modelViewMatrix; uniform mat4 texcoordMatrix; uniform mat4 projMatrix; uniform bool shadingEnabled; uniform bool fogEnabled; uniform bool flatShading; uniform bool specularEnabled; uniform bool generateReflectionTexCoord; uniform float zBias; layout (std140) uniform cbFog { int g_fogMode; float g_fogStart; float g_fogEnd; float g_fogDensity; vec4 g_fogColor; }; layout (std140) uniform cbMaterial { vec4 mtlAmbient; vec4 mtlDiffuse; vec4 mtlSpecular; vec4 mtlEmissive; int mtlSpecularPower; float _padding4; float _padding5; float _padding6; }; // ........................... // Vertex shader's input and output ... // ........................... // Vertex shader code ...
And here is the code of my fragment shader:
// Fragment shader #version 300 es precision highp float; // ........................... // Shared uniforms ... uniform mat4 viewMatrix; uniform mat4 modelViewMatrix; uniform mat4 texcoordMatrix; uniform mat4 projMatrix; uniform bool shadingEnabled; uniform bool fogEnabled; uniform bool flatShading; uniform bool specularEnabled; uniform bool generateReflectionTexCoord; uniform float zBias; layout (std140) uniform cbFog { int g_fogMode; float g_fogStart; float g_fogEnd; float g_fogDensity; vec4 g_fogColor; }; layout (std140) uniform cbMaterial { vec4 mtlAmbient; vec4 mtlDiffuse; vec4 mtlSpecular; vec4 mtlEmissive; int mtlSpecularPower; float _padding4; float _padding5; float _padding6; }; // ........................... // Fragment shader's input and output ... // ........................... // Fragment shader code ...
Please note that all uniform declarations are copied from vertex shader into fragment shader so that they are guaranteed to be identical.
The result is that the program can be successfully linked on Android and some OpenGL ES simulators like PowerVR, but it fail to be linked on iOS 10/11 and the following is the error message:
Error when linking shader program: ERROR: Uniform type mismatch '<uniform cbMaterial>' ERROR: Uniform type mismatch '<uniform cbFog>'
The iOS OpenGL ES complains that uniform block cbMaterial and cbFog have mismatched type. Anyone can help me find the reason for me? Thanks!
PS: I understand that OpenGL ES might be deprecated on macOS 10.14 and iOS 12, I still need to get this working on iOS for certain maintenance reason.
0 comments:
Post a Comment