PDA

View Full Version : Problem with 1dTexture as lookup table



Treehouse
04-23-2011, 03:07 PM
Hello there,

i would like to draw the grayscale color 255 as red and i would like to do this with a FragementShader, but it dosen't work.

I define a lookup texture like this:


glGenTextures(1, &m_tex[0]);
glBindTexture(GL_TEXTURE_1D, m_tex[0]);
// setup texture
glTexParameteri (GL_TEXTURE_1D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri (GL_TEXTURE_1D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);


float colors[256][3];
for (int i = 0; i < 256; i++)
{
if (i == 255)
{
colors[i][0] = i / 255.;
colors[i][1] = 0.;
colors[i][2] = 0.;
}
else
{

colors[i][0] = i / 255.;
colors[i][1] = i / 255.;
colors[i][2] = i / 255.;

}
}

glTexImage1D(GL_TEXTURE_1D, 0, GL_RGB, 256, 0 , GL_RGB, GL_FLOAT, colors);

After this i create my 2D image grayscale texture:


// texture erstellen
glGenTextures(1, &amp;m_tex[1]);
glBindTexture(GL_TEXTURE_2D, m_tex[1]);

// setup texture
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);

// copy image pixel to texture
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, m_gray.width(), m_gray.height(), 0,
GL_LUMINANCE, GL_UNSIGNED_BYTE, m_gray.bits());

Then i define the shaders Fragment and Vertex:


const char *vsrc =
"void main(void)\n"
"{\n"
" gl_Position = ftransform();\n"
"gl_TexCoord[0] = gl_MultiTexCoord0;\n"
"}\n";


const char *fsrc =
"uniform sampler2D sample;\n"
"uniform sampler1D lookup;\n"
"void main(void)\n"
"{\n"
" gl_FragColor = texture1D(lookup, texture2D(sample,gl_TexCoord[0].st).r);\n"
"}\n";



Now i use the Qt QGLWidget to draw the texture. I compile now the
code and bind it to the card.


m_program = new QGLShaderProgram(this);
m_program->addShader(vshader);
m_program->addShader(fshader);
m_program->link();
m_program->setUniformValue("lookup", m_tex[0]);
m_program->setUniformValue("sample", m_tex[1]);
m_program->bind();

And this is my draw function:


paintGL()
{

glEnable(GL_TEXTURE_2D);
glBegin(GL_QUADS);
// clockwise
glTexCoord2f(0.0f, 0.0f); glVertex2f(-1.0f, 1.0f); // oben links
glTexCoord2f(1.0f, 0.0f); glVertex2f(1.0f, 1.0f); // oben rechts
glTexCoord2f(1.0f, 1.0f); glVertex2f(1.0f, -1.0f); // unten rechts
glTexCoord2f(0.0f, 1.0f); glVertex2f(-1.0f, -1.0f); // unten links
glEnd();
glDisable(GL_TEXTURE_2D);

}

Can anyone help me what did i wrong? I see only the 1D lookup texture in my Widget and the color which should be red is black.

Best regards,

Treehouse

Dark Photon
04-23-2011, 05:51 PM
i would like to draw the grayscale color 255 as red and i would like to do this with a FragementShader, but it dosen't work. ... Can anyone help me what did i wrong? I see only the 1D lookup texture in my Widget and the color which should be red is black.
How about a picture? It's not obvious from your description what you are seeing. Just that you "aren't" seeing the all white color show up red.

Could be you're using CLAMP rather than CLAMP_TO_EDGE, so you're getting the texture border mixed in. To fix:



glTexParameteri( GL_TEXTURE_2D , GL_TEXTURE_WRAP_S , GL_CLAMP_TO_EDGE ) ;
glTexParameteri( GL_TEXTURE_2D , GL_TEXTURE_WRAP_T , GL_CLAMP_TO_EDGE ) ;


And of course, for a 1D texture, omit the 2nd line and change 2D to 1D.

Treehouse
04-23-2011, 10:22 PM
Hello Dark Photon,

if i don't bind the shader i see my grayscale image, normal with no problems.

When i change the draw function in this way also with unbind shader:


glEnable(GL_TEXTURE_1D);
glBegin(GL_QUADS);
// clockwise
glTexCoord2f(0.0f, 0.0f); glVertex2f(-1.0f, 1.0f); // oben links
glTexCoord2f(1.0f, 0.0f); glVertex2f(1.0f, 1.0f); // oben rechts
glTexCoord2f(1.0f, 1.0f); glVertex2f(1.0f, -1.0f); // unten rechts
glTexCoord2f(0.0f, 1.0f); glVertex2f(-1.0f, -1.0f); // unten links
glEnd();
glDisable(GL_TEXTURE_1D);


Then i see my 1D Texture with the grayscales from black to white and the last line of pixels are red.

And when bind the shader and i use my 2D draw function. I don't see my grayscale image instead i see the 1D texture from black to white but the last line that must be red is black.

Best regards,

Treehouse

mobeen
04-23-2011, 10:54 PM
You need to pass the active texture where the texture is bound and not the tex id that your texture stores when u pass the uniform to the shader.
Change this line


m_program->setUniformValue("lookup", m_tex[0]);
m_program->setUniformValue("sample", m_tex[1]);

to this


m_program->setUniformValue("lookup", 0);
m_program->setUniformValue("sample", 1);

And then when passing the texture make sure that the texture is bound to the appropriate active texture target.


glGenTextures(1, &amp;m_tex[0]);
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_1D, m_tex[0]);
// setup texture
glTexParameteri (GL_TEXTURE_1D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri (GL_TEXTURE_1D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
...

and the same steps for the other texture


// texture erstellen
glGenTextures(1, &amp;m_tex[1]);
glActiveTexture(GL_TEXTURE1);
glBindTexture(GL_TEXTURE_2D, m_tex[1]);

// setup texture
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);

...


See if this helps.

Treehouse
04-24-2011, 01:26 AM
Hello mobeen,

you made my day. It works thank you very much for this advice.

Best regards,

Treehouse