0
votes

Recently I've been trying to implement my own PNG texture decoder/loader, however like my several previous attempts the outcome is the same... no textures. Here is the code (Not mine! I forget the website) I currently use for loading the image:

public static TextureObject loadTexture(BufferedImage image)
             {
             int[] pixels = new int[image.getWidth() * image.getHeight()];
                image.getRGB(0, 0, image.getWidth(), image.getHeight(), pixels, 0, image.getWidth());

                ByteBuffer buffer = BufferUtils.createByteBuffer(image.getWidth() * image.getHeight()     *                              4); //4 for RGBA, 3 for RGB

            for(int y = 0; y < image.getHeight(); y++){
                for(int x = 0; x < image.getWidth(); x++){
                    int pixel = pixels[y * image.getWidth() + x];
                    buffer.put((byte) ((pixel >> 16) & 0xFF));     // Red component
                    buffer.put((byte) ((pixel >> 8) & 0xFF));      // Green component
                    buffer.put((byte) (pixel & 0xFF));               // Blue component
                    buffer.put((byte) ((pixel >> 24) & 0xFF));    // Alpha component. Only for RGBA
                }
            }

            buffer.flip();
            GL11.glEnable(GL11.GL_TEXTURE_2D);
            int textureID = GL11.glGenTextures();
           GL11.glTexImage2D(GL11.GL_TEXTURE_2D, 0, GL11.GL_RGBA8, image.getWidth(), image.getHeight(), 0, GL11.GL_RGBA, GL11.GL_UNSIGNED_BYTE, buffer);
        return new TextureObject(textureID, image.getWidth(), image.getHeight());   
    }

Searching through similar problems all returned the same cause, not enabled GL_TEXTURE_2D.
I've enabled this, as well as given my quad texture coords.
When I bind my texture and attempt to render it, opengl decides it want's to make the whole screen white. I have Slick-Util in my project for testing, and it renders things fine.
However, if I have the following code in my render() function:

    GL11.glColor3f(1.0F, 1.0F, 1.0F);    

    if(RenderUtil.fontTexture != null) RenderUtil.renderTexturedQuad(RenderUtil.fontTexture, 40,     40, 150, 150);
    Main.t.bind();
    GL11.glBegin(GL11.GL_QUADS);
    GL11.glTexCoord2f(0, 0);
    GL11.glVertex2f(0, 0);
    GL11.glTexCoord2f(0, 1);
    GL11.glVertex2f(0, 512);
    GL11.glTexCoord2f(1, 1);
    GL11.glVertex2f(512, 512);
    GL11.glTexCoord2f(1, 0);
    GL11.glVertex2f(512, 0);
    GL11.glEnd();

... mainly the if(RenderUtil.fontTexture != null) RenderUtil.renderTexturedQuad(RenderUtil.fontTexture, 40, 40, 150, 150), OpenGL will not render anything. Even binding a slick texture and attemping to render that will fail. Here is the renderTexturedQuad() method in full:

public static void renderTexturedQuad(TextureObject texture, int x, int y, int w, int h)
{
    GL11.glColor3f(1.0F, 1.0F, 1.0F);
    GL11.glEnable(GL11.GL_TEXTURE_2D);
    TextureUtil.bind(texture);
    GL11.glPushMatrix();
    GL11.glTranslatef(x, y, 0);
    GL11.glBegin(GL11.GL_QUADS);
    GL11.glTexCoord2f(0, 0);
    GL11.glVertex2f(0, 0);
    GL11.glTexCoord2f(0, 1);
    GL11.glVertex2f(0, h);
    GL11.glTexCoord2f(1, 1);
    GL11.glVertex2f(w, h);
    GL11.glTexCoord2f(1, 0);
    GL11.glVertex2f(w, 0);
    GL11.glEnd();
    GL11.glPopMatrix();
}

The only thing I see that could be setting things wrong is the binding of my texture?

I'd prefer if you didn't refer me to a library or equivalent, this is a learning experience :)

1
what does TextureUtil.bind(texture); do?Dawnkeeper
@Dawnkeeper GL11.glBindTexture(GL11.GL_TEXTURE_2D, texture.GL_TEX_ID);, I guess it's just an unnecessary reference to the GL11 method. Just noticed you fixed up my post, thanks :) Still gotta get used to it.Trey
Are you sure that your texture is loaded correctly? You could try texture = TextureLoader.getTexture("PNG", ResourceLoader.getResourceAsStream("res/image.png")); from Slick instead your own method to test this. See hereDawnkeeper
@Dawnkeeper I did try that :) Currently thats the only way of rendering for me. If I bind and render a slick texture prior to rendering my own texture, the slick texture wont render and the screen goes white. It's as if the screen doesnt clear.Trey
Could the white be your quad(you are setting that color)? The BufferedImage is your texture? Can you verify that it loaded correctly e.g by writing int to a file with ImageIO?Dawnkeeper

1 Answers

1
votes

You need to bind the texture before you load the image data in to it. If you don't glTexImage2D doesn't know where to load the data.

You can bind the texture by calling:

GL11.glBindTexture(GL11.GL_TEXTURE_2D, textureID);

Before:

GL11.glTexImage2D(GL11.GL_TEXTURE_2D, 0, GL11.GL_RGBA8, image.getWidth(), image.getHeight(), 0, GL11.GL_RGBA, GL11.GL_UNSIGNED_BYTE, buffer);

You should also call these lines after you load the image data:

    GL11.glTexParameteri(GL11.GL_TEXTURE_2D, GL11.GL_TEXTURE_WRAP_S, GL11.GL_REPEAT);
    GL11.glTexParameteri(GL11.GL_TEXTURE_2D, GL11.GL_TEXTURE_WRAP_T, GL11.GL_REPEAT);
    GL11.glTexParameteri(GL11.GL_TEXTURE_2D, GL11.GL_TEXTURE_MIN_FILTER, GL11.GL_LINEAR);
    GL11.glTexParameteri(GL11.GL_TEXTURE_2D, GL11.GL_TEXTURE_MAG_FILTER, GL11.GL_NEAREST);