openGL 基礎(chǔ)知識(一)繪制簡單圖形

1. 利用openGL畫點、線、面

glBegin(所畫類型)
這里設(shè)置畫圖所需要的點
glEnd()

openGL中,需要畫點、線、面都是包含在兩條語句中
glBeginglEnd中,所畫圖形的不同都是通過設(shè)置glBegin中的參數(shù)來決定。

  • 畫點 GL_POINTS
    示例 (所有代碼展示皆為display中的語句)
    glClearColor(0.0f, 0.0f, 0.0f,0.0f);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    glBegin(GL_POINTS);
    glVertex2f(0.0f, 0.0f);
    glVertex2f(0.5f, 0.5f);
    glEnd();
    glFlush();

效果

繪制兩點

  • 畫線 GL_LINES
    示例
    glBegin(GL_LINES);
    glVertex2f(0.0f, 0.0f);
    glVertex2f(0.5f, 0.5f);
    glEnd();
    glFlush();
    glClearColor(0.0f, 0.0f, 0.0f,0.0f);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

效果

繪制直線

除此之外還有
GL_LINE_STRIP(很多個點直接連接),GL_LINE_LOOP(收尾相連的閉合線),GL_TRIANGLES(繪制三角形),GL_TRIANGLE_STRIP(確保繪制的三角形都是同方向的),GL_TRIANGLE_FAN等各種繪制方式。

區(qū)別

區(qū)別2

  • 畫圓
static int n = 20;
static GLfloat R = 0.5;
static const GLfloat PI= 3.141592653;
void display(void) {
    glClearColor(0.0f, 0.0f, 0.0f,0.0f);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    glBegin(GL_POLYGON);
    for (int i = 0; i < n; i++) {
        glVertex2f(R*cos(2 * PI / n * i), R*sin(2 * PI / n * i));
    }
    glEnd();
    glFlush();
}
畫圓

注意到,這里使用了GL_POLYGON,這種繪圖方式會將圖形內(nèi)部進行自動填充。如若使用GL_LINE_LOOP則會產(chǎn)生這種效果:

不填充
  • 畫正弦曲線
    利用一定的數(shù)學(xué)公式,使用點與點直線相連的方式可畫出各種各樣的函數(shù)曲線
    示例
void display(void) {
    GLfloat x;
    glClear(GL_COLOR_BUFFER_BIT);
    glBegin(GL_LINES);
    glVertex2f(-1.0f, 0.0f);
    glVertex2f(1.0f, 0.0f);         // 以上兩個點可以畫x軸
    glVertex2f(0.0f, -1.0f);
    glVertex2f(0.0f, 1.0f);         // 以上兩個點可以畫y軸
    glEnd();
    glBegin(GL_LINE_STRIP);
    for (x = -1.0f / factor; x<1.0f / factor; x += 0.01f)
    {
        glVertex2f(x*factor, sin(x)*factor);
    }
    glEnd();
    glFlush();
}

效果

image.png

2. 關(guān)于點與直線

  • 關(guān)于點

點的大小默認(rèn)為1個像素,但也可以改變之。改變的命令為glPointSize,其函數(shù)原型如下:
void glPointSize(GLfloat size);
size必須大于0.0f,默認(rèn)值為1.0f,單位為“像素”。

  • 關(guān)于直線

(1)直線可以指定寬度:
void glLineWidth(GLfloat width);
其用法跟glPointSize類似。

(2)畫虛線。
首先,使用glEnable(GL_LINE_STIPPLE);來啟動虛線模式(使用glDisable(GL_LINE_STIPPLE)可以關(guān)閉之)。
然后,使用glLineStipple來設(shè)置虛線的樣式。
void glLineStipple(GLint factor, GLushort pattern);
pattern是由1和0組成的長度為16的序列,從最低位開始看,如果為1,則直線上接下來應(yīng)該畫的factor個點將被畫為實的;如果為0,則直線上接下來應(yīng)該畫的factor個點將被畫為虛的。

___示例

void display(void) {
    glEnable(GL_LINE_STIPPLE);
    glLineStipple(2, 0x0f0f);
    glLineWidth(10.0f);
    glBegin(GL_LINES);
    glVertex2f(0.0f, 0.0f);
    glVertex2f(0.5f, 0.5f);
    glEnd();
    glFlush();
}
虛線

3. 關(guān)于多邊形的正反面

多邊形在我們的二維坐標(biāo)系中,我們一般把朝向我們的一面認(rèn)為是正面,而把背朝著我們的一面認(rèn)為是反面,在openGL中也存在著正反兩面。接下來我們將通過一個示例,來講解正反兩面的寫法與區(qū)別。

我們在進行繪制正反面之前,我們約定,逆時針方向繪制的面為正面,順時針方向繪制的面為反面。我們通過

glFrontFace(GL_CCW);   // 設(shè)置CCW方向為“正面”,CCW即CounterClockWise,逆時針

設(shè)置逆時針方向為正面。

為了體現(xiàn)出正反兩面的區(qū)別,我們設(shè)置正面為填充模式,反面為線性繪制模式。接下來看我們的示例代碼

     glClear(GL_COLOR_BUFFER_BIT);
     glPolygonMode(GL_FRONT, GL_FILL); // 設(shè)置正面為填充模式
     glPolygonMode(GL_BACK, GL_LINE);   // 設(shè)置反面為線形模式
     glFrontFace(GL_CCW);               // 設(shè)置逆時針方向為正面
     glBegin(GL_POLYGON);               // 按逆時針繪制一個正方形,在左下方
         glVertex2f(-0.5f, -0.5f);
         glVertex2f(0.0f, -0.5f);
         glVertex2f(0.0f, 0.0f);
         glVertex2f(-0.5f, 0.0f);
     glEnd();
     glBegin(GL_POLYGON);               // 按順時針繪制一個正方形,在右上方
         glVertex2f(0.0f, 0.0f);
         glVertex2f(0.0f, 0.5f);
         glVertex2f(0.5f, 0.5f);
         glVertex2f(0.5f, 0.0f);
     glEnd();
     glFlush();

效果

正反兩面

  • 剔除不必要的面

在三位繪圖中,我們難免會遇到遮擋的問題,當(dāng)我們面朝著正面的時候,反面難免會被遮擋而無法看到,所以這個時候我們就可以通過剔除來節(jié)約我們的計算空間。

首先需要通過glEnable(GL_GULL_FACE)來允許剔除(可通過glDisable去除)

glCullFace的參數(shù)可以是GL_FRONT,GL_BACK或者GL_FRONT_AND_BACK,分別表示剔除正面、剔除反面、剔除正反兩面的多邊形。

在上面的代碼中加上這兩句

    glEnable(GL_CULL_FACE);
    glCullFace(GL_FRONT);

只剩下了反面的圖形


剔除正面
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容