I'm currently working on a FPS 3D game using libGDX. I aim to have maze-like levels (like the original Doom and Duke Nukem 3D) so I'm making a level editor with a top-down view and lets you stretch lines (which represent walls) and create sectors. I read that libGDX Models aren't efficient if you plan to have lots of them (I believe that a level could have hundreds of lines). My question: is there an alternative to that? I checked Decals but unfortunately they are not affected by an Environment light. Does anybody have any idea how to improve performance to handle these amount of walls? Should I use BSP-Trees in order to render the walls? Thanks
\$\begingroup\$
\$\endgroup\$
3
-
\$\begingroup\$ LibGDX Models have no way to being less efficient. They are just collections of Vertex and Index Buffers, which would be exactly the case if you were working with OpenGL and wanted to keep a model in memory. \$\endgroup\$– Gustavo MacielCommented Jun 4, 2018 at 15:46
-
\$\begingroup\$ Ok, is there an alternative way to draw walls? (3d rects) \$\endgroup\$– Gad WissbergCommented Jun 4, 2018 at 16:28
-
1\$\begingroup\$ Yes, use a single model for your world, and compose it with lots of meshes. I added an answer as example. \$\endgroup\$– Gustavo MacielCommented Jun 4, 2018 at 19:59
Add a comment
|
1 Answer
\$\begingroup\$
\$\endgroup\$
2
You may look into https://github.com/libgdx/libgdx/wiki/ModelBuilder%2C-MeshBuilder-and-MeshPartBuilder .
You can construct your level walls using a single model with more than one mesh parts.
Here is some sample code:
ModelBuilder worldBuilder = new ModelBuilder();
MeshPartBuilder meshBuilder;
Vector3 corner00 = new Vector3(),
corner10 = new Vector3(),
corner11 = new Vector3(),
corner01 = new Vector3(),
normal = new Vector3();
modelBuilder.begin();
meshBuilder = worldBuilder.part("room1", GL20.GL_TRIANGLES, Usage.Position | Usage.Normal, new Material());
meshBuilder.rect(corner00.set(-10, -10, 0), //room 1, wall 1
corner10.set( 10, -10, 0),
corner11.set( 10, 10, 0),
corner01.set(-10, 10, 0), normal.set(0, 0, 1));
meshBuilder.rect(corner00.set(-10, -10, 10), //room 1, wall 2
corner10.set( 10, -10, 10),
corner11.set( 10, 10, 10),
corner01.set(-10, 10, 10), normal.set(0, 0, -1));
Node node = modelBuilder.node();
node.translation.set(100,0,0); // next room far away
meshBuilder = worldBuilder.part("room2", GL20.GL_TRIANGLES, Usage.Position | Usage.Normal, new Material());
meshBuilder.rect(corner00.set(-10, -10, 0), //room 2, wall 1
corner10.set( 10, -10, 0),
corner11.set( 10, 10, 0),
corner01.set(-10, 10, 0), normal.set(0, 0, 1));
meshBuilder.rect(corner00.set(-10, -10, 10), //room 2, wall 2
corner10.set( 10, -10, 10),
corner11.set( 10, 10, 10),
corner01.set(-10, 10, 10), normal.set(0, 0, -1));
Model worldModel = worldBuilder.end();
This way you can use meshBuilder in room localCoordinates, and use the nodes to control room positioning.
You can also disable node by node later on, if you want to do BSP optimization and only draw adjacent rooms.
-
\$\begingroup\$ Hi @Gustavo Maciel Is there a way to separately change the color of wall 1 or wall 2? \$\endgroup\$– igoCommented Jan 21, 2022 at 2:54
-
1\$\begingroup\$ @igo You'd need to create and assign separate Material instances for wall 1 and wall 2 \$\endgroup\$ Commented Jan 15 at 9:42