gpt4 book ai didi

opengl-es - 写入 gl_FragColor 会导致 Android 上的 INVALID_OPERATION

转载 作者:行者123 更新时间:2023-12-04 22:02:48 26 4
gpt4 key购买 nike

我正在尝试为 NDK 掌握 OGLES2 并坚持使用 GLSL 着色器。情况类似于 the one already highlighted here ,但背后的原因似乎有些不同。

我有最简单的着色器。

顶点:

#version 110
attribute vec3 vPosition;
void main(void)
{
gl_Position = vec4(vPosition, 1.0);
gl_FrontColor = gl_BackColor = vec4(0.3, 0.3, 0.3, 1); // ***
}

分段:

#version 110
void main(void)
{
gl_FragColor = gl_Color;
}

简单直接。我什至在剪辑空间中直接定义我的三角形。
当我在我的 Android 403 设备上运行应用程序时,VS 源代码中的星号( ***)行会调用 glUseProgram 以引发 GL_INVALID_OPERATION 错误(并且所有后续的 glGetAttribLocation 调用都会这样做)。我可以写入 FS 中的 gl_FragColor(一些硬编码的 vec4 值),但甚至无法触摸 VS 中的 gl_FrontColor/ gl_BackColor 值。

E/Adreno200-ES20(16211): <qgl2DrvAPI_glUseProgram:1344>: GL_INVALID_OPERATION
E/Adreno200-ES20(16211): <qgl2DrvAPI_glGetAttribLocation:531>: GL_INVALID_OPERATION

我在着色器编译和链接期间检查了所有可能的错误( glGetErrorglGetShaderInfoLog ),一切都很清楚。

当我将我的 OGL 实现切换到 JOGL 时,该应用程序在 Windows 上运行良好(所有引导和渲染代码保持不变)。我什至可以使用包含颜色的顶点属性,完全没有问题。

有没有办法解决这种行为?我不相信 Android OGLES 实现有那么病态,可能我只是缺少它的一些功能......

最佳答案

OpenGL ES 2.0 没有正面/背面颜色。这已从核心 OpenGL 3.x 中删除,同时从未引入 OpenGL ES 2.0。同样,gl_Color在您的片段着色器中无效。

从技术上讲,我认为 #version 110也是无效的,因为我从未在 OpenGL ES 中遇到过 GLSL 110 的正式规范。这很可能是人们从桌面 GL 遗留下来的一个坏习惯(GLSL 是在 OpenGL 2.0 中引入的,从 #version 110 开始)。 GLSL 100确实存在,但不是作为适当批准的规范;它使用非常古老的 ARB 扩展。

OpenGL ES 2.0 #version 100 介绍了 GLSL ES ,正确的 GLSL ES 着色器应该以 #version 100 开头。 (OpenGL ES 2.0) 或 #version 300 (OpenGL ES 3.0)。

以下是在使用最初为桌面 OpenGL 设计的着色器时可能会遇到的一些预先声明的变量(兼容性配置文件):

顶点

  • gl_FrontColor
  • gl_BackColor
  • gl_FrontSecondaryColor
  • gl_BackSecondaryColor

  • 分段
  • gl_Color
  • gl_SecondaryColor

  • 这些都不是有效的在核心 OpenGL 3.x 或 OpenGL ES 2.0 中;为此,您必须创建自己的变量,在顶点着色器和片段着色器之间共享。

    为了纠正您的情况,我更新了您的顶点和片段着色器以避免使用 gl_FrontColor , gl_Color , ETC..

    修改后的顶点着色器:

    #version 100

    attribute vec3 vPosition;

    // Vertex and Fragment Shaders will both use this varying to communicate
    // interpolated color between vertices...
    varying vec4 color;

    void main (void)
    {
    gl_Position = vec4 (vPosition, 1.0);
    color = vec4 (0.3, 0.3, 0.3, 1.0);
    }

    修改片段着色器:

    #version 100

    /* This takes the place of the old *gl_Color*, but it does not handle
    * polygon side. If you _really_ do need a different color for
    * front and back, then you will have to do things a little
    * differently (SEE BELOW).
    */
    varying vec4 color;

    void main(void)
    {
    gl_FragColor = color;
    }

    很少有你真的需要每面不同的颜色,但如果你真的需要,这里就是你如何实现这一点的方法。为了在 OpenGL ES 2.0 中实现单面颜色,您可以使用内置的 gl_FrontFacing .这个变量是一个 bool 值,告诉你多边形的哪一侧被着色。

    假设的双面片段着色器:

    #version 100

    varying vec4 front_color;
    varying vec4 back_color;

    void main (void) {
    gl_FragColor = gl_FrontFacing ? front_color : back_color;
    }

    如果您正在使用教程来学习 GLSL,我怀疑您正在关注基于桌面 OpenGL 的教程。 OpenGL 的 GLSL 和 OpenGL|ES 的 GLSL 略有不同,在 ES 2.0 中,GLSL 语法大致相当于 OpenGL 的 GLSL 120。

    总体而言,最大的区别在于,大多数仅在桌面 OpenGL 中被弃用的东西实际上已从 OpenGL|ES 中删除。这就是为什么跟随桌面 GL 教程可能不是那么好 - OpenGL 3.0 引入了 GLSL 版本 130,其语法 ES 2.0 不理解。同时,为 OpenGL 3.0 编写的教程最有可能避免使用已弃用的功能。

    尽管 OpenGL 和 OpenGL|ES 是从同一个 API 派生的,但是像这样的细微差别使得学习为一个 API 编写的教程并将它们应用到另一个 API 变得困难:-\

    我在答案的第一部分中讨论了每个版本的 OpenGL、OpenGL ES、GLSL 和 GLSL ES 的规范链接,以帮助您真正“掌握”OGLES2。

    关于opengl-es - 写入 gl_FragColor 会导致 Android 上的 INVALID_OPERATION,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19077295/

    26 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com