サンプル フレームワーク
サンプル フレームワーク
Microsoft® DirectX® 9.0 および Microsoft Direct3D® ソフトウェア開発キット (SDK) のグラフィックス サンプル フレームワークは、DirectX 8.0 のグラフィックス サンプル フレームワークから発展したものである。SDK のサンプルは、デフォルトで (SDK ルート)\Samples\C++ にインストールされる。ここで注目するフォルダは Common と Direct3D である。Common フォルダにはサンプル フレームワークが入っている。Direct3D フォルダには、これらのグラフィックス フレームワークに基づく Direct3D サンプルが入っている。
グラフィックス フレームワークは、5 つのソース モジュールから構成されている。
- d3dapp.cpp は、サンプルで使うアプリケーション インターフェイスを公開する。特に注目すべきなのは、クラス CD3DApplication である。
- d3dfile.cpp は、サンプルが .x ファイルをロードできるようにするための .x file サポートを提供する。特に注目すべきなのは、クラス CD3DMesh および CD3DFrame である。
- d3dfont.cpp は、統計的ビューなどを表示するための基本的なフォント出力サポートを提供する。特に注目すべきなのは、クラス CD3DFont である。
- d3dutil.cpp は、マテリアル、ライト、テクスチャのヘルパー関数のような、汎用的に役立つ 3 次元関数を提供する。
- dxutil.cpp は、メディア、レジストリ、タイマのヘルパー関数のような、汎用的に役立つ DirectX 関数を提供する。
対応するヘッダー ファイルは (SDK ルート)\Samples\C++\Common\Include フォルダにある。
各サンプルは、CD3DApplication のサブクラス (一般に CMyD3DApplication と名付けられる) と、次に示す一連のオーバーライド可能なメソッドを実装する。
// Overridable functions for the 3-D scene created by the application. virtual HRESULT ConfirmDevice(D3DCAPS9*,DWORD,D3DFORMAT) { return S_OK; } virtual HRESULT OneTimeSceneInit() { return S_OK; } virtual HRESULT InitDeviceObjects() { return S_OK; } virtual HRESULT RestoreDeviceObjects() { return S_OK; } virtual HRESULT FrameMove() { return S_OK; } virtual HRESULT Render() { return S_OK; } virtual HRESULT InvalidateDeviceObjects() { return S_OK; } virtual HRESULT DeleteDeviceObjects() { return S_OK; } virtual HRESULT FinalCleanup() { return S_OK; } /* The prototypes for these methods are contained in D3dapp.h in the CD3Dapplication class. The samples create a new application and override those methods that are needed by the application. */
派生クラスの例
この例では、オーバーライド可能なメソッドのサブセットを使う。クラス CMyD3DApplication は、次のメソッドを含んでいる。次に、この各メソッドについて説明する。
class CMyD3DApplication : public CD3DApplication { public: CMyD3DApplication(); protected: HRESULT ConfirmDevice( D3DCAPS9*, DWORD, D3DFORMAT ); HRESULT DeleteRestoreDeviceObjects(); HRESULT RestoreDeviceObjects(); HRESULT FrameMove(); HRESULT Render(); private: LPDIRECT3DVERTEXBUFFER9 m_pVB; // Vertex buffer to hold vertices
コントラクタ
コントラクタは、ウィンドウ タイトルの初期化、深度バッファリングの有効化、および頂点バッファの初期化を行う。
CMyD3DApplication::CMyD3DApplication()
{
m_strWindowTitle = _T("D3D Example"); // title bar string
m_bUseDepthBuffer = TRUE; // enable depth buffer
m_pVB = NULL; // initialize
}
ウィンドウ タイトルは、アプリケーションを起動するとタイトル バーまたはウィンドウ クラスに表示されるワイド文字列である。これはオプションである。
基底クラスは、深度バッファを有効にするためのメンバ変数を含む。このブール値のデフォルト値は FALSE で、深度バッファは無効になる。
ウィンドウ タイトルは、Unicode と ANSI 文字をサポートする TCHAR 文字列である。アプリケーションの起動時に、タイトル バーに表示される。この文字列は CMyD3DApplication の有効期間中、保持される。
デバイスの確認
プロトタイプは、次のようになる。
HRESULT ConfirmDevice(D3DCAPS *pCaps, DWORD dwBehavior,
D3DFORMAT fmtBackBuffer)
}
[in] pCaps - 確認対象デバイスの D3DCAPS 構造体へのポインタ。この構造体のメンバを調べて、指定されたデバイスにアプリケーションが必要とする能力があるかどうかを判断する。
[in] dwBehavior - IDirect3D9::CreateDevice の動作フラグに対応する 0 あるいは複数個のフラグ。次のフラグは指定されたデバイスの動作を示す。
D3DCREATE_PUREDEVICE
D3DCREATE_HARDWARE_VERTEXPROCESSING
D3DCREATE_SOFTWARE_VERTEXPROCESSING
D3DCREATE_MIXED_VERTEXPROCESSING
}
CD3DApplication は次の順序でデバイスの動作を確認する。
- ハードウェア頂点処理を行うピュア デバイス
- ハードウェア頂点処理を行うデバイス
- 混合頂点処理を行うデバイス
- ソフトウェア頂点処理を行うデバイス
ピュア デバイス動作については、ピュア デバイスに対するサポートが示されているデバイスのみを確認する。
ハードウェア頂点処理については、ハードウェアによるトランスフォームとライティングに対するサポートが示されているデバイスのみを確認する。
[in] fmtBackBuffer - デバイスのデフォルトのスワップ チェーンに関連付けられたバック バッファの指定されたフォーマット。
このメソッドをオーバーライドする際、指定されたデバイスの能力、動作およびバック バッファ フォーマットが許容できるものである場合は、アプリケーションでは S_OK を返す必要がある。それ以外の場合は、E_FAIL を返す必要がある。
DeleteDeviceObjects
DeleteDeviceObjects は、アプリケーションを終了するとき、またはデバイスを変更するときに呼び出される。頂点バッファなど、デバイスに依存するオブジェクトを削除するときにこのメソッドを使う。
HRESULT CVShader1::DeleteDeviceObjects() { m_pQuadVB->Release(); m_pQuadVB = NULL; return S_OK;
RestoreDeviceObjects
このメソッドは、アプリケーションでデバイス メモリ オブジェクトおよびデバイス ステートを復元する必要があるときに呼び出される。DirectX デバイスを作成またはサイズ変更したときには、これが必要になる。このメソッドは、オブジェクトの作成とレンダリング ステートの初期化に関するほとんどの作業を行う。
HRESULT CMyD3DApplication::RestoreDeviceObjects() { // Create the vertex buffer.Allocate enough memory (from the default pool) // to hold the custom vertices.Specify the flexible vertex format (FVF), // so the vertex buffer knows what data it contains. if( FAILED( m_pd3dDevice->CreateVertexBuffer( NUM_VERTS*sizeof(CUSTOMVERTEX), 0, D3DFVF_CUSTOMVERTEX, D3DPOOL_DEFAULT, &m_pVB ) ) ) { return E_FAIL; } // Fill the vertex buffer.First, lock the vertex buffer to get access to // the vertices.This mechanism is required because vertex buffers // may be in device memory.Then use memcpy to do a fast data copy. VOID* pVertices; if( FAILED( m_pVB->Lock( 0, sizeof(g_Vertices), (BYTE**)&pVertices, 0 ) ) ) return E_FAIL; memcpy( pVertices, g_Vertices, sizeof(g_Vertices) ); m_pVB->Unlock(); // Set the projection matrix.The size of the back buffer comes from the // base class. D3DXMATRIX matProj; FLOAT fAspect = m_d3dsdBackBuffer.Width / (FLOAT)m_d3dsdBackBuffer.Height; D3DXMatrixPerspectiveFovLH( &matProj, D3DX_PI/4, fAspect, 1.0f, 100.0f ); m_pd3dDevice->SetTransform( D3DTS_PROJECTION, &matProj ); // Set up the view matrix.A view matrix can be defined from an eye // point, a look-at point, and an up-direction vector.In this example, // the eye position is (0,1,-4) the look-at point is (0,0,0) and the // up vector is (0,1,0). D3DXMATRIX matView; D3DXMatrixLookAtLH( &matView, &D3DXVECTOR3( 0.0f, 1.0f,-4.0f ), &D3DXVECTOR3( 0.0f, 0.0f, 0.0f ), &D3DXVECTOR3( 0.0f, 1.0f, 0.0f ) ); m_pd3dDevice->SetTransform( D3DTS_VIEW, &matView ); // Set up default texture states. // Set up render states (this is only one example render state). m_pd3dDevice->SetRenderState( D3DRS_CULLMODE, D3DCULL_NONE ); return S_OK;
このメソッドは、頂点バッファを作成し、その中に頂点データをコピーする。ビュー行列および射影行列も作成する。これらの行列は、頂点バッファ内のオブジェクトに対するカメラの向きを定義する。この例では行っていないが、このメソッドでテクスチャ ステージ ステートを設定できる。変更される可能性の低いレンダリング ステートが設定される。これらによって、シーンのレンダリング方法が決まる。
FrameMove
このメソッドには、アニメーションのように 1 フレームごとに起こるアクションを入れる。この例では、ワールド トランスフォームに、y 軸を中心とした回転を加えている。
HRESULT CMyD3DApplication::FrameMove() { // For our world matrix, just rotate the object about the y-axis. D3DXMATRIX matWorld; D3DXMatrixRotationY( &matWorld, ::TimeGetTime()/150.0f ); m_pd3dDevice->SetTransform( D3DTS_WORLD, &matWorld ); return S_OK; }
Windows メソッド ::TimeGetTime() は、現在時刻を返す。これを 150 で割ると、オブジェクトを一定角度ずつ回転するときの 1 回分の回転角度が得られる。
Render
このメソッドは、出力をレンダリングするときに呼び出される。ビュー ポートをクリアし、シーンとステートの変更をレンダリングする。
HRESULT CMyD3DApplication::Render() { // Clear the viewport. m_pd3dDevice->Clear( 0L, NULL, D3DCLEAR_TARGET|D3DCLEAR_ZBUFFER, D3DCOLOR_XRGB(0,0,0), 1.0f, 0L ); // Begin the scene. if( SUCCEEDED( m_pd3dDevice->BeginScene() ) ) { m_pd3dDevice->SetStreamSource( 0, m_pVB, sizeof(CUSTOMVERTEX) ); m_pd3dDevice->SetFVF( D3DFVF_CUSTOMVERTEX ); m_pd3dDevice->DrawPrimitive( D3DPT_TRIANGLEFAN, 0, NUM_TRIS ); m_pd3dDevice->EndScene(); } return S_OK; }
Render メソッドは、まず、Clear を使用してビューポートをクリアする。次に、対になった BeginScene と EndScene の間に、SetStreamSource を使って、カスタム頂点タイプのサイズのストライドと共に頂点バッファ m_pVB を使うことをランタイムに伝える。次に、最も単純なタイプの柔軟な頂点フォーマット (FVF) シェーダを使うことをランタイムに伝える。最後に、DrawPrimitive を呼び出して四角形をレンダリングする。
その他の関数
DeleteDeviceObjects は、アプリケーションを終了するとき、またはデバイスを変更するときに呼び出される。このメソッドは、デバイスに依存するオブジェクトを削除するために使う。
ConfirmDevice は、デバイスが最小限の機能セットを備えているかどうかをチェックする。このメソッドは、デバイスの初期化中に呼び出される。
InvalidateDeviceObjects は、デバイスに依存するオブジェクトが削除される可能性があるときに呼び出される。通常、このメソッドには、頂点バッファなどのデバイスに依存するオブジェクトを追加する。
OneTimeSceneInit は、最初のアプリケーション起動時に実行する必要があるコード用である。
メーリング リスト
グラフィックスを扱っている他の開発者が見つかる場所の 1 つに、DirectX 開発者のメーリング リストがある。これは DirectX 開発者向けの技術的なディスカッションのフォーラムであり、グラフィックス、ネットワーク、および入力に関する領域をカバーしている。このメーリング リストのアーカイブは、DirectX Dev にある。他のメーリング リストと同様、これは技術サポートのフォーラムではない。しかし、DirectX に関する情報ソースとして有用である。