mirror of
https://github.com/panda3d/panda3d.git
synced 2025-10-01 09:23:03 -04:00
cleaned up window-fullscreen mode and multiple windows mode for dx8 and dx9
This commit is contained in:
parent
a75582f40c
commit
0c85764323
@ -64,12 +64,6 @@ const string threading_model = config_display.GetString("threading-model", "");
|
||||
// until an explicit call to flip_frame() or the next render_frame().
|
||||
const bool auto_flip = config_display.GetBool("auto-flip", true);
|
||||
|
||||
// This indicates if you want multiple window support for same GSG
|
||||
const bool multiple_windows = config_display.GetBool("multiple-windows", false);
|
||||
|
||||
// This indicates if you want window_and_fullscreen support for same GSG
|
||||
const bool window_and_fullscreen = config_display.GetBool("window-and-fullscreen", false);
|
||||
|
||||
// Set this true to yield the timeslice at the end of the frame to be
|
||||
// more polite to other applications that are trying to run.
|
||||
const bool yield_timeslice = config_display.GetBool("yield-timeslice", false);
|
||||
|
@ -45,10 +45,6 @@ extern const bool show_buffers;
|
||||
extern const bool prefer_parasite_buffer;
|
||||
extern const bool prefer_single_buffer;
|
||||
|
||||
extern EXPCL_PANDA const bool multiple_windows;
|
||||
|
||||
extern EXPCL_PANDA const bool window_and_fullscreen;
|
||||
|
||||
extern EXPCL_PANDA void init_libdisplay();
|
||||
|
||||
#endif /* CONFIG_DISPLAY_H */
|
||||
|
@ -965,7 +965,14 @@ do_clear(const RenderBuffer &buffer) {
|
||||
_depth_clear_value, (DWORD)_stencil_clear_value);
|
||||
if(FAILED(hr)) {
|
||||
dxgsg8_cat.error() << "clear_buffer failed: Clear returned " << D3DERRORSTRING(hr);
|
||||
throw_event("panda3d-render-error");
|
||||
// before throwing the event, lets try a 0 flag
|
||||
dxgsg8_cat.error() << "trying with no flag\n";
|
||||
hr = _pD3DDevice->Clear(0, NULL, D3DCLEAR_TARGET, _d3dcolor_clear_value,
|
||||
_depth_clear_value, (DWORD)_stencil_clear_value);
|
||||
if (FAILED(hr)) {
|
||||
dxgsg8_cat.error() << "clear_buffer failed again: Clear returned " << D3DERRORSTRING(hr);
|
||||
// throw_event("panda3d-render-error");
|
||||
}
|
||||
}
|
||||
/* The following line will cause the background to always clear to a medium red
|
||||
_color_clear_value[0] = .5;
|
||||
@ -1001,7 +1008,7 @@ prepare_display_region() {
|
||||
dxgsg8_cat.error()
|
||||
<< "SetViewport(" << l << ", " << u << ", " << w << ", " << h
|
||||
<< ") failed" << D3DERRORSTRING(hr);
|
||||
#if 0
|
||||
#if 1
|
||||
D3DVIEWPORT8 vp_old;
|
||||
_pD3DDevice->GetViewport( &vp_old );
|
||||
dxgsg8_cat.error()
|
||||
@ -4541,7 +4548,7 @@ set_context(DXScreenData *pNewContextData) {
|
||||
//wdxdisplay8_cat.debug() << "SwapChain = "<< _pSwapChain << "\n";
|
||||
}
|
||||
|
||||
void DXGraphicsStateGuardian8::
|
||||
bool DXGraphicsStateGuardian8::
|
||||
create_swap_chain(DXScreenData *pNewContextData) {
|
||||
// Instead of creating a device and rendering as d3ddevice->present()
|
||||
// we should render using SwapChain->present(). This is done to support
|
||||
@ -4550,17 +4557,25 @@ create_swap_chain(DXScreenData *pNewContextData) {
|
||||
|
||||
HRESULT hr;
|
||||
hr = pNewContextData->pD3DDevice->CreateAdditionalSwapChain(&pNewContextData->PresParams, &pNewContextData->pSwapChain);
|
||||
if (FAILED(hr))
|
||||
if (FAILED(hr)) {
|
||||
wdxdisplay8_cat.debug() << "Swapchain creation failed :"<<D3DERRORSTRING(hr)<<"\n";
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void DXGraphicsStateGuardian8::
|
||||
bool DXGraphicsStateGuardian8::
|
||||
release_swap_chain(DXScreenData *pNewContextData) {
|
||||
// Release the swap chain on this DXScreenData
|
||||
HRESULT hr;
|
||||
hr = pNewContextData->pSwapChain->Release();
|
||||
if (FAILED(hr))
|
||||
wdxdisplay8_cat.debug() << "Swapchain release failed:" << D3DERRORSTRING(hr) << "\n";
|
||||
if (pNewContextData->pSwapChain) {
|
||||
hr = pNewContextData->pSwapChain->Release();
|
||||
if (FAILED(hr)) {
|
||||
wdxdisplay8_cat.debug() << "Swapchain release failed:" << D3DERRORSTRING(hr) << "\n";
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool refill_tex_callback(TextureContext *tc,void *void_dxgsg_ptr) {
|
||||
|
@ -362,8 +362,8 @@ public:
|
||||
|
||||
void support_overlay_window(bool flag);
|
||||
|
||||
void create_swap_chain (DXScreenData *pNewContextData);
|
||||
void release_swap_chain (DXScreenData *pNewContextData);
|
||||
bool create_swap_chain (DXScreenData *pNewContextData);
|
||||
bool release_swap_chain (DXScreenData *pNewContextData);
|
||||
void copy_pres_reset(DXScreenData *pNewContextData);
|
||||
|
||||
private:
|
||||
|
@ -424,8 +424,7 @@ support_overlay_window(bool flag) {
|
||||
void wdxGraphicsWindow8::
|
||||
close_window() {
|
||||
wdxdisplay8_cat.debug() << "wdx closed window\n";
|
||||
if (multiple_windows)
|
||||
_dxgsg->release_swap_chain(&_wcontext);
|
||||
_dxgsg->release_swap_chain(&_wcontext);
|
||||
WinGraphicsWindow::close_window();
|
||||
}
|
||||
|
||||
@ -674,6 +673,8 @@ create_screen_buffers_and_device(DXScreenData &Display, bool force_16bpp_zbuffer
|
||||
RECT view_rect;
|
||||
HRESULT hr;
|
||||
|
||||
wdxdisplay8_cat.debug()<<"Display Width "<< dwRenderWidth<<" and PresParam Width "<<_wcontext.PresParams.BackBufferWidth<<"\n";
|
||||
|
||||
// BUGBUG: need to change panda to put frame buffer properties with GraphicsWindow, not GSG!!
|
||||
int frame_buffer_mode = _gsg->get_properties().get_frame_buffer_mode();
|
||||
bool bWantStencil = ((frame_buffer_mode & FrameBufferProperties::FM_stencil) != 0);
|
||||
@ -842,7 +843,7 @@ create_screen_buffers_and_device(DXScreenData &Display, bool force_16bpp_zbuffer
|
||||
pPresParams->SwapEffect = D3DSWAPEFFECT_DISCARD;
|
||||
}
|
||||
|
||||
// assert((dwRenderWidth==pPresParams->BackBufferWidth)&&(dwRenderHeight==pPresParams->BackBufferHeight));
|
||||
//assert((dwRenderWidth==pPresParams->BackBufferWidth)&&(dwRenderHeight==pPresParams->BackBufferHeight));
|
||||
|
||||
hr = pD3D8->CreateDevice(Display.CardIDNum, D3DDEVTYPE_HAL, _hWnd,
|
||||
dwBehaviorFlags, pPresParams, &Display.pD3DDevice);
|
||||
@ -1755,15 +1756,11 @@ open_window(void) {
|
||||
DXGraphicsStateGuardian8 *dxgsg;
|
||||
DCAST_INTO_R(dxgsg,_gsg,false);
|
||||
WindowProperties props;
|
||||
bool discard_device = false;
|
||||
|
||||
if(!choose_device()) {
|
||||
return false;
|
||||
}
|
||||
if (dxgsg->get_pipe()->get_device() && !multiple_windows && !window_and_fullscreen) {
|
||||
wdxdisplay8_cat.error()
|
||||
<< "Could not create window; multiple window support not enabled.\n";
|
||||
return false;
|
||||
}
|
||||
|
||||
wdxdisplay8_cat.debug() << "_wcontext.hWnd is " << _wcontext.hWnd << "\n";
|
||||
if (!WinGraphicsWindow::open_window()) {
|
||||
@ -1777,36 +1774,44 @@ open_window(void) {
|
||||
// call may be an extension to create multiple windows on same device
|
||||
// In that case just create an additional swapchain for this window
|
||||
|
||||
if (dxgsg->get_pipe()->get_device() == NULL || window_and_fullscreen) {
|
||||
wdxdisplay8_cat.debug() << "device is null \n";
|
||||
|
||||
if (!create_screen_buffers_and_device(_wcontext, dx_force_16bpp_zbuffer))
|
||||
return false;
|
||||
dxgsg->get_pipe()->make_device((void*)(&_wcontext));
|
||||
dxgsg->copy_pres_reset(&_wcontext);
|
||||
if (multiple_windows) {
|
||||
// then we have no choice but to waste a framebuffer
|
||||
while(1) {
|
||||
if (dxgsg->get_pipe()->get_device() == NULL || discard_device) {
|
||||
wdxdisplay8_cat.debug() << "device is null or fullscreen\n";
|
||||
|
||||
wdxdisplay8_cat.debug()<<"device width "<<_wcontext.DisplayMode.Width<<"\n";
|
||||
if (!create_screen_buffers_and_device(_wcontext, dx_force_16bpp_zbuffer)) {
|
||||
// just crash here
|
||||
wdxdisplay8_cat.error() << "fatal: must be trying to create two fullscreen windows: not supported\n";
|
||||
exit(1); //return false;
|
||||
}
|
||||
dxgsg->get_pipe()->make_device((void*)(&_wcontext));
|
||||
dxgsg->copy_pres_reset(&_wcontext);
|
||||
dxgsg->create_swap_chain(&_wcontext);
|
||||
break;
|
||||
|
||||
} else {
|
||||
// fill in the DXScreenData from dxdevice here and change the
|
||||
// reference to hWnd.
|
||||
wdxdisplay8_cat.debug() << "device is not null\n";
|
||||
|
||||
dxdev = (DXGraphicsDevice8*)dxgsg->get_pipe()->get_device();
|
||||
props = get_properties();
|
||||
memcpy(&_wcontext,&dxdev->_Scrn,sizeof(DXScreenData));
|
||||
|
||||
_wcontext.PresParams.Windowed = !is_fullscreen();
|
||||
_wcontext.PresParams.hDeviceWindow = _wcontext.hWnd = _hWnd;
|
||||
_wcontext.PresParams.BackBufferWidth = _wcontext.DisplayMode.Width = props.get_x_size();
|
||||
_wcontext.PresParams.BackBufferHeight = _wcontext.DisplayMode.Height = props.get_y_size();
|
||||
|
||||
wdxdisplay8_cat.debug()<<"device width "<<_wcontext.PresParams.BackBufferWidth<<"\n";
|
||||
//wdxdisplay8_cat.debug()<<"debug pSwapChain "<<_wcontext.pSwapChain<<"\n";
|
||||
if (!dxgsg->create_swap_chain(&_wcontext)) {
|
||||
discard_device = true;
|
||||
continue; // try again
|
||||
}
|
||||
init_resized_window();
|
||||
break;
|
||||
}
|
||||
|
||||
} else {
|
||||
// fill in the DXScreenData from dxdevice here and change the
|
||||
// reference to hWnd.
|
||||
wdxdisplay8_cat.debug() << "device is not null\n";
|
||||
|
||||
dxdev = (DXGraphicsDevice8*)dxgsg->get_pipe()->get_device();
|
||||
props = get_properties();
|
||||
|
||||
memcpy(&_wcontext,&dxdev->_Scrn,sizeof(DXScreenData));
|
||||
_wcontext.hWnd = _hWnd;
|
||||
_wcontext.PresParams.hDeviceWindow = _hWnd;
|
||||
_wcontext.PresParams.BackBufferWidth = props.get_x_size();
|
||||
_wcontext.PresParams.BackBufferHeight = props.get_y_size();
|
||||
|
||||
//wdxdisplay8_cat.debug()<<"device width "<<_wcontext.PresParams.BackBufferWidth<<"\n";
|
||||
//wdxdisplay8_cat.debug()<<"debug pSwapChain "<<_wcontext.pSwapChain<<"\n";
|
||||
dxgsg->create_swap_chain(&_wcontext);
|
||||
init_resized_window();
|
||||
}
|
||||
wdxdisplay8_cat.debug() << "swapchain is " << _wcontext.pSwapChain << "\n";
|
||||
return true;
|
||||
|
@ -4541,35 +4541,45 @@ dx_cleanup(bool bRestoreDisplayMode,bool bAtExitFnCalled) {
|
||||
|
||||
void DXGraphicsStateGuardian9::
|
||||
set_context(DXScreenData *pNewContextData) {
|
||||
// dont do copy from window since dx_init sets fields too.
|
||||
// simpler to keep all of it in one place, so use ptr to window struct
|
||||
|
||||
assert(pNewContextData!=NULL);
|
||||
_pScrn = pNewContextData;
|
||||
_pD3DDevice = _pScrn->pD3DDevice; //copy this one field for speed of deref
|
||||
_pSwapChain = _pScrn->pSwapChain; //copy this one field for speed of deref
|
||||
|
||||
//wdxdisplay9_cat.debug() << "SwapChain = "<< _pSwapChain << "\n";
|
||||
// dont do copy from window since dx_init sets fields too.
|
||||
// simpler to keep all of it in one place, so use ptr to window struct
|
||||
|
||||
assert(pNewContextData!=NULL);
|
||||
_pScrn = pNewContextData;
|
||||
_pD3DDevice = _pScrn->pD3DDevice; //copy this one field for speed of deref
|
||||
_pSwapChain = _pScrn->pSwapChain; //copy this one field for speed of deref
|
||||
|
||||
//wdxdisplay9_cat.debug() << "SwapChain = "<< _pSwapChain << "\n";
|
||||
}
|
||||
|
||||
void DXGraphicsStateGuardian9::
|
||||
bool DXGraphicsStateGuardian9::
|
||||
create_swap_chain(DXScreenData *pNewContextData) {
|
||||
// Instead of creating a device and rendering as d3ddevice->present()
|
||||
// we should render using SwapChain->present(). This is done to support
|
||||
// multiple windows rendering. For that purpose, we need to set additional
|
||||
// swap chains here.
|
||||
|
||||
HRESULT hr;
|
||||
hr = pNewContextData->pD3DDevice->CreateAdditionalSwapChain(&pNewContextData->PresParams, &pNewContextData->pSwapChain);
|
||||
if (FAILED(hr))
|
||||
wdxdisplay9_cat.debug() << "Swapchain creation failed :"<<D3DERRORSTRING(hr)<<"\n";
|
||||
// set_context(pNewContextData);
|
||||
// Instead of creating a device and rendering as d3ddevice->present()
|
||||
// we should render using SwapChain->present(). This is done to support
|
||||
// multiple windows rendering. For that purpose, we need to set additional
|
||||
// swap chains here.
|
||||
|
||||
HRESULT hr;
|
||||
hr = pNewContextData->pD3DDevice->CreateAdditionalSwapChain(&pNewContextData->PresParams, &pNewContextData->pSwapChain);
|
||||
if (FAILED(hr)) {
|
||||
wdxdisplay9_cat.debug() << "Swapchain creation failed :"<<D3DERRORSTRING(hr)<<"\n";
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void DXGraphicsStateGuardian9::
|
||||
bool DXGraphicsStateGuardian9::
|
||||
release_swap_chain(DXScreenData *pNewContextData) {
|
||||
// Release the swap chain on this DXScreenData
|
||||
pNewContextData->pSwapChain->Release();
|
||||
// Release the swap chain on this DXScreenData
|
||||
HRESULT hr;
|
||||
if (pNewContextData->pSwapChain) {
|
||||
hr = pNewContextData->pSwapChain->Release();
|
||||
if (FAILED(hr)) {
|
||||
wdxdisplay9_cat.debug() << "Swapchain release failed:" << D3DERRORSTRING(hr) << "\n";
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool refill_tex_callback(TextureContext *tc,void *void_dxgsg_ptr) {
|
||||
|
@ -365,8 +365,8 @@ public:
|
||||
|
||||
void support_overlay_window(bool flag);
|
||||
|
||||
void create_swap_chain (DXScreenData *pNewContextData);
|
||||
void release_swap_chain (DXScreenData *pNewContextData);
|
||||
bool create_swap_chain (DXScreenData *pNewContextData);
|
||||
bool release_swap_chain (DXScreenData *pNewContextData);
|
||||
void copy_pres_reset(DXScreenData *pNewContextData);
|
||||
|
||||
private:
|
||||
|
@ -424,8 +424,7 @@ support_overlay_window(bool flag) {
|
||||
void wdxGraphicsWindow9::
|
||||
close_window() {
|
||||
wdxdisplay9_cat.debug() << "wdx closed window\n";
|
||||
if (multiple_windows)
|
||||
_dxgsg->release_swap_chain(&_wcontext);
|
||||
_dxgsg->release_swap_chain(&_wcontext);
|
||||
WinGraphicsWindow::close_window();
|
||||
}
|
||||
|
||||
@ -1753,15 +1752,11 @@ open_window(void) {
|
||||
DXGraphicsStateGuardian9 *dxgsg;
|
||||
DCAST_INTO_R(dxgsg,_gsg,false);
|
||||
WindowProperties props;
|
||||
bool discard_device = false;
|
||||
|
||||
if(!choose_device()) {
|
||||
return false;
|
||||
}
|
||||
if (dxgsg->get_pipe()->get_device() && !multiple_windows && !window_and_fullscreen) {
|
||||
wdxdisplay9_cat.error()
|
||||
<< "Could not create window; multiple window support not enabled.\n";
|
||||
return false;
|
||||
}
|
||||
|
||||
wdxdisplay9_cat.debug() << "_wcontext.hWnd is " << _wcontext.hWnd << "\n";
|
||||
if (!WinGraphicsWindow::open_window()) {
|
||||
@ -1775,36 +1770,44 @@ open_window(void) {
|
||||
// call may be an extension to create multiple windows on same device
|
||||
// In that case just create an additional swapchain for this window
|
||||
|
||||
if (dxgsg->get_pipe()->get_device() == NULL || window_and_fullscreen) {
|
||||
wdxdisplay9_cat.debug() << "device is null \n";
|
||||
while(1) {
|
||||
if (dxgsg->get_pipe()->get_device() == NULL || discard_device) {
|
||||
wdxdisplay9_cat.debug() << "device is null or fullscreen\n";
|
||||
|
||||
if (!create_screen_buffers_and_device(_wcontext, dx_force_16bpp_zbuffer))
|
||||
return false;
|
||||
dxgsg->get_pipe()->make_device((void*)(&_wcontext));
|
||||
dxgsg->copy_pres_reset(&_wcontext);
|
||||
if (multiple_windows) {
|
||||
// then we have no choice but to waste a framebuffer
|
||||
wdxdisplay9_cat.debug()<<"device width "<<_wcontext.DisplayMode.Width<<"\n";
|
||||
if (!create_screen_buffers_and_device(_wcontext, dx_force_16bpp_zbuffer)) {
|
||||
// just crash here
|
||||
wdxdisplay9_cat.error() << "fatal: must be trying to create two fullscreen windows: not supported\n";
|
||||
exit(1);//return false;
|
||||
}
|
||||
dxgsg->get_pipe()->make_device((void*)(&_wcontext));
|
||||
dxgsg->copy_pres_reset(&_wcontext);
|
||||
dxgsg->create_swap_chain(&_wcontext);
|
||||
break;
|
||||
|
||||
} else {
|
||||
// fill in the DXScreenData from dxdevice here and change the
|
||||
// reference to hWnd.
|
||||
wdxdisplay9_cat.debug() << "device is not null\n";
|
||||
|
||||
dxdev = (DXGraphicsDevice9*)dxgsg->get_pipe()->get_device();
|
||||
props = get_properties();
|
||||
memcpy(&_wcontext,&dxdev->_Scrn,sizeof(DXScreenData));
|
||||
|
||||
_wcontext.PresParams.Windowed = !is_fullscreen();
|
||||
_wcontext.PresParams.hDeviceWindow = _wcontext.hWnd = _hWnd;
|
||||
_wcontext.PresParams.BackBufferWidth = _wcontext.DisplayMode.Width = props.get_x_size();
|
||||
_wcontext.PresParams.BackBufferHeight = _wcontext.DisplayMode.Height = props.get_y_size();
|
||||
|
||||
wdxdisplay9_cat.debug()<<"device width "<<_wcontext.PresParams.BackBufferWidth<<"\n";
|
||||
//wdxdisplay9_cat.debug()<<"debug pSwapChain "<<_wcontext.pSwapChain<<"\n";
|
||||
if (!dxgsg->create_swap_chain(&_wcontext)) {
|
||||
discard_device = true;
|
||||
continue; //try again
|
||||
}
|
||||
init_resized_window();
|
||||
break;
|
||||
}
|
||||
|
||||
} else {
|
||||
// fill in the DXScreenData from dxdevice here and change the
|
||||
// reference to hWnd.
|
||||
wdxdisplay9_cat.debug() << "device is not null\n";
|
||||
|
||||
dxdev = (DXGraphicsDevice9*)dxgsg->get_pipe()->get_device();
|
||||
props = get_properties();
|
||||
|
||||
memcpy(&_wcontext,&dxdev->_Scrn,sizeof(DXScreenData));
|
||||
_wcontext.hWnd = _hWnd;
|
||||
_wcontext.PresParams.hDeviceWindow = _hWnd;
|
||||
_wcontext.PresParams.BackBufferWidth = props.get_x_size();
|
||||
_wcontext.PresParams.BackBufferHeight = props.get_y_size();
|
||||
|
||||
//wdxdisplay9_cat.debug()<<"device width "<<_wcontext.PresParams.BackBufferWidth<<"\n";
|
||||
//wdxdisplay9_cat.debug()<<"debug pSwapChain "<<_wcontext.pSwapChain<<"\n";
|
||||
dxgsg->create_swap_chain(&_wcontext);
|
||||
init_resized_window();
|
||||
}
|
||||
wdxdisplay9_cat.debug() << "swapchain is " << _wcontext.pSwapChain << "\n";
|
||||
return true;
|
||||
|
Loading…
x
Reference in New Issue
Block a user