B4A Library [Class] - OpenGL ES - 2D Image library

Jim Brown

Active Member
Licensed User
Longtime User
Thanks for the information Andrew.

@Informatix,
I am pretty stumped as to why performance is slower. Could it be because I am using OpenGL ES rather than OpenGL 2?
My Draw method per image boils down to:
B4X:
   gl.glEnableClientState(gl.GL_VERTEX_ARRAY)
   gl.glEnableClientState(gl.GL_COLOR_ARRAY)
   gl.glVertexPointerf(2,verts)
   gl.glColorPointerf(4,0,cols)
   If tex(0)>0 Then
      gl.glEnable(gl.GL_TEXTURE_2D) : gl.glEnable(gl.GL_BLEND)
      gl.glBlendFunc(BlendSRC,BlendDST)
      gl.glEnableClientState(gl.GL_TEXTURE_COORD_ARRAY)
      gl.glBindTexture(gl.GL_TEXTURE_2D,tex(0))
      gl.glTexCoordPointerf(2,0,uvs)
   End If
   gl.glPushMatrix
     gl.glTranslatef(X+0.375,Y+0.375,0) ' trick for exact pixelization
     gl.glRotatef(Angle,0,0,1)
     gl.glScalef(FlippedX,FlippedY,1)
     gl.glDrawArrays(gl.GL_TRIANGLE_STRIP,0,4)
   gl.glPopMatrix
   gl.glDisableClientState(gl.GL_VERTEX_ARRAY)
   gl.glDisableClientState(gl.GL_TEXTURE_COORD_ARRAY)
   gl.glDisableClientState(gl.GL_COLOR_ARRAY)
 

Informatix

Expert
Licensed User
Longtime User
With the VBO extension, OpenGL 1.1 gets very good results in (Java) tests. So it's not tied to the version. (And OpenGL 2 is also OpenGL ES; ES means "for embedded system")

Next week, I'll convert a Java program to B4A. I'll compare the performance at each step. We'll see if the problem comes from the OpenGL library or from the class.
 

Informatix

Expert
Licensed User
Longtime User

I did the first test: calling an empty Renderer in B4A and in Java. I log the elapsed time between each call. Code in Java:
B4X:
final GLSurfaceView glsv = new GLSurfaceView(this);
glsv.setEGLConfigChooser(true);
glsv.setRenderer(new myRenderer());
glsv.setRenderMode(GLSurfaceView.RENDERMODE_WHEN_DIRTY);
For the renderer:
B4X:
@Override
public void onDrawFrame(GL10 gl) {
   currTimeD = System.currentTimeMillis();
   if (prevTimeD == 0) {
      Log.d("B4A", "DRAW " + currTimeD);
   } else {
      Log.d("B4A", "DRAW " + currTimeD + " " + (currTimeD - prevTimeD));
   }
   prevTimeD = currTimeD;
}
For the timer:
B4X:
t = new Timer();
t.scheduleAtFixedRate(new TimerTask() {
   @Override
   public void run() {
      currTimeT = System.currentTimeMillis();
      if (prevTimeT == 0) {
         Log.d("B4A", "TICK " + currTimeT);
      } else {
         Log.d("B4A", "TICK " + currTimeT + " " + (currTimeT - prevTimeT));
      }
      prevTimeT = currTimeT;
      glsv.requestRender();
   }
}, 0, 16);

I get exactly the same result in Java and in B4A. With a timer set to 16ms, I get regular calls with GLSurfaceView.RENDERMODE_WHEN_DIRTY.
 

agraham

Expert
Licensed User
Longtime User
Good to know! Most methods in the library merely wrap the OpenGL function directly to expose it to B4A code so the overhead is just marshalling the arguments and doing a single additional function call. The only real overhead in the library is for those OpenGL calls that take a Buffer argument where the B4A exposure takes an array, for example glColorPointer.
B4X:
//public void glColorPointer(int size, int type, int stride, Buffer pointer) 
   public void glColorPointerf(int size, int stride, float[] colors)
   {
      ByteBuffer pbb = ByteBuffer.allocateDirect(colors.length * 4);
      pbb.order(ByteOrder.nativeOrder());
      FloatBuffer cfb = pbb.asFloatBuffer();
      cfb.put(colors);
      cfb.position(0);
      gl.glColorPointer(size, GL10.GL_FLOAT, stride, cfb);
   }
Perhaps your tests should try to check how much degradation the additional Buffer manipulation is causing.
 

Informatix

Expert
Licensed User
Longtime User
I stressed the above code with a stupid loop:
B4X:
int j = 0;
for(int i = 1; i <= 500000; i++)
   j = j + 1;
Log.d("B4A", "  LOOP " + (System.currentTimeMillis() - currTimeT) + " " + j);

Results: I have quite regular calls in Java and in B4A. But there's a big difference between the two results: the Java code is 3,5 times faster ! The conversion of the loop from B4A to Java seems to be the culprit.

Example of Log (Java):
Example of Log (B4A):

EDIT: I copied the converted code in my Java test app and I have the same result as in B4A. This confirms that the loop conversion is inefficient and needs to be improved (the difference is too huge).

EDIT2: The loop in B4A uses double types and converts all results back to int. Simply horrible from a performance point of view. I don't understand why it is converted like this.
 
Last edited:

pons

New Member
Hi agraham, thank you for replying. Do you mean this link for the openg gl 2d library: that is in the 1st page of this thread? For me appears that the file have been moved to the recycle bin.
 
Last edited:
Cookies are required to use this site. You must accept them to continue using the site. Learn more…