Poor results from "smooth" shader values in GLSL

Started by
5 comments, last by Squirmy 10 years, 11 months ago

Hi,

I am using OpenGL GLSL to draw a quad in the form of two triangles. The vertex data includes a float which is 0 for two of the vertices and 1 for the other two. It is specified as smooth in float interp / smooth out float interp in the shaders (although I have tried noperspective also)

What I would like, of course, is for the value received by the fragment shader to be a smooth fade from 0 to 1 across the quad. What I get is as per the attached image:

brokengouraud.png

There are a few quads there as examples. The result is quite close to correct for quads which are quite close to being rectangles, shows signs of distortion as they become slightly trapezoid, and becomes totally unacceptable once one end is significantly larger than the other.

Is there a reliable method that will get me a consistent result? I assume these results are "correct" as defined by the OpenGL standard, but they are really not good enough for what I need :/

Thanks,

Andy

Advertisement

Tesselate your quads into smaller triangles with sides that are near equal. I'm not aware of any better way, that's just how graphics hardware works.

Those results are very odd. You'd expect that if you used a colour picker to read a value half way across an edge, you'd get ~128 (0.5)... but 128 is appearing about 40% of the way across the edges.

Those results are very odd. You'd expect that if you used a colour picker to read a value half way across an edge, you'd get ~128 (0.5)... but 128 is appearing about 40% of the way across the edges.

That could be a gamma thing maybe? It does seem biased towards lighter shades.

That has the classic look of standard affine interpolation. I'm guessing (since you haven't really explained what you're trying to do or provided any code) that you're rendering quads with essentially arbitrary vertices on a 2D plane, rather than actual transformed 3D models, so your fragments don't actually have any depth information - one way or another, your fragment shader isn't receiving any depth information, without which smooth interpolation simply cannot work the way you're expecting it to. In the general case, to smoothly interpolate a value across a quadrilateral requires knowing about all four vertices - it is therefore impossible (outside of specific cases) to do so when the quads are broken up into triangles. And since most GPUs internally break quads into triangles anyway (to simplify dealing with degenerate and self-intersecting). In other words, if you're trying to do do what I think you are, it can't be done without rasterizing the quads yourself.

Well, those aren't the answers I wanted to hear, but I've learned something!

They are 2D triangles on a 2D plane so the Z information is 0 for all vertices.

Those results are very odd. You'd expect that if you used a colour picker to read a value half way across an edge, you'd get ~128 (0.5)... but 128 is appearing about 40% of the way across the edges.

That could be a gamma thing maybe? It does seem biased towards lighter shades.

The affine interpolation was the answer, I think. The bias towards the lighter shades is because it is always the narrow end of the quad which is drawn by a triangle that has two dark vertices, so the smaller of the two triangles is the darker one.

This topic is closed to new replies.

Advertisement