|
電腦遊戲製作開發設計論壇 任何可以在PC上跑的遊戲都可以討論,主要以遊戲之製作開發為主軸,希望讓台灣的遊戲人有個討論、交流、教學、經驗傳承的園地
|
上一篇主題 :: 下一篇主題 |
發表人 |
內容 |
babu61509 散播福音的祭司
註冊時間: 2007-08-26 文章: 142
681.01 果凍幣
|
發表於: 2008-12-29, AM 11:39 星期一 文章主題: [C++/CLI][討論] DirectX 範例 with .NET |
|
|
將 DirectX範例CreateDevice 稍微修改了一下(其實還沒有改的很好...),把視窗跟事件都改用成呼叫.NET :
(重新改好了= = 把.NET部分和DX部分分開寫就沒問題了)
在整合的時候要注意一個問題,managed的類別可以使用unmanaged的類別,但是不能反過來用。
不過也沒什麼關係,只有主視窗類別是用mangaed,其他類別按照原本C++的方式寫就可以了。
代碼: |
#using <System.dll> // 引用 System.dll (專案的參照有設定的話可以不用加)
#using <System.Windows.Forms.dll> // 引用 System.Windows.Forms.dll (專案的參照有設定的話可以不用加)
#include <d3d9.h>
#pragma comment(lib, "d3d9.lib")
#pragma warning( disable : 4996 ) // disable deprecated warning
#pragma warning( default : 4996 )
using namespace System; // 偷懶不用打 System:: 用
using namespace System::Windows::Forms; // 偷懶不用打 System::Windows::Forms 用
// DirectX部分
public class Dxpart{
public:
IDirect3D9* g_pD3D; // Used to create the D3DDevice
IDirect3DDevice9* g_pd3dDevice; // Our rendering device
Dxpart(){
g_pD3D = NULL;
g_pd3dDevice = NULL;
}
~Dxpart(){
if( g_pd3dDevice != NULL )
g_pd3dDevice->Release();
if( g_pD3D != NULL )
g_pD3D->Release();
}
int CreateDevice(HWND hWnd){
if( SUCCEEDED( InitD3D( hWnd ) ) )
{
return 1;
}
return 0;
}
HRESULT InitD3D( HWND hWnd )
{
// Create the D3D object, which is needed to create the D3DDevice.
if( NULL == ( g_pD3D = Direct3DCreate9( D3D_SDK_VERSION ) ) )
return E_FAIL;
// Set up the structure used to create the D3DDevice. Most parameters are
// zeroed out. We set Windowed to TRUE, since we want to do D3D in a
// window, and then set the SwapEffect to "discard", which is the most
// efficient method of presenting the back buffer to the display. And
// we request a back buffer format that matches the current desktop display
// format.
D3DPRESENT_PARAMETERS d3dpp;
ZeroMemory( &d3dpp, sizeof( d3dpp ) );
d3dpp.Windowed = TRUE;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpp.BackBufferFormat = D3DFMT_UNKNOWN;
// Create the Direct3D device. Here we are using the default adapter (most
// systems only have one, unless they have multiple graphics hardware cards
// installed) and requesting the HAL (which is saying we want the hardware
// device rather than a software one). Software vertex processing is
// specified since we know it will work on all cards. On cards that support
// hardware vertex processing, though, we would see a big performance gain
// by specifying hardware vertex processing.
if( FAILED( g_pD3D->CreateDevice( D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hWnd,
D3DCREATE_SOFTWARE_VERTEXPROCESSING,
&d3dpp, &g_pd3dDevice ) ) )
{
return E_FAIL;
}
// Device state would normally be set here
return S_OK;
}
void Render(){
if( NULL == g_pd3dDevice )
return;
// Clear the backbuffer to a blue color
g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB( 0, 0, 255 ), 1.0f, 0 );
// Begin the scene
if( SUCCEEDED( g_pd3dDevice->BeginScene() ) )
{
// Rendering of scene objects can happen here
// End the scene
g_pd3dDevice->EndScene();
}
// Present the backbuffer contents to the display
g_pd3dDevice->Present( NULL, NULL, NULL, NULL );
}
};
// .NET 部分
namespace Clr01{
public ref class Form1: public System::Windows::Forms::Form
{
private:
Dxpart* dxins;
public:
Form1()
{
this->dxins = new Dxpart();
this->Text = "D3D Tutorial 01: CreateDevice";
this->dxins->CreateDevice((HWND)this->Handle.ToPointer());
this->Paint += gcnew PaintEventHandler(this, &Form1::Render);
}
private:
void Form1::Render(Object^ sender, PaintEventArgs^ e)
{
dxins->Render();
}
};
// 進入點
int main(void)
{
Application::Run( gcnew Form1 );
return 0;
}
}
|
_________________ 已經畢業了!!
babu61509 在 2009-4-8, AM 11:14 星期三 作了第 6 次修改 |
|
回頂端 |
|
|
babu61509 散播福音的祭司
註冊時間: 2007-08-26 文章: 142
681.01 果凍幣
|
發表於: 2008-12-29, PM 12:50 星期一 文章主題: |
|
|
DirectX 的 Vertices 範例 :
代碼: |
#using <System.dll> // 引用 System.dll (專案的參照有設定的話可以不用加)
#using <System.Windows.Forms.dll> // 引用 System.Windows.Forms.dll (專案的參照有設定的話可以不用加)
#include <d3d9.h>
#pragma comment(lib, "d3d9.lib")
#pragma warning( disable : 4996 ) // disable deprecated warning
#pragma warning( default : 4996 )
using namespace System; // 偷懶不用打 System:: 用
using namespace System::Windows::Forms; // 偷懶不用打 System::Windows::Forms 用
struct CUSTOMVERTEX
{
FLOAT x, y, z, rhw; // The transformed position for the vertex
DWORD color; // The vertex color
};
// Our custom FVF, which describes our custom vertex structure
#define D3DFVF_CUSTOMVERTEX (D3DFVF_XYZRHW|D3DFVF_DIFFUSE)
// DirectX部分
public class Dxpart{
public:
IDirect3D9* g_pD3D; // Used to create the D3DDevice
IDirect3DDevice9* g_pd3dDevice; // Our rendering device
LPDIRECT3DVERTEXBUFFER9 g_pVB;
Dxpart(){
g_pD3D = NULL;
g_pd3dDevice = NULL;
g_pVB = NULL;
}
~Dxpart(){
if( g_pVB != NULL )
g_pVB->Release();
if( g_pd3dDevice != NULL )
g_pd3dDevice->Release();
if( g_pD3D != NULL )
g_pD3D->Release();
}
int CreateDevice(HWND hWnd){
if( SUCCEEDED( InitD3D( hWnd ) ) )
{
if( SUCCEEDED( InitVB() ) )
{
return 2;
}
return 1;
}
return 0;
}
HRESULT InitVB()
{
// Initialize three Vertices for rendering a triangle
CUSTOMVERTEX Vertices[] =
{
{ 150.0f, 50.0f, 0.5f, 1.0f, 0xffff0000, }, // x, y, z, rhw, color
{ 250.0f, 250.0f, 0.5f, 1.0f, 0xff00ff00, },
{ 50.0f, 250.0f, 0.5f, 1.0f, 0xff00ffff, },
};
// Create the vertex buffer. Here we are allocating enough memory
// (from the default pool) to hold all our 3 custom Vertices. We also
// specify the FVF, so the vertex buffer knows what data it contains.
if( FAILED( g_pd3dDevice->CreateVertexBuffer( 3 * sizeof( CUSTOMVERTEX ),
0, D3DFVF_CUSTOMVERTEX,
D3DPOOL_DEFAULT, &g_pVB, NULL ) ) )
{
return E_FAIL;
}
// Now we fill the vertex buffer. To do this, we need to Lock() the VB to
// gain access to the Vertices. This mechanism is required becuase vertex
// buffers may be in device memory.
VOID* pVertices;
if( FAILED( g_pVB->Lock( 0, sizeof( Vertices ), ( void** )&pVertices, 0 ) ) )
return E_FAIL;
memcpy( pVertices, Vertices, sizeof( Vertices ) );
g_pVB->Unlock();
return S_OK;
}
HRESULT InitD3D( HWND hWnd )
{
// Create the D3D object, which is needed to create the D3DDevice.
if( NULL == ( g_pD3D = Direct3DCreate9( D3D_SDK_VERSION ) ) )
return E_FAIL;
// Set up the structure used to create the D3DDevice. Most parameters are
// zeroed out. We set Windowed to TRUE, since we want to do D3D in a
// window, and then set the SwapEffect to "discard", which is the most
// efficient method of presenting the back buffer to the display. And
// we request a back buffer format that matches the current desktop display
// format.
D3DPRESENT_PARAMETERS d3dpp;
ZeroMemory( &d3dpp, sizeof( d3dpp ) );
d3dpp.Windowed = TRUE;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpp.BackBufferFormat = D3DFMT_UNKNOWN;
// Create the Direct3D device. Here we are using the default adapter (most
// systems only have one, unless they have multiple graphics hardware cards
// installed) and requesting the HAL (which is saying we want the hardware
// device rather than a software one). Software vertex processing is
// specified since we know it will work on all cards. On cards that support
// hardware vertex processing, though, we would see a big performance gain
// by specifying hardware vertex processing.
if( FAILED( g_pD3D->CreateDevice( D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hWnd,
D3DCREATE_SOFTWARE_VERTEXPROCESSING,
&d3dpp, &g_pd3dDevice ) ) )
{
return E_FAIL;
}
// Device state would normally be set here
return S_OK;
}
void Render(){
// Clear the backbuffer to a blue color
g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB( 0, 0, 255 ), 1.0f, 0 );
// Begin the scene
if( SUCCEEDED( g_pd3dDevice->BeginScene() ) )
{
// Draw the triangles in the vertex buffer. This is broken into a few
// steps. We are passing the Vertices down a "stream", so first we need
// to specify the source of that stream, which is our vertex buffer. Then
// we need to let D3D know what vertex shader to use. Full, custom vertex
// shaders are an advanced topic, but in most cases the vertex shader is
// just the FVF, so that D3D knows what type of Vertices we are dealing
// with. Finally, we call DrawPrimitive() which does the actual rendering
// of our geometry (in this case, just one triangle).
g_pd3dDevice->SetStreamSource( 0, g_pVB, 0, sizeof( CUSTOMVERTEX ) );
g_pd3dDevice->SetFVF( D3DFVF_CUSTOMVERTEX );
g_pd3dDevice->DrawPrimitive( D3DPT_TRIANGLELIST, 0, 1 );
// End the scene
g_pd3dDevice->EndScene();
}
// Present the backbuffer contents to the display
g_pd3dDevice->Present( NULL, NULL, NULL, NULL );
}
};
// .NET 部分
namespace Clr01{
public ref class Form1: public System::Windows::Forms::Form
{
private:
Dxpart* dxins;
public:
Form1()
{
this->dxins = new Dxpart();
this->Text = "D3D Tutorial 02: Vertices";
this->dxins->CreateDevice((HWND)this->Handle.ToPointer());
this->Paint += gcnew PaintEventHandler(this, &Form1::Render);
}
private:
void Form1::Render(Object^ sender, PaintEventArgs^ e)
{
dxins->Render();
}
};
// 進入點
int main(void)
{
Application::Run( gcnew Form1 );
return 0;
}
}
|
_________________ 已經畢業了!! |
|
回頂端 |
|
|
babu61509 散播福音的祭司
註冊時間: 2007-08-26 文章: 142
681.01 果凍幣
|
發表於: 2008-12-29, PM 6:32 星期一 文章主題: |
|
|
DirectX 範例 Matrices :
(在這個範例中 我改用計時器來render圖,因為對於WndProc的東西還不到家,不知道怎麼判斷是否為idle狀態,其實用一個執行緒來跑也是可以的)
代碼: |
#using <System.dll> // 引用 System.dll (專案的參照有設定的話可以不用加)
#using <System.Windows.Forms.dll> // 引用 System.Windows.Forms.dll (專案的參照有設定的話可以不用加)
#include <d3dx9.h>
#pragma comment(lib, "d3d9.lib")
#pragma comment(lib, "d3dx9.lib")
#pragma comment(lib, "winmm.lib")
#pragma warning( disable : 4996 ) // disable deprecated warning
#pragma warning( default : 4996 )
using namespace System; // 偷懶不用打 System:: 用
using namespace System::Windows::Forms; // 偷懶不用打 System::Windows::Forms 用
struct CUSTOMVERTEX
{
FLOAT x, y, z, rhw; // The transformed position for the vertex
DWORD color; // The vertex color
};
// Our custom FVF, which describes our custom vertex structure
#define D3DFVF_CUSTOMVERTEX (D3DFVF_XYZ|D3DFVF_DIFFUSE)
// DirectX部分
public class Dxpart{
public:
IDirect3D9* g_pD3D; // Used to create the D3DDevice
IDirect3DDevice9* g_pd3dDevice; // Our rendering device
LPDIRECT3DVERTEXBUFFER9 g_pVB;
Dxpart(){
g_pD3D = NULL;
g_pd3dDevice = NULL;
g_pVB = NULL;
}
~Dxpart(){
if( g_pVB != NULL )
g_pVB->Release();
if( g_pd3dDevice != NULL )
g_pd3dDevice->Release();
if( g_pD3D != NULL )
g_pD3D->Release();
}
int CreateDevice(HWND hWnd){
if( SUCCEEDED( InitD3D( hWnd ) ) )
{
if( SUCCEEDED( InitGeometry() ) )
{
return 2;
}
return 1;
}
return 0;
}
HRESULT InitGeometry()
{
// Initialize three vertices for rendering a triangle
CUSTOMVERTEX g_Vertices[] =
{
{ -1.0f,-1.0f, 0.0f, 0xffff0000, },
{ 1.0f,-1.0f, 0.0f, 0xff0000ff, },
{ 0.0f, 1.0f, 0.0f, 0xffffffff, },
};
// Create the vertex buffer.
if( FAILED( g_pd3dDevice->CreateVertexBuffer( 3 * sizeof( CUSTOMVERTEX ),
0, D3DFVF_CUSTOMVERTEX,
D3DPOOL_DEFAULT, &g_pVB, NULL ) ) )
{
return E_FAIL;
}
// Fill the vertex buffer.
VOID* pVertices;
if( FAILED( g_pVB->Lock( 0, sizeof( g_Vertices ), ( void** )&pVertices, 0 ) ) )
return E_FAIL;
memcpy( pVertices, g_Vertices, sizeof( g_Vertices ) );
g_pVB->Unlock();
return S_OK;
}
HRESULT InitD3D( HWND hWnd )
{
// Create the D3D object.
if( NULL == ( g_pD3D = Direct3DCreate9( D3D_SDK_VERSION ) ) )
return E_FAIL;
// Set up the structure used to create the D3DDevice
D3DPRESENT_PARAMETERS d3dpp;
ZeroMemory( &d3dpp, sizeof( d3dpp ) );
d3dpp.Windowed = TRUE;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpp.BackBufferFormat = D3DFMT_UNKNOWN;
// Create the D3DDevice
if( FAILED( g_pD3D->CreateDevice( D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hWnd,
D3DCREATE_SOFTWARE_VERTEXPROCESSING,
&d3dpp, &g_pd3dDevice ) ) )
{
return E_FAIL;
}
// Turn off culling, so we see the front and back of the triangle
g_pd3dDevice->SetRenderState( D3DRS_CULLMODE, D3DCULL_NONE );
// Turn off D3D lighting, since we are providing our own vertex colors
g_pd3dDevice->SetRenderState( D3DRS_LIGHTING, FALSE );
return S_OK;
}
void Render(){
// Clear the backbuffer to a black color
g_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB( 0, 0, 0 ), 1.0f, 0 );
// Begin the scene
if( SUCCEEDED( g_pd3dDevice->BeginScene() ) )
{
// Setup the world, view, and projection Matrices
SetupMatrices();
// Render the vertex buffer contents
g_pd3dDevice->SetStreamSource( 0, g_pVB, 0, sizeof( CUSTOMVERTEX ) );
g_pd3dDevice->SetFVF( D3DFVF_CUSTOMVERTEX );
g_pd3dDevice->DrawPrimitive( D3DPT_TRIANGLESTRIP, 0, 1 );
// End the scene
g_pd3dDevice->EndScene();
}
// Present the backbuffer contents to the display
g_pd3dDevice->Present( NULL, NULL, NULL, NULL );
}
void SetupMatrices()
{
// For our world matrix, we will just rotate the object about the y-axis.
D3DXMATRIXA16 matWorld;
// Set up the rotation matrix to generate 1 full rotation (2*PI radians)
// every 1000 ms. To avoid the loss of precision inherent in very high
// floating point numbers, the system time is modulated by the rotation
// period before conversion to a radian angle.
UINT iTime = timeGetTime() % 1000;
FLOAT fAngle = iTime * ( 2.0f * D3DX_PI ) / 1000.0f;
D3DXMatrixRotationY( &matWorld, fAngle );
g_pd3dDevice->SetTransform( D3DTS_WORLD, &matWorld );
// Set up our view matrix. A view matrix can be defined given an eye point,
// a point to lookat, and a direction for which way is up. Here, we set the
// eye five units back along the z-axis and up three units, look at the
// origin, and define "up" to be in the y-direction.
D3DXVECTOR3 vEyePt( 0.0f, 3.0f,-5.0f );
D3DXVECTOR3 vLookatPt( 0.0f, 0.0f, 0.0f );
D3DXVECTOR3 vUpVec( 0.0f, 1.0f, 0.0f );
D3DXMATRIXA16 matView;
D3DXMatrixLookAtLH( &matView, &vEyePt, &vLookatPt, &vUpVec );
g_pd3dDevice->SetTransform( D3DTS_VIEW, &matView );
// For the projection matrix, we set up a perspective transform (which
// transforms geometry from 3D view space to 2D viewport space, with
// a perspective divide making objects smaller in the distance). To build
// a perpsective transform, we need the field of view (1/4 pi is common),
// the aspect ratio, and the near and far clipping planes (which define at
// what distances geometry should be no longer be rendered).
D3DXMATRIXA16 matProj;
D3DXMatrixPerspectiveFovLH( &matProj, D3DX_PI / 4, 1.0f, 1.0f, 100.0f );
g_pd3dDevice->SetTransform( D3DTS_PROJECTION, &matProj );
}
};
// .NET 部分
namespace Clr01{
public ref class Form1: public System::Windows::Forms::Form
{
private:
Dxpart* dxins;
System::Windows::Forms::Timer t1;
public:
Form1()
{
this->dxins = new Dxpart();
this->t1.Interval = 10;
t1.Tick += gcnew EventHandler(this, &Form1::Render);
t1.Start();
this->Text = "D3D Tutorial 03: Matrices";
this->dxins->CreateDevice((HWND)this->Handle.ToPointer());
}
private:
void Form1::Render(Object^ sender, EventArgs^ e)
{
dxins->Render();
}
};
// 進入點
int main(void)
{
Application::Run( gcnew Form1 );
return 0;
}
}
|
_________________ 已經畢業了!! |
|
回頂端 |
|
|
songfat 時常出沒的會員
註冊時間: 2008-01-25 文章: 34
192.68 果凍幣
|
發表於: 2009-4-7, AM 12:34 星期二 文章主題: |
|
|
由於小弟我之前一直使用win32 api的方式來產生控制項@@",在研究室做實驗時相當麻煩,想換成windows form的c++/cli + native dx,剛好看到有大大寫了個範例,感謝大大啊@@讓我省了好多時間。 |
|
回頂端 |
|
|
|
|
您 無法 在這個版面發表文章 您 無法 在這個版面回覆文章 您 無法 在這個版面編輯文章 您 無法 在這個版面刪除文章 您 無法 在這個版面進行投票 您 可以 在這個版面附加檔案 您 可以 在這個版面下載檔案
|
|