09.描画の高速化(頂点バッファオブジェクトの利用)
08.で作成したモデルビューアの描画処理は、頂点配列を用いた描画処理でした。
頂点配列を用いた描画処理では、glDrawArrays や glDrawElements の呼び出しのたびに、頂点データが、クライアントメモリからグラフィックスメモリへコピーされます。
頂点バッファオブジェクト ( Vertex Buffer Object : VBO ) を用いた描画処理では、頂点データを、事前にクライアントメモリからグラフィックスメモリにコピーしておき、glDrawArrays や glDrawElements の呼び出しのときには、コピー済みの頂点データを用いて描画します。
頂点バッファオブジェクト ( Vertex Buffer Object : VBO ) を用いた描画処理は、頂点配列を用いた描画処理よりも高速に描画されます。
解説
頂点バッファオブジェクト ( Vertex Buffer Object : VBO ) を用いた描画を行うためには、構築処理と、描画処理と、破棄処理を作成する必要があります。
構築処理では、頂点バッファオブジェクトの作成、頂点データのクライアントメモリからグラフィックスメモリへのコピー、を行います。
- glGenBuffer関数で、頂点バッファオブジェクトを作成します。
- glBindBuffer関数で、作成した頂点バッファオブジェクトをバインドします。
- glBufferData関数で、データをクライアントメモリからグラフィックスメモリにコピーします。
描画処理では、頂点バッファオブジェクトをバインドし、バインドした頂点バッファオブジェクトを用いて描画を行います。
- glBindBuffer関数で、作成した頂点バッファをバインドします。
- glVertexPointer関数は、頂点バッファオブジェクトを使用するときには、配列データのアドレスを渡す代わりに、データのオフセット量を渡します。
- glDrawArrays関数を用いて、描画します。
破棄処理では、頂点バッファオブジェクトの削除を行います。
- glDeleteBuffer関数で、作成した頂点バッファオブジェクトを削除します。
プロジェクトを開く
08.で作成したモデルビューワプロジェクトを開きます。
モデルデータ構造のVBO対応
モデルクラスについて、
頂点配列に関するメンバー変数、メンバー関数の宣言を削除します。
VBOに関するメンバー変数を追加します。
VBOに関する関数の宣言を追加します。
コンストラクタにVBOに関するメンバー変数の初期化処理を追加します。
Model.hのCModelのクラス宣言の内容を以下のようにします。
VBOの作成と破棄の定義
頂点配列に関する関数の定義を削除します。
VBOに関する2つの関数(作成と破棄)の定義を追加します。
OpenGL拡張機能を使用するためのヘッダーファイルのインクルードを追加します。
Model.cppの内容を以下のようにします。
VBOの作成の関数の呼び出し
ファイルからのモデルデータの読み込み処理の後に、VBO作成が実施されるようにします。
ModelViewer.cpp の WndProc関数の、WM_COMMAND ウィンドウメッセージ処理の、ID_FILE_OPEN コマンド処理の
glrenderer.m_model.DestroyArray();
glrenderer.m_model.MakeArray();
をコメントアウトし、
glrenderer.m_model.MakeVBO();
を追加します。
ピック描画のVBO対応
ピック描画の色配列についても、グラフィックスメモリにコピーするようにします。
モデルビューアレンダラクラスについて、
色配列に関するメンバー変数(m_abt4VertexIdColor、m_abt4TriangleIdColor)を削除します。
色配列に関するメンバー関数(MakeArray、DestroyArray)の宣言を削除します。
VBOに関するメンバー変数(m_auiVboID)を追加します。
VBOに関する関数(MakeVBO、DestroyVBO、GetVertexIdColorVboID、GetTriangleIdColorVboID)の宣言を追加します。
OpenGL初期化処理関数(InitializeOpenGL)、OpenGL終了処理関数(UninitializeOpenGL)の宣言を追加します。
ModelViewerRenderer.hのCModelViewerRendererのクラス宣言の内容を以下のようにします。
ピック描画用のVBOの作成と破棄の定義
ModelViewerRenderer.cppの、
色配列に関する関数の呼び出しを削除します。
色配列に関する関数の宣言を削除します。
コンストラクタに、VBOに関するメンバー変数の初期化処理を追加します。
VBOに関する2つの関数(作成と破棄)の定義を追加します。
ピック描画用のVBOの作成と破棄の関数の呼び出し
モデルビューアーレンダラクラスに、OpenGL初期化処理関数、OpenGL終了処理関数をオーバーライドします。オーバーライドしたのOpenGL初期化処理関数、OpenGL終了処理関数に、VBOの作成と破棄の関数の呼び出しを追加します。
OpenGLRendererBase.h のベースOpenGLレンダラクラスの
メンバ関数
InitializeOpenGL
をprotected関数、さらにvirtual関数とします。
OpenGLRendererPick.h のピックOpenGLレンダラクラスの
メンバ関数
UninitializeOpenGL
をvirtual関数とします。
描画処理のVBO対応
描画処理をVBOに対応した処理に変更します。
ModelViewerRenderer.cpp の CModelViewerRenderer:RenderModel関数の内容を以下のようにします。
ビルドし、エラー、警告がないことを確認します。
実行
実行し、08.で作成したモデルビューワと、描画速度を比較します。
描画速度はステータスバーに表示されます。
- fps
- frame per second : 1秒間に描画できる回数を表します。数値が大きいほど、描画速度は速いことになります。
- spf
- second per frame : 1回の描画に要する時間を表します。数値が小さいほど、描画速度は速いことになります。
09.で作成したモデルビューワの描画速度:500[fps]前後(数値はPCの性能に依存します)
08.で作成したモデルビューワの描画速度:333[fps]前後(数値はPCの性能に依存します)
ダウンロード
ソースファイルダウンロード ( ModelViewerOpenGLWinAPI2015_09_vbo.zip )
関連ページ
前項目:08.描画の高速化(頂点配列)
次項目:10.光源の効果の利用