1

I am trying to load an image into OpenGL texture.

I created a window and GL 4.4 Core Forward-Compatible context:

context

Here's the code I'm using to load the image and create the texture:

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"

The commented out line is another attempt to put anything meaningful into that texture.

Here's what gDebugger reports for the texture information:

texture information

And here's what it shows for the texture contents:

texture contents

When I print out the structure returned by JuicyPixels, it prints out distinct byte sequences that most certainly don't produce a flat image.

In this example I'm not rendering the texture, and I'm using raw binding generated by the gl package. I had exactly the same behaviour (with the same shade of teal) when using OpenGL package. It unsurprisingly rendered as a flat rectangle on the screen.

I have tried with different images, sized 128x128 and NPOT (100x100 as in the screenshots).

What could be causing that behaviour?

Full source.

Bartek Banachewicz
  • 38,596
  • 7
  • 91
  • 135
  • 1
    To whoever closed this as "without the clear problem statement/missing code" - the code is linked as Gist, because the Q is too long already, and the parts in the gist aren't relevant to the problem at hand; they're presented merely for convenience. As for the statement, I think it's pretty obvious I'm not loading a PNG with just teal colour in it, huh. – Bartek Banachewicz Feb 06 '15 at 16:02
  • 2
    Since when is `N/A` a sensible value for `GL_TEXTURE_MIN_FILTER` on a regular 2D texture? Are you sure this isn't just gDEBugger being stupid? Or maybe it put `N/A` there because your minification filter includes mipmapping, but your number of texture LODs is wrong? – Andon M. Coleman Feb 06 '15 at 18:09
  • Have you tried looking at the output of glGetError? – Mokosha Feb 07 '15 at 02:42
  • @Mokosha I always set gDebugger to break on errors. – Bartek Banachewicz Feb 07 '15 at 17:47

2 Answers2

1

This is most probably the bug in gDEBugger. After some manipulations and actually drawing the texture, I've verified that it indeed contains the right data.

Bartek Banachewicz
  • 38,596
  • 7
  • 91
  • 135
0

Combining the highly functional Haskell with OpenGL, the poster child of messy state, is tenebrific at best, and therefore I confess to being a little over my head with this exact scenario.

However, it is well-known that OpenGL textures are incomplete without both a minification filter and a magnification filter that match the data (see here). I didn't see such in the code, so your texture is incomplete. In C, you would add something like:

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

As pointed out in the comments, this probably shouldn't be causing gDEBugger to give bogus output; skimming the documentation, I didn't see anything that requires textures to be complete to be read from (and gDEBugger works by intercepting GL calls anyway). Still, reading from a texture with mismatched sampling filters feels wrong to me; I wouldn't be surprised if it's an edge case.

geometrian
  • 14,775
  • 10
  • 56
  • 132
  • 1
    Well. The default filters are well-defined. It is mipmapping for minification, making the texture not _mipmapping-complete_. However, the texture object itself is till valid, can be read back, or be accessed with `texelFetch`. That gdebugger output is totally misleading, as there is no way to get some `N/A` state there. I don't say that setting those filters is a bad idea, but that won't fix the issue here. – derhass Feb 07 '15 at 16:46
  • @derhass hmmmm, you're right. See edit; I have clarified my intention. – geometrian Feb 07 '15 at 17:20
  • As expected, adding the proper filter settings didn't change gDebugger output. – Bartek Banachewicz Feb 10 '15 at 10:39