C# と VB.NET の質問掲示板

ASP.NET、C++/CLI、Java 何でもどうぞ

C# と VB.NET の入門サイト

Re[10]: C++ DirectX xファイルの読み込み


(過去ログ 60 を表示中)

[トピック内 13 記事 (1 - 13 表示)]  << 0 >>

■34187 / inTopicNo.1)  C++ DirectX xファイルの読み込み
  
□投稿者/ キャットメ (1回)-(2009/03/22(Sun) 14:48:01)

分類:[C/C++] 

初めて質問させていただきます。使用言語(C++) ソフト(Visual C++ 2008)

「15歳からはじめるDirectX9 3Dゲームプログラミング教室(C++編)」という本を使っています。
そこで、xファイルを読み込み表示させるため、以下のようにmy3dlib.h my3Dlib.cpp main.cppを書き、いくつものエラーを乗り越えたのですが、エラーが出なくなったと思ったら今度はウィンドウが一瞬表示されてすぐに消えてしまう、という事態になってしまいました。一応すべては見直したのですが、何が間違っているのかわかりません。

何かお気づきの点がありましたら、どんなことでもいいので教えてください。よろしくお願い致します。



---------------------------------------------my3dlib.h--------------------------------
#include <Windows.h>
#include <mmsystem.h>
#include <d3dx9.h>
#include <tchar.h>




struct Model
{
	LPD3DXMESH				pmesh;
	D3DMATERIAL9*			pmaterials;
	LPDIRECT3DTEXTURE9*		ptextures;
	DWORD					nummaterials;
	BOOL used;
};


//グローバル変数
extern LPDIRECT3D9			g_pD3D;
extern LPDIRECT3DDEVICE9	g_pd3dDevice;
extern float				g_aspect;
extern Model				g_models[];

//関数プロトタイプ宣言
HRESULT InitD3DWindow(LPCTSTR wintitle, int w,int h);
int LoadModel(LPCTSTR filename);
void RenderModel(int idx);


--------------------------------------------my3Dlib.cpp--------------------------------------------
#include "my3dlib.h"

LPDIRECT3D9		    g_pD3D = NULL;
LPDIRECT3DDEVICE9	g_pd3dDevice = NULL;
float				g_aspect = 1.0f;
const int			MAXMODEL = 64; //64のxファイルを配列
Model				g_models[MAXMODEL];



//リソースの解放
void CleanupD3D(){

	for(int i=0; i<MAXMODEL; i=i+1)
	{
		if(g_models[i].used==TRUE)
		{
			if(g_models[i].pmaterials!=NULL)
			{
				delete[] g_models[i].pmaterials;
			}
			if(g_models[i].ptextures!=NULL)
			{
				for(DWORD j=0; j<g_models[i].nummaterials; j=j+1)
				{
					g_models[i].ptextures[j]->Release();
				}
				delete[] g_models[i].ptextures;
			}
			if(g_models[i].pmesh!=NULL)
			{
				g_models[i].pmesh->Release();
			}
		}
	}

	if(g_pd3dDevice!=NULL) g_pd3dDevice->Release();
	if(g_pD3D!=NULL) g_pD3D->Release();
}

//ウィンドウプロシージャー
LRESULT WINAPI MsgProc(HWND hWnd, UINT msg,WPARAM wParam,LPARAM lParam)
{
	switch(msg)
	{
	case WM_DESTROY:
		CleanupD3D();
		PostQuitMessage(0);
		return 0;
	}

	return DefWindowProc(hWnd,msg,wParam,lParam);
}





HRESULT InitD3DWindow(LPCTSTR wintitle,int w,int h)
{

	ZeroMemory(&g_models,sizeof(Model)*MAXMODEL);
	//ウィンドウクラス作成
	WNDCLASSEX wc = {sizeof(WNDCLASSEX),CS_CLASSDC,MsgProc,0L,0L,GetModuleHandle(NULL),NULL,NULL,NULL,NULL,_T("D3D Window Class"),NULL};
	RegisterClassEx(&wc);
	//ウィンドウ作成
	HWND hWnd = CreateWindow( _T("D3D Window Class"),wintitle,WS_OVERLAPPED | WS_SYSMENU,100,100,w,h,NULL,NULL,wc.hInstance,NULL);

	//ビューポートアスペクトの記録
	g_aspect = (float)w / (float)h;

	//D3D9の作成
	if(NULL==(g_pD3D = Direct3DCreate9( D3D_SDK_VERSION)))
		return E_FAIL;

	//D3Dデバイスの作成
	D3DPRESENT_PARAMETERS d3dpp;
	ZeroMemory(&d3dpp,sizeof(d3dpp));
	d3dpp.Windowed=TRUE;
	d3dpp.SwapEffect= D3DSWAPEFFECT_DISCARD;
	d3dpp.BackBufferFormat=D3DFMT_UNKNOWN;
	d3dpp.EnableAutoDepthStencil=TRUE;
	d3dpp.AutoDepthStencilFormat=D3DFMT_D16;

	if(FAILED(g_pD3D->CreateDevice(D3DADAPTER_DEFAULT,D3DDEVTYPE_HAL,hWnd,D3DCREATE_HARDWARE_VERTEXPROCESSING,&d3dpp,&g_pd3dDevice)))
	{
			if(FAILED(g_pD3D->CreateDevice(D3DADAPTER_DEFAULT,D3DDEVTYPE_HAL,hWnd,D3DCREATE_SOFTWARE_VERTEXPROCESSING,&d3dpp,&g_pd3dDevice)))
			{
				return E_FAIL;
			}
	}

	//Zバッファをオン
	g_pd3dDevice->SetRenderState(D3DRS_ZENABLE,TRUE);
	ShowWindow(hWnd,SW_SHOWDEFAULT);

	return S_OK;
}


//Xファイルを読み込む関数
int LoadModel(LPCTSTR filename)
{
	int idx;
	for(idx=0; idx<MAXMODEL; idx=idx+1)
	{
		if(g_models[idx].used==FALSE) break;
	}
	if(idx>=MAXMODEL) return -1;

	LPD3DXBUFFER pD3DXMtrlBuffer;

	if(FAILED(D3DXLoadMeshFromX(filename,D3DXMESH_SYSTEMMEM,g_pd3dDevice,NULL,&pD3DXMtrlBuffer,NULL,&g_models[idx].nummaterials,&g_models[idx].pmesh)))
	{
		MessageBox(NULL,_T("Xファイルが見つかりません"),_T("3D lib"),MB_OK);
		return -1;
	}

	//マテリアルとテクスチャ記録用配列確保
	D3DXMATERIAL* d3dxMaterials=
		(D3DXMATERIAL*)pD3DXMtrlBuffer->GetBufferPointer();
	int num=g_models[idx].nummaterials;
	if(g_models[idx].pmaterials==NULL) return -1;
	g_models[idx].ptextures=new LPDIRECT3DTEXTURE9[num];
	if(g_models[idx].ptextures==NULL) return -1;

	for(int i=0; i<num; i=i+1)
	{
		//マテリアルのコピー
		g_models[idx].pmaterials[i]=d3dxMaterials[i].MatD3D;
		//アンビエント色の設定
		g_models[idx].pmaterials[i].Ambient=
			g_models[idx].pmaterials[i].Diffuse;
		//テクスチャの読み込み
		g_models[idx].ptextures[i] = NULL;
		if(d3dxMaterials[i].pTextureFilename !=NULL&&
			lstrlenA(d3dxMaterials[i].pTextureFilename)>0)
		{
			if(FAILED(D3DXCreateTextureFromFileA(g_pd3dDevice,d3dxMaterials[i].pTextureFilename,&g_models[idx].ptextures[i])))
			{
				MessageBox(NULL,_T("テクスチャが見つかりません"),_T("3D Lib"),MB_OK);
				return -1;
			}
		}
	}

	pD3DXMtrlBuffer->Release();
	g_models[idx].used=TRUE;
	return idx;
}

void RenderModel(int idx)
{
	if(g_models[idx].used==FALSE) return;

	for(DWORD i=0; i<g_models[idx].nummaterials; i=i+1)
	{
		g_pd3dDevice->SetMaterial(&g_models[idx].pmaterials[i]);
		g_pd3dDevice->SetTexture(0,g_models[idx].ptextures[i]);
		g_models[idx].pmesh->DrawSubset(i);
	}
}


------------------------------------------main.cpp---------------------------------------------------
#include "my3dlib.h"

int modelindex;

void Render()
{
	g_pd3dDevice->Clear(0,NULL,D3DCLEAR_TARGET|D3DCLEAR_ZBUFFER,D3DCOLOR_XRGB(0,0,255),1.0f,0);

	if(SUCCEEDED(g_pd3dDevice->BeginScene()))
	{
		RenderModel(modelindex);
		g_pd3dDevice->EndScene();
	}

	g_pd3dDevice->Present(NULL,NULL,NULL,NULL);
}

//WinMain関数
INT WINAPI WinMain( HINSTANCE hInst,HINSTANCE,LPSTR,INT)
{
	if(SUCCEEDED(InitD3DWindow(_T("My3DLibTest"),640,480)))
	{
		modelindex= LoadModel(_T("catsenkan.x"));
		if(modelindex==-1) return 0;

		
		//メッセージループ
		MSG msg = {0};
		while(msg.message!=WM_QUIT)
		{
			if(PeekMessage(&msg,NULL,0U,0U,PM_REMOVE))
			{
				TranslateMessage(&msg);
				DispatchMessage(&msg);
			}

			else
			{
				Render();
			}
		}
	}
	

	UnregisterClass(_T("D3D Window Class"),GetModuleHandle(NULL));
	return 0;
}

引用返信 編集キー/
■34188 / inTopicNo.2)  Re[1]: C++ DirectX xファイルの読み込み
□投稿者/ キャットメ (2回)-(2009/03/22(Sun) 14:48:58)
2009/03/22(Sun) 14:52:14 編集(投稿者)

間違えて返信してしまいました。
引用返信 編集キー/
■34194 / inTopicNo.3)  Re[2]: C++ DirectX xファイルの読み込み
□投稿者/ 土居 (5回)-(2009/03/22(Sun) 18:46:47)
No34188 (キャットメ さん) に返信
これは回答ではなく、個人的な意見と受け止めてください。

C++ DirectXでゲームを作成していると思われますが、C#とXNAという環境で開発を行うほうが
より効率的ではないかと思うのですが、いかがでしょうか?

引用返信 編集キー/
■34202 / inTopicNo.4)  Re[3]: C++ DirectX xファイルの読み込み
□投稿者/ キャットメ (3回)-(2009/03/22(Sun) 22:21:05)
No34194 (土居 さん) に返信
C#やXNAなどで開発した方が効率的とは自分もよく耳にします。
しかし、効率的に開発というよりC++の勉強をしたいと思っているので今のところは他の言語は考えていません。
ご意見ありがとうございました。
引用返信 編集キー/
■34216 / inTopicNo.5)  Re[4]: C++ DirectX xファイルの読み込み
□投稿者/ .SHO (760回)-(2009/03/23(Mon) 10:31:41)
とりあえず、ウィンドウの表示に不要な処理を削って
もっと小さなプログラムにして問題を絞り込みましょう。
引用返信 編集キー/
■34217 / inTopicNo.6)  Re[4]: C++ DirectX xファイルの読み込み
□投稿者/ 出水 (122回)-(2009/03/23(Mon) 10:40:49)
InitD3DWindowが失敗しているってことはないでしょうか?
落ちている場所までをこっちで特定するのは難しいので、
デバッガのトレースを使って、どういう風に処理が流れているのか確認して見てください

>土居さん
宗教論なので深入りはしませんが、私ならC#/XNAよりC++/DirectXを使います
引用返信 編集キー/
■34231 / inTopicNo.7)  Re[5]: C++ DirectX xファイルの読み込み
□投稿者/ キャットメ (4回)-(2009/03/23(Mon) 20:04:50)
No34216 (.SHO さん) に返信
C++は今勉強中でして、本の通りにしかできる技術がないので、
処理を削るということは残念ながらできません。
ご意見ありがとうございました。
引用返信 編集キー/
■34232 / inTopicNo.8)  Re[6]: C++ DirectX xファイルの読み込み
□投稿者/ キャットメ (5回)-(2009/03/23(Mon) 20:13:01)
No34217 (出水さん) に返信
InitD3DWindowをもう一度見直してみましたが、落ちている場所はやはりありませんでした。
できるだけ検索して調べてみたのですが、デバッガのトレースとはどのようにすればいいのでしょうか?

引用返信 編集キー/
■34233 / inTopicNo.9)  Re[5]: C++ DirectX xファイルの読み込み
□投稿者/ 土居 (6回)-(2009/03/23(Mon) 20:35:10)
2009/03/23(Mon) 20:38:36 編集(投稿者)

No34217 (出水 さん) に返信
失礼しました
引用返信 編集キー/
■34238 / inTopicNo.10)  Re[7]: C++ DirectX xファイルの読み込み
□投稿者/ 出水 (123回)-(2009/03/24(Tue) 04:42:20)
> InitD3DWindowをもう一度見直してみましたが、落ちている場所はやはりありませんでした。
> できるだけ検索して調べてみたのですが、デバッガのトレースとはどのようにすればいいのでしょうか?

落ちている場所がありませんでした、というのは具体的にどういう作業をしたのでしょうか

デバッガの使い方はここでどうでしょう?
http://www.nitoyon.com/vc/tutorial/debug/
引用返信 編集キー/
■34251 / inTopicNo.11)  Re[8]: C++ DirectX xファイルの読み込み
□投稿者/ ごう (13回)-(2009/03/24(Tue) 13:00:58)
my3Dlib.cppにあるLoadModel関数について見てください。
if(g_models[idx].pmaterials==NULL) return -1; 
という記述がありますね。
この記述以前に、g_models[idx].pmaterialsに対して実体を作ったり、
値をセットしたりしていませんから、
この部分は常にg_models[idx].pmaterials==NULLがいつも成立していますね。
(その結果、描画をする前にLoadModel関数を抜けてきてしまっている)

このようなことは、Visual Studioのデバッグ機能を使えば
「どこで問題が発生しているのか」を見極めることができるようになります。
参考になるページを紹介しておきますので、読んで貴殿の言う「落ちている場所」を探してみてください。
http://journal.mycom.co.jp/articles/2008/08/18/debug/index.html
引用返信 編集キー/
■34323 / inTopicNo.12)  Re[9]: C++ DirectX xファイルの読み込み
□投稿者/ キャットメ (6回)-(2009/03/25(Wed) 23:29:38)
No34238 (出水さん) に返信
お恥ずかしながら最初の投稿に書いたとおり、一冊の本に頼っているため
知識が曖昧なままプログラミングをしていました。
(ほとんどまる写しです。しかし、甘い考えかもしれませんが
 やっていくうちに分かっていくものと思っています。)
なので、その本と照らし合わせて抜けている場所がなかったという意味だったのですが
ごうさんの指摘の通り、一行抜けていました。大変ご迷惑をおかせしました。
しかし、質問したことにより、本には記載されていないデバッガという手段があることを知れたため
本当に感謝しています。ありがとうございました。



引用返信 編集キー/
■34324 / inTopicNo.13)  Re[10]: C++ DirectX xファイルの読み込み
□投稿者/ キャットメ (7回)-(2009/03/25(Wed) 23:37:34)
No34251 (ごう さん) に返信
ご指摘のとおり、一行抜けていました。
何分初心者のため、エラーがでないと間違えを見つけることが
困難でした。しかし、出水さんおよびごうさんに紹介していただいた
ページが大変わかりやすく、デバッガやブレークポイントの設定といった
知識を知ることができました。
これからは極力これらの手段を使い、自力で間違えを見つけられるようにしたいです。
本当にありがとうございました。

解決済み
引用返信 編集キー/


トピック内ページ移動 / << 0 >>

このトピックに書きこむ

過去ログには書き込み不可

管理者用

- Child Tree -