# The Industry's Foundation for High Performance Graphics

1. ## blending

Hi! i have a problem with blending.. my code should blend a valume made of 3 "slices" and read the blended value.. From what I’ve read, the function GL_ONE_MINUS_SRC_ALPHA should calculate the blended value(for 3 "slices" like in my code), resolving this expression:
((µ1*α1)*(1-α2)+ µ2*α2)*(1-α3)+(µ3*α3)

where µ1 is the value of the first "slice" and α1 is the alpha value of the first slice ( and so on...)

so.. the result is 2 ( that is a reasonable result). but the result of the program is always half of the expected value. f.e. with 3 slices and the values µ1=1,µ2=2,µ3=3 the result is 1 (instead of 2), if the result should be 40, the program give 20 and so on.. so i think that the program is correct because it is wrong in a "correct way". maybe there's something that i don't know about the method, or maybe i'm not considerating all.. please help!!!!!!!!

#include <cstdio>
#include <cstdlib>
using namespace std;

#include <gl\glew.h>
#include <gl\glut.h>
#include <gl\gl.h>
#include <gl\glu.h>

#include <windows.h>

//trasforms alpha from double to char and from 0 and 255
char DoubleToChar(double alpha){
return (char)(alpha*255.0);
}

int main(int argc, char **argv) {

//Volume values: it represents a 1x1x3 volume ( 3 slices along z)
unsigned char Volumevalues[12]={1,0,0,1,2,0,0,0,3,0,0,0};
Volumevalues [3]=DoubleToChar(1.0);
Volumevalues [7]=DoubleToChar(1.0/2.0);
Volumevalues [11]=DoubleToChar(1.0/3.0);
unsigned char result [16]; //array for the result

//initialize glut
glutInit (&argc, argv);
glewInit();

// create the texture
GLuint tex;
glGenTextures (1, &tex);
glBindTexture(GL_TEXTURE_3D,tex);

// sets texture’s parameters
glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_WRAP_S, GL_CLAMP);
glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_WRAP_T, GL_CLAMP);

//allocate the texture
glTexImage3D(GL_TEXTURE_3D,0,GL_RGBA,1,1,4,0,GL_RG BA,GL_UNSIGNED_BYTE, Volumevalues);

//viewport transform for 1:1 pixel=texel=data mapping
glMatrixMode(GL_PROJECTION);
gluOrtho2D(0.0,1,0.0,1);
glMatrixMode(GL_MODELVIEW);
glViewport(0,0,1,1);

glPushMatrix();

glEnable(GL_TEXTURE_3D);
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA,GL_ONE_MINUS_SRC_ALPHA);

float a= ((float)0.5)/3.0;
float b =((float)1.5)/3.0;
float c= ((float)2.5)/3.0;

glTexCoord3f(0.0,0.0,a); glVertex2f(0,0);
glTexCoord3f(0.0,1.0,a); glVertex2f(0,1);
glTexCoord3f(1.0,1.0,a); glVertex2f(1,1);
glTexCoord3f(1.0,0.0,a); glVertex2f(1,0);

glTexCoord3f(0.0,0.0,b); glVertex2f(0,0);
glTexCoord3f(0.0,1.0,b); glVertex2f(0,1);
glTexCoord3f(1.0,1.0,b); glVertex2f(1,1);
glTexCoord3f(1.0,0.0,b); glVertex2f(1,0);

glTexCoord3f(0.0,0.0,c); glVertex2f(0,0);
glTexCoord3f(0.0,1.0,c); glVertex2f(0,1);
glTexCoord3f(1.0,1.0,c); glVertex2f(1,1);
glTexCoord3f(1.0,0.0,c); glVertex2f(1,0);

glEnd();
glPopMatrix();

glutSwapBuffers();

//reads datas from the frame buffer and write them into the array result

// print out results
printf("Data before roundtrip:\n");
for (int i=0; i<16; i++)
printf("%d\n", Volumevalues [i]);
printf("Data after roundtrip:\n");
for (int i=0; i<4; i++)
printf("%d\n",result[i]);

getchar();

return 0;

}

2. ## Re: blending

Are you taking numerical inaccuracies into account?

e.g. in the first pass, if you have a value of 2 (range 0...255) with an alpha of 0.15, the resulting value is 0.30 which is rounded down to 0 when writing to a 32bpp RGBA framebuffer.

If you want to avoid this, use a for-loop in a fragment shader to iterate over the different slices.

N.

3. ## Re: blending

From what I’ve read, the function GL_ONE_MINUS_SRC_ALPHA should calculate the blended value(for 3 "slices" like in my code), resolving this expression:
((µ1*α1)*(1-α2)+ µ2*α2)*(1-α3)+(µ3*α3)
In order for your equation to be correct, you must ensure that the destination color before doing any rendering is (0, 0, 0, 0). Otherwise, you should use a separate blending equation for the first pass.

And put your code in [ code ] tags.

4. ## Re: blending

for Nico: alpha values are trasformed into the range 0-255 (the first fuction in the code), so using a char and not a float ,why there should be numerical inaccuracies? and.. what do you mean with your solution? isn't it enough blend the slices like i do?

for Korval: i tryed to clear the color buffer, but the result is the same..

suggestions???(i am repetitive but, i remind you that the program works.. in a "correct" wrong way, and the strange thing is that in the result, alpha value is 127 ( i don't mind because i need only the color values..) that is half of 255 (half like the color value), maybe there's a relation..

5. ## Re: blending

I don't know how to be any clearer than in my previous post. Suppose you want to calculate the sum of 3 values in the range 0-255. The range of this sum is 0-3*255 and you are writing the result to a pixel with a range of 0-255 so it's impossible to get the full resolution of your result, hence the inaccuracies.

PS. If you just want to calculate the mean of three values (sum divided by count) you can use.

Code :
```glClearColor(0.0,0.0,0.0,0.0);
glClear(GL_COLOR_BUFFER_BIT);
glBlendColor(1.0/count,1.0/count,1.0/count,1.0/count);
glBlendEquation(GL_CONSTANT_COLOR,GL_ONE);
glEnable(GL_BLEND);```

N.

6. ## Re: blending

I'll ask the more obvious question. Why use GL at all?
You aren't doing graphics. You are doing math and it's something that could be done in a few clock cycles on the CPU.

7. ## Re: blending

IIRC he's trying to simulate radiography...

8. ## Re: blending

for Nico:
1- so i don't need to use one_minus_src_alpha?
2- the program gives me an error.. to many arguments in glBlendequation; i searched and the parameters you wrote aren't accepted by the function, It must be GL_FUNC_ADD, GL_FUNC_SUBTRACT, GL_FUNC_REVERSE_SUBTRACT, GL_MIN, GL_MAX, GL_ALPHA_MIN_SGIX, or GL_ALPHA_MAX_SGIX.
are you sure that the name is correct?

9. ## Re: blending

2- it is glBlendFunc, and you need the GL_ARB_imaging extension use GL_CONSTANT_COLOR

10. ## Re: blending

I checked with a program if my pc supports that extension, and the answer is yes. I've changed the code into this:

Code :
```#include <cstdio>
#include <cstdlib>
using namespace std;

#include <gl\glew.h>
#include <gl\glut.h>
#include <gl\gl.h>
#include <gl\glu.h>

#include <windows.h>

//trasforms alpha from double to char and from 0 and 255
char DoubleToChar(double alpha){
return (char)(alpha*255.0);
}

int main(int argc, char **argv) {

//Volume values: it represents a 1x1x3 volume ( 3 slices along z)
unsigned char Volumevalues[12]={1,0,0,1,2,0,0,0,3,0,0,0};
Volumevalues [3]=DoubleToChar(1.0);
Volumevalues [7]=DoubleToChar(1.0/2.0);
Volumevalues [11]=DoubleToChar(1.0/3.0);
unsigned char result [12]; //array for the result

//initialize glut
glutInit (&amp;argc, argv);
glewInit();

// create the texture
GLuint tex;
glGenTextures (1, &amp;tex);
glBindTexture(GL_TEXTURE_3D,tex);

// sets texture’s parameters
glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_WRAP_S, GL_CLAMP);
glTexParameteri(GL_TEXTURE_3D, GL_TEXTURE_WRAP_T, GL_CLAMP);

//allocate the texture
glTexImage3D(GL_TEXTURE_3D,0,GL_RGBA,1,1,4,0,GL_RGBA,GL_UNSIGNED_BYTE, Volumevalues);

//viewport transform for 1:1 pixel=texel=data mapping
glMatrixMode(GL_PROJECTION);
gluOrtho2D(0.0,1,0.0,1);
glMatrixMode(GL_MODELVIEW);
glViewport(0,0,1,1);

glClearColor(0.0,0.0,0.0,0.0);
glClear(GL_COLOR_BUFFER_BIT);
glBlendColor(1.0/3,1.0/3,1.0/3,1.0/3);
glBlendEquation(GL_CONSTANT_COLOR);
glEnable(GL_BLEND);

glPushMatrix();

glEnable(GL_TEXTURE_3D);

float a= ((float)0.5)/3.0;
float b =((float)1.5)/3.0;
float c= ((float)2.5)/3.0;

glTexCoord3f(0.0,0.0,a); glVertex2f(0,0);
glTexCoord3f(0.0,1.0,a); glVertex2f(0,1);
glTexCoord3f(1.0,1.0,a); glVertex2f(1,1);
glTexCoord3f(1.0,0.0,a); glVertex2f(1,0);

glTexCoord3f(0.0,0.0,b); glVertex2f(0,0);
glTexCoord3f(0.0,1.0,b); glVertex2f(0,1);
glTexCoord3f(1.0,1.0,b); glVertex2f(1,1);
glTexCoord3f(1.0,0.0,b); glVertex2f(1,0);

glTexCoord3f(0.0,0.0,c); glVertex2f(0,0);
glTexCoord3f(0.0,1.0,c); glVertex2f(0,1);
glTexCoord3f(1.0,1.0,c); glVertex2f(1,1);
glTexCoord3f(1.0,0.0,c); glVertex2f(1,0);

glEnd();
glPopMatrix();

//reads datas from the frame buffer and write them into the array result

// print out results
printf("Data before roundtrip:\n");
for (int i=0; i<16; i++)
printf("%d\n", Volumevalues [i]);
printf("Data after roundtrip:\n");
for (int i=0; i<4; i++)
printf("%d\n",result[i]);

getchar();

return 0;

}```

but the result is always the same.. 1! not 2! where is the error? i have missed something??

#### Posting Permissions

• You may not post new threads
• You may not post replies
• You may not post attachments
• You may not edit your posts
•