Fragment shader to process texture data and pass through - opengl

I'm trying to use an atomic counter in a fragment shader.
Basically I'm displaying just a textured quad and need to make calculations on the texture data, and display the unaltered texture.
I began with writing a simple pass-through fragment shader, but the displayed texture is plain color. Either i'm missing something, i'm not sure if to use also vertex shader, as i'm processing only texture, seemed obsolete to me.
Fragment shader code:
#version 420
uniform vec2 texture_coordinate; uniform sampler2D my_color_texture;
void main() {
gl_FragColor = texture2D(my_color_texture, texture_coordinate);
}
Rendering pipeline - using shaprGL, but it's easily readable:
gl.Enable(OpenGL.GL_TEXTURE_2D);
String s = "my_color_texture"; //name of the texture variable in shader
gl.UseProgram(graycounter); // graycounter is a compiled/linked shader
GLint my_sampler_uniform_location = gl.GetUniformLocation(graycounter, s);
gl.ActiveTexture(OpenGL.GL_TEXTURE0);
gl.BindTexture(OpenGL.GL_TEXTURE_2D, ((dTexture)texture).texture); //texture id, working without shader on
gl.Uniform1ARB(my_sampler_uniform_location, 0);
gl.Begin(OpenGL.GL_QUADS); // show the rectangle
gl.Color(1.0f, 1.0f, 1.0f);
gl.TexCoord(0.0f, 0.0f); gl.Vertex(0.0f, 0.0f, 0.0f); // Bottom Left Of The Texture and Quad
gl.TexCoord(1.0f, 0.0f); gl.Vertex(w, 0.0f, 0.0f); // Bottom Right Of The Texture and Quad
gl.TexCoord(1.0f, 1.0f); gl.Vertex(w, h, 0.0f); // Top Right Of The Texture and Quad
gl.TexCoord(0.0f, 1.0f); gl.Vertex(0.0f, h, 0.0f); // Top Left Of The Texture and Quad
gl.End();
gl.UseProgram(0);

uniform vec2 texture_coordinate;
Uniform values do not change from fragment to fragment; that's why they're called "uniform". You probably wanted in rather than uniform.
Granted, since you're using legacy features, you probably need to hook into the gl_TexCoord[] array. That's what the legacy vertex processor (since you're not using a VS) will spit out. Texture coordinate 0 will map to gl_TexCoord[0].

I did figure it finally out, and if someone has the same problem, here is the vertex shader - note no min.version
out vec4 texCoord;
void main(void)
{
gl_Position = ftransform();
texCoord=gl_TextureMatrix[0] * gl_MultiTexCoord0;
}
and the fragment shader - using version #440 to support atomic counters
#version 440
layout (binding = 0, offset = 0) uniform atomic_uint g1;
uniform sampler2D my_color_texture;
in vec4 texCoord;
out vec4 fragColour;
void main() {
fragColour = texture2D(my_color_texture,texCoord.xy);
if (abs(fragColour.r*255 - 0)<1) atomicCounterIncrement(g1);
}

Related

Simple GLSL render chain doesn't draw reliably

I have a simple compositing system which is supposed to render different textures and a background texture into an FBO. It also renders some primitives.
Here's an example:
I'm rendering using a simple GLSL shader for the texture and another one for the primitive. Also, I'm waiting for each shader to finish using glFinish after each glDrawArrays call.
So basically:
tex shader (background tex)
tex shader (tex 1)
primitive shader
tex shader (tex 2)
tex shader (tex 3)
When I only do this once, it works. But if I do another render pass directly after the first one finished, some textures just aren't rendered.
The primitive however is always rendered.
This doesn't happen always, but the more textures I draw, the more often this occurs.
Thus, I'm assuming that this is a timing problem.
I tried to troubleshoot for the last two days and I just can't find the reason for this.
I'm 100% sure that the textures are always valid (I downloaded them using glGetTexImage to verify).
Here are my texture shaders.
Vertex shader:
#version 150
uniform mat4 mvp;
in vec2 inPosition;
in vec2 inTexCoord;
out vec2 texCoordV;
void main(void)
{
texCoordV = inTexCoord;
gl_Position = mvp * vec4(inPosition, 0.0, 1.0);
}
Fragment shader:
#version 150
uniform sampler2D tex;
in vec2 texCoordV;
out vec4 fragColor;
void main(void)
{
fragColor = texture(tex, texCoordV);
}
And here's my invocation:
NSRect drawDestRect = NSMakeRect(xPos, yPos, str.texSize.width, str.texSize.height);
NLA_VertexRect rect = NLA_VertexRectFromNSRect(drawDestRect);
int texID = 0;
NLA_VertexRect texCoords = NLA_VertexRectFromNSRect(NSMakeRect(0.0f, 0.0f, 1.0f, 1.0f));
NLA_VertexRectFlipY(&texCoords);
[self.texApplyShader.arguments[#"inTexCoord"] setValue:&texCoords forNumberOfVertices:4];
[self.texApplyShader.arguments[#"inPosition"] setValue:&rect forNumberOfVertices:4];
[self.texApplyShader.arguments[#"tex"] setValue:&texID forNumberOfVertices:1];
GetError();
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, str.texName);
glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
glFinish();
The setValue:forNumberOfCoordinates: function is an object-based wrapper around OpenGL's parameter application functions. It basically does this:
glBindVertexArray(_vertexArrayObject);
glBindBuffer(GL_ARRAY_BUFFER, _vertexBufferObject);
glBufferData(GL_ARRAY_BUFFER, bytesForGLType * numVertices, value, GL_DYNAMIC_DRAW);
glEnableVertexAttribArray((GLuint)self.boundLocation);
glVertexAttribPointer((GLuint)self.boundLocation, numVectorElementsForType, GL_FLOAT, GL_FALSE, 0, 0);
Here are two screenshots of what it should look like (taken after first render pass) and what it actually looks like (taken after second render pass):
https://www.dropbox.com/s/0nmquelzo83ekf6/GLRendering_issues_correct.png?dl=0
https://www.dropbox.com/s/7aztfba5mbeq5sj/GLRendering_issues_wrong.png?dl=0
(in this example, the background texture is just black)
The primitive shader is as simple as it gets:
Vertex:
#version 150
uniform mat4 mvp;
uniform vec4 inColor;
in vec2 inPosition;
out vec4 colorV;
void main (void)
{
colorV = inColor;
gl_Position = mvp * vec4(inPosition, 0.0, 1.0);
}
Fragment:
#version 150
in vec4 colorV;
out vec4 fragColor;
void main(void)
{
fragColor = colorV;
}
Found the issue... I didn't realize that the FBO is drawn to the screen already after the first render pass. This happens on a different thread and wasn't locked properly.
Apparently the context was switched while the compositing took place which explains why it caused different issues randomly depending on when the second thread switched the context.

alpha not changing transparency of object using glsl shader

How come when i manually change the alpha value in array, being passed to shader, the result is the same for both 0.0f and 1.0f?
I was expecting the object to be drawn with some level of transparency, depending on alpha value.
I'm not using any textures. I always see my red object against a black background.
accessing glsl variable from java ..
float[] color = {1.0f, 0.0f, 0.0f, 1.0f};
gl2.glGetUniformLocation(shaderProgram, "vColor");
gl2.glUniform4fv(mColorHandle, 1, color, 0);
glsl, fragment shader ..
#version 120
uniform vec4 vColor;
void main() {
gl_FragColor = vColor;
gl_FragColor.a = 0.0; // does not make object transparent
// gl_FragColor.a = 1.0; // does not make object transparent
}
Needed to enable blending ..
gl2.glEnable(GL.GL_BLEND);
gl2.glBlendFunc(GL.GL_SRC_ALPHA, GL.GL_ONE_MINUS_SRC_ALPHA);

Converting Points to Triangle_strip in geometry shader, how to pass UV's

I'm currently trying to pass points into a custom wrote sprite batcher, right now I have it so the points get the position and use the dimensions to create a triangle strip of a quad. my question though is if the geometry shader gets a single point then how do I pass around texture coordinates to the fragment shader?
I'm also trying to think about texture aliasing so the texture coordinates might not always be 0 to 1
Well, you emit 4 unique vertices right? Just assign each of the corners you emit in the geometry shader a different coordinate in the range [0.0,1.0] where (0,0) is the bottom-left of the image and (1,1) is the top-right.
Consider the following Geometry Shader:
#version 330
layout (points) in;
layout (triangle_strip, max_vertices = 4) out;
out vec2 tex_coord;
void main (void) {
const vec2 coordinates [] = vec2 [] (vec2 (0.0f, 0.0f),
vec2 (1.0f, 0.0f),
vec2 (1.0f, 1.0f),
vec2 (0.0f, 1.0f));
for (int i = 0; i < 4; i++) {
gl_Position = gl_in [0].gl_Position + vec4 (coordinates [i], 0.0f, 0.0f);
tex_coord = coordinates [i];
EmitVertex ();
}
}

How do I get textures to work in OpenGL?

I'm using the tutorials on http://arcsynthesis.org/gltut/ to learn OpenGL, it's required, I have to use it. Mostly I want to apply the textures from Tutorial 15 onto objects in tutorial 7 (world with UBO).
For now it seemed like the textures only work when mipmaps are turned on. This comes with a downside: The only mipmap used is the one with an index of zero, and that's the 1 colored 1x1 pixel one. I tried setting the minimum level of a mipmap higher or turning off mipmaps entirely, but even that doesn't fix thing, because then everything turns pitch black. Now I'll list the most important parts of my program
EDIT: I guess I'll add more details...
The vertex shader has something like this:
#version 330
layout(location = 0) in vec4 position;
layout(location = 1) in vec4 color;
layout(location = 2) in vec3 normal;
//Added these later
layout(location = 5) in vec2 texCoord;
out vec2 colorCoord;
smooth out vec4 interpColor;
out vec3 vertexNormal;
out vec3 modelSpacePosition;
out vec3 cameraSpacePosition;
uniform mat4 worldToCameraMatrix;
uniform mat4 modelToWorldMatrix;
uniform mat3 normalModelToCameraMatrix;
uniform vec3 dirToLight;
uniform vec4 lightIntensity;
uniform vec4 ambientIntensity;
uniform vec4 baseColor;
uniform mat4 cameraToClipMatrix;
void main()
{
vertexNormal = normal;
vec3 normCamSpace = normalize(normalModelToCameraMatrix * vertexNormal);
cameraSpacePosition = normCamSpace;
float cosAngIncidence = dot(normCamSpace, dirToLight);
cosAngIncidence = clamp(cosAngIncidence, 0, 1);
modelSpacePosition.x = position.x;
modelSpacePosition.y = position.y;
modelSpacePosition.z = position.z;
vec4 temp = modelToWorldMatrix * position;
temp = worldToCameraMatrix * temp;
gl_Position = cameraToClipMatrix * temp;
interpColor = ((lightIntensity * cosAngIncidence) + (ambientIntensity)) * baseColor;
colorCoord= texCoord ;
}
The fragment shader like this:
#version 330
in vec3 vertexNormal;
in vec3 modelSpacePosition;
smooth in vec4 interpColor;
uniform vec3 modelSpaceLightPos;
uniform vec4 lightIntensity2;
uniform vec4 ambientIntensity2;
out vec4 outputColor;
//Added later
in vec2 colorCoord;
uniform sampler2D colorTexture;
void main()
{
vec3 lightDir2 = normalize(modelSpacePosition - modelSpaceLightPos);
float cosAngIncidence2 = dot(normalize(vertexNormal), lightDir2);
cosAngIncidence2 = clamp(cosAngIncidence2, 0, 1);
float light2DistanceSqr = dot(modelSpacePosition - modelSpaceLightPos, modelSpacePosition - modelSpaceLightPos);
//added
vec4 texture2 = texture(colorTexture, colorCoord);
outputColor = ((ambientIntensity2 + (interpColor*2))/4) +
((((interpColor) * lightIntensity2/200 * cosAngIncidence2) + (ambientIntensity2* interpColor ))
/( ( sqrt(light2DistanceSqr) + light2DistanceSqr)/200 ));
//No outputColor for texture testing
outputColor = texture2 ;
}
}
Those were both shaders. And here are the parts added to the .cpp:
#include <glimg/glimg.h>
#include "../framework/directories.h"
[...]
const int g_colorTexUnit = 0;
GLuint g_checkerTexture = 0;
And here's the loader for the texture:
void LoadCheckerTexture()
{
try
{
std::string filename(LOCAL_FILE_DIR);
filename += "checker.dds";
std::auto_ptr<glimg::ImageSet>
pImageSet(glimg::loaders::dds::LoadFromFile(filename.c_str()));
glGenTextures(1, &g_checkerTexture);
glBindTexture(GL_TEXTURE_2D, g_checkerTexture);
glimg::SingleImage image = pImageSet->GetImage(0, 0, 0);
glimg::Dimensions dims = image.GetDimensions();
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB8, dims.width, dims.height, 0, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, image.GetImageData());
glBindTexture(GL_TEXTURE_2D, 0);
}
catch(std::exception &e)
{
printf("%s\n", e.what());
throw;
}
}
Naturally I've got this in void init():
LoadCheckerTexture();
And then when rendering the object:
glActiveTexture(GL_TEXTURE0 + g_colorTexUnit);
glBindTexture(GL_TEXTURE_2D,g_checkerTexture);
g_pLeftMesh->Render();
glBindSampler(g_colorTexUnit, 0);
glBindTexture(GL_TEXTURE_2D, 0);
With all of this, I get put pitch black for everything, however when I change the outputColor equation into "texture + outputColor;", everything looks normal. I have no idea what I'm doing wrong here. A friend tried to help me, we removed some unnecessairy stuff, but we got nothing running.
Ok guys, I've worked on this whole thing, and did manage to somehow get it running. First off I had to add samplers:
GLuint g_samplers;
//Add Later
void CreateSamplers()
{
glGenSamplers(1, &g_samplers);
glSamplerParameteri(g_samplers, GL_TEXTURE_WRAP_S, GL_REPEAT);
glSamplerParameteri(g_samplers, GL_TEXTURE_WRAP_T, GL_REPEAT);
//Linear mipmap Nearest
glSamplerParameteri(g_samplers, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glSamplerParameteri(g_samplers, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
}
I also added this to the file thing:
glimg::OpenGLPixelTransferParams xfer = glimg::GetUploadFormatType(pImageSet->GetFormat(), 0);
glimg::SingleImage image = pImageSet->GetImage(0, 0, 0);
glimg::Dimensions dims = image.GetDimensions();
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, dims.width, dims.height, 0,
xfer.format, xfer.type, image.GetImageData());
The xfer variable does get the format and type adjusted to the dds.
Also the render code got turned into this:
//Added necessary
glActiveTexture(GL_TEXTURE0 + g_colorTexUnit);
glBindTexture(GL_TEXTURE_2D,g_checkerTexture);
glBindSampler(g_colorTexUnit, g_samplers);
g_pLeftMesh->Render();
glBindSampler(g_colorTexUnit, 0);
glBindTexture(GL_TEXTURE_2D, 0);
And of course at the end of init() I needed to add the CreateSamplers thing:
//Added this later
LoadCheckerTexture();
CreateSamplers();
I'm sorry for all the trouble with all this, but guess OpenGL really is just this confusing and it was just dumb luck that I got it right. Just posting this so that people know
Your fail to add textures may be caused by:
Have you add texture coordinates to objects? (this is the most probable cause, because you are adding textures to non textured tutorial), add textures to VAO.
Did you add uniform textureunit (Sampler2D)? (it must be uniform, else texturing will not work properly)
Is your texture loaded,binded,enabled (GL_TEXTURE_2D) ?
Is your active texture unit - 0? if not change layout/multitexture coords or set active texture 0
This two codes are simple texturing shaders (texture unit 0) no special things (like light,blend,bump,...):
tm_l2g is transformation local obj space -> world space (Modelview)
tm_g2s is transformation world space -> screen space (Projection)
pos are vertex coordinates
txt are texture coordinates
col are colors
Do not forget to change uniform names and layout locations to yours.
Vertex:
//------------------------------------------------------------------
#version 420 core
//------------------------------------------------------------------
uniform mat4x4 tm_l2g;
uniform mat4x4 tm_g2s;
layout(location=0) in vec3 pos;
layout(location=1) in vec4 col;
layout(location=2) in vec2 txr;
out smooth vec4 pixel_col;
out smooth vec2 pixel_txr;
//------------------------------------------------------------------
void main(void)
{
vec4 p;
p.xyz=pos;
p.w=1.0;
p=tm_l2g*p;
p=tm_g2s*p;
gl_Position=p;
pixel_col=col;
pixel_txr=txr;
}
//------------------------------------------------------------------
fragment:
//------------------------------------------------------------------
#version 420 core
//------------------------------------------------------------------
in smooth vec4 pixel_col;
in smooth vec2 pixel_txr;
uniform sampler2D txr_texture0;
out layout(location=0) vec4 frag_col;
//------------------------------------------------------------------
void main(void)
{
vec4 col;
col=texture(txr_texture0,pixel_txr.st);
frag_col=col*pixel_col;
}
//------------------------------------------------------------------
[edit1] CPU old style OpenGL render code (initializations are not included its only render code they can be found here)
//------------------------------------------------------------------
// set modelview,projection,textures,bind GLSL programs...
GLfloat a=10.0,z=0.0;
glColor3f(1.0,1.0,1.0);
glBegin(GL_QUADS);
// textured quad
glTexCoord2f(0.0,0.0); glVertex3f(-a,-a,z);
glTexCoord2f(0.0,1.0); glVertex3f(-a,+a,z);
glTexCoord2f(1.0,1.0); glVertex3f(+a,+a,z);
glTexCoord2f(1.0,0.0); glVertex3f(+a,-a,z);
// reverse order quad to be shore that at least one passes by CULL_FACE
glTexCoord2f(1.0,0.0); glVertex3f(+a,-a,z);
glTexCoord2f(1.0,1.0); glVertex3f(+a,+a,z);
glTexCoord2f(0.0,1.0); glVertex3f(-a,+a,z);
glTexCoord2f(0.0,0.0); glVertex3f(-a,-a,z);
glEnd();
//------------------------------------------------------------------
[edit2] ok here goes VAO/VBO render code,...
//------------------------------------------------------------------------------
// enum of VBO locations (it is also your layout location) I use enums for simple in code changes
enum _vbo_enum
{
_vbo_pos=0, // glVertex
_vbo_col, // glColor
_vbo_tan, // glNormal
_vbo_unused0, // unused (at least i dont see anything at this location in your code)
_vbo_unused1, // unused (at least i dont see anything at this location in your code)
_vbo_txr, // glTexCoord
_vbos
};
//------------------------------------------------------------------------------
// 'global' names and size for OpenGL mesh in VAO/VBO ... similar ot texture names/handles
GLuint vao[1],vbo[_vbos],num_pnt=0;
//------------------------------------------------------------------------------
void VAO_init_cube() // call this before VAO use,...but after OpenGL init !
{
//[1] first you need some model to render (mesh), here is a simple cube
// size,position of cube - change it that it is visible in your scene
const GLfloat a=1.0,x=0.0,y=0.0,z=0.0;
// cube points 3f x,y,z
GLfloat mesh_pos[]=
{
x-a,y-a,z-a,x-a,y+a,z-a,x+a,y+a,z-a,x+a,y-a,z-a,
x-a,y-a,z+a,x-a,y+a,z+a,x+a,y+a,z+a,x+a,y-a,z+a,
x-a,y-a,z-a,x-a,y-a,z+a,x+a,y-a,z+a,x+a,y-a,z-a,
x-a,y+a,z-a,x-a,y+a,z+a,x+a,y+a,z+a,x+a,y+a,z-a,
x-a,y-a,z-a,x-a,y+a,z-a,x-a,y+a,z+a,x-a,y-a,z+a,
x+a,y-a,z-a,x+a,y+a,z-a,x+a,y+a,z+a,x+a,y-a,z+a,
};
// cube colors 3f r,g,b
GLfloat mesh_col[]=
{
0.0,0.0,0.0,0.0,1.0,0.0,1.0,1.0,0.0,1.0,0.0,0.0,
0.0,0.0,1.0,0.0,1.0,1.0,1.0,1.0,1.0,1.0,0.0,1.0,
0.0,0.0,0.0,0.0,0.0,1.0,1.0,0.0,1.0,1.0,0.0,0.0,
0.0,1.0,0.0,0.0,1.0,1.0,1.0,1.0,1.0,1.0,1.0,0.0,
0.0,0.0,0.0,0.0,1.0,0.0,0.0,1.0,1.0,0.0,0.0,1.0,
1.0,0.0,0.0,1.0,1.0,0.0,1.0,1.0,1.0,1.0,0.0,1.0,
};
// cube normals 3f x,y,z
GLfloat mesh_tan[]=
{
-0.6,-0.6,-0.6,-0.6,+0.6,-0.6,+0.6,+0.6,-0.6,+0.6,-0.6,-0.6,
-0.6,-0.6,+0.6,-0.6,+0.6,+0.6,+0.6,+0.6,+0.6,+0.6,-0.6,+0.6,
-0.6,-0.6,-0.6,-0.6,-0.6,+0.6,+0.6,-0.6,+0.6,+0.6,-0.6,-0.6,
-0.6,+0.6,-0.6,-0.6,+0.6,+0.6,+0.6,+0.6,+0.6,+0.6,+0.6,-0.6,
-0.6,-0.6,-0.6,-0.6,+0.6,-0.6,-0.6,+0.6,+0.6,-0.6,-0.6,+0.6,
+0.6,-0.6,-0.6,+0.6,+0.6,-0.6,+0.6,+0.6,+0.6,+0.6,-0.6,+0.6,
};
// cube texture coords 2f s,t
GLfloat mesh_txr[]=
{
0.0,0.0,0.0,1.0,1.0,1.0,1.0,0.0,
0.0,0.0,0.0,1.0,1.0,1.0,1.0,0.0,
0.0,0.0,0.0,1.0,1.0,1.0,1.0,0.0,
0.0,0.0,0.0,1.0,1.0,1.0,1.0,0.0,
0.0,0.0,0.0,1.0,1.0,1.0,1.0,0.0,
0.0,0.0,0.0,1.0,1.0,1.0,1.0,0.0,
};
// init VAO/VBO
glGenVertexArrays(1,vao); // allocate 1 x VAO
glGenBuffers(_vbos,vbo); // allocate _vbos x VBO
// copy mesh to VAO/VBO ... after this you do not need the mesh anymore
GLint i,sz,n; // n = number of numbers per 1 entry
glBindVertexArray(vao[0]);
num_pnt=sizeof(mesh_pos)/(sizeof(GLfloat)*3); // num of all points in mesh
i=_OpenGLVAOgfx_pos; n=3; sz=sizeof(GLfloat)*n;
glBindBuffer(GL_ARRAY_BUFFER,vbo[i]);
glBufferData(GL_ARRAY_BUFFER,sz*num_pnt,mesh_pos,GL_STATIC_DRAW);
glEnableVertexAttribArray(i);
glVertexAttribPointer(i,n,GL_FLOAT,GL_FALSE,0,0);
i=_OpenGLVAOgfx_col; n=3; sz=sizeof(GLfloat)*n;
glBindBuffer(GL_ARRAY_BUFFER,vbo[i]);
glBufferData(GL_ARRAY_BUFFER,sz*num_pnt,mesh_col,GL_STATIC_DRAW);
glEnableVertexAttribArray(i);
glVertexAttribPointer(i,n,GL_FLOAT,GL_FALSE,0,0);
i=_OpenGLVAOgfx_tan; n=3; sz=sizeof(GLfloat)*n;
glBindBuffer(GL_ARRAY_BUFFER,vbo[i]);
glBufferData(GL_ARRAY_BUFFER,sz*num_pnt,mesh_tan,GL_STATIC_DRAW);
glEnableVertexAttribArray(i);
glVertexAttribPointer(i,n,GL_FLOAT,GL_FALSE,0,0);
i=_OpenGLVAOgfx_txr; n=2; sz=sizeof(GLfloat)*n;
glBindBuffer(GL_ARRAY_BUFFER,vbo[i]);
glBufferData(GL_ARRAY_BUFFER,sz*num_pnt,mesh_txr,GL_STATIC_DRAW);
glEnableVertexAttribArray(i);
glVertexAttribPointer(i,n,GL_FLOAT,GL_FALSE,0,0);
glBindVertexArray(0);
}
//------------------------------------------------------------------------------
void VAO_draw() // call this to draw your mesh,... need to enable and bind textures,... before use
{
glDisable(GL_CULL_FACE);
glEnable(GL_DEPTH_TEST);
glDepthFunc(GL_LEQUAL);
glBindVertexArray(vao[0]);
glEnableVertexAttribArray(_vbo_pos);
glEnableVertexAttribArray(_vbo_col);
glEnableVertexAttribArray(_vbo_tan);
glDisableVertexAttribArray(_vbo_unused0);
glEnableVertexAttribArray(_vbo_txr);
glDrawArrays(GL_QUADS,0,num_pnt);
glDisableVertexAttribArray(_vbo_pos);
glDisableVertexAttribArray(_vbo_col);
glDisableVertexAttribArray(_vbo_tan);
glDisableVertexAttribArray(_vbo_unused0);
glDisableVertexAttribArray(_vbo_unused1);
glDisableVertexAttribArray(_vbo_txr);
glBindVertexArray(0);
}
//------------------------------------------------------------------------------
void VAO_exit() // clean up ... call this when you do not need VAO/VBO anymore
{
glDisableVertexAttribArray(_vbo_pos);
glDisableVertexAttribArray(_vbo_col);
glDisableVertexAttribArray(_vbo_tan);
glDisableVertexAttribArray(_vbo_unused0);
glDisableVertexAttribArray(_vbo_unused1);
glDisableVertexAttribArray(_vbo_txr);
glBindVertexArray(0);
glDeleteVertexArrays(1,vao);
glDeleteBuffers(_vbos,vbo);
}
//------------------------------------------------------------------------------
[edit3] if you are win32/64 user you can try my IDE for GLSL
It is very simple and easy to use, but cannot change texture/attrib locations. Press [F1] for help,... [F9] for run [F10] for return to normal OpenGL mode. Also txt-editor is little buggy sometimes but it is enough for my purpose.
GLSL IDE

GLSL/OpenGL - Single color instead of the texture

I recently started learning GLSL, and now i have a problem with texturing. I've read all topics about it, i've found the same problem solid color problem, but there was a different problem that caused that. So, i have a simple quadrilateral(ground) and i simply want to render a grass texture on it. Shaders:
Fragment:
#version 330
uniform sampler2D color_texture;
in vec4 color;
out vec2 texCoord0;
void main()
{
gl_FragColor = color+texture(color_texture,texCoord0.st);
}
Vertex:
#version 330
uniform mat4 projection_matrix;
uniform mat4 modelview_matrix;
in vec3 a_Vertex;
in vec3 a_Color;
in vec2 a_texCoord0;
out vec4 color;
out vec2 texCoord0;
void main()
{
texCoord0 = a_texCoord0;
gl_Position = (projection_matrix * modelview_matrix) * vec4(a_Vertex, 1.0);
color = vec4(a_Color,0.3);
}
My texture and primitive coords:
static GLint m_primcoords[12]=
{0,0,0,
0,0,100,
100,0,100,
100,0,0};
static GLfloat m_texcoords[8]=
{0.0f,0.0f,
0.0f,1.0f,
1.0f,1.0f,
1.0f,0.0f};
Buffers:
glBindBuffer(GL_ARRAY_BUFFER,vertexcBuffer);
glBufferData(GL_ARRAY_BUFFER,sizeof(GLint)*12,m_primcoords,GL_STATIC_DRAW);
glBindBuffer(GL_ARRAY_BUFFER,colorBuffer);
glBufferData(GL_ARRAY_BUFFER,sizeof(GLfloat)*12,m_colcoords,GL_STATIC_DRAW);
glBindBuffer(GL_ARRAY_BUFFER,textureBuffer);
glBufferData(GL_ARRAY_BUFFER,sizeof(GLfloat)*8,m_texcoords,GL_STATIC_DRAW);
and my rendering method:
GLfloat modelviewMatrix[16];
GLfloat projectionMatrix[16];
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glLoadIdentity();
cameraMove();
GLuint texturegrass = ploadtexture("grass.BMP");
glBindTexture(GL_TEXTURE_2D, texturegrass);
glGetFloatv(GL_MODELVIEW_MATRIX,modelviewMatrix);
glGetFloatv(GL_PROJECTION_MATRIX,projectionMatrix);
shaderProgram->sendUniform4x4("modelview_matrix",modelviewMatrix);
shaderProgram->sendUniform4x4("projection_matrix",projectionMatrix);
glEnableVertexAttribArray(0);
glEnableVertexAttribArray(1);
glEnableVertexAttribArray(2);
glActiveTexture(GL_TEXTURE0);
shaderProgram->sendUniform("color_texture",0);
glBindBuffer(GL_ARRAY_BUFFER,colorBuffer);
glVertexAttribPointer((GLint)1,3,GL_FLOAT,GL_FALSE,0,0);
glBindBuffer(GL_ARRAY_BUFFER,textureBuffer);
glVertexAttribPointer((GLint)2,2,GL_FLOAT,GL_FALSE,0,(GLvoid*)m_texcoords);
glBindBuffer(GL_ARRAY_BUFFER,vertexcBuffer);
glVertexAttribPointer((GLint)0,3,GL_INT,GL_FALSE,0,0);
glDrawArrays(GL_QUADS,0,12);
So, it looks like the code only reads 4 pixels from my texture(corners) and the output color will be outColor = ctopleft+ctopright+cbotleft+cbotright like this.
I send more code if you want, but i think the problem lies behind these lines.
I tried different coordinates, ordering, everything. I also read almost all topics about problems like this. Im using the beginning ogl game programming 2nd ed., but dont have cd, so i cant check if I'm coding well, cuz only parts of codes are in the book.
There are a couple of problems with your code.
In the fragment shader, you have declared texCoord0 as out, it should be in in the fragment shader and out in the vertex shader, since it is passed from one to the other.
You are binding your texture before you set the "active" texture unit. It defaults to GL_TEXTURE0, but this is still bad practice.