2012-02-10 66 views
2

我現在的渲染方式並沒有什麼問題,但我覺得這不是處理渲染的好方法。我正在使用SDL。一個乾淨的方式來渲染東西

它歸結到這一點,我有一些抽象類

class Renderable 

有兩個功能。

virtual void update() = 0; 
virtual void doRender(SDL_Surface* surface) = 0; 

我有另一類

class RenderManager 

隨着1 std::vector

std::vector<Renderable*> _world; 

和2 std::queue

std::queue<Renderable*> _addQueue; 
std::queue<Renderable*> _delQueue; 

這兩個隊列包含需要添加到下一個滴答的可渲染對象以及需要刪除的可渲染對象。盡一切辦法給了我一些問題,現在我想到了這一點,這是有道理的(至少我是這麼做的)。

可執行文件可以靜態添加和從RenderManager中刪除自己。

這裏或多或少的處理一切的函數。

void renderAll() { 
    std::vector<Renderable*>::iterator begin, end; 
    begin = _world.begin(); 
    end = _world.end(); 

    for (;begin != end; ++begin) { 
     (*begin)->update(); 
     (*begin)->doRender(_mainWindow); // _mainWindow is the screen of course 
    } 

    begin = world.begin(); 

    if (_delQueue.size() > 0) { 
     for (unsigned int i = 0; i < _delQueue.size(); i++) { 
      std::vector<Renderable*>::iterator del; 
      del = std::find(begin, end, _delQueue.front()); 

      if (del != end) { 
       delete *del; 
       _world.erase(del); 
      } 
      _delQueue.pop(); 
     } 
    } 

    if (_addQueue.size() > 0) { 
     for (unsigned int i = 0; i < _addQueue.size(); i++) { 
      Renderable* front = _addQueue.front(); 

      // _placement is a property of Renderable calculated by RenderManager 
      // where they can choose the level they want to be rendered on. 
      _world.insert(begin + front->_placement, front); 
      _addQueue.pop(); 
     } 
    } 
} 

我對C++很陌生,但我想我至少在平均規模上知道我的方式。我甚至更新SDL,但它看起來非常簡單易學。我很擔心,因爲我有3個大環一起。我嘗試了一次,但我在循環過程中遇到了問題,導致了大量的破壞。但我並不是說我做對了! :)

我在想也許是涉及到線程的東西?

編輯:

啊,對不起,含糊不清。 「更清潔」我的意思是更有效。我的方法也沒有「問題」,我只是覺得有一個更有效的方法。

+0

我不明白你的做法。性能? – rasmus 2012-02-10 00:42:59

+1

這是一個很難回答的問題,主要是因爲「渲染」是一個非常普遍的術語,處理它的最佳方式將在很大程度上取決於特定的渲染類型。另外,「最好」是主觀的:你說的是性能最高的?最簡單的代碼? – 2012-02-10 00:44:07

+1

您可以使用[std :: remove](http://www.cplusplus.com/reference/algorithm/remove/)來代替手動循環_delQueue。 – 2012-02-17 12:34:31

回答

0

首先,我會說不要修理沒有損壞的東西。您是否遇到性能問題?除非你在每一幀中大量添加和刪除「可呈現的東西」,否則我看不到你有什麼大問題。當然,就整體應用而言,它可能是一個笨拙的設計,但是你沒有說明這是一種什麼樣的應用,所以很難判斷,如果不是不可能的話。

但是,我可以猜測並說,因爲您使用的是SDL,所以您有機會開發遊戲。就我個人而言,我總是通過爲每個活動對象提供渲染方法來渲染遊戲對象,並使用對象管理器爲每個對象循環指向每個對象的指針並調用此渲染方法。因爲不斷移除矢量中間的某個項目可能會導致內存複製(向量保證連續內存)導致速度變慢,所以您可以在每個要刪除的對象中設置一個標誌,並定期將對象管理器執行「垃圾收集」,同時刪除所有設置了該標誌的對象,因此減少了需要完成的複製量。在垃圾收集發生之前,管理者只是忽略標記的對象,不會每次打勾都調用它的渲染方法 - 就好像它已經消失了一樣。實際上,這與您在隊列系統中所擁有的不同,事實上,如果遊戲對象是從您的「可渲染」類派生的,則它可能被視爲相同。

順便問一下,有什麼理由在訪問它們的元素之前查詢隊列大小?如果size()是0,則for循環將無法操作。

相關問題