Convert image to buffer in Java

I am trying to implement some simple 3D functions in the game that I am currently developing. I use the LibGDX Game Engine to achieve this, because it seemed to work well with OpenGL ES, however, I ran into a problem due to my inability to figure out how to create a simple Buffer object from an image in Java.

Problem

The goal for me is to have a cube rotating around in three-dimensional space, with some textures on it. The problem is that although I managed to render the cube and make it rotate, I cannot find any tutorials, code examples or documentation on how to actually decode the image in Buffer to texture the cube. I found quite a few examples illustrating how to do this in Android, but this limits the need to use the BitmapFactory.decodeResource(<your_image here>) method in the Android SDK, which is not an option for me, as I try to allow my code to be portable to many platforms.

It is for this reason that I came to the conclusion that I must somehow find a way to decode the image (the .bmp file) in Buffer in order to use the Gdx.gl10.glTexImage2D() method that I found bundled with OpenGL ES.

What have i tried so far

I used many alternatives to try and find a solution, some of which include:

  • Using the Texture.bind() method built into the Texture class that ships with the LibGDX package.
  • Attempting to decode an image using the Java ImageIO package .
  • Using some other decoding tools such as image4j library.

Some code

Here are some of the code I use to render Cube. A lot of OpenGL "switch switchers" is omitted for clarity, so if you think I missed something, post a comment and I will confirm that it is just in another part of another class.

I know this code will be quite suffocating for sifting, so I did my best to comment on it if necessary.

Please note that this code represents my current implementation and is the code associated with the Debug Information section below.

 public void draw(){ // This is used to hold the OpenGL pointer to the texture int[] textures = new int[1]; // Tells the GPU to render the vertices in a clockwise manner Gdx.gl10.glFrontFace(GL10.GL_CW); // Informs OpenGL of the location of the vertices Gdx.gl10.glVertexPointer(3, GL10.GL_FLOAT, 0, mVertexBuffer); // Bind the texture pointer in OpenGL to the texture Gdx.gl10.glBindTexture(GL10.GL_TEXTURE_2D, textures[0]); // This is the function I found in LibGDX that I think I am supposed to use? mTexture.bind(); // Some "switch-flipping" in OpenGL Gdx.gl10.glTexParameterf(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_MIN_FILTER, GL10.GL_NEAREST); Gdx.gl10.glTexParameterf(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_MAG_FILTER, GL10.GL_LINEAR); Gdx.gl10.glTexParameterf(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_WRAP_S, GL10.GL_CLAMP_TO_EDGE); Gdx.gl10.glTexParameterf(GL10.GL_TEXTURE_2D, GL10.GL_TEXTURE_WRAP_T, GL10.GL_CLAMP_TO_EDGE); Gdx.gl10.glTexEnvf(GL10.GL_TEXTURE_ENV, GL10.GL_TEXTURE_ENV_MODE, GL10.GL_REPLACE); // This tells OpenGL to assign my Texture to the 3D Image Gdx.gl10.glTexImage2D(GL10.GL_TEXTURE_2D, 0, GL10.GL_RGB, 256, 256, 0, GL10.GL_RGB, GL10.GL_UNSIGNED_BYTE, mTexture); // Finally, this draws the objects to the screen Gdx.gl.glDrawElements(GL10.GL_TRIANGLES, 6, GL10.GL_UNSIGNED_BYTE, mIndexBuffer); } 

My question

How do you decode an image directly in Buffer in Java? If this is not possible, then how should I try to texture my 3D objects in LibGDX? Are there any other resources I should consult with?

Debug information

Last updated: March 19, 2013 12:45 pm EST

Here is some information related to the current debugging process of my application. I will update this as I progress on this issue:

  • At the moment, when I launch my application, I get the error Invalid memory access of location 0x0 rip=0x11dc77564 , maybe this implementation is correct, and I just skip some syntax elsewhere?
  • I am currently studying this additional resource that I found after sifting through some forums.
  • It would seem that the Mesh object would be correct here. I will try to continue this implementation and update my results! I have not been able to find this before, since the LibGDX team is considered "deprecated", so I'm not sure if this will be replaced soon.

Additional Information

Some things to consider when answering my question:

  • It should be noted that I do this using the LibGDX Game Engine , and for this reason I will also post on their forums on this issue.

  • In addition, it seems that there are many ways to get a BufferedImage from an image, however there is no way to extract a Buffer from this BufferedImage . Am I just forgetting something obvious here? Is BufferedImage really all I need?

  • I would prefer not to include the Android SDK in my build path and use their simple BitmapFactory.decodeResource(<your_image_here>) method.

  • I'm currently trying to implement this using OpenGL ES 1.0 for compatibility reasons.

+4
source share
1 answer

I think you want to avoid the raw texture APIs and OpenGL buffers and stick with the Libgdx Mesh and Texture wrappers. They hide a bunch of OpenGL details. Of course, if you are interested in learning the details of OpenGL, this will not help. (But perhaps you can get everyone to work with the Libgdx APIs and then look at their source to see what is actually happening).

The first step is to make sure that your Mesh (or your original mVertexBuffer OpenGL list, if you are not using Mesh ) contains the correct (u, v) texture coordinates with each vertex. These coordinates will refer to the β€œcurrent” texture during rendering. See https://code.google.com/p/libgdx/wiki/MeshColorTexture#Texture .

First, define your Mesh to include text information with each vertex:

 mesh = new Mesh(true, 3, 3, new VertexAttribute(Usage.Position, 3, "a_position"), new VertexAttribute(Usage.ColorPacked, 4, "a_color"), new VertexAttribute(Usage.TextureCoordinates, 2, "a_texCoords")); 

(This grid also has color data, but you can leave a line with "a_color" if you don't want to mix raw color data.)

Another preload step is to load the texture file into the Libgdx texture. Assuming the file is packaged in the standard location β€œassets”, you should simply download it with a relative path:

 Texture texture = new Texture("path/to/image.bmp"); 

Libgdx can usually download and parse BMP, PNG, and JPEG files. For other formats, I think you need to create a Pixmap object yourself, and then connect it to the Texture .

Secondly, make sure that each vertex has (u, v) texture coordinates associated with it:

 mesh.setVertices(new float[] { -0.5f, -0.5f, 0, Color.toFloatBits(255, 0, 0, 255), 0, 1, 0.5f, -0.5f, 0, Color.toFloatBits(0, 255, 0, 255), 1, 1 0, 0.5f, 0, Color.toFloatBits(0, 0, 255, 255), 0.5f, 0 }); 

Each line above defines "(x, y, z, rgba, u, v)" for each vertex. ("Rgba" is all color compressed into one float.)

At this point, you have defined Mesh with the coordinates of the information and texture (u, v) Color .

The second step is to link your texture during the render call, so that the coordinates (u, v) in Mesh have a link:

 texture.bind(); mesh.render(GL10.GL_TRIANGLES, 0, 3); 

You do not need to use any of the OpenGL APIs or vertices.

+2
source

All Articles