cocos2d-x 學習: CCTextureAtlas 簡介

CCTextureAtlas是一個大圖繪製管理類。說白了,它本身保存一張大圖的紋理和一個記錄畫大圖某一區域的信息結構體的數組,通過操縱這個數組你可以繪製出一批四邊形,這些四邊形的紋理和繪製的座標都存放在你操作的數組之中的(又把廢話重複了一遍。)

由於CCTextureAtlas使用了opengl的VBO(頂點數組對象),所以用CCTextureAtlas所作的繪製在效率上比較高。

下面介紹一下該類的成員:

1.GLuint  m_pBuffersVBO[2],這是兩個opengl VBO的句柄。一個用來做頂點數組句柄,一個用來做頂點索引數組句柄。

2.GLushort  *m_pIndices,這是一個頂點索引數組的類本地備份。

3 ccV3F_C4B_T2F_Quad *  m_pQuads ,這是一個頂點數組的類本地備份。這應該是CCTextureAtlas類實現的核心,所有該類的功能都再圍繞該結構體在做操縱。

4. CCTexture2D  *m_pTexture,這是保存大圖的紋理管理類。

5  int  m_uCapacity,四邊形的容量。

6 int  m_uTotalQuads,實際上使用的四邊形的數目。

7 m_bDirty ,當前opengl VBO中的數據是否是髒數據。爲什麼會存在這麼一個類呢?實際上因爲CCTextureAtlas容許你動態改變它管理的四邊形數據,一旦你改變了該數據就需要一個標誌位告訴該類在繪製四邊形的時候把VBO中得數據更新掉。該成員就是起這個作用。

該類的主要功能和實現介紹

初始化。

         該類的初始化需要提供的參數,除了需要加載的圖片外還需要提供一個容量值。

初始化的流程:

 1.如果提供一個文件名作爲紋理參數,則調用紋理緩衝的加載該圖片,如果提供紋理則接着到下一步。

2 根據提供的容量nCapaciity,malloc分配nCapaciity大小的ccV3F_C4B_T2F_Quad 數組,和6倍nCapaciity的容量的GLuint數組。

3 生成VBO。

4 初始化頂點索引數組。該操作在CCTextureAtlas::initIndices()中完成,特別注意索引初始化的順序。

            代碼如下:

 

  1. /*這段代碼取自CCTextureAtlas::initIndices()  
  1. *四邊形存儲形式如圖 : 0 — 2  opengl中繪圖逆時針算正向繪製,所以正確順序是0-1-2,3-2-1。  
  1. *<span style="white-space:pre">     </span>       |  / |  
  1. */<span style="white-space:pre">        </span>       1 — 3  
  1. for( unsigned int i=0; i < m_uCapacity; i++)  
  2.     {  
  3. #if CC_TEXTURE_ATLAS_USE_TRIANGLE_STRIP  
  4.         m_pIndices[i*6+0] = i*4+0;  
  5.         m_pIndices[i*6+1] = i*4+0;  
  6.         m_pIndices[i*6+2] = i*4+2;        
  7.         m_pIndices[i*6+3] = i*4+1;  
  8.         m_pIndices[i*6+4] = i*4+3;  
  9.         m_pIndices[i*6+5] = i*4+3;  
  10. #else  
  11.         m_pIndices[i*6+0] = (GLushort)(i*4+0);  
  12.         m_pIndices[i*6+1] = (GLushort)(i*4+1);  
  13.         m_pIndices[i*6+2] = (GLushort)(i*4+2);  
  14.   
  15.         // inverted index. issue #179  
  16.         m_pIndices[i*6+3] = (GLushort)(i*4+3);  
  17.         m_pIndices[i*6+4] = (GLushort)(i*4+2);  
  18.         m_pIndices[i*6+5] = (GLushort)(i*4+1);        
  19.         //      m_pIndices[i*6+3] = i*4+2;  
  20.         //      m_pIndices[i*6+4] = i*4+3;  
  21.         //      m_pIndices[i*6+5] = i*4+1;    
  22. #endif    
  23. }  
通過上面的代碼我們很容易看出四邊形是通過繪製兩個三角形繪製出來的。

在這函數的結尾,將頂點數組和頂點索引數組導入到opengl中,下面這段代碼就不解釋了,如果你實在想知道,建議你看看opengl方面的書籍。

  1. #if CC_USES_VBO  
  2.     glBindBuffer(GL_ARRAY_BUFFER, m_pBuffersVBO[0]);  
  3.     glBufferData(GL_ARRAY_BUFFER, sizeof(m_pQuads[0]) * m_uCapacity, m_pQuads, GL_DYNAMIC_DRAW);  
  4.     glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, m_pBuffersVBO[1]);  
  5.     glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(m_pIndices[0]) * m_uCapacity * 6, m_pIndices, GL_STATIC_DRAW);  
  6.     glBindBuffer(GL_ARRAY_BUFFER, 0);  
  7.     glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);  
  8. #endif // CC_USES_VBO  


CCTextureAtlas繪製功能的實現是在這個函數中CCTextureAtlas::drawNumberOfQuads,裏面大部分都是opengl的命令,比較令我感興趣的是這句話:

  1. if (m_bDirty)  
  2.     {  
  3.         glBufferSubData(GL_ARRAY_BUFFER, sizeof(m_pQuads[0]) * start, sizeof(m_pQuads[0]) * n, &m_pQuads[start]);  
  4.         m_bDirty = false;  
  5.     }  
這句話的作用就是之前說的。如果該類所管理的四邊形信息結構體數組被外界改了,需要置位m_bDirty爲true,這樣在畫的時候,就把相關的數據更新到opengl中。

CCTextureAtlas提供了增刪改查m_pQuads的函數。值得一提的是CCTextureAtlas::resizeCapacity這個函數。

resizeCapacity會根據重置數組大小重新生成數組,然後它要重新生成那兩個VBO(你知道,不知道看前面吧),然後初始化索引。

好了,打多了眼疼。就到這裏吧。

本文轉載於zhidejll的專欄,地址http://blog.csdn.net/liuzhidejll/article/details/7298954

發佈了21 篇原創文章 · 獲贊 11 · 訪問量 13萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章