OpenGL學習 (六)座標系統

OpenGL學習 (六)座標系統

參考官方文檔https://learnopengl-cn.github.io/

將座標變換爲標準化設備座標,然後轉換爲屏幕座標的過程是分佈進行的。有5個比較重要的座標系統:

  • 局部座標
  • 世界座標
  • 觀察座標
  • 裁剪座標
  • 屏幕座標

座標變換的過程中會用到幾個變換矩陣:模型、觀察、投影矩陣。

現在我們可以進行3D繪圖了。

頂點着色器shader.vs

#version 330 core
layout(location=0) in vec3 aPos;
layout(location=1) in vec3 aColor;
layout(location=2) in vec2 aTexCoord;

out vec3 ourColor;
out vec2 TexCoord;
uniform mat4 transform;
uniform mat4 model;
uniform mat4 view;
uniform mat4 projection;

void main(){
	gl_Position=projection*view*model*vec4(aPos.x,aPos.y,aPos.z,1.0);
	ourColor=aColor;
	TexCoord=vec2(aTexCoord.x,1.0-aTexCoord.y);
}

main.cpp

...;
const unsigned int screenWidth = 800, screenHeight = 600;
...;
while(...){
    ...;
    ourShader.use();
		//
		glm::mat4 model = glm::mat4(1.0f);
		model = glm::rotate(model, glm::radians(-55.0f), glm::vec3(1.0f, 0.0f, 0.0f));
		glm::mat4 view = glm::mat4(1.0f);
		view = glm::translate(view, glm::vec3(0.0f, 0.0f, -3.0f));
		glm::mat4 projection = glm::mat4(1.0f);
		projection = glm::perspective(glm::radians(45.0f), (float)screenWidth / (float)screenHeight, 0.1f, 100.0f);
		int modelLoc = glGetUniformLocation(ourShader.ID, "model");
		glUniformMatrix4fv(modelLoc, 1, GL_FALSE, glm::value_ptr(model));
		int viewLoc = glGetUniformLocation(ourShader.ID, "view");
		glUniformMatri![opentk_40](C:\Users\xhh\Pictures\QQ瀏覽器截圖\opentk_40.png)x4fv(viewLoc, 1, GL_FALSE, &view[0][0]);
		int projectionLoc = glGetUniformLocation(ourShader.ID, "projection");
		glUniformMatrix4fv(projectionLoc, 1, GL_FALSE, glm::value_ptr(projection));
    ...;
}
...;

最後運行的效果爲:
在這裏插入圖片描述

然後我們來渲染一個立方體:

main.cpp

...;
float vertices[] = {
		//     ---- 位置 ----         - 紋理座標 -
			 0.5f,  0.5f, 0.5f,      1.0f, 1.0f,   // 右上
			 0.5f, -0.5f, 0.5f,      1.0f, 0.0f,   // 右下
			-0.5f, -0.5f, 0.5f,      0.0f, 0.0f,   // 左下
			-0.5f,  0.5f, 0.5f,      0.0f, 1.0f,    // 左上
			0.5f,  0.5f, 0.5f,      1.0f, 1.0f,   // 右上
			-0.5f, -0.5f, 0.5f,      0.0f, 0.0f,   // 左下

			 0.5f,  0.5f, -0.5f,      1.0f, 1.0f,   // 右上
			 0.5f, -0.5f, -0.5f,      1.0f, 0.0f,   // 右下
			-0.5f, -0.5f, -0.5f,      0.0f, 0.0f,   // 左下
			-0.5f,  0.5f, -0.5f,      0.0f, 1.0f,    // 左上
			0.5f,  0.5f, -0.5f,      1.0f, 1.0f,   // 右上
			-0.5f, -0.5f,-0.5f,      0.0f, 0.0f,   // 左下

			 0.5f,  0.5f, 0.5f,      0.0f, 1.0f,   // 右上
			 0.5f, 0.5f, -0.5f,      0.0f, 0.0f,   // 右下
			0.5f, -0.5f, -0.5f,      1.0f, 0.0f,   // 左下
			0.5f,  -0.5f, -0.5f,      1.0f, 0.0f,    // 左上
			0.5f,  -0.5f, 0.5f,      1.0f, 1.0f,   // 右上
			0.5f, 0.5f,0.5f,      0.0f, 1.0f,   // 左下

			-0.5f,  0.5f, 0.5f,      0.0f, 1.0f,   // 右上
			- 0.5f, 0.5f, -0.5f,      0.0f, 0.0f,   // 右下
			-0.5f, -0.5f, -0.5f,      1.0f, 0.0f,   // 左下
			-0.5f,  -0.5f, -0.5f,      1.0f, 0.0f,    // 左上
			-0.5f,  -0.5f, 0.5f,      1.0f, 1.0f,   // 右上
			-0.5f, 0.5f,0.5f,      0.0f, 1.0f,   // 左下

			0.5f,  0.5f, 0.5f,      0.0f, 1.0f,   // 右上
			 0.5f, 0.5f, -0.5f,      0.0f, 0.0f,   // 右下
			-0.5f, 0.5f, -0.5f,      1.0f, 0.0f,   // 左下
			-0.5f,  0.5f, -0.5f,      1.0f, 0.0f,    // 左上
			-0.5f,  0.5f, 0.5f,      1.0f, 1.0f,   // 右上
			0.5f, 0.5f,0.5f,      0.0f, 1.0f,   // 左下

			0.5f,  -0.5f, 0.5f,      0.0f, 1.0f,   // 右上
			 0.5f, -0.5f, -0.5f,      0.0f, 0.0f,   // 右下
			-0.5f, -0.5f, -0.5f,      1.0f, 0.0f,   // 左下
			-0.5f,  -0.5f, -0.5f,      1.0f, 0.0f,    // 左上
			-0.5f,  -0.5f, 0.5f,      1.0f, 1.0f,   // 右上
			0.5f, -0.5f,0.5f,      0.0f, 1.0f,   // 左下
	};
...;
while(...){
    ...;
    //每次迭代之前清楚深度緩衝和顏色緩衝
	glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);
		//開啓深度測試
	glEnable(GL_DEPTH_TEST);
    ...;
    model = glm::rotate(model,(float)glfwGetTime()* glm::radians(55.0f), glm::vec3(0.5f, 1.0f, 0.0f));
    ...;
    glDrawArrays(GL_TRIANGLES, 0, 36);
    ...;
}
...;

這樣運行的結果如圖
在這裏插入圖片描述

另外,我們還可以在屏幕上顯示更多的立方體:

...;
glm::vec3 cubePositions[] = {
  glm::vec3( 0.0f,  0.0f,  0.0f), 
  glm::vec3( 2.0f,  5.0f, -15.0f), 
  glm::vec3(-1.5f, -2.2f, -2.5f),  
  glm::vec3(-3.8f, -2.0f, -12.3f),  
  glm::vec3( 2.4f, -0.4f, -3.5f),  
  glm::vec3(-1.7f,  3.0f, -7.5f),  
  glm::vec3( 1.3f, -2.0f, -2.5f),  
  glm::vec3( 1.5f,  2.0f, -2.5f), 
  glm::vec3( 1.5f,  0.2f, -1.5f), 
  glm::vec3(-1.3f,  1.0f, -1.5f)  
};
...;
while(...){
    ...;
    glBindVertexArray(VAO);

		for (unsigned int i = 0; i < 10; i++)
		{
			glm::mat4 model=glm::mat4(1.0f);
			model = glm::translate(model, cubePositions[i]);
			float angle = 20.0f * i;
			model = glm::rotate(model,(float)glfwGetTime()* glm::radians(angle), glm::vec3(1.0f, 0.3f, 0.5f));
			ourShader.setMat4("model", model);

			glDrawArrays(GL_TRIANGLES, 0, 36);
		}
    ...;
}

這樣會得到10個旋轉着的立方體。
在這裏插入圖片描述

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章