开发者

Efficient way to convert a 2D bitmap into a 3D cube model?

开发者 https://www.devze.com 2023-01-28 23:39 出处:网络
I want to create cube model of a 32x32 bitmap in opengl. For example, the result should look something like this given a 2D bitmap of Bob-omb from Super Mario: http://fc02.deviantart.net/fs49/f/2009/1

I want to create cube model of a 32x32 bitmap in opengl. For example, the result should look something like this given a 2D bitmap of Bob-omb from Super Mario: http://fc02.deviantart.net/fs49/f/2009/186/f/a/Bob_omb_in_Minecraft_by_Luafox.png The idea is to represent each 2D pixel from the bitmap as a 3D cube.

Each model will represent an enemy in a game so I need to be able to render these quickly. What would be a good way of doing this?

One attempt I've made is to generate a static 3D model from the bitmap by first creating a 32x32x2 grid of vertices and then creating trian开发者_开发百科gles from these vertices in the appropriate places to form the cube faces. One big problem I'm having though is how to store the colors and normals for the faces. The triangles of each face need to share a vertex and that shared vertex needs to store the color and the normal for that face. However, I don't think I have enough vertices for each face to have the appropriate color and normal. I can't think of an elegant way to solve this.


You'll be fastest if you render the front face as a single texture mapped GL_QUAD, using alpha and GL_ALPHA_TEST for the 'transparent' parts. You then make the boundary, i.e. the non front-facing squares, as one or more GL_QUAD_STRIPs.

If you are determined to draw the sprite as a series of actual cubes, for example if you want to blow up the sprite into separate cubes, or if you have very detailed textures on the small cube faces, then make a display list for one cube and call that display list repeatedly.


Regarding storing colors and normals for the faces; I think you have to accept that you need to duplicate vertices in the same position for the different faces. If two vertices share some attributes but differ in others, they are essentially different - even if one attribute that they share is their position.

So, you should build some VBOs, with duplicate vertices as necessary. You may want to run this as a design-time step and save the results into a convenient format to save some work at runtime.

edit: That doesn't mean that you need to have separate vertices for every single corner of every face of every cube. Actually, the cheapest way to render what you want (while the blocks are together) with a reasonably easy implementation would probably be to render the front and back each as two triangles, using a texture for colour, GL_MAG_FILTER, GL_NEAREST sampling and careful alignment of texture coordinates, using a pixel shader to clip on transparent texels.

You will then need to do a bit more work (not necessarily at run time) to work out which faces will be visible from the sides, and make each of those as geometry (all of that geometry being a single static VBO to display, thus reducing both the number of draw calls and geometry cost as compared to for example calling a -deprecated, although still often useful- display list for each cube). Again, with care you can ensure that this precisely joins with the invisible parts of the front and back faces.

If you do then want to have your enemies blow up and have the constituent cubes go their separate ways, you can then switch to a more expensive version displaying every single cube.


Just a hint on how you can find some interesting readings about that: search for "voxel". http://en.wikipedia.org/wiki/Voxel

Maybe you would like to take a look to the source code of the open source game engines Cube/Sauerbraten, that are based on cubes subdivision for the maps, and come with a nice in-game editor: http://sauerbraten.org/

0

精彩评论

暂无评论...
验证码 换一张
取 消