- 음악과 나 -/『 짬 통 』

framework( minpress.com ) - 2

noon2dy 2006. 10. 31. 15:23

4. 3D 게임 프로그래밍을 위한 CD3DApplication 클래스의 활용
■ 활용 목적
Direct3D의 초기 셋팅과 초기화는 항상 일정하다. 일정하다고 하여서 무시할
수 있는 부분은 아니지만 이와 같은 부분에 코딩의 시간을 할애하기 보다는
Microsoft에서 이미 검증과 인증이 끝난 공인된 코드를 사용하는 것이 안정
적이며, 효율적이라 생각을 한다. 이는 우리가 Direct3D라는 COM을 그냥 사
용하는 것과 같다고 볼수 있다.
이 CD3DAppication 클래스는 Visual Studio의 DirectX AppWizrad에서도
프레임 워크로써 제공을 하기 때문에 코드의 안정성에는 조금의 의심도 할
필요가 없으며, 버전 업데이트 시에 항상 클래스의 성능이 향상 되고 있다.
이 CD3DApplication 클래스는 이미 안정적이고, 특별한 하드웨어에 대한 예
외적인 처리를 한꺼번에 처리 해줄수 있도록 그들만의 특색을 가지고 코딩이
되어 있다.
이 코드를 이용한다면 셋팅에 대한 안정성은 상당히 높을 것이며, 게임 초기
셋팅으로 인한 문제점은 모두 극복이 가능하다.
특히나 이 클래스는 게임 프로그래밍을 이제 시작하는 초급자와 중급자에게
는 특히 도움이 되는 유용한 클래스이다. 이러한 이유에서 이 클래스의 사용
을 적극 권한다.

■ DirectX AppWizrad를 이용한 프레임워크 활용 예



[ DirectX AppWizrad를 이용하여서 프로젝트 파일 및 기본 프레임 워크 생성 ]




[ Application 의 API 형태 및 MFC 형태 설정 ]




[ 프로젝트 파일 내에 CD3DApplication 프레임 워크 자동 삽입]




[ 생성 프레임 워크 안의 소스 코드에서의 상속 관계 ]




[ 메인 프로그램 안에서의 CD3DApplication Class의 활용 ]


■ CD3DApplcation class에서 제공하는 오버라이딩 가능 함수
virtual HRESULT ConfirmDevice(D3DCAPS8*,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; }
위의 함수는 virtual 로 선언되어서 CD3Application 클래스에서 제공하는
오버라이딩 함수이다. 이는 상속시에 상속된 클래스안에서 다시 선언하여서
프로그래밍이 가능하다는 것을 말한다.
이젠 이 함수안에 어떤 기능을 어떻게 프로그래밍을 하는 것이 중요하며,
특히나 이와 같은 함수가 언제 호출되는지를 파악하는 것이 중요하다.

4.1 CD3DApplication 클래스의 내부 함수 및 변수
■ 어플리케이션의 상태를 저장하는 내부 변수
D3DAdapterInfo m_Adapters[10];
DWORD m_dwNumAdapters;
DWORD m_dwAdapter;
BOOL m_bWindowed;
BOOL m_bActive;
BOOL m_bReady;
BOOL m_bHasFocus;

■ 타이밍에 사용되는 내부 변수
BOOL m_bFrameMoving;
BOOL m_bSingleStep;

■ 내부 에러 처리 함수
HRESULT DisplayErrorMsg( HRESULT hr, DWORD dwType );

■ 3D장면을 렌더링하고 관리하기 위한 내부 함수
HRESULT BuildDeviceList();
BOOL FindDepthStencilFormat( UINT iAdapter, D3DDEVTYPE DeviceType,
D3DFORMAT TargetFormat, D3DFORMAT* pDepthStencilFormat );
HRESULT Initialize3DEnvironment();
HRESULT Resize3DEnvironment();
HRESULT ToggleFullscreen();
HRESULT ForceWindowed();
HRESULT UserSelectNewDevice();
VOID Cleanup3DEnvironment();
HRESULT Render3DEnvironment();
virtual HRESULT AdjustWindowForChange();
static INT_PTR CALLBACK SelectDeviceProc( HWND hDlg, UINT msg,
WPARAM wParam, LPARAM lParam );

■ 3D장면을 생성하고 렌더링하기 위해 쓰이는 주요 객체
// Main objects used for creating and rendering the 3D scene
D3DPRESENT_PARAMETERS m_d3dpp; // Parameters for CreateDevice/Reset
HWND m_hWnd; // The main app window
HWND m_hWndFocus; // The D3D focus window (usually same as m_hWnd)
HMENU m_hMenu; // App menu bar (stored here when fullscreen)
LPDIRECT3D8 m_pD3D; // The main D3D object
LPDIRECT3DDEVICE8 m_pd3dDevice; // The D3D rendering device
D3DCAPS8 m_d3dCaps; // Caps for the device
D3DSURFACE_DESC m_d3dsdBackBuffer; // Surface desc of the backbuffer
DWORD m_dwCreateFlags; // Indicate sw or hw vertex processing
DWORD m_dwWindowStyle; // Saved window style for mode switches
RECT m_rcWindowBounds; // Saved window bounds for mode switches
RECT m_rcWindowClient; // Saved client area size for mode switches

■ 타이밍에 사용되는 변수
FLOAT m_fTime; // Current time in seconds
FLOAT m_fElapsedTime; // Time elapsed since last frame
FLOAT m_fFPS; // Instanteous frame rate
TCHAR m_strDeviceStats[90]; // String to hold D3D device stats
TCHAR m_strFrameStats[90]; // String to hold frame stats

■ 어플리케이션에서 자유롭게 설정하여 사용할수 있는 변수
// Overridable variables for the app
TCHAR* m_strWindowTitle; // Title for the app's window
BOOL m_bUseDepthBuffer; // Whether to autocreate depthbuffer
DWORD m_dwMinDepthBits; // Minimum number of bits needed in depth buffer
DWORD m_dwMinStencilBits; // Minimum number of bits needed in stencil buffer
DWORD m_dwCreationWidth; // Width used to create window
DWORD m_dwCreationHeight; // Height used to create window
BOOL m_bShowCursorWhenFullscreen; // Whether to show cursor when fullscreen
BOOL m_bClipCursorWhenFullscreen; // Whether to limit cursor pos when fullscreen

■ 3D장면을 위해 오버라이드 되어야 할 가상 함수
// Overridable functions for the 3D scene created by the app
virtual HRESULT ConfirmDevice(D3DCAPS8*,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; }

■ 어플리케이션을 생성하고 구동시키고 멈추고 지우는 함수
// Functions to create, run, pause, and clean up the application
virtual HRESULT Create( HINSTANCE hInstance );
virtual INT Run();
virtual LRESULT MsgProc( HWND hWnd, UINT uMsg,
WPARAM wParam, LPARAM lParam );
virtual VOID Pause( BOOL bPause );



■ SDK에서의 오버라이딩 함수에 대한 간단한 함수 용도 설명 부분
OneTimeSceneInit() - To initialize app data (alloc mem, etc.)
InitDeviceObjects() - To initialize the 3D scene objects
FrameMove() - To animate the scene
Render() - To render the scene
DeleteDeviceObjects() - To cleanup the 3D scene objects
FinalCleanup() - To cleanup app data (for exitting the app)
MsgProc() - To handle Windows messages

4.2 CD3DApplication 클래스 함수 호출 계층도
거의 모든 셋팅에 관한 사항과 게임 로직이 이 클래스안에 전부 구현이 되어 있
다.
다만 화면에 무엇을 나타낼것가에 관한 사항은 역시 프로그래머의 역할이다.
그러기 때문에 이 클래스의 형식에 맞추어서 프로그래밍을 할필요가 있다.
이는 MFC로 프로젝트를 생성하면 어느 정도의 코딩이 자동으로 되어서 Hello
World!라는 윈도우 프로그램을 버튼만으로 제작을 할수 있도록 하는 것과 같으
며, 각 이벤트 메시지에 따라서 MFC 프로그래밍의 구조에 맞게 프로그래밍을
해 주는 것과 거의 동일하다.
주요 함수를 먼저 파악하고 가상 함수가 언제 호출되는 지를 파악하면 이 클래
스를 사용하는데에는 별문제가 없고, 응용함에 있어서 무리가 없을 것이다.

■ Create()
+ Direct3DCreate8() : Direct3D 객체를 생성
+ BuildDeviceList() : 적합한 디바이스 드라이버를 찾아내는 역할
+ ConfirmDevice() : 적합한 하드 웨어(비디오카드의 기능)를 승인해 주는 역할
+ CreateWindow() : 윈도우 생성
+ DXUtil_Timer() : 타이머 구동
+ oneTimesceneInit() : 기하학 정보 초기화, 프로그램 전체에서 1번만 호 출됨
+ Initialize3DEnvironment() : 3D 환경 초기화
+ AdjustWindowForChange() : 윈도우모드와 전체화면 모드의 윈도우스타일 설정
+ InitDeviceObjects() : 초기화된 디바이스( m_pd3dDevice ) 설정
+ RestoreDeviceObjects() : 사용자의 월드, 프로젝션, 뷰, 텍스쳐를 초기화
---> 위의 함수중 하나라도 실패하면 아래의 순서로 호출된다.
+ InvalidateDeviceObjects(); 디바이스를 무효화함
+ DeleteDeviceObjects(); 디바이스를 제거함
+ Device Release함
+ m_bReady = TRUE; // The app is ready to go

■ Run() : 윈도우 메시지 처리와 3D 렌더링 함수 호출 하는 역할
    + m_bActive, m_bReady 변수 관여
+ Render3DEnvironment() : 게임 내의 모든 이동과 3D 렌더링
+ TestCooperativeLevel() : 렌더링 협력 레벨 테스트
( 디바이스 작동가능 여부 테스트 = 디바이스 포커스 체크 )
위의 함수 실패하면 Resize3DEnvironment()를 호출하여 디바이스 리셋
+ FrameMove() : 모든 장면의 사물들의 위치값, 회전값 변경을 담당
(에니메이션 담당)
   + Render() : BeginScene() ~ EndScene()의 안에 있는 모든 것을 화면에 보여 주는 기능
  + Present() : 페이지 플리핑 역할

■ Cleanup3DEnvironment()
+ InvalidateDeviceObjects();
+ DeleteDeviceObjects();
+ FinalCleanup();

위에서 나열한 3가지의 함수가 D3D를 생성하고 구동시키며, 클리어 시켜주는
함수이다. 이 3가지의 함수면 D3D를 생성하고 구동하는 것은 문제가 없다.
즉 아래와 같이 API 형태로 사용할수 있다. 아래의 코드는 DirectX AppWizrad
를 이용하여서 생성한 코드의 일부이다.

INT WINAPI WinMain( HINSTANCE hInst, HINSTANCE, LPSTR, INT )
{
CMyD3DApplication d3dApp;

g_pApp = &d3dApp;
g_hInst = hInst;

if( FAILED( d3dApp.Create( hInst ) ) )
return 0;

return d3dApp.Run();
}

LRESULT CMyD3DApplication::MsgProc( HWND hWnd, UINT msg, WPARAM wParam,
LPARAM lParam )
{
............................................

return CD3DApplication::MsgProc( hWnd, msg, wParam, lParam );
}

Cleanup3DEnvironment() 함수의 실행은 이곳에서 자동 실행된다.
CD3DApplication::MsgProc( hWnd, msg, wParam, lParam )
{
.....................................
case WM_CLOSE:
Cleanup3DEnvironment();
}

만약 이 CD3DApplication::MsgProc( hWnd, msg, wParam, lParam )를 사용하지 않는다면
상속 받은 클래스의 소멸자안에 Cleanup3DEnvironment();를 정의 해주어야 한다.
즉 CTestD3DApplication::~CTestD3DApplication() { Cleanup3DEnvironment(); } 이다.

이 코드가 D3D를 구동시고 생성시키고 메시지 처리를 하는 기본 구조이다.

 

4.3 주요 참조 함수 부가 설명
■ Resize3DEnvironment()
+ InvalidateDeviceObjects() : Device와 관련된 모든 객체를 해제시켜 주는
코드를 호출하는 함수이다.
+ Reset() : 디바이스의 모든 부분을 Release하고 그전 디바이스와는 다른
주소의 디바이스를 얻어오며, device size, format등을 다시
재 설정해주는 함수이다. 이 함수의 실행과 동시에 모든 텍스쳐
의 메모리 표면의 정보를 잃어 버리며, 관리되는 텍스쳐들을 비
디오 메모리로부터 모두 방출시키고 모든 상태정보를 잃는다.
이는 디바이스를 리셋하기 때문에 이와 같이 된다.
+ 백버퍼를 Device의 체인 연결후에 Release()한다.
+ RestoreDeviceObjects() : 상속된 클래스의 함수로써 사용자의 월드, 프
로젝션, 텍스쳐를 초기화, 디바이스가 바뀔때 디바이스 셋

■ ToggleFullScreen()
+ AdjustWindowForChange() : 윈도우모드와 전체화면 모드의 윈도우 스타
일 설정
+ Resize3DEnvironment();
+ ForceWindowed() : 윈도우 모드일경우에만
      + InvalidateDeviceObjects();
      + DeleteDeviceObjects();
+ Initialize3DEnvironment();

■ Initialize3DEnvironment()
① 3D 환경을 초기화 하는 역할

② 전체 화면에서의 커서를 처리하는 역할
m_bShowCursorWhenFullScreen 변수를 상속한 클래스에서 TRUE로 설정
하면 풀모드에서 커서를 나타내게 할수 있다.

CMyD3DApplication::CMyD3DApplication()
{
      .................................................
      m_bShowCursorWhenFullScreen = TRUE;
      ..................................................
}

③ CD3DApplication을 상속해서 만든 클래스의 InitDeviceObjects() 및
RestoreDeviceObjects()를 호출하는 역할
InitDeviceObjects(), RestoreDeviceObjects()를 순서대로 호출하여 상속함
수를 초기화를 한다.
여기서 초기화란 상속받은 클래스의 InitDeviceObjects(),
RestoreDeviceObjects()함수안에서 초기화 된 디바이스를 사용자가 정의
한 함수로 초기화 하는 것과, 텍스쳐, 월드, 뷰, 프로젝션을 초기화 하는
것을 말한다.
다시말해서 초기화된 디바이스를 상속한 클래스로 넘겨주는 부분이다.

④ 윈도우의 위치 설정 역할

⑤ 위의 기능중에서 한가지라도 실패하면 아래의 함수를 호출하여서 디바이스
를 무효화하고 제거되며 다시 Initialize3DEnvironment()가 호출된다.
- InvalidateDeviceObjects(), DeleteDeviceObjects()

[ 참고 ]
★ AdjustWindowForChange() : 윈도우 모드, 전체 모드에 따라서 윈도우 스타
일을 설정하여 주는 역할을 한다.
- DXUtil_Timer()
강력한 타이머 함수
옵션 :
      TIMER_RESET : 타이머를 리셋
      TIMER_START : 타이머 시작
      TIMER_STOP : 타이머 정지나 일시적으로 정지
      TIMER_ADVACE : 타이머를 0.1초 단위로 진행
      TIMER_GETABSOLUTETIME : 시스템의 절대 시간을 가져온다
      TIMER_GETAPPTIME : 현재의 시간을 가져온다
      TIMER_GETELAPSEDTIME : 이전의 이 메시지호출이 있은후부터의
      경과된시간을 가져 온다.
- InvalidateDeviceObjects()
이 함수는 CD3DApplication클래스로부터 상속된 클래스의 함수로써, Device
와 관련된 모든 Objects를 Release해주는 함수부분이다.
그리고 제 설정해주어서 다시 생성한다.
이를 실행해주는 함수는 CD3DApplication의 Resize3DEnvironment()함수이다.

4.4 생각해야할 메시지 처리 부분
- WM_EXTERMENULOOP : 메뉴선택시에 들어오는 메시지 타이머를 멈춤으로써 랜더링 루프를 정지시켜 주어야 한다.
- WM_EXITMENULOOP : 메뉴 선택이 끝나면 들어오는 메시지
타이머를 다시 시작시켜서 랜더링을 재 가동시킴.
- WM_EXITSIZEMOVE : 윈도우의 이동, 크기변환의 모달 루프를 빠져 나왔을때 윈도우로 보내지는 메시지이다.
윈도우의 사용자가 윈도우의 타이틀바나 크기 변환 경계선을 클릭했을 경우에 발생한다.
이때는 타이머를 다시 재가동 시켜주어야한다.
- WM_ENTERSIZEMOVE : WM_EXITSIZEMOVE의 반대이기 때문에 타이머를 정지시킨다.

4.5 호출되는 순서(순차적으로 호출됨)
■ 최초 윈도우의 시작시에
(화면에 윈도우가 그려지기전에, 프로그램 초기 실행시)
① oneTimeSceneInit()
② InitDeviceObjects()
③ RestoreObjects()

■ 윈도우 화면이 생성되면
① InvalidateDeviceObjects()
② RestoreDeviceObjects()
③ FrameMove()
④ Render()

■ 윈도우 사이즈와 디바이스가 바뀌는 경우
① InvalidateDeviceObjects()
② RestoreDeviceObjects()

■ 윈도우 종료시
① InvalidateDeviceObjects()
② DeleteDeviceObjects();

[ 정리 사항 ]
① InitDeviceObjects()
- 어플리케이션 시작시

② InvalidateDeviceObjects()
- 어플리케이션 종료시
- 디바이스가 바뀌었을 경우
[ 코드 ]
Run()
      + Render3DEnvironment() : 게임 내의 모든 이동과 3D 렌더링
           + TestCooperativeLevel() : 디바이스 작동 가능 여부 체크
           => 디바이스 작동 불가하면 Resize3DEnvironment()
                + “InvalidateDeviceObjects()”

- 윈도우 싸이즈가 바뀔때 : Resize3DEnvironment()에서 호출

③ RestoreDeviceObjects()
- 윈도우 싸이즈가 바뀔때
- 디바이스가 바뀔때
- 어플리케이션 최초 시작될때

④ DeleteDeviceObjects();
- 어플리 케이션 종료시에

※ CD3DApplication에서는 기본적인 지오메트릭 파이프라인에 대한 어떠한 셋팅도 되어있지 않다.
이부분은 상속받는 클래스의 RestoreObject()이나 InitDeviceObject()에서 이루어져야 한다.
만약 윈도우의 크기에 따라서 값들이 바뀌는 지오메트릭은 RestoreObject()에 선언을 하며, 그 외에 한번 선언으로 끝나는 것은 InitDeviceObject()에 해주면 된다.

4.6 CD3DApplication Class를 이용한 MFC Single Window 프로그램 framework
■ 포함 헤더
- View 헤더에 선언
"d3d8.h", "d3dx8.h", "d3dapp.h" "d3dutil.h" "dxutil.h"

■ 링크 라이브러리
- dxguid.lib ddraw.lib d3d8.lib d3dx8.lib d3dxof.lib winmm.lib

■ 사용하고자하는 DX 유틸리티 파일에 포함해야하는 헤더MFC의 표준 공통
헤더 파일이기에 모든 클래스에 포함 시켜주어야 한다.
- #include "stdafx.h"



■ Project에 새로운 폴더를 만들어 각 파일을 관리할경우의 Project Setting
위와 같이 등록을 해주어야 컴파일시에 위의 폴더를 컴파일러가
컴파일을 할수 있다.


■ 최종 출력 윈도우 화면




■ 함수 선언 및 코드
① App Class 부분
- onIdle()
[ 코드 ]
CProject3View *g_View = NULL;

BOOL CProject3App::OnIdle(LONG lCount)
{
// TODO: Add your specialized code here and/or call the base class
// CheckForLostFullscreen(); //윈도우 모드일경우는 필요가 없다
if( m_pMainWnd->IsIconic() )
      return FALSE;
if( g_View->IsReady() )
{
      g_View->RenderScene();
}

return TRUE;
}

② View Class 부분
- View()
[ 코드 ]
extern CProject3View *g_View ;

CProject3View::CProject3View()
{
// TODO: add construction code here
g_View = this;
m_bUseDepthBuffer = TRUE; //Note: z좌표를 사용할것인지를 결정하는 플래그
           //CD3DApplication으로 부터 오버로드되는 부분(중요) }

- ~View()
[ 코드 ]
CProject3View::~CProject3View()
{
Cleanup3DEnvironment();
}

- onInitialUpdate()
[ 코드 ]
CProject3View::OnInitialUpdate()
{
CD3DApplication::m_hWnd = GetSafeHwnd();
CD3DApplication::Create( AfxGetInstanceHandle() );
}

- onSize() : 윈도우의 크기에 따라서 D3D의 뷰의 크기도 바뀌어야 한다.
[ 코드 ]
CProject3View::OnSize(UINT nType, int cx, int cy)
{
if( m_bReady ) //D3D 생성 체크 부분
{
      m_d3dpp.BackBufferWidth = cx;
      m_d3dpp.BackBufferHeight = cy;
      Resize3DEnvironment();
}
}

- oneTimeSceneInit() : 게임의 기하학 데이터들을 초기화
[ 코드 ]
HRESULT CProject3View::OneTimeSceneInit()
{
      return S_OK;
}

- FrameMove() : 모든 이동과 변환 값 설정 부분 및 뷰 변환 부분
[ 코드 ]
HRESULT CProject3View::FrameMove()
{
      return S_OK;
}

- Render()
[ 코드 ]
HRESULT CProject3View::Render()
{
m_pd3dDevice->Clear( 0, NULL, D3DCLEAR_TARGET|D3DCLEAR_ZBUFFER,
                D3DCOLOR_XRGB( 30, 50, 100), 1.0f, 0 );
if( SUCCEEDED( m_pd3dDevice->BeginScene() ) )
{
      ...........렌더링 ....................
      m_pd3dDevice->EndScene();
}
return S_OK;
}

- InitDeviceObjects()
[ 코드 ]
HRESULT CProject3View::InitDeviceObjects()
{
      return S_OK;
}

- RestoreDeviceObjects()
: 지오메트릭 파이프 라인 설정 및 윈도우의 크기에 따라서 바뀌는 부분
은 여기에서 프로그래밍을 해준다.
[ 코드 ]
HRESULT CProject3View::RestoreDeviceObjects()
{
//Note: 카메라의 위치(기본적으 로 z값만 셋한다)
D3DXVECTOR3 vEyePt = D3DXVECTOR3( 0.0f, 0.0f, -30.0f );
           //Note: 카메라의 촛점
D3DXVECTOR3 vLookatPt = D3DXVECTOR3( 0.0f, 0.0f, 0.0f );
           //Note: 카메라의 up값(기본적으로 y값만 1.0으로 셋)
D3DXVECTOR3 vUpVec = D3DXVECTOR3( 0.0f, 1.0f, 0.0f );

D3DXMATRIX matWorld, matView, matProj;

D3DXMatrixIdentity( &matWorld );
D3DXMatrixLookAtLH( &matView, &vEyePt, &vLookatPt, &vUpVec );//카메라셋
FLOAT fAspect = m_d3dsdBackBuffer.Width/(FLOAT)m_d3dsdBackBuffer.Height;
//Note; 근거리와 원거리를 셋하는 부분
D3DXMatrixPerspectiveFovLH( &matProj, D3DX_PI/4, fAspect, 1.0f, 1000.0f );
m_pd3dDevice->SetTransform( D3DTS_WORLD, &matWorld );
m_pd3dDevice->SetTransform( D3DTS_VIEW, &matView );
m_pd3dDevice->SetTransform( D3DTS_PROJECTION, &matProj );

//Note: 카메라 뷰의 크기를 셋하는 부분
D3DVIEWPORT8 vp;
vp.X = 0;
vp.Y = 0;
vp.Width = m_d3dsdBackBuffer.Width;
vp.Height = m_d3dsdBackBuffer.Height;
vp.MinZ = 0.0f;
vp.MaxZ = 1.0f;
m_pd3dDevice->SetViewport( &vp );

return S_OK;
}

- DeleteDeviceObjects()
[ 코드 ]
HRESULT CProject3View::DeleteDeviceObjects()
{
return S_OK;
}

- InvalidateDeviceObjects()
[ 코드 ]
HRESULT CProject3View::InvalidateDeviceObjects()
{
return S_OK;
}

- FinalCleanup()
[ 코드 ]
HRESULT CProject3View::FinalCleanup()
{
return S_OK;
}

- onActivateView()
[ 코드 ]
void CProject3View::OnActivateView(BOOL bActivate, CView* pActivateView, CView*
            pDeactiveView)
{
// TODO: Add your specialized code here and/or call the base class
m_bActive = bActivate;
CView::OnActivateView(bActivate, pActivateView, pDeactiveView);
}

- ConfirmDevice()
[ 코드 ]
//Note: 하드웨어 지원 체크하는 부분 (이 부분은 꼭 있어야 한다)
HRESULT CProject3View::ConfirmDevice(D3DCAPS8 *pCaps, DWORD dwBehavior,
                  D3DFORMAT Format)
{
if( !(dwBehavior & D3DCREATE_SOFTWARE_VERTEXPROCESSING) &&
           !(pCaps->VertexShaderVersion >= D3DVS_VERSION(1, 0)) )
     {
           return E_FAIL;
     }

     return S_OK;
}


■ MFC 프로그래밍 방법
① CD3DApplication을 View Class로 상속을 한다.
class CProject3View : public CView, public CD3DApplication
{ ..............................

② App Class에서 onIdle() 부분을 아래와 같이 프로그래밍 한다.
이 부분은 거의 고정적이다.

BOOL CProject3App::OnIdle(LONG lCount)
{
     // TODO: Add your specialized code here and/or call the base class
     if( m_pMainWnd->IsIconic() || g_View == NULL )
           return FALSE;

     if( g_View->IsReady() )
     {
           g_View->RenderScene();
     }

     return TRUE;
}

여기서 g_View->RenderScene()의 함수의 내용은 이와 같다.
void RenderScene() { Render3DEnvironment(); }로 되어 있다.
그 이유는 Render3DEnvironment()가 protected의 속성을 가져서 외부에서
참조를 못하게 되어 있기에 이와같은 함수를 View 부분에 만들어 두고,
App Class에서 사용한다.


③ View Class에서 위의 View(), ~View(), onInitialUpdate(), Render()만
프로그래밍을 한다. 이 4개의 함수는 MFC에서 CD3DApplication를 이용하
여서 기본적으로 셋하는 부분들이다.

이로써 게임툴을 만들기 위한 DirectDraw와 Direct3D의 framework를 학습을 하였다.
이를 기반으로 자신의 게임에 맞는 툴을 제작하여야 할것이며, 한가지 알고 있어야하는
것은 이와 같은 게임 툴은 프로그래머를 위한 툴이 아닌 게임 디자이너들이 사용하여야
할 툴이기에 각 설정 인터페이스에 신경을 써서 제작을 하여야 한다는 것을 기억하기 바란다.

 

 

 

'- 음악과 나 - > 『 짬 통 』' 카테고리의 다른 글

framework( Minpress.com )  (0) 2006.10.31
IndexBuffer  (0) 2006.10.08
Mesh  (0) 2006.10.08
Texture  (0) 2006.10.07
Light  (0) 2006.10.07