坐标系与基本图元(8)
全屏幕显示
游戏程序通常都是运行在全屏幕模式下,进行全屏显示的关键是使用全屏显示的渲染设备。创建全屏显示模式渲染设备同窗口模式渲染设备基本相同,区别是将d3dpp.Windowed设置为FALSE,告诉Direct3D系统,将要创建的是全屏模式渲染设备。此外,还需要明确指定后台缓冲区的大小和格式,这和创建窗口模式渲染设备是不相同的,在创建窗口模式渲染设备时可将后台缓冲区格式设置为D3DFMT_UNKNOWN,后台缓冲区大小也可取默认值,而在创建全屏模式渲染设备时这些都需要明确指定。
首先调用函数GetAdapterDisplayMode()获得显示器当前的显示模式:
Retrieves the current display mode of the adapter.
HRESULT GetAdapterDisplayMode(
UINT Adapter,
D3DDISPLAYMODE * pMode
);
Parameters
- Adapter
- [in] Ordinal number that denotes the display adapter to query. D3DADAPTER_DEFAULT is always the primary display adapter.
- pMode
- [in, out] Pointer to a D3DDISPLAYMODE structure, to be filled with information describing the current adapter's mode.
Return Values
If the method succeeds, the return value is D3D_OK.If Adapter is out of range or pMode is invalid, this method returns D3DERR_INVALIDCALL.
Remarks
IDirect3D9::GetAdapterDisplayMode will not return the correct format when the display is in an extended format, such as 2:10:10:10. Instead, it returns the format X8R8G8B8.
Describes the display mode.
typedef struct D3DDISPLAYMODE {
UINT Width;
UINT Height;
UINT RefreshRate;
D3DFORMAT Format;
} D3DDISPLAYMODE, *LPD3DDISPLAYMODE;
Members
- Width
- Screen width, in pixels.
- Height
- Screen height, in pixels.
- RefreshRate
- Refresh rate. The value of 0 indicates an adapter default.
- Format
- Member of the D3DFORMAT enumerated type, describing the surface format of the display mode.
运行截图:
完整源代码:
#include
<
d3d9.h
>
#define CLASS_NAME "GameApp"
#define release_com(p) do { if(p) { (p)->Release(); (p) = NULL; } } while(0)
IDirect3D9 * g_d3d;
IDirect3DDevice9 * g_device;
IDirect3DVertexBuffer9 * g_vertex_buffer;
struct sCustomVertex
{
float x, y, z, rhw;
DWORD color;
};
#define D3DFVF_CUSTOM_VERTEX (D3DFVF_XYZRHW | D3DFVF_DIFFUSE)
void init_vertices()
{
sCustomVertex vertices[] =
{
{ 100.0f , 650.0f , 0.5f , 1.0f , 0xffff0000 , },
{ 500.0f , 100.0f , 0.5f , 1.0f , 0xff00ff00 , },
{ 900.0f , 650.0f , 0.5f , 1.0f , 0xff0000ff , },
};
// push vertex data into vertex buffer
g_device -> CreateVertexBuffer( sizeof (vertices), 0 , D3DFVF_CUSTOM_VERTEX, D3DPOOL_DEFAULT, & g_vertex_buffer, NULL);
void * ptr;
g_vertex_buffer -> Lock( 0 , sizeof (vertices), ( void ** ) & ptr, 0 );
memcpy(ptr, vertices, sizeof (vertices));
g_vertex_buffer -> Unlock();
}
bool init_d3d(HWND hwnd)
{
g_d3d = Direct3DCreate9(D3D_SDK_VERSION);
if (g_d3d == NULL)
return false ;
D3DPRESENT_PARAMETERS d3dpp;
ZeroMemory( & d3dpp, sizeof (d3dpp));
D3DDISPLAYMODE display_mode;
g_d3d -> GetAdapterDisplayMode(D3DADAPTER_DEFAULT, & display_mode);
d3dpp.Windowed = FALSE;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpp.BackBufferWidth = display_mode.Width;
d3dpp.BackBufferHeight = display_mode.Height;
d3dpp.BackBufferFormat = display_mode.Format;
if (FAILED(g_d3d -> CreateDevice(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hwnd, D3DCREATE_SOFTWARE_VERTEXPROCESSING,
& d3dpp, & g_device)))
{
return false ;
}
init_vertices();
return true ;
}
void cleanup()
{
release_com(g_vertex_buffer);
release_com(g_device);
release_com(g_d3d);
}
void render()
{
g_device -> Clear( 0 , NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB( 5 , 5 , 5 ), 1.0f , 0 );
g_device -> BeginScene();
g_device -> SetStreamSource( 0 , g_vertex_buffer, 0 , sizeof (sCustomVertex));
g_device -> SetFVF(D3DFVF_CUSTOM_VERTEX);
g_device -> DrawPrimitive(D3DPT_TRIANGLELIST, 0 , 1 );
g_device -> EndScene();
g_device -> Present(NULL, NULL, NULL, NULL);
}
LRESULT WINAPI WinProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch (msg)
{
case WM_KEYDOWN:
switch (wParam)
{
case VK_ESCAPE:
DestroyWindow(hwnd);
break ;
}
break ;
case WM_DESTROY:
PostQuitMessage( 0 );
return 0 ;
}
return DefWindowProc(hwnd, msg, wParam, lParam);
}
int WINAPI WinMain(HINSTANCE inst, HINSTANCE, LPSTR, INT)
{
WNDCLASSEX wc;
wc.cbSize = sizeof (WNDCLASSEX);
wc.style = CS_CLASSDC;
wc.lpfnWndProc = WinProc;
wc.cbClsExtra = 0 ;
wc.cbWndExtra = 0 ;
wc.hInstance = inst;
wc.hIcon = NULL;
wc.hCursor = NULL;
wc.hbrBackground = NULL;
wc.lpszMenuName = NULL;
wc.lpszClassName = CLASS_NAME;
wc.hIconSm = NULL;
if ( ! RegisterClassEx( & wc))
return - 1 ;
HWND hwnd = CreateWindow(CLASS_NAME, " Direct3D App " , WS_OVERLAPPEDWINDOW, 200 , 100 , 600 , 500 ,
NULL, NULL, wc.hInstance, NULL);
if (hwnd == NULL)
return - 1 ;
if (init_d3d(hwnd))
{
ShowWindow(hwnd, SW_SHOWDEFAULT);
UpdateWindow(hwnd);
MSG msg;
ZeroMemory( & msg, sizeof (msg));
while (msg.message != WM_QUIT)
{
if (PeekMessage( & msg, NULL, 0 , 0 , PM_REMOVE))
{
TranslateMessage( & msg);
DispatchMessage( & msg);
}
render();
}
}
cleanup();
UnregisterClass(CLASS_NAME, wc.hInstance);
return 0 ;
}
#define CLASS_NAME "GameApp"
#define release_com(p) do { if(p) { (p)->Release(); (p) = NULL; } } while(0)
IDirect3D9 * g_d3d;
IDirect3DDevice9 * g_device;
IDirect3DVertexBuffer9 * g_vertex_buffer;
struct sCustomVertex
{
float x, y, z, rhw;
DWORD color;
};
#define D3DFVF_CUSTOM_VERTEX (D3DFVF_XYZRHW | D3DFVF_DIFFUSE)
void init_vertices()
{
sCustomVertex vertices[] =
{
{ 100.0f , 650.0f , 0.5f , 1.0f , 0xffff0000 , },
{ 500.0f , 100.0f , 0.5f , 1.0f , 0xff00ff00 , },
{ 900.0f , 650.0f , 0.5f , 1.0f , 0xff0000ff , },
};
// push vertex data into vertex buffer
g_device -> CreateVertexBuffer( sizeof (vertices), 0 , D3DFVF_CUSTOM_VERTEX, D3DPOOL_DEFAULT, & g_vertex_buffer, NULL);
void * ptr;
g_vertex_buffer -> Lock( 0 , sizeof (vertices), ( void ** ) & ptr, 0 );
memcpy(ptr, vertices, sizeof (vertices));
g_vertex_buffer -> Unlock();
}
bool init_d3d(HWND hwnd)
{
g_d3d = Direct3DCreate9(D3D_SDK_VERSION);
if (g_d3d == NULL)
return false ;
D3DPRESENT_PARAMETERS d3dpp;
ZeroMemory( & d3dpp, sizeof (d3dpp));
D3DDISPLAYMODE display_mode;
g_d3d -> GetAdapterDisplayMode(D3DADAPTER_DEFAULT, & display_mode);
d3dpp.Windowed = FALSE;
d3dpp.SwapEffect = D3DSWAPEFFECT_DISCARD;
d3dpp.BackBufferWidth = display_mode.Width;
d3dpp.BackBufferHeight = display_mode.Height;
d3dpp.BackBufferFormat = display_mode.Format;
if (FAILED(g_d3d -> CreateDevice(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hwnd, D3DCREATE_SOFTWARE_VERTEXPROCESSING,
& d3dpp, & g_device)))
{
return false ;
}
init_vertices();
return true ;
}
void cleanup()
{
release_com(g_vertex_buffer);
release_com(g_device);
release_com(g_d3d);
}
void render()
{
g_device -> Clear( 0 , NULL, D3DCLEAR_TARGET, D3DCOLOR_XRGB( 5 , 5 , 5 ), 1.0f , 0 );
g_device -> BeginScene();
g_device -> SetStreamSource( 0 , g_vertex_buffer, 0 , sizeof (sCustomVertex));
g_device -> SetFVF(D3DFVF_CUSTOM_VERTEX);
g_device -> DrawPrimitive(D3DPT_TRIANGLELIST, 0 , 1 );
g_device -> EndScene();
g_device -> Present(NULL, NULL, NULL, NULL);
}
LRESULT WINAPI WinProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
switch (msg)
{
case WM_KEYDOWN:
switch (wParam)
{
case VK_ESCAPE:
DestroyWindow(hwnd);
break ;
}
break ;
case WM_DESTROY:
PostQuitMessage( 0 );
return 0 ;
}
return DefWindowProc(hwnd, msg, wParam, lParam);
}
int WINAPI WinMain(HINSTANCE inst, HINSTANCE, LPSTR, INT)
{
WNDCLASSEX wc;
wc.cbSize = sizeof (WNDCLASSEX);
wc.style = CS_CLASSDC;
wc.lpfnWndProc = WinProc;
wc.cbClsExtra = 0 ;
wc.cbWndExtra = 0 ;
wc.hInstance = inst;
wc.hIcon = NULL;
wc.hCursor = NULL;
wc.hbrBackground = NULL;
wc.lpszMenuName = NULL;
wc.lpszClassName = CLASS_NAME;
wc.hIconSm = NULL;
if ( ! RegisterClassEx( & wc))
return - 1 ;
HWND hwnd = CreateWindow(CLASS_NAME, " Direct3D App " , WS_OVERLAPPEDWINDOW, 200 , 100 , 600 , 500 ,
NULL, NULL, wc.hInstance, NULL);
if (hwnd == NULL)
return - 1 ;
if (init_d3d(hwnd))
{
ShowWindow(hwnd, SW_SHOWDEFAULT);
UpdateWindow(hwnd);
MSG msg;
ZeroMemory( & msg, sizeof (msg));
while (msg.message != WM_QUIT)
{
if (PeekMessage( & msg, NULL, 0 , 0 , PM_REMOVE))
{
TranslateMessage( & msg);
DispatchMessage( & msg);
}
render();
}
}
cleanup();
UnregisterClass(CLASS_NAME, wc.hInstance);
return 0 ;
}