Reputation: 2258
I am porting a C++ 2D game to Android with the help of the NDK and the SDL; and I use OpenGL to render the sprites. The performances are quite disappointing.
After some investigations, I have found that the bottleneck is in the OpenGL calls during the rendering procedure. Wait a second! Before pasting the classic answer telling not change GL states, not to bind already bound textures and so on, please read the following.
Actually, even if I display a single 364x353 rgba texture in a middle of a black screen, it happens that the rendering takes almost 20 ms. The procedure can be summarized like this:
Edit The code below used to call glFlush()
. As thokra pointed out in the comments, this is not necessary. Nevertheless, removing it did not improve the performances.
glClear( GL_COLOR_BUFFER_BIT );
glBindTexture( the_texture );
glEnable(GL_BLEND);
glEnableClientState( GL_COLOR_ARRAY );
glColorPointer( 4, GL_FLOAT, 0, colors );
glEnableClientState( GL_VERTEX_ARRAY );
glVertexPointer( 2, GL_FLOAT, 0, positions );
glEnableClientState( GL_TEXTURE_COORD_ARRAY );
glTexCoordPointer( 2, GL_FLOAT, 0, texture_positions );
glDrawArrays( GL_TRIANGLE_FAN, 0, vertex_count );
glDisableClientState( GL_TEXTURE_COORD_ARRAY );
glDisableClientState( GL_VERTEX_ARRAY );
glDisableClientState( GL_COLOR_ARRAY );
glDisable(GL_BLEND);
//glFlush();
SDL_GL_SwapWindow( window );
The execution of the last two lines of this function (flush and swap) is very irregular in duration. It can take from 4 to 12 ms!
The best hints I could find on the web are this question on StackOverflow and this thread on Google Groups.
The answers to the questions on StackOverflow are of no help. According to the author of the question:
clearing vs not clearing frame with glClear doesn't affect fps for me. Neither does enabling/disabling blending.
and
[…] just want to see if using compressed textures improves fill rate. It seems it doesn't […]
The Google Groups thread is very similar to my problem but it ended when the author gave up:
So basically, there's no way to draw a 480x854 image on screen with OpenGL at 60fps because of the texel reading bottleneck.
Seriously, no way? Why the call to both glFlush()
and SDL_GL_SwapWindow()
takes so long? And why is it so irregular? Can't I do anything about it?
I did a quick search in SDL2's source code and found that SDL_GL_SwapWindow()
uses the Java Native Interface to call a Java method which will do the work. Can it be the cause of the irregularity? What can I do about this?
Upvotes: 1
Views: 2821
Reputation: 1
I don't know if you are still doing it but try to consult Google for this matter. You will not get a rational answer from anywhere else on the web. 20ms is basically 50FPS. You mostly get like 250FPS doing those simple task you asked. What if, just what if, it is INTENTIONALLY LEFT OUT TO BE SLOW?
We used to code in simple intercept calls and used whole VGA card. But nowadays even in smartphones it is ran in something like VIRTUAL MODE. You need to get those DIRECT ACCESS to video chip in assembly or c level. Ask and consult google about this.
Upvotes: -1