OpenGL纹理包含不良数据 - 发生了什么?

时间:2015-02-06 15:41:26

标签: opengl haskell juicy-pixels

我正在尝试将图像加载到OpenGL纹理中。

我创建了一个窗口和GL 4.4 Core Forward-Compatible上下文:

context

这是我用来加载图像和创建纹理的代码:

load :: IO ()
load = do
    image <- JP.readImage "image.png"
    case image of
        (Left err) -> do print err
                         exitWith (ExitFailure 1)
        (Right imgData) -> do 
            a <- malloc
            glGenTextures 1 a
            texId <- peek a
            free a
            loadImgIntoTexture texId imgData

loadImgIntoTexture texId (JP.ImageRGBA8 (JP.Image width height dat)) = do
    glBindTexture GL_TEXTURE_2D texId
    unsafeWith dat $ glTexImage2D GL_TEXTURE_2D 0 GL_RGBA (fromIntegral width) (fromIntegral height) 0 GL_RGBA GL_UNSIGNED_BYTE . castPtr
    --p <- mallocBytes $ (fromIntegral width) * (fromIntegral height) * 4
    --glTexImage2D GL_TEXTURE_2D 0 GL_RGBA (fromIntegral width) (fromIntegral height) 0 GL_RGBA GL_UNSIGNED_BYTE (castPtr p)
    print "everything ok"

注释掉的行是另一种尝试将任何有意义的东西放入该纹理中。

以下是gDebugger为纹理信息报告的内容:

texture information

以下是纹理内容的显示内容:

texture contents

当我打印出JuicyPixels返回的结构时,会打印出明显不会生成平面图像的不同字节序列。

在这个例子中,我没有渲染纹理,而是使用gl包生成的原始绑定。使用OpenGL包时,我的行为完全相同(使用相同的蓝绿色)。毫不奇怪,它在屏幕上呈现为扁平矩形。

我尝试过不同的图像,尺寸为128x128和NPOT(截图中为100x100)。

可能导致这种行为的原因是什么?

Full source

2 个答案:

答案 0 :(得分:1)

将功能强大的Haskell与混乱状态的海报孩子OpenGL结合在一起,充其量只是一个聪明的因素,因此我承认在这个具体情况下有点过头了。

然而,众所周知,如果没有缩小滤镜和与数据匹配的放大滤镜,OpenGL纹理就不完整(参见here)。我在代码中没有看到这样的内容,所以你的纹理不完整。在C中,您可以添加如下内容:

glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR);
glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_LINEAR);

正如评论中所指出的,这可能不应该导致gDEBugger给出虚假输出;浏览文档时,我没有看到任何需要纹理完整才能读取的内容(并且gDEBugger无论如何通过拦截GL调用来工作)。尽管如此,从具有不匹配采样过滤器的纹理中读取对我来说是错误的;如果它是一个边缘案例,我不会感到惊讶。

答案 1 :(得分:0)

这很可能是gDEBugger中的错误。经过一些操作并实际绘制纹理后,我已经确认它确实包含正确的数据。