We closed this forum 18 June 2010. It has served us well since 2005 as the ALPHA forum did before it from 2002 to 2005. New discussions are ongoing at the new URL http://forum.processing.org. You'll need to sign up and get a new user account. We're sorry about that inconvenience, but we think it's better in the long run. The content on this forum will remain online.
Page Index Toggle Pages: 1
PGraphicsGL.java bug (Read 2240 times)
PGraphicsGL.java bug
Jul 1st, 2005, 8:53pm
 
Hi,

I've been looking at the OpenGL library trying to understand why the pixels[] things didn't work.

I think it must be that the modelview and projection matrices are not right.  But there is also a small conception problem in the updatePixels() function.

The problem is that glRasterPos() is a position in a 3D space which is treated as any other glVertex, this means it is transformed by the modelview and projection matrices.  This is obviously not what the users expects.  In P3D when we transform the pixels[] and we updatePixels() these are not painted in a position depending on the camera, they are painted directly to the screen.

To fix it, the MODELVIEW must be set to the Identity matrix and the PROJECTION must be set to the orthogonal matrix right before the glRasterPos().
All the buffers must be cleared aswell. Since what the user is doing by updatePixels() is forgetting any alpha values and printing a completely redesigned frame.

I'm not that great in programming, but I did a small crappy modification that looks like this:
Code:

public void updatePixels() {
// flip vertically (opengl stores images upside down),

int index = 0;
int yindex = (height - 1) * width;
for (int y = 0; y < height/2; y++) {
if (BIG_ENDIAN) {
// and convert ARGB back to opengl RGBA components (big endian)
for (int x = 0; x < width; x++) {
int temp = pixels[index];
/*
pixels[index] =
((pixels[yindex] >> 24) & 0xff) |
((pixels[yindex] << 8) & 0xffffff00);
pixels[yindex] =
((temp >> 24) & 0xff) |
((temp << 8) & 0xffffff00);
*/
pixels[index] = ((pixels[yindex] << 8) & 0xffffff00) | 0xff;
pixels[yindex] = ((temp << 8) & 0xffffff00) | 0xff;

index++;
yindex++;
}

} else {
// convert ARGB back to native little endian ABGR
for (int x = 0; x < width; x++) {
int temp = pixels[index];

pixels[index] = 0xff000000 |
((pixels[yindex] << 16) & 0xff0000) |
(pixels[yindex] & 0xff00) |
((pixels[yindex] >> 16) & 0xff);

pixels[yindex] = 0xff000000 |
((temp << 16) & 0xff0000) |
(temp & 0xff00) |
((temp >> 16) & 0xff);

index++;
yindex++;
}
}
yindex -= width*2;
}

// re-pack ARGB data into RGBA for opengl (big endian)
/*
for (int i = 0; i < pixels.length; i++) {
pixels[i] = ((pixels[i] >> 24) & 0xff) |
((pixels[i] << 8) & 0xffffff00);
}
*/

//System.out.println("running glDrawPixels");
//gl.glRasterPos2i(width/2, height/2);
//gl.glRasterPos2i(width/2, 1); //height/3);
//gl.glRasterPos2i(1, height - 1); //1, 1);

// for some reason, glRasterPos(0, height) won't draw anything.
// my guess is that it's getting "clipped", so adding an epsilon
// makes it work. also, height-1 would be the logical start,
// but apparently that's not how opengl coordinates work

/////// MODIFICATIONS //////
gl.glClear(GL.GL_COLOR_BUFFER_BIT | GL.GL_DEPTH_BUFFER_BIT | GL.GL_STENCIL_BUFFER_BIT | GL.GL_ACCUM_BUFFER_BIT);
gl.glMatrixMode(GL.GL_MODELVIEW);
gl.glPushMatrix();
gl.glLoadIdentity();

gl.glMatrixMode(GL.GL_PROJECTION);
gl.glPushMatrix();
gl.glLoadIdentity();
gl.glOrtho( 0, width, 0, height, 0, 1 );
/////// END OF MODIFICATIONS //////

gl.glRasterPos2f(0.0f,0.0f); // I put (0,0) since we have rechanged the projection matrix and forgot the glScalef(1,-1,1) of before

/////// SOME DEBUGGING CODE /////
float[] buff = new float[4];
byte[] bufb = new byte[1];
gl.glGetBooleanv(GL.GL_CURRENT_RASTER_POSITION_VALID,bufb);
gl.glGetFloatv(GL.GL_CURRENT_RASTER_POSITION,buff);
System.out.println("Current raster pos validity = ("+bufb[0]+")");
System.out.println("Current raster pos = ("+buff[0]+","+buff[1]+","+buff[2]+";"+buff[3]+")");
/////// END OF DEBUGGING CODE //////

gl.glDrawPixels(width, height, GL.GL_RGBA, GL.GL_UNSIGNED_BYTE, pixels);

/////// MODIFICATIONS //////
gl.glMatrixMode(GL.GL_PROJECTION);
gl.glPopMatrix();

gl.glMatrixMode(GL.GL_MODELVIEW);
gl.glPopMatrix();
/////// END OF MODIFICATIONS //////
}


Note:  this only works for me in some runs, NOT all the time.  I find it wierd, but I'm guessing it has to do with some threading desync or something.

Here is a test applet (run it several times to find a good result).  Compare it to the result using P3D:
Code:

import processing.opengl.*;

void setup()
{
size(100, 100, OPENGL);
background(255,255,255);
color azul = color(0, 0, 125);
loadPixels();
for (int i=0; i<(width*height/2)-width/2; i++) {
pixels[i] = azul;
}
updatePixels();
}



PS: I do think the OpenGL library needs a cleaning and structuring.  But I have not time at all at this point. I would be willing to help to who's willing to do it though.
Re: PGraphicsGL.java bug
Reply #1 - Jul 8th, 2005, 5:46pm
 
Ok, so a few extra tests I made seem to point that sometimes it draws and sometimes it doesn't.  And that when it draws, if I move another window from a different program over the applet, it will erase that part of the drawing (applet).

It seems to be a problem with the refreshing of the window applet.

Any help with this?  or am I totally on the wrong track.
Re: PGraphicsGL.java bug
Reply #2 - Jul 8th, 2005, 8:00pm
 
regarding the matrices, i think this is the source of the problem, because the way that the matrices are handled was changed to get the camera stuff working properly right around the release of 85/86. identity isn't quite what we want but we need to make sure things aren't in a dissarray when glRasterPos() is called.

fwiw, translate() etc don't get passed on to opengl, they're done inside PGraphics3 along with the lighting, and PGraphicsGL just gets a bunch of triangles and lines to blit as fast as it can.

as far as "I do think the OpenGL library needs a cleaning and structuring.  But I have not time at all at this point. I would be willing to help to who's willing to do it though." you're looking at alpha/beta quality code that i'm writing very hastily. when code is being added/removed rapidly (as is the case for the gl stuff), it's a foolish waste of time to clean functions that are likely to be ripped right back out. it can be cleaned much later (closer to 1.0) when things are debugged.
Re: PGraphicsGL.java bug
Reply #3 - Jul 21st, 2005, 1:05pm
 
Quote:
identity isn't quite what we want but we need to make sure things aren't in a dissarray when glRasterPos() is called


hi fry, thanks for the explaination and sorry to insist with this.  I seem to be missing something.

I understand much better now that the openGL library only boosts the drawing of triangles and lines, not the transformations (with the transf matrices), etc.  it looks like it doesn't boost the lighting either, but it does the texturing?

going back to my first problem:
why wouldn't the identity matrix do the trick? from my undersanding, since with updatePixels() and loadPixels(), we are dealing with the screen pixels directly, no transformation should be done.  And since no depth information plays a role with set(), image(),... we should forget about the projection matrix (this is use projmatrix=any with z=0, or use projmatrix=ortho with z=any)

thanks for helping me understanding this a bit better.
Page Index Toggle Pages: 1