VertexElement

ゲーム製作日誌 プログラム編 No.10-3 「GPUにヘルプを渡す」


 前回は画面に表示させる頂点をデータとして用意したので、今回はそれをGPUにも読んで解釈できるように、読み方(ヘルプ)を伝える処理を扱っていきます。


1,頂点の構成情報をまとめる意味とは


 前回、頂点一つ一つを構造体としてまとめてデータを作成しました。それを実際に三角形の描画を行うGPUに転送する必要があります。

vertexwhat
 しかし、転送するときは頂点一つ一つを区切ってわかるように書き込まれるのではなく、すべての頂点が連続してメモリに書き込まれていきます。また座標や色等のデータも続けて書き込まれるために、もはやデータが送られてきたGPUにはどこをどう読めばいいのかわからない状態になってしまいます。


vertexgive
 それでもGPUに、読み方の指南書を渡してあげれば話は別です。上図のような情報を与えておけば「0~12の位置に座標が書いてあって、12~28には色が書いてあるんだな」と解釈できるわけです。
 そのため、頂点の座標や色がどの部分に書き込まれているのかを事前にGPUに伝えることが必要となるのです。今後はその情報のことを「頂点の構成情報」と呼びますが、まずはその情報の作り方から見て行きましょう。



2,頂点の構成情報を作る

 頂点の構成情報を作るためには、まず頂点の構成要素(座標や色)一つ一つがどこに書き込まれていて、どんな役割を持つのかをVertexElementを作成して決めていきます。


VertexEle
 これがVertexElementのコンストラクタです。いま気にするべきは2,3,5行目です。
 
  • 2行目には、データが始まる番地を書く
    vertexgive
    例えば、座標はこの表でいうと「0」番目から始まっています。ですので座標用のVertexElementを作成するときは、2行目の引数を「0」に設定するわけです。色でしたら「12」になりますね

  • 3行目には、データの型を書く

    データの型は、C#でいうint,float,string等と同じものです。3つ要素(xyz)があるものなら「.Float3」と、4つ要素(rgba,xyzw)があるものなら「.Float4」と設定します。つまり座標なら3の方で、色なら4ですね。

  • 4行目には、使用目的を書く

    座標だったら「Position」とか、色だったら「Color」と書いておきます。まんまです。


 まとめると以下の様な定義をしてあげれば良いわけです。
//座標用
new VertexElement(0, 0, DeclarationType.Float3, DeclarationMethod.Default, DeclarationUsage.Position, 0)

//色用 new VertexElement(0, 12, DeclarationType.Float4, DeclarationMethod.Default, DeclarationUsage.Color, 0)


 次に、作った情報をすべて配列にまとめます。その際、配列の最後の要素には終わりの合図としてVertexElement.VertexDeclarationEndをいれておきます。作った配列は、前回作った頂点構造体の中に入れておくと扱いが楽です。
[StructLayout(LayoutKind.Sequential)]
public struct PositionColor
{
    public Vector3 Position;
    public Vector4 Color;
    public static readonly VertexElement[] Elements =
{
new VertexElement(0, 0, DeclarationType.Float3, DeclarationMethod.Default, DeclarationUsage.Position, 0), new VertexElement(0, 12, DeclarationType.Float4, DeclarationMethod.Default, DeclarationUsage.Color, 0), VertexElement.VertexDeclarationEnd
}; }


 ここまでで作ったVertexElement配列を使って、VertexDeclarationというものを作成します。これがGPUに与える指南書になります。VertexDeclarationは、Direct3D9デバイスを初期化してからでなければ作れません。
VertexDeclaration vertexDec = new VertexDeclaration(D3Device, PositionColor.Elements);


4,まとめ

 GPUには、頂点データを連続的に書き並べたバイト列のみが転送されてくるため各要素の位置や意味をそれだけでは解釈することができません。
 そこで、あらかじめ解釈するためのヘルプのようなものを渡しておくことで、GPUにも頂点の意味を理解することが可能になります。今回は、そのヘルプの作成の仕方を扱いました。
 次回は、解釈の仕方が分かったGPUに頂点データを送ってみようと思います。

P.S.
 今回が一番の山場だったので次回は今回苦労した分楽になる予定?
 

ゲーム製作日誌 プログラム編 No.10-1 「ポリゴン描画の全体の流れ」


 今回と次回では、Direct3Dを使って画面に三角形を描画するまでを扱っていきたいと思います。やることにしては意外とやることが多く、また後々の基本になることになるので何回かに分割して説明していきます。


1,ポリゴン描画の流れ

 「ポリゴン」とは、複数の点を結んだ線で囲まれた多角形のことを言います。

 例えば「三角ポリゴン」といえば、3つの頂点を結んだ三角形のことでして、今後はその三角形のみを扱っていきます。なぜ三角ポリゴンしか使わないかといえば、自分たちが使おうとしているDirect3Dが三角形の表示しか扱っていないからです。基本的にどんな図形でも三角形を何個も並べれば形作れるのでそういう仕様になっているのでしょうね。

polygon


 そんな三角形をDirect3D9で描画するには以下の手順を踏まなければいけません。

  1. 頂点自体のデータを用意する

    ・頂点1要素を表す構造体を定義する

    ・構造体の配列を作って全頂点のデータを作成する


  2. 頂点データが記録された位置を定義する

    ・頂点の各項目がどの位置に記録されているかをVertexElementで指定する

    ・指定したVertexElementでVertexDeclarationを作成する


  3. 頂点をグラフィックボードに送るための準備

    ・専用の格納場所VertexBufferを作成する

    ・頂点の配列をVertexBufferに書き込む


  4. 頂点を画面に表示するためのシェーダを用意する

    ・シェーダをコンパイルする

    ・シェーダの実体であるEffectを作成する


  5. 画面に描画する

    ・描画対象の空間(世界)の状況を設定する

    ・描画する


  6. 不必要なものを破棄する

    ・VertexBufferとVertexDeclarationとEffectを破棄する



 全体的に見ても、たかが三角形の描画でいろいろな準備が必要となっています。はっきりいってめんどうくさそうですね。
 でも拡張性つまり多種なシーンを作り出すためにここまで複雑な作りになっているわけですから、基本を大切にすべく次回からは一つ一つじっくり解説していきます。 
twitterはこちら
ニコ生放送します
ギャラリー
  • ウマモサク
  • ウマモサク
  • ウマモサク
  • 3/17 制作記録
  • 3/17 制作記録
  • C91告知
  • C91告知
  • C91告知
  • C91告知
アクセスカウンター
  • 今日:
  • 昨日:
  • 累計:

  • ライブドアブログ