opengl - estadistica - glm github
glm:: explicación de la perspectiva (2)
Crea una matriz de proyección, es decir, la matriz que describe el conjunto de ecuaciones lineales que transforma vectores del espacio del ojo en el espacio del clip. Las matrices realmente no son magia negra. En el caso de OpenGL, resultan ser una disposición de números de 4 por 4:
X_x Y_x Z_x T_x
X_y Y_y Z_y T_y
X_z Y_z Z_z T_z
X_w Y_w Z_w W_w
Puedes multiplicar un vector de 4 por una matriz de 4 × 4:
v'' = M * v
v''_x = M_xx * v_x + M_yx * v_y + M_zx * v_z + M_tx * v_w
v''_y = M_xy * v_x + M_yy * v_y + M_zy * v_z + M_ty * v_w
v''_z = M_xz * v_x + M_yz * v_y + M_zz * v_z + M_tz * v_w
v''_w = M_xw * v_x + M_yw * v_y + M_zw * v_z + M_tw * v_w
Después de alcanzar el espacio de clip (es decir, después del paso de proyección), se recortan las primitivas. Los vértices resultantes del recorte están pasando por la división de perspectiva, es decir,
v''_x = v_x / v_w
v''_y = v_y / v_w
v''_z = v_z / v_w
( v_w = 1 = v_w / v_w )
Y eso es. En realidad, no pasa nada en todos esos pasos de transformación que la multiplicación ordinaria de matriz-vector.
Ahora, lo bueno de esto es que las matrices se pueden usar para describir la alineación relativa de un sistema de coordenadas dentro de otro sistema de coordenadas. Lo que hace la transformación de perspectiva es que permite que los vértices z-valores "se deslicen" en sus valores w proyectados también. Y por la perspectiva divida una no unidad w causará "distorsión" de las coordenadas de los vértices. Los vértices con una z pequeña se dividirán por una pequeña w, por lo tanto, sus coordenadas "explotarán", mientras que los vértices con una z grande se "exprimirán", que es lo que está causando el efecto de perspectiva.
Estoy tratando de entender lo que hace el siguiente código:
glm::mat4 Projection = glm::perspective(35.0f, 1.0f, 0.1f, 100.0f);
¿Crea una matriz de proyección ? ¿Quita todo lo que no está en la vista del usuario? No pude encontrar nada en la página de API , y lo único que pude encontrar en el pdf en su sitio web fue este:
gluPerspective:
glm::mat4 perspective(float fovy, float aspect, float zNear,
float zFar);
glm::dmat4 perspective(
double fovy, double aspect, double zNear,
double zFar);
From GLM_GTC_matrix_transform extension: <glm/gtc/matrix_transform.hpp>
Pero no explica los parámetros. Tal vez me perdí algo.
Esta es una versión independiente de la misma función. Esto es más o menos una versión de copiar y pegar del original .
# include <math.h>
# include <stdlib.h>
# include <string.h>
typedef struct s_mat {
float *array;
int width;
int height;
} t_mat;
t_mat *mat_new(int width, int height)
{
t_mat *to_return;
to_return = (t_mat*)malloc(sizeof(t_mat));
to_return->array = malloc(width * height * sizeof(float));
to_return->width = width;
to_return->height = height;
return (to_return);
}
void mat_zero(t_mat *dest)
{
bzero(dest->array, dest->width * dest->height * sizeof(float));
}
void mat_set(t_mat *m, int x, int y, float val)
{
if (m == NULL || x > m->width || y > m->height)
return ;
m->array[m->width * (y - 1) + (x - 1)] = val;
}
t_mat *mat_perspective(float angle, float ratio,
float near, float far)
{
t_mat *to_return;
float tan_half_angle;
to_return = mat_new(4, 4);
mat_zero(to_return);
tan_half_angle = tan(angle / 2);
mat_set(to_return, 1, 1, 1 / (ratio * tan_half_angle));
mat_set(to_return, 2, 2, 1 / (tan_half_angle));
mat_set(to_return, 3, 3, -(far + near) / (far - near));
mat_set(to_return, 4, 3, -1);
mat_set(to_return, 3, 4, -(2 * far * near) / (far - near));
return (to_return);
}