2012-02-10 13 views
2

私は今レンダリングしている方法には何の問題もありませんが、レンダリングを処理する方法としてはとても良いとは思いません。私はSDLを使用しています。クリーンなものレンダリング

それは私は2つの機能では、いくつかの抽象クラスに

class Renderable 

を持ってこれに沸きます。

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

私は1 std::vector

std::vector<Renderable*> _world; 

と2 std::queue

std::queue<Renderable*> _addQueue; 
std::queue<Renderable*> _delQueue; 
で別のクラス

class RenderManager 

を持っています

2つのキューには、次のティックで追加する必要があるレンダラブルと、削除する必要があるレンダラブルが格納されます。ワンショットですべてを行うことは問題をもたらし、私はそれについて考えるようになりました。それは意味があります(私がやったやり方)。

Renderableは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つの大きなループを一緒に持っているので心配です。ワンショットで試してみましたが、ループ中に_worldのサイズ変更で問題が発生し、大量の破壊が発生しました。しかし、私はそれが正しいと主張していない! :)

私はおそらくスレッドを含む何かを考えていたのですか?

編集:

ああ、あいまいなのは残念です。 「クリーナー」は効率的です。私のアプローチには「問題」もなく、より効率的な方法があると感じています。

+0

私はあなたのアプローチに問題はありません。パフォーマンス? – rasmus

+1

これは答えが非常に難しい質問です。なぜなら、主に「レンダリング」は非常に一般的な用語であり、それを処理する最良の方法は、特定の種類のレンダリングに大きく依存するからです。また、「最高」は主観的です。あなたはほとんどの演技者について話していますか?最も簡単なコードですか? –

+1

_delQueueを手動でループするのではなく、[std :: remove](http://www.cplusplus.com/reference/algorithm/remove/)を使用して調べることができます。 –

答えて

0

まず、壊れていないものを修正しないでください。パフォーマンスの問題が発生していますか?フレームごとに膨大な量の「レンダラブル」を追加したり削除したりしない限り、私はあなたの持つ大きな問題を見ることはできません。もちろん、全体的なアプリケーションの面では、それは不器用なデザインかもしれませんが、これがどのようなアプリケーションのためのものなのかを明記していないので、判断が不可能ではないにしても、難しいです。

しかし、SDLを使用しているため、ゲームを開発している可能性があります。個人的に私は常に各アクティブなオブジェクトのレンダリングメソッドを持つことによってゲームオブジェクトをレンダリングし、オブジェクトマネージャを使用して各オブジェクトへのポインタを1サイクルごとに循環させ、このレンダリングメソッドを呼び出します。ベクトルの中央からアイテムを絶えず削除すると、メモリの内部コピー(ベクトルは連続したメモリが保証される)のために減速を引き起こす可能性があるため、削除されるときに設定されるすべてのオブジェクトにフラグを設定し、マネージャは「ガベージコレクション」を実行し、このフラグを設定したすべてのオブジェクトを同時に削除して、実行する必要があるコピーの量を減らします。ガーベジコレクションが発生する前の段階で、マネージャはフラグが設定されたオブジェクトを無視し、そのたびにそのレンダリングメソッドを呼び出さず、消えたかのように処理します。実際にはゲームオブジェクトがあなたの 'レンダラブル'クラスから派生していれば、それは同じとみなすことができます。

ところで、要素にアクセスする前にキューサイズを照会する理由はありますか? size()が0の場合、forループはとにかく動作しません。

関連する問題