15 #include "wdxGraphicsPipe9.h" 16 #include "wdxGraphicsBuffer9.h" 17 #include "dxGraphicsStateGuardian9.h" 18 #include "pStatTimer.h" 21 #define FL << "\n" << __FILE__ << " " << __LINE__ << "\n" 39 GraphicsBuffer(engine, pipe, name, fb_prop, win_prop, flags, gsg, host)
43 _saved_color_buffer = NULL;
44 _saved_depth_buffer = NULL;
45 _color_backing_store = NULL;
46 _depth_backing_store = NULL;
51 _screenshot_buffer_type = _draw_buffer_type;
53 _shared_depth_buffer = 0;
58 cout <<
"+++++ wdxGraphicsBuffer9 constructor " <<
this <<
" " <<
this ->
get_name ( ) <<
"\n";
68 dxgsg -> _graphics_buffer_list.push_back(_this);
78 ~wdxGraphicsBuffer9() {
81 cout <<
"----- wdxGraphicsBuffer9 destructor " <<
this <<
" " <<
this ->
get_name ( ) <<
"\n";
90 dxgsg -> _graphics_buffer_list.remove(_this);
103 list <wdxGraphicsBuffer9 *>::iterator graphics_buffer_iterator;
105 graphics_buffer_iterator = _shared_depth_buffer_list.begin( );
106 while (graphics_buffer_iterator != _shared_depth_buffer_list.end( )) {
107 graphics_buffer = (*graphics_buffer_iterator);
108 if (graphics_buffer) {
112 graphics_buffer_iterator = _shared_depth_buffer_list.begin( );
116 this -> close_buffer ( );
131 begin_frame_spam(mode);
135 if (_dxgsg -> _d3d_device == 0) {
139 if (mode == FM_render) {
140 if (!save_bitplanes()) {
143 if (!rebuild_bitplanes()) {
147 clear_cube_map_selection();
151 return _gsg->begin_frame(current_thread);
164 end_frame_spam(mode);
167 if (mode == FM_render) {
171 _gsg->end_frame(current_thread);
173 if (mode == FM_render) {
175 clear_cube_map_selection();
186 bool wdxGraphicsBuffer9::
189 DWORD render_target_index;
191 render_target_index = 0;
193 hr = _dxgsg -> _d3d_device -> GetRenderTarget (render_target_index, &_saved_color_buffer);
194 if (!SUCCEEDED (hr)) {
195 dxgsg9_cat.error ( ) <<
"GetRenderTarget " << D3DERRORSTRING(hr) FL;
199 _saved_depth_buffer = 0;
200 hr = _dxgsg -> _d3d_device -> GetDepthStencilSurface (&_saved_depth_buffer);
201 if (hr == D3DERR_NOTFOUND) {
205 if (!SUCCEEDED (hr)) {
206 dxgsg9_cat.error ( ) <<
"GetDepthStencilSurface " << D3DERRORSTRING(hr) FL;
219 void wdxGraphicsBuffer9::
220 restore_bitplanes() {
222 DCAST_INTO_V(dxgsg, _gsg);
225 DWORD render_target_index;
227 render_target_index = 0;
229 hr = dxgsg -> _d3d_device ->
230 SetRenderTarget (render_target_index, _saved_color_buffer);
231 if (!SUCCEEDED (hr)) {
232 dxgsg9_cat.error ( ) <<
"SetRenderTarget " << D3DERRORSTRING(hr) FL;
234 if (_saved_depth_buffer) {
235 hr = _dxgsg -> _d3d_device -> SetDepthStencilSurface (_saved_depth_buffer);
236 if (!SUCCEEDED (hr)) {
237 dxgsg9_cat.error ( ) <<
"SetDepthStencilSurface " << D3DERRORSTRING(hr) FL;
243 hr = _dxgsg -> _d3d_device -> SetRenderTarget (i, NULL);
244 if (!SUCCEEDED (hr)) {
245 dxgsg9_cat.error ( ) <<
"SetRenderTarget " << i <<
" " << D3DERRORSTRING(hr) FL;
249 _saved_color_buffer->Release();
250 if (_saved_depth_buffer) {
251 _saved_depth_buffer->Release();
253 _saved_color_buffer = NULL;
254 _saved_depth_buffer = NULL;
265 bool wdxGraphicsBuffer9::
266 rebuild_bitplanes() {
272 IDirect3DTexture9 *color_d3d_tex = 0;
273 IDirect3DTexture9 *depth_d3d_tex = 0;
274 IDirect3DCubeTexture9 *color_cube = 0;
275 IDirect3DCubeTexture9 *depth_cube = 0;
276 IDirect3DSurface9 *color_surf = 0;
277 IDirect3DSurface9 *depth_surf = 0;
278 DWORD render_target_index;
280 render_target_index = 0;
284 if ((_host != 0)&&(_creation_flags & GraphicsPipe::BF_size_track_host)) {
285 if (_host->get_size() != _size) {
287 _host->get_y_size());
303 int color_tex_index = -1;
304 int depth_tex_index = -1;
307 for (
size_t i = 0; i != cdata->_textures.size(); ++i) {
308 const RenderTexture &rt = cdata->_textures[i];
309 RenderTextureMode rtm_mode = rt._rtm_mode;
310 if (rtm_mode == RTM_bind_or_copy) {
311 RenderTexturePlane plane = rt._plane;
322 case RTP_aux_hrgba_0:
323 case RTP_aux_hrgba_1:
324 case RTP_aux_hrgba_2:
325 case RTP_aux_hrgba_3:
326 case RTP_aux_float_0:
327 case RTP_aux_float_1:
328 case RTP_aux_float_2:
329 case RTP_aux_float_3:
331 CDWriter cdataw(_cycler, cdata,
false);
332 cdataw->_textures[i]._rtm_mode = RTM_none;
339 CDWriter cdataw(_cycler, cdata,
false);
340 cdataw->_textures[i]._rtm_mode = RTM_copy_texture;
350 if (color_tex_index < 0) {
352 if ((_color_backing_store)&&
353 ((bitplane_x != _backing_sizex)||(bitplane_y != _backing_sizey))) {
354 _color_backing_store->Release();
355 _color_backing_store = NULL;
357 if (!_color_backing_store) {
358 hr = _dxgsg->_d3d_device->CreateRenderTarget(bitplane_x, bitplane_y,
359 _saved_color_desc.Format,
360 _saved_color_desc.MultiSampleType,
361 _saved_color_desc.MultiSampleQuality,
363 &_color_backing_store,
365 if (!SUCCEEDED(hr)) {
366 dxgsg9_cat.error ( ) <<
"CreateRenderTarget " << D3DERRORSTRING(hr) FL;
369 color_surf = _color_backing_store;
372 if (_color_backing_store) {
373 _color_backing_store->Release();
374 _color_backing_store = NULL;
381 color_tex->
prepare_now(0, _gsg->get_prepared_objects(), _gsg));
386 <<
"Unable to re-create texture " << *color_ctx->
get_texture() << endl;
390 color_d3d_tex = color_ctx->_d3d_2d_texture;
391 nassertr(color_d3d_tex != 0,
false);
392 hr = color_d3d_tex -> GetSurfaceLevel(0, &color_surf);
393 if (!SUCCEEDED(hr)) {
394 dxgsg9_cat.error ( ) <<
"GetSurfaceLevel " << D3DERRORSTRING(hr) FL;
398 color_cube = color_ctx->_d3d_cube_texture;
399 nassertr(color_cube != 0,
false);
401 if (_cube_map_index >= 0 && _cube_map_index < 6) {
402 hr = color_cube -> GetCubeMapSurface ((D3DCUBEMAP_FACES) _cube_map_index, 0, &color_surf);
403 if (!SUCCEEDED(hr)) {
404 dxgsg9_cat.error ( ) <<
"GetCubeMapSurface " << D3DERRORSTRING(hr) FL;
413 release_depth =
true;
414 if (depth_tex_index < 0) {
415 if (_shared_depth_buffer) {
416 if (_shared_depth_buffer -> _depth_backing_store) {
418 printf (
"SHARE DEPTH BUFFER\n");
420 depth_surf = _shared_depth_buffer -> _depth_backing_store;
421 release_depth =
false;
424 if (depth_surf == 0) {
426 if ((_depth_backing_store)&&
427 ((bitplane_x != _backing_sizex)||(bitplane_y != _backing_sizey))) {
428 _depth_backing_store->Release();
429 _depth_backing_store = NULL;
431 if (!_depth_backing_store) {
432 hr = _dxgsg -> _d3d_device ->
433 CreateDepthStencilSurface (bitplane_x, bitplane_y, _saved_depth_desc.Format,
434 _saved_depth_desc.MultiSampleType, _saved_depth_desc.MultiSampleQuality,
435 false, &_depth_backing_store, NULL);
436 if (!SUCCEEDED(hr)) {
437 dxgsg9_cat.error ( ) <<
"CreateDepthStencilSurface " << D3DERRORSTRING(hr) FL;
440 depth_surf = _depth_backing_store;
444 if (_depth_backing_store) {
445 _depth_backing_store->Release();
446 _depth_backing_store = NULL;
449 if (_shared_depth_buffer) {
450 depth_tex = _shared_depth_buffer ->
get_texture(depth_tex_index);
452 if (depth_tex == 0) {
457 depth_tex->
set_format(Texture::F_depth_stencil);
460 depth_tex->
prepare_now(0, _gsg->get_prepared_objects(), _gsg));
464 <<
"Unable to re-create texture " << *depth_ctx->
get_texture() << endl;
468 depth_d3d_tex = depth_ctx->_d3d_2d_texture;
469 nassertr(depth_d3d_tex != 0,
false);
470 hr = depth_d3d_tex -> GetSurfaceLevel(0, &depth_surf);
471 if (!SUCCEEDED(hr)) {
472 dxgsg9_cat.error ( ) <<
"GetSurfaceLevel " << D3DERRORSTRING(hr) FL;
476 depth_cube = depth_ctx->_d3d_cube_texture;
477 nassertr(depth_cube != 0,
false);
478 hr = depth_cube -> GetCubeMapSurface ((D3DCUBEMAP_FACES) _cube_map_index, 0, &depth_surf);
479 if (!SUCCEEDED(hr)) {
480 dxgsg9_cat.error ( ) <<
"GetCubeMapSurface " << D3DERRORSTRING(hr) FL;
486 _backing_sizex = bitplane_x;
487 _backing_sizey = bitplane_y;
491 hr = _dxgsg -> _d3d_device -> SetRenderTarget (render_target_index, color_surf);
492 if (!SUCCEEDED (hr)) {
493 dxgsg9_cat.error ( ) <<
"SetRenderTarget " << D3DERRORSTRING(hr) FL;
498 hr = _dxgsg -> _d3d_device -> SetDepthStencilSurface (depth_surf);
499 if (!SUCCEEDED (hr)) {
500 dxgsg9_cat.error ( ) <<
"SetDepthStencilSurface " << D3DERRORSTRING(hr) FL;
504 render_target_index = 1;
521 case RTP_aux_hrgba_0:
522 case RTP_aux_hrgba_1:
523 case RTP_aux_hrgba_2:
524 case RTP_aux_hrgba_3:
525 case RTP_aux_float_0:
526 case RTP_aux_float_1:
527 case RTP_aux_float_2:
528 case RTP_aux_float_3:
531 IDirect3DTexture9 *color_d3d_tex = 0;
532 IDirect3DSurface9 *color_surf = 0;
533 IDirect3DCubeTexture9 *color_cube = 0;
539 <<
"Unable to re-create texture " << *color_ctx->
get_texture() << endl;
543 color_d3d_tex = color_ctx->_d3d_2d_texture;
544 nassertr(color_d3d_tex != 0,
false);
546 hr = color_d3d_tex -> GetSurfaceLevel(0, &color_surf);
547 if (!SUCCEEDED(hr)) {
548 dxgsg9_cat.error ( ) <<
"GetSurfaceLevel " << D3DERRORSTRING(hr) FL;
551 hr = _dxgsg -> _d3d_device -> SetRenderTarget (render_target_index, color_surf);
552 if (SUCCEEDED (hr)) {
553 render_target_index++;
555 dxgsg9_cat.error ( ) <<
"SetRenderTarget " << render_target_index <<
" " << D3DERRORSTRING(hr) FL;
557 color_surf->Release();
572 if ((color_surf != 0)&&(color_surf != _color_backing_store)) {
573 color_surf->Release();
577 if ((depth_surf != 0)&&(depth_surf != _depth_backing_store)) {
578 depth_surf->Release();
597 DWORD render_target_index;
599 render_target_index = 0;
601 _cube_map_index = page;
606 IDirect3DCubeTexture9 *color_cube = 0;
607 IDirect3DSurface9 *color_surf = 0;
608 int color_tex_index = -1;
612 for (
size_t i = 0; i != cdata->_textures.size(); ++i) {
613 const RenderTexture &rt = cdata->_textures[i];
614 RenderTextureMode rtm_mode = rt._rtm_mode;
615 if (rtm_mode == RTM_bind_or_copy) {
617 if ((tex->
get_format() != Texture::F_depth_stencil)&&
618 (tex->
get_format() != Texture::F_depth_component)&&
619 (color_tex_index < 0)) {
622 CDWriter cdataw(_cycler, cdata,
false);
623 nassertv(cdata->_textures.size() == cdataw->_textures.size());
624 cdataw->_textures[i]._rtm_mode = RTM_copy_texture;
634 color_tex->
prepare_now(0, _gsg->get_prepared_objects(), _gsg));
635 color_cube = color_ctx->_d3d_cube_texture;
636 if (color_cube && _cube_map_index >= 0 && _cube_map_index < 6) {
637 hr = color_cube -> GetCubeMapSurface ((D3DCUBEMAP_FACES) _cube_map_index, 0, &color_surf);
638 if (!SUCCEEDED(hr)) {
639 dxgsg9_cat.error ( ) <<
"GetCubeMapSurface " << D3DERRORSTRING(hr) FL;
642 hr = _dxgsg -> _d3d_device -> SetRenderTarget (render_target_index, color_surf);
643 if (!SUCCEEDED (hr)) {
644 dxgsg9_cat.error ( ) <<
"SetRenderTarget " << D3DERRORSTRING(hr) FL;
647 color_surf->Release();
652 render_target_index = 1;
665 case RTP_aux_hrgba_0:
666 case RTP_aux_hrgba_1:
667 case RTP_aux_hrgba_2:
668 case RTP_aux_hrgba_3:
669 case RTP_aux_float_0:
670 case RTP_aux_float_1:
671 case RTP_aux_float_2:
672 case RTP_aux_float_3:
675 IDirect3DSurface9 *color_surf = 0;
676 IDirect3DCubeTexture9 *color_cube = 0;
683 printf (
"CUBEMAP i = %d, RenderTexturePlane = %d, _cube_map_index %d \n", i, plane, _cube_map_index);
686 color_cube = color_ctx->_d3d_cube_texture;
687 if (color_cube && _cube_map_index >= 0 && _cube_map_index < 6) {
688 hr = color_cube -> GetCubeMapSurface ((D3DCUBEMAP_FACES) _cube_map_index, 0, &color_surf);
689 if (!SUCCEEDED(hr)) {
690 dxgsg9_cat.error ( ) <<
"GetCubeMapSurface " << D3DERRORSTRING(hr) FL;
693 hr = _dxgsg -> _d3d_device -> SetRenderTarget (render_target_index, color_surf);
694 if (SUCCEEDED (hr)) {
695 render_target_index++;
697 dxgsg9_cat.error ( ) <<
"cube map SetRenderTarget " << render_target_index <<
" " << D3DERRORSTRING(hr) FL;
699 color_surf->Release();
732 while (PeekMessage(&msg, NULL, 0, 0, PM_NOREMOVE)) {
743 void wdxGraphicsBuffer9::
746 if (_color_backing_store) {
747 _color_backing_store->Release();
748 _color_backing_store = NULL;
750 if (_depth_backing_store) {
751 _depth_backing_store->Release();
752 _depth_backing_store = NULL;
755 _cube_map_index = -1;
766 bool wdxGraphicsBuffer9::
778 DCAST_INTO_R(_dxgsg, _gsg,
false);
780 if (!save_bitplanes()) {
785 hr = _saved_color_buffer -> GetDesc (&_saved_color_desc);
786 if (!SUCCEEDED (hr)) {
787 dxgsg9_cat.error ( ) <<
"GetDesc " << D3DERRORSTRING(hr) FL;
790 hr = _saved_depth_buffer -> GetDesc (&_saved_depth_desc);
791 if (!SUCCEEDED (hr)) {
792 dxgsg9_cat.error ( ) <<
"GetDesc " << D3DERRORSTRING(hr) FL;
795 _fb_properties = _dxgsg->
796 calc_fb_properties(_saved_color_desc.Format,
797 _saved_depth_desc.Format,
798 _saved_depth_desc.MultiSampleType,
799 _saved_depth_desc.MultiSampleQuality);
800 _fb_properties.set_force_hardware(1);
803 if (!rebuild_bitplanes()) {
817 void wdxGraphicsBuffer9::
821 if (!GetMessage(&msg, NULL, 0, 0)) {
828 TranslateMessage(&msg);
830 DispatchMessage(&msg);
851 if (
this != input_graphics_output && input_graphics_output) {
857 printf (
"share_depth_buffer\n");
863 printf (
"ERROR: share_depth_buffer: non matching width \n");
870 printf (
"ERROR: share_depth_buffer: non matching height \n");
879 _shared_depth_buffer = input_graphics_output;
894 if (_shared_depth_buffer) {
896 printf (
"wdxGraphicsBuffer9 unshare_depth_buffer \n");
902 _shared_depth_buffer = 0;
916 if (input_graphics_output) {
918 _shared_depth_buffer_list.push_back(input_graphics_output);
932 if (input_graphics_output) {
934 _shared_depth_buffer_list.remove(input_graphics_output);
void unregister_shared_depth_buffer(GraphicsOutput *graphics_output)
Unregister who is sharing the depth buffer.
A GraphicsStateGuardian for rendering into DirectX9 contexts.
Format get_format() const
Returns the format of the texture, which represents both the semantic meaning of the texels and...
Texture * get_texture() const
Returns the pointer to the associated Texture object.
void set_size_and_recalc(int x, int y)
Changes the x_size and y_size, then recalculates structures that depend on size.
virtual bool share_depth_buffer(GraphicsOutput *graphics_output)
Will attempt to use the depth buffer of the input graphics_output.
virtual Texture * get_texture(int i=0) const
Returns the nth texture into which the GraphicsOutput renders.
TextureType get_texture_type() const
Returns the overall interpretation of the texture.
Represents a texture object, which is typically a single 2-d image but may also represent a 1-d or 3-...
int get_y_size() const
Returns the visible height of the window or buffer, if it is known.
void set_format(Format format)
Changes the format value for the texture components.
bool create_texture(DXScreenData &scrn)
Use panda texture's pixelbuffer to create a texture for the specified device.
virtual void select_target_tex_page(int page)
Called internally when the window is in render-to-a-texture mode and we are in the process of renderi...
virtual void end_frame(FrameMode mode, Thread *current_thread)
This function will be called within the draw thread after rendering is completed for a given frame...
virtual void process_events()
Honor any requests recently made via request_open() or request_close().
void set_size_padded(int x=1, int y=1, int z=1)
Changes the size of the texture, padding if necessary, and setting the pad region as well...
static AutoTextureScale get_textures_power_2()
This flag returns ATS_none, ATS_up, or ATS_down and controls the scaling of textures in general...
A container for the various kinds of properties we might ask to have on a graphics window before we o...
void clear(Thread *current_thread)
Clears the entire framebuffer before rendering, according to the settings of get_color_clear_active()...
An offscreen render buffer.
An offscreen buffer for rendering into.
An object to create GraphicsOutputs that share a particular 3-D API.
virtual void process_events()
Do whatever processing is necessary to ensure that the window responds to user events.
This template class calls PipelineCycler::read() in the constructor and PipelineCycler::release_read(...
int count_textures() const
If the GraphicsOutput is set to render into a texture, returns the number of textures that are being ...
This template class calls PipelineCycler::write() in the constructor and PipelineCycler::release_writ...
This is a base class for the various different classes that represent the result of a frame of render...
int get_x_size() const
Returns the visible width of the window or buffer, if it is known.
TextureContext * prepare_now(int view, PreparedGraphicsObjects *prepared_objects, GraphicsStateGuardianBase *gsg)
Creates a context for the texture on the particular GSG, if it does not already exist.
virtual bool begin_frame(FrameMode mode, Thread *current_thread)
This function will be called within the draw thread before beginning rendering for a given frame...
static int up_to_power_2(int value)
Returns the smallest power of 2 greater than or equal to value.
A thread; that is, a lightweight process.
Encapsulates all the communication with a particular instance of a given rendering backend...
const string & get_name() const
Returns the name that was passed to the GraphicsOutput constructor.
virtual void unshare_depth_buffer()
Discontinue sharing the depth buffer.
This class is the main interface to controlling the render process.
TypeHandle is the identifier used to differentiate C++ class types.
A container for the various kinds of properties we might ask to have on a graphics frameBuffer before...
RenderTexturePlane get_texture_plane(int i=0) const
Returns the RenderTexturePlane associated with the nth render-texture.
const FrameBufferProperties & get_fb_properties() const
Returns the framebuffer properties of the window.
void register_shared_depth_buffer(GraphicsOutput *graphics_output)
Register/save who is sharing the depth buffer.