Java-Gaming.org    
Featured games (81)
games approved by the League of Dukes
Games in Showcase (480)
Games in Android Showcase (110)
games submitted by our members
Games in WIP (547)
games currently in development
News: Read the Java Gaming Resources, or peek at the official Java tutorials
 
    Home     Help   Search   Login   Register   
Pages: [1]
  ignore  |  Print  
  How can I improve my rendering? (VAO/VBO)  (Read 1365 times)
0 Members and 1 Guest are viewing this topic.
Offline BloodShura

Senior Newbie


Exp: 2 years



« Posted 2014-05-01 16:40:00 »

(First, sorry for my bad english, I'm brazilian :/)

Good afternoon,

Well, I'm learning OpenGL/LWJGL right now, and I'm developing a little 2d game:



My problem is, even it's a 2D game, with 12 entities on my map, I'm having only 30 FPS. Yes, it's a crappy 2009' notebook with Intel on-board graphics and a simple dual-core CPU, but the same way, 30 FPS is sooo little for a 2D game.

So I've been reading some tutorials, articles, topics and etc about Sprite Batching, VBOs and VAOs, but I couldn't get it well. My rendering class right now is an edited Tessellator-class taken from Minecraft, used for testing and learning purposes only.

The class "Tessellator" right now:

http://www.java-gaming.org/?action=pastebin&id=909

Aand the "VertexObject" class used in Tessellator:

http://www.java-gaming.org/?action=pastebin&id=910

(Methods like hasColor(), getColor(), hasTexture(), getTextureUV(), etc, are all from sub-class Tessellator, but I'm sure they doesn't matter here.)

So, how can this be improved? I know there's a better solution for glXPointer, but even reading a lot I can't put it on practice.

Thanks in advance.
Offline orogamo
« Reply #1 - Posted 2014-05-02 09:20:41 »

If you are only using static images/tiles, you can use DisplayLists
Basically what it does is to pre-process your opengl vertices/normals etc.
So instead of letting opengl process everything realtime(every frame), DisplayLists computes it at startup.
BUT
If you have any animations, you should not use DisplayLists.
As DisplayLists only support static data.

You can also use VAO/VBO, but Display Lists are easier to setup.
And it can also be faster on older computers(at least in my experience)

TODO:
  • Create a Display list for every texture/tile
  • Use DisplayList instead of vertives (glBegin & glEnd)
  • Done! Cheesy

Take a look HERE or HERE for an example.
Or you can search google for Examples/Tutorials Smiley
Offline princec

JGO Kernel


Medals: 362
Projects: 3
Exp: 16 years


Eh? Who? What? ... Me?


« Reply #2 - Posted 2014-05-02 10:06:03 »

First things first, profile it. Run with -Xprof, let's see the output.

Cas Smiley

Games published by our own members! Check 'em out!
Legends of Yore - The Casual Retro Roguelike
Offline BloodShura

Senior Newbie


Exp: 2 years



« Reply #3 - Posted 2014-05-02 14:04:17 »

@orogamo:
Yes I've already seen the display lists, but the problem is: I have some animated tiles. But I'll try it, like rendering all static tiles via display lists and after, draw animated tiles separated, but I still think that the problem isn't the tiles itself, but yes the entities, and the entities are always in movement and changing sprites so display lists won't work :/ Anyway, thanks.

@princec:
Hey there, my -Xprof log result: http://www.java-gaming.org/?action=pastebin&id=911

As you can see, my org.shura.rpg.game.map.MapPhysics.detectTerrainIntersection is taking 15% of the time, but I still don't think this is the main issue (yeah, today I'll try to modify some things on it). GL.drawArrays is using 24%, and java.util.zip.Deflater.deflateBytes (wtf?) is using 13%.
Offline princec

JGO Kernel


Medals: 362
Projects: 3
Exp: 16 years


Eh? Who? What? ... Me?


« Reply #4 - Posted 2014-05-02 14:51:16 »

There's too much noise in that output... would you run it for maybe 5 minutes and then let's see the output again. Any startup code will be pushed out of the way then and we'll see what's really going on. Though right now yes, glDrawArrays is definitely your bottleneck, followed by your collision algorithm.

Cas Smiley

Offline BloodShura

Senior Newbie


Exp: 2 years



« Reply #5 - Posted 2014-05-02 19:31:20 »

Hey there,
Just saying, probably tomorrow I'll post it, because I upgraded from Win7 -> Win 8 and Intel haven't published the drivers for my graphics board, so yea it'll take some time 'til I be able to re-open my game.
Offline BloodShura

Senior Newbie


Exp: 2 years



« Reply #6 - Posted 2014-05-03 03:33:07 »

New log (around 4 minutes of execution):
http://www.java-gaming.org/?action=pastebin&id=912
Offline princec

JGO Kernel


Medals: 362
Projects: 3
Exp: 16 years


Eh? Who? What? ... Me?


« Reply #7 - Posted 2014-05-03 09:05:14 »

Right, that's much more clear.

There are two areas you can optimise then: the first one is the number of calls you are making to glDrawArrays - why so many? And secondly that detectTerrainIntersection method is suspiciously slow.

So, what are you drawing with each call to glDrawArrays? You're not drawing single sprites are you?

Cas Smiley

Offline BloodShura

Senior Newbie


Exp: 2 years



« Reply #8 - Posted 2014-05-03 14:46:05 »

Erm... hm... well... yeah, I'm drawing each sprite separately :// I'm very newbie on OpenGL, started learning like 1 month. I don't know how to name it correctly, but the Tessellator class is something like "vertex array immediate mode", isn't it?

Btw, the detectTerrainIntersection was my fault, I was calling it for each entity, each tick. Now I've made some 'cached collisions' workaround and it's working great, not even getting 4% on profilling.

So yeah, the problem is my stupid Tessellator class with immediate mode for every block and every entity on world, since I still am not that experienced to do something like Sprite Batching.

@Edit: Oh, and glBindTexture is taking 8%... another problem from immediate mode.
Offline princec

JGO Kernel


Medals: 362
Projects: 3
Exp: 16 years


Eh? Who? What? ... Me?


« Reply #9 - Posted 2014-05-04 23:26:24 »

Well, there's 3 things you need to do:

1. Pack all your sprites into texture atlases. Plenty of information around about how to do this.
2. Sort your sprites according to rendering state needed, eg. blend mode, texture binding
3. Batch all your sprites up into groups with the same rendering state, writing indices out to an index array, and use glDrawElements to draw, say, 100 sprites in one go, rather than 100 calls to glDrawArrays.

Stop using that tesselator thing.

Cas Smiley

Games published by our own members! Check 'em out!
Legends of Yore - The Casual Retro Roguelike
Offline BloodShura

Senior Newbie


Exp: 2 years



« Reply #10 - Posted 2014-05-04 23:52:28 »

Well, there's 3 things you need to do:

1. Pack all your sprites into texture atlases. Plenty of information around about how to do this.
2. Sort your sprites according to rendering state needed, eg. blend mode, texture binding
3. Batch all your sprites up into groups with the same rendering state, writing indices out to an index array, and use glDrawElements to draw, say, 100 sprites in one go, rather than 100 calls to glDrawArrays.

Stop using that tesselator thing.

Cas Smiley

Hello, and thanks for answering me, I know how boring this can be.

Well, I'll follow your tips ^^. Just wondering, when you say writing indices out to an index array, it's something like the method 'addVertex' here http://www.java-gaming.org/?action=pastebin&id=910? If yes, is it possible to configure more vertex properties, like brightness and etc using this array? (As I've seen, Minecraft have block brightness, and they are set on the arrays sent to glDrawArrays too.)
Offline princec

JGO Kernel


Medals: 362
Projects: 3
Exp: 16 years


Eh? Who? What? ... Me?


« Reply #11 - Posted 2014-05-05 10:24:37 »

Well, you know how you're doing glDrawArrays() and pointing it 4 vertices in a row each time?

Instead, write out all the vertex indices into a big int[] array:
{1,2,3,4,5,6,7,8,9,10...}

and then call glDrawElements() using that array. It joins up the vertices in order, each index points at a vertex. As yours are all conveniently in order (probably as quads, yes?) then your int array will indeed look like that example above, with 4 indices per quad.

Cas Smiley

Pages: [1]
  ignore  |  Print  
 
 

 

Add your game by posting it in the WIP section,
or publish it in Showcase.

The first screenshot will be displayed as a thumbnail.

atombrot (25 views)
2014-08-19 09:29:53

Tekkerue (24 views)
2014-08-16 06:45:27

Tekkerue (23 views)
2014-08-16 06:22:17

Tekkerue (13 views)
2014-08-16 06:20:21

Tekkerue (20 views)
2014-08-16 06:12:11

Rayexar (58 views)
2014-08-11 02:49:23

BurntPizza (38 views)
2014-08-09 21:09:32

BurntPizza (30 views)
2014-08-08 02:01:56

Norakomi (37 views)
2014-08-06 19:49:38

BurntPizza (67 views)
2014-08-03 02:57:17
List of Learning Resources
by Longor1996
2014-08-16 10:40:00

List of Learning Resources
by SilverTiger
2014-08-05 19:33:27

Resources for WIP games
by CogWheelz
2014-08-01 16:20:17

Resources for WIP games
by CogWheelz
2014-08-01 16:19:50

List of Learning Resources
by SilverTiger
2014-07-31 16:29:50

List of Learning Resources
by SilverTiger
2014-07-31 16:26:06

List of Learning Resources
by SilverTiger
2014-07-31 11:54:12

HotSpot Options
by dleskov
2014-07-08 01:59:08
java-gaming.org is not responsible for the content posted by its members, including references to external websites, and other references that may or may not have a relation with our primarily gaming and game production oriented community. inquiries and complaints can be sent via email to the info‑account of the company managing the website of java‑gaming.org
Powered by MySQL Powered by PHP Powered by SMF 1.1.18 | SMF © 2013, Simple Machines | Managed by Enhanced Four Valid XHTML 1.0! Valid CSS!