Gamebryo遍曆子結點
for (NiUInt32 i = 0; i < pkNode->GetArrayCount(); ++i)
DoSomething(pkNode->GetAt(i);
for (NiUInt32 i = 0; i < pkNode->GetChildCount(); ++i)
DoSomething(pkNode->GetAt(i);
兩段代碼,天壤之別,前者正確,後者錯誤。由於GB在DetachNode時不刪除結點而只是置空,被刪除結點仍然佔據一個位置而被GetAt()訪問到,所以後者可能導致遍曆不到很多結點。
Gamebryo座標系
Gamebryo中貌似預設Y軸為上方向,X軸為右方向,Z軸為前方想;而矩陣相乘,貌似誰在前就採取誰的座標系。
Gamebryo和Unicode
Gamebryo同時提供顯示二位元組的Unicode字元(UTC-2)和Ascii字元的支援。
UnicodeCharacterSets例子裡展示了這種支援。程式可以從NFF檔案中擷取字型資訊產生NiFont對象。NFF檔案可以通過NiFontCreator建立。
儘管如此,Gamebryo裡的其他字串,比如檔案名稱,檔案路徑,對象名稱等,仍然是Ascii編碼。
而且,通過定義UNICODE或_UNIOCDE宏來定製Gamebryo是不被支援的。
Ni2DBuffer VS NiPixelData
Ni2DBuffer和NiPixelData的區別在於,Ni2DBuffer儲存於顯存中,而作為Gamebryo裡最主要的紋理資料(紋理檔案系統大多數都通過這種資料類型操作紋理),NiPixelData儲存於記憶體中。
使用CEGUI
使用CEGUI需要實現其Texture和Renderer兩個介面。其中Renderer要實現其addQuad()方法,而Texture要實現其loadFromFile()和loadFromMemory()方法。
CEGUI使用類成員函數作為回呼函數的辦法
類成員函數作為回呼函數一般會聲明該成員函數為static,之後採用類似全域函數一樣的調用方法來使用;
CEGUI則使用普通的類成員函數作為回呼函數。要求傳入該類的指標,以及成員函數的指標,之後做類似“類->函數()”這樣的調用。而與第一種方法不同的是,後者需要儲存一份類成員的指標,由於各個類不盡相同,所以採用一個模板對象用來進行儲存。在這裡,CEGUI使所有的模板對象首先繼承自一個純虛介面,之後管理器中儲存介面指標即可。這樣就達到了儲存不同模板對象的目的。非常取巧。
CEGUI渲染
CEGUI在每個視窗儲存一份待渲染的RenderCache對象,該對象裡維護了一份渲染所需的映像列表和文本列表,分別對應視窗的圖素和文字。
渲染時,由映像(image)上溯到映像集(imageset)進而得到實體的Texture並通過它調用addQuad完成渲染。
文字在渲染時被轉換成一張一張圖片,之後按照上述方法進行渲染。由於在解析文字時,CEGUI以分行符號'/n'作為換行標誌,所以可以看成一塊文本其實就是以'/n'為分隔的一排排小張圖片渲染而成的。由文本得到映像的方法見font類的getGlyphData()函數。這個過程涉及到從記憶體建立圖片,因此所有希望使用CEGUI字的程式,都需要實現其Texture的loadFromMemory()方法。
Gamebryo Alpha Blending
Gamebryo中帶有AlphaProperty的物體會在繪製時將自身像素點與螢幕上對應的像素點按照指定方式進行Alpha混合。
CEGUI Property
CEGUI以字串作為類屬性Property的索引,同時CEGUI通過Property的方式提供一種無差別訪問對象屬性(get/setProperty)的一種方法。例如,繼承自PropertySet的Window中包含有d_windowRender和d_lookNFeel成員,外部要訪問這兩個成員,一般不通過調用getWindowRender或者getlookNFeel這樣的方法;而是通過Window中同時包含的靜態成員d_windowRenderProperty和d_lookNFeelProperty,利用其(靜態)方法得到/更改對應這兩個成員的字串。這種方法的代價是,字串作為索引可能在效能方面有所下降。
to be continued...