Estou aprendendo alguns conceitos básicos do OpenGL, mas estou me perguntando por que existe uma chamada glNormal
para definir o normal dos vértices.
Se eu criar um triângulo simples como este:
glBegin(GL_TRIANGLES);
glVertex3f(0,0,0);
glVertex3f(1,0,0);
glVertex3f(0,1,0);
glEnd();
Os normais não deveriam ser definidos implicitamente pelo tipo de primitivo geométrico? Se eu não definir um normal, o OpenGL o calculará?
Respostas:
Chamar
glNormal
várias vezes entreglBegin/End
permite definir um normal por vértice, em vez de por primitivo.Para uma malha mais complexa que consiste em vários triângulos, você deseja que o normal em um vértice dependa dos outros triângulos da geometria circundante e não apenas do normal do triângulo ao qual pertence.
Aqui está um exemplo da mesma geometria com:
(0,0,1)
):O modelo de sombra padrão (
GL_SMOOTH
) faz com que os normais dos vértices da face sejam interpolados pela face. Para as normais por vértice, isso resulta em uma esfera sombreada suave, mas, para as normais por face, você acaba com a aparência facetada característica.fonte
Não, o GL não calcula uma norma para você. Não sei como deve ser o normal. Suas primitivas não significam nada fora da rasterização (e alguns outros lugares). O GL não sabe quais faces (triângulos) compartilham um vértice (calcular isso em tempo de execução é muito caro sem o uso de diferentes estruturas de dados).
Você precisa pré-processar a "sopa triangular" de uma malha para encontrar vértices comuns e calcular normais. Isso deve ser feito antes que o jogo corra para a velocidade.
Também existem casos como arestas duras em que geometricamente existe um vértice compartilhado no canto, mas você deseja normais separados para que acenda corretamente. No modelo de renderização GL / D3D, você precisa de dois vértices separados (na mesma posição) para isso, cada um com um normal separado.
Você precisará de tudo isso para UVs e mapeamento de textura também.
fonte
A resposta curta é que você realmente não precisa definir um normal. Os vetores normais são usados apenas se você estiver executando a iluminação OpenGL (ou talvez algum outro cálculo que possa depender deles), mas se isso não se aplicar a você (ou se você estiver usando algum outro método para fazer iluminação, por exemplo, mapas de luz ), é possível omitir com prazer todas as chamadas glNormal.
Então, vamos supor que você esteja fazendo algo em que especificar glNormal faz sentido e analisar mais um pouco.
glNormal pode ser especificado por primitivo ou por vértice. Com os normais per primitivos, tudo o que isso significa é que todos os normais de cada vértice na face primitiva na mesma direção. Às vezes é isso que você deseja, mas às vezes não é - onde os normais por vértice são úteis é que permitem que cada vértice tenha sua própria face.
Veja o exemplo clássico de uma esfera. Se cada triângulo em uma esfera tivesse o mesmo normal, o resultado final seria bastante facetado. Provavelmente não é isso que você deseja, mas sim um sombreamento suave. Portanto, o que você faz é calcular a média normal de cada triângulo que compartilha um vértice comum e obter um resultado sombreado suave.
fonte
Exemplo mínimo que ilustra alguns detalhes de como
glNormal
funciona com raios difusos.Os comentários da
display
função explicam o que cada triângulo significa.Teoria
No OpenGL, cada vértice possui seu próprio vetor normal associado.
O vetor normal determina a luminosidade do vértice, que é usado para determinar a luminosidade do triângulo.
Quando uma superfície é perpendicular à luz, é mais brilhante que uma superfície paralela.
glNormal
define o vetor normal atual, usado para todos os seguintes vértices.O valor inicial para o normal antes de todos nós
glNormal
é0,0,1
.Os vetores normais devem ter a norma 1 ou as cores mudam!
glScale
também altera a duração dos normais!glEnable(GL_NORMALIZE);
faz com que o OpenGL defina automaticamente sua norma como 1 para nós. This GIF ilustra isso lindamente.Bibliografia:
fonte
Você precisa do glNormal para implementar alguns recursos dependentes do codificador. Por exemplo, você pode querer criar normais para preservar arestas duras.
fonte