PDA

View Full Version : this glsl 1.3 thing



nib
08-16-2008, 09:06 AM
ok, its the first time I've looked at it. Don't really pay attention to the API wars. First impression...noob time. :)

The thing that strikes me is all the built in uniform state stuff is deprecated? gl_ModelViewProjectionMatrix is depreciated. Do I call ftransform instead? Are there new built in names for these variables?

I don't like to have to program uniforms all the time. It requires a compile. I suppose avoiding a compile is what scripting is all about.

Often, I need to make a filter. You have to make a kernel. I end up having to make a uniform variable like k[4][4] for a filter -- a compile. But I would like this in my script. So, can I do something like this? This would be a time saver.

float k[4][4] = {
{1,2,3,4},
{1,2,3,4},
{1,2,3,4},
{1,2,3,4}
};

Does Apple have example code for the opengl 3.0 stuff? Trying to get on the same wavelength or anticipate where this is going. :)

Zengar
08-16-2008, 09:49 AM
1. There is no OpenGL 3.0 on Apple yet and probably won't be there for at least half a year (but who knows).

2. In GL3.0 all fixed-function was deprecated. GLSL 1.30 reflects this by removing the corresponding features.

3. Why does "programming uniforms requires a compile"? And GLSL is not scripting. Can you elaborate?

4. You will have to ask someone else if there are array constants in GLSL, I don't know...

nib
08-16-2008, 11:59 AM
Hmm, your right its not scripting. The program is being complied and not interpreted.

Have not read enough of the spec to probably comment about it. But all the depreciated stuff caught my eye and made me curious.

I suppose what I mean is if I'm going to pass in something with a uniform then I have to go into my c and c++ code and make a change. eg. glUniformxx (?) Thus, a recompile. But if its a built in uniform state variable, I just use it. So, all these state variables are gone and I'm now have to make a uniform call.(?) Unless, I'm really missing the point why they depreciated them. Hmm, the point is the fixed pipeline is gone. :) ok, so am I to compute say modelviewprojection matrix by hand? No more glTranslate, glRotate etc. Then pass in the matrix I make to the script? Looks like I'm confused.

Maybe, having less of these uniforms makes things faster and drivers simpler. If drivers are simpler then the driver is probably more bug free which would be a good thing. But this situation might take a little more work for the application developer but potential more flexible.

The version of glsl on my mac is 1.2. The matrix example shown above is a compile error. Think that syntax is not accepted. Would be nice, though.

I'll just have to read up some more on this. Don't want to be a whiner. :)

dletozeun
08-16-2008, 12:14 PM
hmmm, I don't understand anything you say... but do you understand what Zengar said, it is pretty clear.

And shader is not "recompilated" after setting a uniform, it does only some optimization, which is apparently a performance issue until 3.0 but would be fixed in the next release.

V-man
08-16-2008, 12:35 PM
You don't recompile when you change a uniform.
You need to bind the shader (glUseProgram) and then upload the uniform (glUniformXX) and that's all.

For matrices, you use a math library to generate the matrices you need and upload them as uniforms.

Yes, it takes more work from the developer.

nib
08-16-2008, 04:33 PM
Been reading a little more. I understand the flat,smooth,in, out stuff.

I'm a little confused by :

in int gl_VertexID;

is going to be:

vec4 v = mymatrix[gl_VertexID]; //? where is mymatrix?

This is an index into some type of array. But what array? Wait a minute here. :) Am I passing in an array of uniforms or is there one defined?

I had gotten rid of my displays lists from before. Now, I'm using a vbo. So, gl_VertexID is an index into it somehow. I call glBufferData and set it to GL_STATIC_DRAW.

Also, when I mentioned compiling before I was alluding to when I would develop my code I would need to recompile all my c++ code to create a uniform. If I were using the state variables like in glsl 1.2 I'd just change the glsl text file that would be compiled during run time -- not as painful.

Kazade
08-17-2008, 02:46 AM
I'm gonna explain what I think I know, and then probably complicate this further :)

If you are avoiding the deprecated stuff I *believe* you need to keep track of your own modelview and projection matrices, and then pass them into your shaders with glUniformMatrix4f or whatever. Then you can use them in the same way you use the built in uniforms.

That of course does mean that you have some math library to make your life easier. You could actually emulate the current functionality by keeping your own homebrew matrix stacks and current matrices and implement your own MatrixMode, PushMatrix, PopMatrix, Translate etc.

The bit that I'm totally confused about with all this deprecation stuff is that glColor, glTexCoord and glColorPointer, glTexCoordPointer etc. have all been deprecated, how do I send colours/texcoords to my vertex shader if I'm rendering with VBOs? (The answer to this is quite likely obvious, it's early in the morning here and I haven't had a coffee)

Kazade
08-17-2008, 03:06 AM
OK, I'm gonna answer my own question here. glVertexAttribPointer is not deprecated (I thought it was because in the spec it says glVertexAttrib* is, I guess the * doesn't mean everything beginning with glVertexAttrib :) )

So that's how you send the colors etc. but now I see glVertexPointer is deprecated, so how do we use VBOs? I'm so confused :p

Komat
08-17-2008, 04:34 AM
(I thought it was because in the spec it says glVertexAttrib* is, I guess the * doesn't mean everything beginning with glVertexAttrib :) )

Actually that section says that the VertexAttrib* calls used for specifying current value of vertex attribute are not deprecated. It does not talk about the functions specifying the vertex arrays.



So that's how you send the colors etc. but now I see glVertexPointer is deprecated, so how do we use VBOs? I'm so confused :p
It is the same as with the colors. You use a generic attribute to pass that value. However there is one catch. You need to ensure that enabled array is attached to the generic attribute zero (which is equivalent of the VertexPointer array) or nothing should be drawn (at least I did not found change in that behavior in the OGL3 specification).

Komat
08-17-2008, 04:50 AM
in int gl_VertexID;

The value contains index of the vertex within the vertex array. You only need to use it if you wish to modify processing of the vertex based on its index within the vertex array. What you do with it is entirely up to you, it is just a value.

Kazade
08-17-2008, 06:21 AM
So that's how you send the colors etc. but now I see glVertexPointer is deprecated, so how do we use VBOs? I'm so confused :p
It is the same as with the colors. You use a generic attribute to pass that value. However there is one catch. You need to ensure that enabled array is attached to the generic attribute zero (which is equivalent of the VertexPointer array) or nothing should be drawn (at least I did not found change in that behavior in the OGL3 specification).

OK cool that makes sense, onto my next deprecation question (sorry about hijacking this thread a little) how do we replace GL_CLAMP?

Komat
08-17-2008, 07:35 AM
how do we replace GL_CLAMP?
By GL_CLAMP_TO_EDGE

nib
08-17-2008, 09:58 AM
I see the gl_MultiTexCoordX is depreciated. So, I should replace my calls to glTexCoordPointer with glVertexAttribPointer.

Then in my new glsl code I use the keyword "attribute". atrribute is different on a per vertex basis. Whereas a uniform is the same over the programs entire execute. For instance, in bump mapping ...

attribute vec3 t;
attribute vec3 b;
attribute vec3 n; //looks like gl_Normal is depreciated too. Need to pass in?

----

I'm doing something like this currently:

glClientActiveTexture(GL_TEXTURE1);
glBindBuffer( GL_ARRAY_BUFFER, _vbo_id );
glTexCoordPointer( 3, GL_FLOAT, 0, (char *) NULL );
glEnableClientState(GL_TEXTURE_COORD_ARRAY);

//do more stuff

glDrawArrays( GL_TRIANGLES, 0, _verts );

I suppose it would change to something like:

glEnableVertexAttribArrayARB( 1 );
glBindBuffer( GL_ARRAY_BUFFER, _vbo_id );
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 0, (char *) NULL );

glEnableClientState(GL_TEXTURE_COORD_ARRAY); //??? does this matter anymore

//do more stuff

glDrawArrays( GL_TRIANGLES, 0, _verts );

nib
08-17-2008, 10:09 AM
Shoot it says built in "attributes" are depreciated. ok, so I defined the attribute. There must be a call to map that to atrrib array to 1. Or do I use glGetUniformLocation or something like that? I bet glEnableVertexAttribArray is using one of those depreciated built ins. Sorry about the confusion. Dealing with the effect of a glsl lobotomy. :)

Xmas
08-17-2008, 11:05 AM
You can either explicitly bind attributes to attribute indices with glBindAttribLocation before linking a program. Or you can let the OpenGL implementation assign locations during linking and get them with glGetAttribLocation.

nib
08-17-2008, 01:20 PM
One other question. I notice gl_TextureMatrix is depreciated.

I like this variable because I could write to it once before I draw the frame and all my glsl programs could access it. I'd store my texture matrix there for instance. Maybe a frame counter -- not necessarily texture related stuff. So, I do something like this at the beginning of a frame:

glActiveTexture(GL_TEXTURE5);
glMatrixMode(GL_TEXTURE);
glLoadMatrixf(temp[0]);
glMatrixMode(GL_MODELVIEW);
glActiveTexture(GL_TEXTURE0);

Is there a new mechanism to write out to all programs *once*? If I make a uniform to each program then I've got to keep track where to write the uniform and I would have to write a uniform to each program. If I can write once then things are faster.

nib
08-18-2008, 12:10 PM
Did some more reading. Not trying to make a monolog here. The trials and tribulations of prepping my opengl code.

But it looks like I'm suppose to replace the "attribute" with "in". Also, ftransform will be gone and I'm suppose to add "invariant" to an "out". I think the glEnableClientState is fixed pipeline stuff so I get rid of it. But I'm a little confused because at some point I have to enter vertex data ... I need to tell it its vertex data. The rest is attributes I suppose.

For now, in glsl 1.2, I pass my tangent data as a vertex attribute. ( for tbn stuff ) I get the normal from gl_Normal and can calculate the binormal with a cross product. So, I figure in the future I make the normals an attribute ( or "in" ) But I don't think I can make the normal and tex coords an attribute with 1.2. Made my program freak out with textures on the nvidia card.

I suppose calls to glMaterialfv need to be replaced by a uniform. Funny, but people's glsl scripts are sure going to look different from each other when all these built in state variables are gone.

I wonder if I could pass in a texture and then use gl_VertexID with it. Like looking at an array of data? That certainly might be easier than all these funny calls. Plus, a texture is in viedo memory which is fast. Sort of like a vbo.

If I recall, OpenGL 3.0 has multisample for FBOs? Currently, I make my FBO twice as big then copy it down to the smaller frame buffer to get a anti aliasing down sample effect. Sure would not mind using a smaller buffer.

Komat
08-18-2008, 04:14 PM
Is there a new mechanism to write out to all programs *once*? If I make a uniform to each program then I've got to keep track where to write the uniform and I would have to write a uniform to each program.

The only way in which you can change content of standard uniform variable in more than one program is to use the EXT_bindable_uniform extensions (currently Nvidia GF8+ only ).

Komat
08-18-2008, 04:33 PM
But I'm a little confused because at some point I have to enter vertex data ... I need to tell it its vertex data. The rest is attributes I suppose.

What do you mean with the "vertex data"? The vertex position is for the shader just another attribute.



So, I figure in the future I make the normals an attribute ( or "in" ) But I don't think I can make the normal and tex coords an attribute with 1.2. Made my program freak out with textures on the nvidia card.

With what error the program failed? The Nvidia has some aliasing between the generic attributes and the built-in attributes. It is not possible (at least it was not possible some time ago) to use generic attribute (bound using the glBindAttribLocation) and its aliased built-in attribute at the same time on Nvidia card.



I wonder if I could pass in a texture and then use gl_VertexID with it. Like looking at an array of data? That certainly might be easier than all these funny calls.

You can use to use the gl_VertexID to index into a texture however unless you have some special reason to do so, putting the data directly inside the vertex array should be more effective.

nib
08-18-2008, 07:28 PM
This part was confusing me -- the actual vertex data. Must of created a conflict with the aliasing you described.

I suppose in 3.0 it would convert to an attribute like everything else :

glBindAttribLocation (program_object, 4, "vbo_vertex"); // in vec3 vbo_vertex;

---

glEnableVertexAttribArray(4);

----

glBindBuffer( GL_ARRAY_BUFFER, _vbo_id );
glVertexAttribPointer(4, 3, GL_FLOAT, GL_FALSE, 0, (char *) NULL );

//Now you don't need the gl_Vertex anymore.

I was trying glVertexAttribPointer for vertex, normal, texcoord, and tangent but the textures were not showing up in 1.2. Probably because of the aliasing conflict. Plain colors seemed to work.

Hmm, these vbo/ uniform changes do not seem that bad. But the matrix changes do worry me. eg. getting rid of glRotate etc. There is vvector.h which has been useful. I'd like to make a class that uses accelerate library for the matrix stuff. This is a good project for the open source folk. Might take a little more work. Just a search and replace on those calls -- sprinkled everywhere. Then a glUniformMatrix call to get the data into the shader -- I'd have to call this for every shader.

I'll just have to incrementally change these things. When 3.0 arrives on the mac, I'm sure the compiler might give a depreciation warning message and that will be a motivator for people. :)

nib
08-20-2008, 04:31 PM
Huff, this is all starting to jolt my memory.

Ironically, I used to have my own uniform names for material colors like specular, ambient, diffuse, etc. Because I migrated away from CG and I did not know what to expect in glsl. So, I made my own names. But that way sucked. I was constantly having to check the unform for the id and setting it on a shader by shader basis. I'd have to do that all up front and it was a pain. Of course, all these different shaders happened to have potential different uniform location numbers. Could not make an assumption using something like glBindAttribLocation where I could set the number up front -- pretty sure I cant do that with uniforms. Hmm, unless its the order in which I declare the uniform in the shader program but I figure the compiler is going to assign the number.

Where as, with something like, gl_FrontMaterial.diffuse I'd just call

glMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, mDiffuse);

and populate gl_FrontMaterial.diffuse. Which is much more appealing to me. Plus, if I happened to switch to a different shader then I did not have to call the uniform again. The material values could of changed since I last used that shader.

Think this gets back to setting a uniform that shaders can share. So, I only set it once and not a zillion times. Huff, I don't really want to change that.

Maybe, I'm totally missing the point again.

nib
08-20-2008, 08:15 PM
GL_EXT_bindable_uniform would assign a uniform a number and not the compiler. Alas, its only supported in the highest end nvidia cards and the software renderer on the mac.

nib
08-30-2008, 10:59 AM
Hmm, looking over my uniforms for materials. There is a place in my program where I set up the samplers. It looks for names of samplers there anyways. This is a good spot to check for my uniform names and migrate away. Put it all into a map structure. So, done with changing my uniforms with regard to materials. I see that light information is going to be deprecated too. More uniforms. Not using the fixed function pipeline anymore. Slowly swap it out little by little.

BTW, in the OpenGL Wikipedia there was a good vbo example under extensions. A couple typos but it really helped. I could do things faster.

MrB
09-24-2008, 07:46 AM
By the way,
If you took a look at the OpenGL ES 2.0 specification, you would get a fairly good view of what the OpenGL 3.0 spec would look like with all of the fixed function actually removed.

So far, you are correct in saying that you need to use Bind/GetAttribLocation, in conjunction with VertexAttribPointer, and you *will* need to create user defined uniforms for all the fixed function state you were using.

Unfortunately, until uniform buffers (or something equivalent) are elevated to ARB extension or core status, you will have to set the uniforms for each program they are used in (and they will almost certainly have different uniform locations for each program) in order to be portable.

bakura
02-01-2009, 04:22 PM
Hej !

Sorry if it has already been said, but I'm trying to understand GLSL 1.3.

I think I have understood the new in, out, inout, and the different interpolation qualifiers. However, I'm really lost with all those deprecated varying and uniform variables.

Here are the things I don't understand :



in mat4x4 ModelViewProjectionMatrix;

invariant out vec4 gl_Position;

void main ()
{
gl_Position = ModelViewProjectionMatrix * ????????
}




Same for texture mapping :



smooth out vec2 TexCoords;

void main ()
{
TexCoords = ?????? gl_TexCoord[0] and gl_MultiTexCoordn are deprecated !!
}



Thanks ^^

martinsm
02-02-2009, 04:49 AM
You define your own attributes instead of predefined:


in vec3 vertex_position;
uniform mat4x4 ModelViewProjectionMatrix;

void main ()
{
gl_Position = ModelViewProjectionMatrix * vec4(vertex_position, 1.0);
}

nib
02-02-2009, 09:26 AM
I ran into some odd behavior. I changed my materials from the default state to uniforms I passed in. The shader was generic. So, I would just set these uniforms. It was working.

Problems started when the scene would get complicated. I would set these uniforms too much and my frames would skip. I could hear the disk at the precise moment grind a little. It was like virtual memory was being triggered by setting uniforms too much. This would especially appear to be a problem with the first 10 seconds of drawing.

So, rather than use a uniform to pass in material colors etc. I just hard coded constants for these colors. Performance then skyrocketed and I do not hear anymore swaps happening causing the frame skips. I guess its a specific shader versus general purpose shader issue.

The lesson is only set uniforms once at the beginning of the frame. Otherwise, you'll be in for trouble. :)

bakura
02-03-2009, 06:02 AM
Martinsm > Hum, okej but... how can I pass to vertex_position the right vertex coordinates ?

Furthemore, what is gl_VertexID ?

martinsm
02-03-2009, 06:54 AM
Read here: http://www.opengl.org/discussion_boards/ubbthreads.php?ubb=showflat&Main=49081&Number=252276
You do it same way as in OGL2.

gl_VertexID is integer index for the vertex.
You can read about it in GLSL 1.30 spec on page 58 and in GL3 spec in page 106. Read the fine manual, please ;)

bakura
02-09-2009, 02:17 PM
I had no answer on GD, but I think it's better here ;) so I just copy-past my message :

In the doc, it's said that the use of gl_FragData[n] is deprecated, and to use "out" instead. But how the hell can we know in which texture data is written. Let's take an exemple : with GLSL 1.20, when I want to write something using the FBO extension, I used to doing that :

gl_FragData[0] = myVec41;
gl_FragData[1] = myVec42;


It was easy to know that the texture bounded to unit 1 has myVec41, and that texture bounded to unit 2 has myVec42. But how can we know now with GLSL 1.30 ?

From what I've understood, it's something like that :

out vec4 myVec41;
out vec4 myVec42;

void main ()
{
// Don't use gl_FragData
}





I think that GLSL 1.30 is intelligent enough, so myVec41 will be written to the first active texture (because it is declared first), and myVec42 will be written to the second active texture (because it is declared second).

Am I right ? Furthermore, what if I want to write myVec41 in a the third active unit, and myVec42 to the fourth one ?

Thanks ;)

martinsm
02-10-2009, 02:53 AM
But how the hell can we know in which texture data is written.
GL3.0 spec says it clearly ;) Read section 3.12.2 Shader Outputs.

You bind output variables from fragment shader with glBindFragDataLocation before linking your program:


glBindFragDataLocation(programId, 0, "myVec41");
glBindFragDataLocation(programId, 1, "myVec42");
glLinkProgram(programId);

This means myVec41 will go to first draw buffer and myVec42 will go to second. You specifiy draw buffers with glDrawBuffers function.

bakura
02-10-2009, 08:11 AM
Oh yes, this is because I only read GLSL specs... Thank you ;). I'll read the whole OpenGL 3.0 specs too.