跳轉到內容

OpenGL 程式設計/基礎/二維物件

來自華夏公益教科書

繪製三角形和四邊形

[編輯 | 編輯原始碼]

glRectf() 雖然有用,但它不允許我們對矩形的單個頂點進行太多控制。為了給我們更多控制,並能夠繪製更復雜的形狀,我們必須使用不同的函式。

獨立的頂點定義形狀

[編輯 | 編輯原始碼]

開始一個頂點定義的形狀

[編輯 | 編輯原始碼]

要開始一個由頂點定義的形狀,我們使用 glBegin() 函式。glBegin() 接受一個引數:你想建立的形狀型別。以下是一些可能的引數

  • GL_TRIANGLES
  • GL_QUADS
  • GL_POLYGON

四邊形是任何具有 4 個頂點的形狀:矩形、正方形、梯形等。頂點的位置將定義它是哪種型別的形狀。

雖然多邊形聽起來很適合繪製複雜形狀,但請向下滾動檢視有關多邊形限制的警告:多邊形有很多限制,在某些情況下你可能最好使用一系列連線的四邊形或三角形。

定義頂點

[編輯 | 編輯原始碼]

在呼叫 glBegin() 之後,我們實際上使用 glVertex2f(float xPosition, float yPosition) 來定義頂點。

glBegin(GL_XYZ);
glVertex2f(-1.0f,-0.5f);
glVertex2f(1.0f,-0.25f);
...

重要提示:你定義頂點的順序很重要!一般來說,如果你按逆時針順序定義頂點,則正面將朝向你,這通常是你想要的。這種區別在我們進入 3D 時變得非常重要,所以請確保按逆時針順序定義你的頂點,除非你知道自己在做什麼!如果你想按順時針順序定義頂點,請確保在你的 setup() 函式中包含此函式

glFrontFace(GL_CW);

它將允許你僅按順時針順序繪製。

要結束一個頂點定義的形狀,只需呼叫 glEnd(),它不接受任何引數。

此顯示函式將在我們的螢幕中央繪製一個黑色的梯形。

void display() {
       glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
       glColor3f(0.0f, 0.0f, 0.0f); // sets color to black.
       glBegin(GL_QUADS);
               glVertex2f(-0.25f, 0.25f); // vertex 1
               glVertex2f(-0.5f, -0.25f); // vertex 2
               glVertex2f(0.5f, -0.25f); // vertex 3
               glVertex2f(0.25f, 0.25f); // vertex 4
       glEnd();
       glutSwapBuffers();
}

關於樣式的說明:對 glVertex() 的呼叫有時會縮排以將其與 glBegin() 和 glEnd() 分開。前面示例中的縮排不是錯誤。

高效地繪製一系列連線的形狀

[編輯 | 編輯原始碼]

如果我們要繪製一系列形狀,其中每個形狀都與另一個形狀共享一條邊或頂點,那麼沒有理由重複對 glVertex2f() 的如此多次呼叫。相反,我們使用一個特殊引數呼叫 glBegin() 以指示我們要繪製這些物件的“條帶”。

使用 glBegin 與 GL_TRIANGLE_STRIP 或 GL_QUAD_STRIP

[編輯 | 編輯原始碼]

當我們使用這兩個引數中的任何一個呼叫 glBegin() 時,我們可以繪製一系列三角形或四邊形,其中每個三角形或四邊形都與另一個三角形或四邊形共享一條邊。這一個很好的用途是繪製複雜的形狀,例如一個 2D 聖誕樹。

三角形條帶由用於三角形的 3 個初始頂點定義,然後每個額外的三角形由一個頂點定義。任何給定的三角形都是由它的一個頂點和它前面的兩個頂點形成的。

四邊形條帶由用於四邊形的 4 個初始頂點定義,然後每個額外的四邊形由兩個頂點定義。任何給定的四邊形都是由它的兩個頂點和它前面的兩個頂點形成的。

該程式的示例輸出

以下程式碼使用三角形條帶定義一個房子的形狀,它有一個傾斜的屋頂。

void display() {
       glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
       glColor3f(0.0f, 0.0f, 0.0f); // sets color to black.
       glBegin(GL_TRIANGLE_STRIP); // draw in triangle strips
               glVertex2f(0.0f, 0.75f); // top of the roof
               glVertex2f(-0.5f, 0.25f); // left corner of the roof
               glVertex2f(0.5f, 0.25f); // right corner of the roof
               glVertex2f(-0.5f, -0.5f); // bottom left corner of the house
               glVertex2f(0.5f, -0.5f); //bottom right corner of the house
       glEnd();
       glutSwapBuffers();
}

在這裡,定義了三個三角形,一個用於屋頂,一個用於房子的左上角,一個用於房子的右下角。

使用 glBegin 與 GL_TRIANGLE_FAN

[編輯 | 編輯原始碼]

如果我們要繪製一堆三角形,其中每個三角形都共享一個預定義的頂點(例如,在原點),我們可以使用三角形扇形。三角形扇形透過奇數個頂點定義一個形狀。第一個頂點定義一箇中心點,每個三角形都將該點作為頂點。然後,每兩個頂點都與初始頂點一起使用來定義一個三角形。

#include <GL/glut.h>

void init(){ 
    glClearColor(0,0,0,0);
    glMatrixMode(GL_PROJECTION);
    gluOrtho2D(0,100,0,200);
}
void Display(){
     glClear(GL_COLOR_BUFFER_BIT);
     glBegin(GL_TRIANGLE_FAN);
         glColor3f(1,0,0);
         glVertex2f(0,0.5);
         glVertex2f(-0.4,0);
 	 glVertex2f(0.4,0);
         glColor3f(0,1,0);
 	 glVertex2f(0,-0.5);
     glEnd();
     glFlush(); 
} 

int main(int argc, char **argv){ 	
    glutInit(& argc, argv);
    glutInitDisplayMode(GLUT_SINGLE|GLUT_RGB);
    glutInitWindowSize(500,500);
    glutInitWindowPosition(200,200);
    glutCreateWindow("line");
    glutDisplayFunc(Display);
    init();
    glutMainLoop();
	
    return 0;
}

內置於 GLUT 的形狀

[編輯 | 編輯原始碼]

GLUT 有一些內建物件,只需呼叫一個簡單的函式就可以使用它們。這些物件中最有趣和最有用的物件是

函式 二維形狀 三維形狀 註釋
glutSolidSphere(float radius, int slices, int stacks) 圓形 球體 為 slices 和 stacks 引數選擇一個 20-100 的整數;數字越大,球體/圓形越準確。
glutSolidCube(double size) 正方形 立方體
glutSolidCone(double base, double height, int slices, int stacks) 三角形 圓錐體 slices 引數越大,圓錐體看起來越平滑。
glutSolidTorus(double innerRadius, double outerRadius, int nSides, int rings) 環面
glutSolidTeapot(float radius) 茶壺 茶壺 是的,一個茶壺。請參閱維基百科文章“Utah 茶壺”,瞭解為什麼選擇了一個茶壺。
華夏公益教科書