2012-02-18 47 views
0

我正在用C++和DirectX 9編寫圖形引擎,我打算在後期階段在遊戲中使用它。前一段時間,我寫了一個功能齊全的2D引擎和OpenGL中一個基本的3D引擎,但現在我決定在DirectX 9,開始一個新項目DirectX 9中面向對象渲染框架的一般方法?

在我以前的引擎,我做了Entitystd::vector可能包含Tank,Weapon,Particle等子類型。然後,我會通過多態性做類似'for each Entity in std::vector do Entity->Draw()'的操作。繪圖功能將做glVertex3f(...)

現在我的問題是:如何在DirectX 9中實現類似的面向對象的框架?我正在考慮爲每個類型(Tank,Weapon)保留一個頂點陣列,該頂點從文件加載,將所有對象的所有頂點複製到相同的頂點緩衝區,然後爲每個頂點子集調用DrawPrimitive。這是做這個/一般方式的正確方法嗎?還是應該爲場景中的不同對象創建不同的頂點緩衝區?一些僞代碼會很好地說明正確的實現。

回答

0

這取決於你的目標是什麼,如果你想要效率,你可以用一個關聯句柄在std::unordered_map中加載你的網格物體,紋理相同,那麼這將允許你實例化相同對象類型的向量。

如果你想保持它更簡單,你可以創建一個容器來存儲所有的實體和所需的渲染信息(類似於你的'舊'引擎),儘管可能會希望使用一個剔除數據結構作爲以及(像Octree):

class RenderInfo 
{ 
    IDirect3DVertexBuffer9* pVertex; 
    IDirect3DIndexBuffer9* pIndex; 
    //... 
}; 

class EntityController 
{ 
    std::vector<std::pair<Entity,std::shared_ptr<RenderInfo>>> Entities; 
    void Draw() 
    { 
     foreach e in Entities 
      e.first.Draw(e.second); 
    } 
} 

這裏std::shared_ptr<RenderInfo>將是唯一的一個VB/IB對,以避免不必要的重複

+0

比方說,我會實現你的簡單的方法解決問題(然後可能實例化的稍後階段的相同對象)。你將在實體的Draw函數中做什麼?將頂點複製到VB中,調用DrawPrimitives()併爲實體向量中的每個實體清空VB? – red 2012-02-18 23:32:08

+0

您應該爲每個不同的網格保留一個vb和一個ib。在渲染前簡單地激活正確的。不要改變它們的內容。圖形卡針對靜態vb/ib進行了優化。通過更改vb/ib的內容,可以在GPU和CPU之間生成大量流量。 – rasmus 2012-02-19 01:16:09