// 비디오 모드 전환 BOOL SetDisplayModeWin( HWND hWnd, DWORD Width, DWORD Height, DWORD BPP ) { // Set Cooperative Level HRESULT hresult = lpDD->SetCooperativeLevel( hWnd,DDSCL_NORMAL ); if ( hresult != DD_OK ) { MESSAGE( "lpDD->SetCooperativeLevel" ); return FALSE; } // Primary Surface 생성 DDSURFACEDESC2 ddsd; ZeroMemory( &ddsd, sizeof( ddsd ) ); ddsd.dwSize = sizeof(ddsd); ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE | DDSCAPS_3DDEVICE; // Primary surface 생성 hresult = lpDD->CreateSurface( &ddsd, &lpDDSPrimary, NULL ); if ( hresult != DD_OK ) { MESSAGE( "lpDD2->CreateSurface(lpDDSPrimary)" ); return FALSE; } int w,h; RECT lpRect; GetWindowRect( GetDesktopWindow() , &lpRect ); w = lpRect.right - lpRect.left; h = lpRect.bottom - lpRect.top; // 백 버퍼 1 생성 ZeroMemory( &ddsd, sizeof(ddsd) ); ddsd.dwSize=sizeof(ddsd); ddsd.dwFlags=DDSD_CAPS|DDSD_HEIGHT|DDSD_WIDTH; ddsd.ddsCaps.dwCaps=DDSCAPS_OFFSCREENPLAIN|DDSCAPS_3DDEVICE| DDSCAPS_VIDEOMEMORY; ddsd.dwWidth = w; ddsd.dwHeight = h; lpDD->CreateSurface(&ddsd,&lpDDSBack,NULL); lpDD->CreateClipper( 0, &lpDDClipper , NULL ); lpDDClipper->SetHWnd( 0, hWnd ); lpDDSPrimary->SetClipper( lpDDClipper ); lpDDClipper->Release(); DDPIXELFORMAT ddpx; // z-buffer Surface 생성 ZeroMemory( &ddsd, sizeof(ddsd) ); ddsd.dwSize = sizeof(ddsd); ddsd.dwFlags = DDSD_CAPS | DDSD_WIDTH | DDSD_HEIGHT| DDSD_PIXELFORMAT; ddsd.dwWidth = w; ddsd.dwHeight = h; lpD3D->EnumZBufferFormats( lpD3DDeviceDesc->guid , EnumZBufferCallback , (VOID *)&ddpx ); memcpy( &ddsd.ddpfPixelFormat , &ddpx , sizeof( DDPIXELFORMAT ) ); //###################################################################################### //작 성 자 : 오 영 석 ::CopyMemory( &g_ddpfPixelFormatZ, &ddsd.ddpfPixelFormat, sizeof(g_ddpfPixelFormatZ) ); //###################################################################################### // 하드웨어 이면 z-buffer를 비디오 메모리에 만든다. if ( lpD3DDeviceDesc->bIsHardware ) ddsd.ddsCaps.dwCaps = DDSCAPS_ZBUFFER | DDSCAPS_VIDEOMEMORY; else ddsd.ddsCaps.dwCaps = DDSCAPS_ZBUFFER | DDSCAPS_SYSTEMMEMORY; // Create the ZBuffer surface. hresult = lpDD->CreateSurface( &ddsd, &lpDDSZBuffer, NULL ); if ( hresult != DD_OK ) { MESSAGE( "lpDD2->CreateSurface(lpDDSZBuffer)" ); return FALSE; } // Back Surface에 Z-buffer를 붙인다. hresult = lpDDSBack->AddAttachedSurface( lpDDSZBuffer ); if ( hresult != DD_OK ) { MESSAGE( "lpDDSBack->AddAttachedSurface" ); return FALSE; } // Direct3D Device 생성 hresult = lpD3D->CreateDevice( lpD3DDeviceDesc->guid, lpDDSBack, &lpD3DDevice, NULL ); if ( hresult != D3D_OK ) { MESSAGE( "lpD3D->CreateDevice" ); return FALSE; } // Viewport 크기 설정 D3DRect.x1 = 0; D3DRect.y1 = 0; D3DRect.x2 = w; D3DRect.y2 = h; smScreenWidth = Width; smScreenHeight = Height; return TRUE; }
// 비디오 모드 전환 BOOL SetDisplayMode( HWND hWnd, DWORD Width, DWORD Height, DWORD BPP ) { // Set Cooperative Level smTextureBPP = BPP; if ( WindowMode ) return SetDisplayModeWin( hWnd , Width , Height , BPP ); HRESULT hresult = lpDD->SetCooperativeLevel( hWnd, DDSCL_EXCLUSIVE | DDSCL_FULLSCREEN | DDSCL_ALLOWMODEX ); if ( hresult != DD_OK ) { MESSAGE( "lpDD->SetCooperativeLevel" ); return FALSE; } // 풀화면 모드로 전환 hresult = lpDD->SetDisplayMode( Width, Height, BPP, 0, 0 ); if ( hresult != DD_OK ) { MESSAGE( "lpDD3->SetDisplayMode" ); return FALSE; } // Primary Surface 생성 DDSURFACEDESC2 ddsd; ZeroMemory( &ddsd, sizeof(ddsd) ); ddsd.dwSize = sizeof(ddsd); ddsd.dwBackBufferCount = 1; ddsd.dwFlags = DDSD_CAPS | DDSD_BACKBUFFERCOUNT; ddsd.ddsCaps.dwCaps = DDSCAPS_PRIMARYSURFACE | DDSCAPS_FLIP | DDSCAPS_COMPLEX | DDSCAPS_VIDEOMEMORY | DDSCAPS_3DDEVICE; // Primary surface 생성 hresult = lpDD->CreateSurface( &ddsd, &lpDDSPrimary, NULL ); if ( hresult != DD_OK ) { MESSAGE( "lpDD->CreateSurface(lpDDSPrimary)" ); return FALSE; } // Back Surface 생성(?) DDSCAPS2 ddscaps; ddscaps.dwCaps = DDSCAPS_BACKBUFFER; hresult = lpDDSPrimary->GetAttachedSurface( &ddscaps, &lpDDSBack ); if ( hresult != DD_OK ) { MESSAGE( "lpDDSPrimary->GetAttachedSurface" ); return FALSE; } //////////// 클리퍼 생성 //////////////////////// lpDD->CreateClipper( 0, &lpDDClipper , NULL ); lpDDClipper->SetHWnd( 0, hWnd ); lpDDSPrimary->SetClipper( lpDDClipper ); lpDDClipper->Release(); // z-buffer Surface 생성 ZeroMemory( &ddsd, sizeof(ddsd) ); ddsd.dwSize = sizeof(ddsd); ddsd.dwFlags = DDSD_CAPS | DDSD_WIDTH | DDSD_HEIGHT | DDSD_PIXELFORMAT; ddsd.dwWidth = Width; ddsd.dwHeight = Height; lpD3D->EnumZBufferFormats( IID_IDirect3DHALDevice , EnumZBufferCallback , (VOID *)&ddsd.ddpfPixelFormat ); //###################################################################################### //작 성 자 : 오 영 석 ::CopyMemory( &g_ddpfPixelFormatZ, &ddsd.ddpfPixelFormat, sizeof(g_ddpfPixelFormatZ) ); //###################################################################################### // 하드웨어 이면 z-buffer를 비디오 메모리에 만든다. if ( lpD3DDeviceDesc->bIsHardware ) ddsd.ddsCaps.dwCaps = DDSCAPS_ZBUFFER | DDSCAPS_VIDEOMEMORY; else ddsd.ddsCaps.dwCaps = DDSCAPS_ZBUFFER | DDSCAPS_SYSTEMMEMORY; // Create the ZBuffer surface. hresult = lpDD->CreateSurface( &ddsd, &lpDDSZBuffer, NULL ); if ( hresult != DD_OK ) { MESSAGE( "lpDD2->CreateSurface(lpDDSZBuffer)" ); return FALSE; } // Back Surface에 Z-buffer를 붙인다. hresult = lpDDSBack->AddAttachedSurface( lpDDSZBuffer ); if ( hresult != DD_OK ) { MESSAGE( "lpDDSBack->AddAttachedSurface" ); return FALSE; } // Direct3D Device 생성 hresult = lpD3D->CreateDevice( lpD3DDeviceDesc->guid, lpDDSBack, &lpD3DDevice, NULL ); if ( hresult != D3D_OK ) { MESSAGE( "lpD3D->CreateDevice" ); return FALSE; } // Viewport 크기 설정 D3DRect.x1 = 0; D3DRect.y1 = 0; D3DRect.x2 = Width; D3DRect.y2 = Height; smScreenWidth = Width; smScreenHeight = Height; return TRUE; }