繁体   English   中英

在OpenGL ES和Android中编译片段着色器程序时出错

[英]Error in Compiling Fragment Shader Program in OpenGL es , Android

我是OpenGL的新手,今天我正尝试为Android OS中的OpenGL的GPGPU使用编译一些着色器程序。 我有两个问题:1)我只想编写片段着色器,是否也需要编写顶点着色器? 2)编译着色器源代码时遇到一些错误。 我的源代码定义为:

 final String src = "#version 310 es\\n" + "uniform sampler2D texUnit;\\n" + "uniform int sequence;\\n" + "void main(void)\\n" + "{\\n" + "const vec3 DotValue = {0.299f , 0.587f , 0.114f};\\n" + "vec2 texCoord = gl_TexCoord[0].xy;\\n" + "vec4 CurrentPixelData = texture2D(texUnit, texCoord);\\n" + "float temp = CurrentPixelData.x * DotValue.x + CurrentPixelData.y * DotValue.y + CurrentPixelData.z * DotValue.z;\\n" + "vec4 result = {temp,temp,temp,CurrentPixelData.w};\\n" + "gl_FragColor = result;\\n" + "}\\n"; 

创建着色器的代码是:

 int fragment = GLES20.glCreateShader(GLES20.GL_FRAGMENT_SHADER); GLES20.glShaderSource(fragment,src); GLES20.glCompileShader(fragment); int[] compiled = new int[1]; GLES20.glGetShaderiv(fragment, GLES20.GL_COMPILE_STATUS, compiled, 0); //compile[0] != 0 : compiled successfully if (compiled[0] == 0) { Log.e(TAG, "Could not compile shader: "); Log.e(TAG, GLES20.glGetShaderInfoLog(fragment)); GLES20.glDeleteShader(fragment); fragment = 0; } else { Log.i(TAG, "Compiled shader with source length " + src.length()); } 

但是,当我尝试调试应用程序时,在logcat中存在有关着色器编译的一些错误:

  0:6: L0001: Expected token ';', found '{' 0:7: L0002: Undeclared variable 'gl_TexCoord' 0:8: L0002: No matching function for call to 'texture2D' 0:9: L0002: Undeclared variable 'CurrentPixelData' 0:10: L0001: Expected token ';', found '{' 0:11: L0002: Undeclared variable 'gl_FragColor' 

谁能帮助我我的代码有什么问题? 提前致谢。

您确实需要顶点着色器和片段着色器。

捕获的着色器编译日志已经突出显示了语法错误。 提供有关它们的更多详细信息:

  1. 您需要使用构造函数语法来初始化向量:

     const vec3 DotValue = vec3(0.299 , 0.587, 0.114); 
  2. gl_TexCoord不是内置变量。 您可能在曾经存在过的桌面OpenGL的代码示例中看到了它。 但是即使在那儿它也已被弃用,并且在OpenGL ES中从未出现过。 您需要自己将纹理坐标传递到着色器中。

  3. texture2D()不是内置函数。 用于采样2D纹理的函数在GLSL较旧的版本中以前是这样命名的,但是现在在名为texture()各种采样器类型中重载了该函数:

     vec4 CurrentPixelData = texture(texUnit, texCoord); 
  4. 看起来只是上一个错误的跟进错误。

  5. 与错误1相同:

     vec4 result = vec4(temp, temp, temp, CurrentPixelData.w); 
  6. gl_FragColor曾经是旧版GLSL版本中的内置变量,但现在已弃用并删除。 你需要带限定符定义自己的变量out定义用作着色器的输出变量(一个或多个)。

您必须编写一个顶点着色器。 必须为gl_Position赋值,以创建三角形,然后创建像素(片段)。 如果使用纹理贴图,则需要分配一个变化变量,并将纹理坐标指定给顶点。 之后,为每个片段内插这些坐标。 最基本的顶点着色器是:

    const char* simpleVertexShader=
    "attribute vec4 position;"
    "attribute vec4 inputTextureCoordinate;
    "varying   vec2 textureCoordinate;"
    "void main(){"
    "gl_Position = position;"
    "textureCoordinate = inputTextureCoordinate.xy;"
    "}";

在片段着色器中,您在vec3和vec4 init中存在语法错误。 应该这样完成:

  "const vec3 DotValue = vec3(0.299 , 0.587 , 0.114);\n"

  "vec4 result = vec4(temp,temp,temp,CurrentPixelData.w);\n"

注意,float字面量在glsl中不需要'f'后缀。

您的固定代码:

  final String src = "#version 310 es\n" +
        "precision   highp float;"
        "uniform sampler2D texUnit;\n" +
    "varying   vec2 textureCoordinate" +
        "void main(void)\n" +
        "{\n" +
        "const vec3 DotValue = vec3(0.299 , 0.587 , 0.114);\n" +
        "vec2 texCoord = textureCoordinate;\n" +
        "vec4 CurrentPixelData  = texture2D(texUnit, texCoord);\n" +
        "float temp = CurrentPixelData.x * DotValue.x + CurrentPixelData.y * DotValue.y + CurrentPixelData.z * DotValue.z;\n" +
        "vec4 result = vec4(temp,temp,temp,CurrentPixelData.w);\n" +
        "gl_FragColor = result;\n" +
        "}\n";

如果您从一个好的openGL教程开始,这对您来说会容易得多。

祝好运!

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM