I heard that I should use normals instead of colors, because colors are deprecated. (Is that true?) Normals have something to do with the reflection of light, but I can't find a clear and intuitive explanation. What is a normal?
相关问题
- Is GLFW designed to use without LWJGL (in java)?
- glDrawElements only draws half a quad
- DBGrid - How to set an individual background color
- Scaling png font down
- OpenGL buffer update [duplicate]
相关文章
- Converting glm::lookat matrix to quaternion and ba
- Emacs/xterm color annoyance on Linux
- Behavior of uniforms after glUseProgram() and spee
- Keep constant number of visible circles in 3D anim
- matplotlib bwr-colormap, always centered on zero
- MeshLab: How to import XYZRGB file
- GLEW and Qt5 redefinition of headers
- How do I remove axis from a rotation matrix?
Many things are now deprecated, including normals and colors. That just means that you have to implement them yourself. With normals you can shade your objects. It's up to you to make the calculations but there are a lot of tutorials on e.g. Gouraud/Phong shading.
Edit: There are two types of normals: face normals and vertex normals. Face normals point away from the triangle, vertex normals point away from the vertex. With vertex normals you can achieve better quality, but there are many uses also for face normals, e.g. they can be used in collision detection and shadow volumes.
A normal in general is a unit vector whose direction is perpendicular to a surface at a specific point. Therefore it tells you in which direction a surface is facing. The main use case for normals are lighting calculations, where you have to determine the angle (or practically often its cosine) between the normal at a given surface point and the direction towards a lightsource or a camera.
glNormal
minimal exampleglNormal
is a deprecated OpenGL 2 method, but it is simple to understand, so let's look into it. The modern shader alternative is discussed below.This example illustrates some details of how
glNormal
works with diffuse lightning.The comments of the
display
function explain what each triangle means.Theory
In OpenGL 2 each vertex has its own associated normal vector.
The normal vector determines how bright the vertex is, which is then used to determine how bright the triangle is.
OpenGL 2 used the Phong reflection model, in which light is separated into three components: ambient, diffuse and specular. Of those, diffuse and specular components are affected by the normal:
glNormal
sets the current normal vector, which is used for all following vertexes.The initial value for the normal before we all
glNormal
is0,0,1
.Normal vectors must have norm 1, or else colors change!
glScale
also alters the length of normals!glEnable(GL_NORMALIZE);
makes OpenGL automatically set their norm to 1 for us. This GIF illustrates that beautifully.Why it is useful to have normals per vertexes instead of per faces
Both spheres below have the same number of polygons. The one with normals on the vertexes looks much smoother.
OpenGL 4 fragment shaders
In newer OpenGL API's, you pass the normal direction data to the GPU as an arbitrary chunk of data: the GPU does not know that it represents the normals.
Then you write a hand-written fragment shader, which is an arbitrary program that runs in the GPU, which reads the normal data you pass to it, and implements whatever lightning algorithm you want. You can implement Phong efficiently if you feel like it, by manually calculating some dot products.
This gives you full flexibility to change the algorithm design, which is a major features of modern GPUs. See: https://stackoverflow.com/a/36211337/895245
Examples of this can be found in any of the "modern" OpenGL 4 tutorials, e.g. https://github.com/opengl-tutorials/ogl/blob/a9fe43fedef827240ce17c1c0f07e83e2680909a/tutorial08_basic_shading/StandardShading.fragmentshader#L42
Bibliography