OpenGL ES學習筆記(二):畫一個三角形

示例最終效果

這篇筆記的關鍵在于對OpenGL ES繪圖7個步驟中的函數各個參數的的解讀,筆者之前看別人的文章被這些函數的參數弄的暈頭轉向,看了這本書之后終于理解透徹。


準備

  1. 首先復習一下為緩存提供數據的7個步驟,可以在第一篇筆記中查看,這里不再贅述。
  2. iOS中使用OpenGL ES的框架為GLKit,Demo中會使用UIViewController的子類GLKViewController作為主控制器,將控制器的view轉換為GLKView,這樣可以省去設置GLKView代理等操作。

需要注意本例中直接使用默認新建的項目,需要在storyboard中修改ViewController中View的類型為GLKView,需要在ViewController.h中把父類改為GLKViewController。

  1. 示例概要:
    • 準備三角形頂點數據數組
    • 設置GLKView的上下文為當前的上下文
    • 設置著色器屬性
    • 申請、綁定、緩存頂點數據
    • 在代理方法中,準備繪圖
      • 著色器準備
      • 清理
      • 啟用緩存頂點數據、設置指針、繪圖
    • dealloc方法中刪除緩存數據

示例解說

一、準備頂點數據數組
  • 聲明一個結構體保存一個頂點的數據
  • 創建一個C數組保存三角形的3個頂點

/** 保存每個頂點的數據 */
typedef struct vector {
    GLKVector3 positionCoords;
}SceneVertex;

/** 保存三角形3個頂點的數據 */
static const SceneVertex vertices[] = {
    {{-0.5, -0.5, 0}},
    {{ 0.5, -0.5, 0}},
    {{-0.5,  0.5, 0}}
};

二、設置當前的上下文為view的上下文
/** 強轉view為GLKView,需要在storyboard中也要修改 */
GLKView *view = (GLKView *)self.view;

/** 斷言,判斷view的類型 */
NSAssert([view isMemberOfClass:[GLKView class]], @"View controller's view is not a GLKView");
    
/** 創建一個OpenGL ES 2.0的上下文給view */
view.context = [[EAGLContext alloc] initWithAPI:kEAGLRenderingAPIOpenGLES2];
    
/** 將view的上下文設置為當前的上下文 */
[EAGLContext setCurrentContext:view.context];
三、設置著色器,三角顏色及背景色
/** 為OpenGL ES 2.0創建一個默認的基本效果并提供給片元著色器程序,用于之后的繪圖渲染 */
_baseEffect = [[GLKBaseEffect alloc] init];
_baseEffect.useConstantColor = GL_TRUE;
_baseEffect.constantColor = GLKVector4Make(200.0, /** 紅 */
                                           0.0,   /** 綠 */
                                           0.0,   /** 藍 */
                                           1.f);  /** alpha */

/** 設置背景色,存儲到當前的上下文中 */
glClearColor(1.0, 1.0, 1.0, 1.0);
四、申請、綁定、緩存

函數的參數說明已經在注釋中寫的非常詳細了!

/** 申請、綁定并初始化一塊緩存,將繪圖信息保存到GPU的當中 */
/** ①申請 */
glGenBuffers(1,                 /** 指定要生成的緩存標識符的數量 */
             &vertexBufferID);  /** 指針:緩存標識符的地址 */
/** ②綁定 */
glBindBuffer(GL_ARRAY_BUFFER,   /** 綁定什么類型的緩存:頂點屬性數組 */
             vertexBufferID);   /** 需要綁定的緩存的標識符(標識符為0表示沒有緩存,就不會綁定數據) */
/** ③緩存數據 */
glBufferData(GL_ARRAY_BUFFER,   /** 初始化緩存信息 */
             sizeof(vertices),  /** 緩存需要拷貝的大小 */
             vertices,          /** 需要拷貝的數據:拷貝數據的地址 */
             GL_STATIC_DRAW);   /** 提示:告訴上下文緩存適合放到GPU內存中,因為數據很少被更改,可以幫助OpenGL ES優化內存 */

五、開始繪圖
  • 當GLKView需要重新繪制時就會調用代理方法glkView:drawInRect:

  • 在代理方法內,開始準備繪圖工作

    /** 準備繪制 */
    [_baseEffect prepareToDraw];
    
    /** 清理之前的繪圖 */
    glClear(GL_COLOR_BUFFER_BIT);
    
  • 啟用頂點數據、設置指針、開始繪圖

    /** ④啟用頂點數據 */
    glEnableVertexAttribArray(GLKVertexAttribPosition);
    
    /** ⑥設置指針:目的在于告訴OpenGL ES頂點數據在哪里以及解釋每個頂點保存的數據 */
    glVertexAttribPointer(GLKVertexAttribPosition, /** 頂點數據 */
                        3,                       /** 每個頂點包含3個數據 */
                        GL_FLOAT,                /** 頂點數據類型 */
                        GL_FALSE,                /** 固定點數據是否歸一化或直接轉固定值:不轉換,直接使用float類型數據,可以幫助OpenGL ES優化內存 */
                        sizeof(SceneVertex),     /** 步幅:從一個頂點到另一個需要跨過多少字節,取單個頂點大小 */
                        NULL);                   /** 告訴OpenGL ES可以從當前綁定的頂點緩存的開始位置訪問頂點數據 */
    
    glDrawArrays(GL_TRIANGLES,  /** 告訴GPU怎樣渲染緩存內的頂點數據:渲染三角形 */
               0,             /** 第一個需要渲染的頂點位置 */
               3);            /** 渲染的頂點數量 */
    
六、最后的清理工作

在dealloc方法中清理緩存

/** 如果有緩存的情況下 */
if (vertexBufferID != 0) {
        
    /** ⑦刪除緩沖區數據 */
    glDeleteBuffers(1, &vertexBufferID);
        
    /** 將標識符設置為0 */
    vertexBufferID = 0;
}
    
/** 將當前上下文設置nil */
[EAGLContext setCurrentContext:nil];

小結

  • 示例算是OpenGL ES中最簡單的,只是為了熟悉7個步驟而生,旨在熟悉基本的流程、函數及函數的各個參數。
  • 代碼會在后續統一上傳到github,其實基本上都貼出來了,當然有需要的可以自行下載。
最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 229,362評論 6 537
  • 序言:濱河連續發生了三起死亡事件,死亡現場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發現死者居然都...
    沈念sama閱讀 99,013評論 3 423
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事?!?“怎么了?”我有些...
    開封第一講書人閱讀 177,346評論 0 382
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 63,421評論 1 316
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 72,146評論 6 410
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發上,一...
    開封第一講書人閱讀 55,534評論 1 325
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 43,585評論 3 444
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 42,767評論 0 289
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當地人在樹林里發現了一具尸體,經...
    沈念sama閱讀 49,318評論 1 335
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 41,074評論 3 356
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發現自己被綠了。 大學時的朋友給我發了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 43,258評論 1 371
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 38,828評論 5 362
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質發生泄漏。R本人自食惡果不足惜,卻給世界環境...
    茶點故事閱讀 44,486評論 3 347
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 34,916評論 0 28
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 36,156評論 1 290
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 51,993評論 3 395
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 48,234評論 2 375

推薦閱讀更多精彩內容