camera is located at the origin of coordinate, facing the negative axis
glm::vec3 cameraTarget = glm::vec3(0.0f, 0.0f, 0.0f);
glm::vec3 cameraDirection = glm::normalize(cameraPos - cameraTarget);
// the up is usually the world up
glm::vec3 up = glm::vec3(0.0f, 1.0f, 0.0f);
glm::vec3 cameraRight = glm::normalize(glm::cross(up, cameraDirection));
glm::vec3 cameraUp = glm::cross(cameraDirection, cameraRight);
glm::mat4 view;
view = glm::lookAt(glm::vec3(0.0f, 0.0f, 3.0f), // position
glm::vec3(0.0f, 0.0f, 0.0f), // target
glm::vec3(0.0f, 1.0f, 0.0f)); // up
direction.x = cos(glm::radians(pitch)) * cos(glm::radians(yaw));
direction.y = sin(glm::radians(pitch));
direction.z = cos(glm::radians(pitch)) * sin(glm::radians(yaw));
// define a callback
void mouse_callback(GLFWwindow* window, double xpos, double ypos);
// regist it
glfwSetCursorPosCallback(window, mouse_callback);
// enable it
glfwSetInputMode(window, GLFW_CURSOR, GLFW_CURSOR_DISABLED);
glm::ortho(0.0f, 800.0f, 0.0f, 600.0f, 0.1f, 100.0f);
glm::mat4 proj = glm::perspective(glm::radians(45.0f), (float)width/(float)height, 0.1f, 100.0f);
OpenGL stores all its depth information in a z-buffer, also known as a depth buffer. GLFW automatically creates such a buffer for you (just like it has a color-buffer that stores the colors of the output image). The depth is stored within each fragment (as the fragment’s z value) and whenever the fragment wants to output its color, OpenGL compares its depth values with the z-buffer and if the current fragment is behind the other fragment it is discarded, otherwise overwritten. This process is called depth testing and is done automatically by OpenGL.
glEnable(GL_DEPTH_TEST);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
// shader
#version 330 core
layout (location=0) in vec3 aPos;
uniform mat4 model;
uniform mat4 view;
uniform mat4 project;
void main(){
gl_Position = project * view * model * vec4(aPos, 1.0);
}
// pass the data
glm::mat4 model = glm::mat4(1.0f); // make sure to initialize matrix to identity matrix first
glm::mat4 view = glm::mat4(1.0f);
glm::mat4 projection = glm::mat4(1.0f);
model = glm::rotate(model, (float)glfwGetTime(), glm::vec3(0.5f, 1.0f, 0.0f));
view = glm::translate(view, glm::vec3(0.0f, 0.0f, -3.0f));
projection = glm::perspective(glm::radians(45.0f), (float)SCR_WIDTH / (float)SCR_HEIGHT, 0.1f, 100.0f);
ourShader.setMat4("model", model);
ourShader.setMat4("view", view);
// note: currently we set the projection matrix each frame, but since the projection matrix rarely changes it's often best practice to set it outside the main loop only once.
ourShader.setMat4("project", projection);
a course about matrix transformation : https://www.khanacademy.org/math/linear-algebra/matrix-transformations
[ 1 0 0 T x 0 1 0 T y 0 0 1 T z 0 0 0 S 4 ] ⋅ ( x y z 1 ) = ( x + T x y + T y z + T z 1 ) \begin{bmatrix} 1 & 0 & 0&T_x \\ 0& 1 & 0& T_y\\ 0& 0& 1 & T_z\\ 0&0 &0 & S_4 \end{bmatrix} \cdot \begin{pmatrix} x \\ y \\z \\1\end{pmatrix} = \begin{pmatrix} x+T_x \\ y+T_y \\z+T_z \\1\end{pmatrix} ⎣⎢⎢⎡100001000010TxTyTzS4⎦⎥⎥⎤⋅⎝⎜⎜⎛xyz1⎠⎟⎟⎞=⎝⎜⎜⎛x+Txy+Tyz+Tz1⎠⎟⎟⎞
Homogeneous coordinates
The w component of a vector is also known as a homogeneous coordinate. To get the 3D vector from a homogeneous vector we divide the x, y and z coordinate by its w coordinate. We usually do not notice this since the w component is 1.0 most of the time. Using homogeneous coordinates has several advantages: it allows us to do translations on 3D vectors (without a w component we can’t translate vectors) .
Also, whenever the homogeneous coordinate is equal to 0 the vector is specifically known as a direction vector since a vector with a w coordinate of 0 cannot be translated.
for example, Rotation around the X-axis:
[
1
0
0
0
0
cos
(
θ
)
−
sin
(
θ
)
0
0
sin
(
θ
)
cos
(
θ
)
0
0
0
0
S
4
]
⋅
(
x
y
z
1
)
=
(
x
cos
(
θ
)
⋅
y
−
sin
(
θ
)
⋅
z
sin
(
θ
)
⋅
y
+
c
o
s
(
θ
)
⋅
z
1
)
\begin{bmatrix} 1 & 0 & 0&0 \\ 0& \cos(\theta) & -\sin(\theta)& 0\\ 0& \sin(\theta)& \cos(\theta) & 0\\ 0&0 &0 & S_4 \end{bmatrix} \cdot \begin{pmatrix} x \\ y \\z \\1\end{pmatrix} = \begin{pmatrix} x\\ \cos(\theta) \cdot y- \sin(\theta) \cdot z\\\sin(\theta) \cdot y+cos(\theta) \cdot z\\1\end{pmatrix}
⎣⎢⎢⎡10000cos(θ)sin(θ)00−sin(θ)cos(θ)0000S4⎦⎥⎥⎤⋅⎝⎜⎜⎛xyz1⎠⎟⎟⎞=⎝⎜⎜⎛xcos(θ)⋅y−sin(θ)⋅zsin(θ)⋅y+cos(θ)⋅z1⎠⎟⎟⎞
we can make an object rotate around arbitrary unit axis by combining rotation matrix. But we use a matrix to make it.
e.g. Scale and then translate
the website for download: https://glm.g-truc.net/0.9.8/index.html
eg:
// includes
#include <glm/glm.hpp>
#include <glm/gtc/matrix_transform.hpp>
#include <glm/gtc/type_ptr.hpp>
// vertex shader
#version 330 core
layout (location = 0) in vec3 aPos;
uniform mat4 transform;
void main()
{
gl_Position = transform * vec4(aPos, 1.0f);
}
// get transformation matrix
glm::mat4 trans = glm::mat4(1.0f);
trans = glm::translate(trans, glm::vec3(1.0f, 1.0f, 0.0f));
trans = glm::rotate(trans, glm::radians(90.0f), glm::vec3(0.0, 0.0, 1.0));
trans = glm::scale(trans, glm::vec3(0.5, 0.5, 0.5));
// set the data
unsigned int transformLoc = glGetUniformLocation(ourShader.ID, "transform");
glUniformMatrix4fv(transformLoc, 1, GL_FALSE, glm::value_ptr(trans));
// glUniformMatrix4fv(transformLoc, 1, GL_FALSE, &trans[0][0]);
因篇幅问题不能全部显示,请点此查看更多更全内容
Copyright © 2019- ovod.cn 版权所有 湘ICP备2023023988号-4
违法及侵权请联系:TEL:199 1889 7713 E-MAIL:2724546146@qq.com
本站由北京市万商天勤律师事务所王兴未律师提供法律服务