這次的筆記,我們通過一個OpenGL的一個簡單使用案例,并結(jié)合上個筆記中的名詞解釋,來看看它是如何繪制渲染到屏幕的。實現(xiàn)效果為繪制一個正方形,并可以通過鍵盤控制正方形移動。
案例的大致執(zhí)行流程可分為main->SetupRC->changeSize->RenderScene。
首先我們需要做一些準備工作,這里我們引入了OpenGL繪制所需要用到的幾個頭文件,并定義了一個著色管理器和一個批次類

main
main函數(shù)中我們主要用來初始化OpenGL環(huán)境變量,設置窗口,標題,注冊一些回調(diào)函數(shù)等
int main(int argc, char* argv[])
{
gltSetWorkingDirectory(argv[0]);
glutInit(&argc, argv);
//申請一個顏色緩存區(qū)、深度緩存區(qū)、雙緩存區(qū)、模板緩存區(qū)
glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGBA | GLUT_DEPTH | GLUT_STENCIL);
//設置window 的尺寸
glutInitWindowSize(800, 600);
//創(chuàng)建window的名稱
glutCreateWindow("GL_POINTS");
//注冊回調(diào)函數(shù)(改變尺寸)
glutReshapeFunc(ChangeSize);
//點擊空格時,調(diào)用的函數(shù)
glutKeyboardFunc(KeyPressFunc);
//特殊鍵位函數(shù)(上下左右)
glutSpecialFunc(SpecialKeys);
//顯示函數(shù)
glutDisplayFunc(RenderScene);
//判斷一下是否能初始化glew庫,確保項目能正常使用OpenGL 框架
GLenum err = glewInit();
if (GLEW_OK != err) {
fprintf(stderr, "GLEW Error: %s\n", glewGetErrorString(err));
return 1;
}
//繪制
SetupRC();
//runloop運行循環(huán)
glutMainLoop();
return 0;
}
SetupRC
觸發(fā)條件:手動main函數(shù)觸發(fā)
處理業(yè)務:1.設置窗口背景顏色
2.初始化存儲著色器shaderManager
3.設置圖形頂點數(shù)據(jù)
4.利用GLBatch三角形批次類,將數(shù)據(jù)傳遞到著色器
void setupRC(){
//設置清屏顏色(背景顏色)
glClearColor(0.98f, 0.40f, 0.7f, 1);
//沒有著色器,在OpenGL 核心框架中是無法進行任何渲染的。初始化一個渲染管理器。
shaderManager.InitializeStockShaders();
//修改為GL_TRIANGLE_FAN ,4個頂點
triangleBatch.Begin(GL_TRIANGLE_FAN, 4);
triangleBatch.CopyVertexData3f(vVerts);
triangleBatch.End();
}
changeSize
觸發(fā)條件:當屏幕大小發(fā)生改變/第一次創(chuàng)建窗口時,會調(diào)用
處理業(yè)務:1.設置OpenGL視口
2.設置OpenGL投影方式等
void ChangeSize(int w,int h){
if (h==0) {
h=1;
}
glViewport(0,0, w, h);//設置視口
}
RenderScene
自定義函數(shù),通過glutDisplayFunc(函數(shù)名)注冊為顯示渲染函數(shù),當屏幕發(fā)生變化/或者開發(fā)者主動渲染會調(diào)用此函數(shù),用來實現(xiàn)數(shù)據(jù)->渲染的過程
觸發(fā)條件:1.系統(tǒng)自動觸發(fā) 2.手動調(diào)用函數(shù)觸發(fā)
處理業(yè)務:1.清理緩存區(qū)(顏色,深度,模版緩存區(qū)等)
2.使用存儲著色器
3.繪制圖形
void RenderScene(void){
//清除緩存區(qū)
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT|GL_STENCIL_BUFFER_BIT);
//設置一組浮點數(shù)來表示紅色
GLfloat vRed[] = {1.0,0.0,0.0,1.0f};
//4x4矩陣
M3DMatrix44f mTransfromMatrix;
//平移
m3dTranslationMatrix44(mTransfromMatrix, xPos, yPos, 0.0f);
//將矩陣結(jié)果 提交給固定著色器(平面著色器)中繪制
shaderManager.UseStockShader(GLT_SHADER_FLAT,mFinalTransform,vRed);
//提交著色器
triangleBatch.Draw();
//將后臺緩沖區(qū)進行渲染,然后結(jié)束后交換給前臺
glutSwapBuffers();
}
SpecialKeys
自定義函數(shù),這是我們在main()中添加的對鍵盤按鈕點擊后的監(jiān)聽回調(diào),在這里可以判斷我們點擊了鍵盤上的哪個鍵。xPos,yPos為x軸,y軸上的偏移量
void SpecialKeys(int key, int x, int y){
GLfloat stepSize = 0.025f;
if (key == GLUT_KEY_UP) {
yPos += stepSize;
}
if (key == GLUT_KEY_DOWN) {
yPos -= stepSize;
}
if (key == GLUT_KEY_LEFT) {
xPos -= stepSize;
}
if (key == GLUT_KEY_RIGHT) {
xPos += stepSize;
}
//碰撞檢測
if (xPos < (-1.0f + blockSize)) {
xPos = -1.0f + blockSize;
}
if (xPos > (1.0f - blockSize)) {
xPos = 1.0f - blockSize;
}
if (yPos < (-1.0f + blockSize)) {
yPos = -1.0f + blockSize;
}
if (yPos > (1.0f - blockSize)) {
yPos = 1.0f - blockSize;
}
//這是觸發(fā)重繪的一個API,類似于調(diào)用setNeedsDisplay()
glutPostRedisplay();
}