Jogl,仅创建红色通道 u16 但得到“纹理类型和格式组合无效”

Posted

技术标签:

【中文标题】Jogl,仅创建红色通道 u16 但得到“纹理类型和格式组合无效”【英文标题】:Jogl, creating only red channel u16 but getting "Texture type and format combination is not valid" 【发布时间】:2014-02-07 10:47:40 【问题描述】:

所以,我正在尝试通过 id 来实现拣货。这意味着对于每个 drawArray,不同的唯一 id 将被设置为统一并保存在纹理上的红色组件中。

16位绰绰有余(65k元素),所以我选择使用shorts,我知道uniform变量只能是ui,但我还是决定试一试

我还发现了另一个问题,here,其中的答案包含一个短裤的小例子

但是这里我的代码初始化帧缓冲区和两个纹理,一个用于深度,一个用于 color_attachment0,只有红色分量为 16

        textures = new int[2];
        fbo = new int[1];

        gl3.glGenTextures(2, textures, 0);
        gl3.glGenFramebuffers(1, fbo, 0);
        /**
         * Depth.
         */
        gl3.glBindTexture(GL3.GL_TEXTURE_RECTANGLE, textures[depth]);

        gl3.glTexParameteri(GL3.GL_TEXTURE_RECTANGLE, GL3.GL_TEXTURE_WRAP_S, GL3.GL_CLAMP_TO_EDGE);
        gl3.glTexParameteri(GL3.GL_TEXTURE_RECTANGLE, GL3.GL_TEXTURE_WRAP_T, GL3.GL_CLAMP_TO_EDGE);
        gl3.glTexParameteri(GL3.GL_TEXTURE_RECTANGLE, GL3.GL_TEXTURE_MIN_FILTER, GL3.GL_NEAREST);
        gl3.glTexParameteri(GL3.GL_TEXTURE_RECTANGLE, GL3.GL_TEXTURE_MAG_FILTER, GL3.GL_NEAREST);

        gl3.glTexImage2D(GL3.GL_TEXTURE_RECTANGLE, 0, GL3.GL_DEPTH_COMPONENT32F, width, height, 0, GL3.GL_DEPTH_COMPONENT, GL3.GL_FLOAT, null);
        /**
         * IDs.
         */
        gl3.glBindTexture(GL3.GL_TEXTURE_RECTANGLE, textures[id]);

        gl3.glTexParameteri(GL3.GL_TEXTURE_RECTANGLE, GL3.GL_TEXTURE_WRAP_S, GL3.GL_CLAMP_TO_EDGE);
        gl3.glTexParameteri(GL3.GL_TEXTURE_RECTANGLE, GL3.GL_TEXTURE_WRAP_T, GL3.GL_CLAMP_TO_EDGE);
        gl3.glTexParameteri(GL3.GL_TEXTURE_RECTANGLE, GL3.GL_TEXTURE_MIN_FILTER, GL3.GL_NEAREST);
        gl3.glTexParameteri(GL3.GL_TEXTURE_RECTANGLE, GL3.GL_TEXTURE_MAG_FILTER, GL3.GL_NEAREST);

        gl3.glTexImage2D(GL3.GL_TEXTURE_RECTANGLE, 0, GL3.GL_R16UI, width, height, 0, GL3.GL_RED, GL3.GL_UNSIGNED_SHORT, null);
        /**
         * FBO.
         */
        gl3.glBindFramebuffer(GL3.GL_FRAMEBUFFER, fbo[0]);
        gl3.glFramebufferTexture2D(GL3.GL_FRAMEBUFFER, GL3.GL_DEPTH_ATTACHMENT, GL3.GL_TEXTURE_RECTANGLE, textures[depth], 0);
        gl3.glFramebufferTexture2D(GL3.GL_FRAMEBUFFER, GL3.GL_COLOR_ATTACHMENT0, GL3.GL_TEXTURE_RECTANGLE, textures[id], 0);

我在 id-glTexImage2D 收到以下错误

GLDebugEvent[ id 0x502
    type Error
    severity High: dangerous undefined behavior
    source GL API
    msg GL_INVALID_OPERATION error generated. Texture type and format combination is not valid.
    when 1391769197680
    source 4.4 (Compat profile, arb, debug, ES2 compat, ES3 compat, FBO, hardware) - 4.4.0 - hash 0x1c19b340]
java.lang.Exception: Stack trace
at java.lang.Thread.dumpStack(Thread.java:1364)
at jogamp.opengl.GLDebugMessageHandler$StdErrGLDebugListener.messageSent(GLDebugMessageHandler.java:308)
at jogamp.opengl.GLDebugMessageHandler.sendMessage(GLDebugMessageHandler.java:293)
at jogamp.opengl.GLDebugMessageHandler.glDebugMessageARB(GLDebugMessageHandler.java:319)
at jogamp.opengl.gl4.GL4bcImpl.dispatch_glTexImage2D1(Native Method)
at jogamp.opengl.gl4.GL4bcImpl.glTexImage2D(GL4bcImpl.java:27313)
at javax.media.opengl.DebugGL4bc.glTexImage2D(DebugGL4bc.java:19874)
at ec.rendering.input.picking.EC_Picking.initRenderingTargets(EC_Picking.java:107)

为了完整起见,这里是 VS:

#version 330

layout (location = 0) in vec3 position;

uniform mat4 modelToWorldMatrix;

layout(std140) uniform GlobalMatrices 
    mat4 worldToCameraMatrix;
    mat4 cameraToClipMatrix;
;

void main() 

    gl_Position = cameraToClipMatrix * (worldToCameraMatrix * vec4(position, 1.0));

modelToWorldMatrix 目前尚未考虑

这里是FS:

#version 330

uniform uint id;

out vec4 outputColor;

void main() 

    outputColor = vec4(id, 0, 0, 1);

穿短裤可行吗?

Jogl,Opengl 3.3

编辑:现在看来我解决了那部分

gl3.glTexImage2D(GL3.GL_TEXTURE_RECTANGLE, 0, GL3.GL_R16I, width, height, 0, GL3.GL_RED_INTEGER, GL3.GL_SHORT, null);

但现在当我尝试设置短统一值时出现错误

gl3.glUniform1i(pickModel.getIdUL(), (int)mesh.getId());

错误

GLDebugEvent[ id 0x502
    type Error
    severity High: dangerous undefined behavior
    source GL API
    msg GL_INVALID_OPERATION error generated. Wrong component type or count.
    when 1391779682993
    source 4.4 (Compat profile, arb, debug, ES2 compat, ES3 compat, FBO, hardware) - 4.4.0 - hash 0x5ee072e3]

统一位置似乎是正确的,因为它不是 -1(实际上是 1)...

那我怎么上传短片呢?

【问题讨论】:

对现有答案是否有任何其他问题或反馈,或者您自己已经解决了问题? @ChristianRau 不,我没有,因为即使是清除颜色opengl.org/discussion_boards/showthread.php/… 我也有不一致的地方,所以我决定放弃.. 【参考方案1】:

您的大部分问题都与 OpenGL 在转换方面不如您预期的那么友好这一事实有关。

首先对于glUniform 调用,统一变量的类型和大小必须与函数完全匹配。具体来说,the documentation 说:

GL_INVALID_OPERATION 如果有符号整数之一生成 此函数的变体用于加载类型的统一变量 unsigned int、uvec2、uvec3、uvec4 或这些数组。

因此,如果您的id 变量是uint,则您必须改用glUniform1ui(注意u!)。


除此之外,帧缓冲区的输出格式和着色器的输出格式之间也存在不匹配。如果要写入整数纹理,则需要从着色器中写入实际整数,因此将 outputColor 更改为

out int outputID;

或许

out ivec4 outputID;

如果有必要(当然,如果使用GL_R16UI,则使用“u”)。


顺便说一句,你确定你需要一个有符号整数纹理吗(因为无符号对于你的用例来说会更自然)?你说把glTexImage2D调用改成

gl3.glTexImage2D(GL3.GL_TEXTURE_RECTANGLE, 0, GL3.GL_R16I, width, height, 0, GL3.GL_RED_INTEGER, GL3.GL_SHORT, null);

使纹理错误消失,但这很可能是因为使用了GL_RED_INTEGER 而不仅仅是GL_RED,不一定是因为使用了签名格式。所以GL_R16UIGL_UNSIGNED_SHORTGL_RED_INTEGER(当然还有uintuvec4 作为输出变量)值得一试。

请记住,类型始终必须匹配。

【讨论】:

嗨,Christian,感谢您的回答,绝对值得一试,无论如何,我希望您看看我的这篇文章,并告诉我您对 clear on an 的看法int (short/int/u 不管什么) 纹理。 opengl.org/discussion_boards/showthread.php/…

以上是关于Jogl,仅创建红色通道 u16 但得到“纹理类型和格式组合无效”的主要内容,如果未能解决你的问题,请参考以下文章

在 jogl 中渲染大型 VBO 对象

您可以使用 JOGL 创建 3D 组件吗?

使用 JOGL GL3 核心的第一人称相机

索引越界异常尝试使用 Swing 和 JOGL 创建窗口

JOGL 阴影映射

仅查找结果后面的链接