1 /*---------------------------------------------------------------------------*\
5 * Copyright (C) 2000-2002 by the OpenSG Forum *
9 * contact: dirk@opensg.org, gerrit.voss@vossg.org, jbehr@zgdv.de *
11 \*---------------------------------------------------------------------------*/
12 /*---------------------------------------------------------------------------*\
15 * This library is free software; you can redistribute it and/or modify it *
16 * under the terms of the GNU Library General Public License as published *
17 * by the Free Software Foundation, version 2. *
19 * This library is distributed in the hope that it will be useful, but *
20 * WITHOUT ANY WARRANTY; without even the implied warranty of *
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
22 * Library General Public License for more details. *
24 * You should have received a copy of the GNU Library General Public *
25 * License along with this library; if not, write to the Free Software *
26 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. *
28 \*---------------------------------------------------------------------------*/
29 /*---------------------------------------------------------------------------*\
37 \*---------------------------------------------------------------------------*/
40 //---------------------------------------------------------------------------
42 //---------------------------------------------------------------------------
44 #define CHECK_FRAMEBUFFER_STATUS() \
48 OSGGETGLFUNC_GL3_ES( glCheckFramebufferStatus, \
49 osgGlCheckFramebufferStatus, \
50 _uiFuncCheckFramebufferStatus ); \
52 status = osgGlCheckFramebufferStatus(GL_FRAMEBUFFER); \
57 case GL_FRAMEBUFFER_COMPLETE: \
59 case GL_FRAMEBUFFER_UNSUPPORTED: \
60 FWARNING(("Unsupported Framebuffer\n")); \
61 /* choose different formats */ \
63 case GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT: \
64 FWARNING(("Incomplete Attachment\n")); \
66 case GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT: \
67 FWARNING(("Incomplete Missing Attachment\n")); \
69 case GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS_EXT: \
70 FWARNING(("Incomplete Dimensions\n")); \
72 case GL_FRAMEBUFFER_INCOMPLETE_FORMATS_EXT: \
73 FWARNING(("Incomplete Formats\n")); \
75 case GL_FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER: \
76 FWARNING(("Incomplete Draw Buffer\n")); \
78 case GL_FRAMEBUFFER_INCOMPLETE_READ_BUFFER: \
79 FWARNING(("Incomplete Read Buffer\n")); \
81 case GL_FRAMEBUFFER_INCOMPLETE_MULTISAMPLE: \
82 FWARNING(("Incomplete Multisample\n")); \
85 FWARNING(("Unknown error %x\n", status)); \
93 #include <boost/bind.hpp>
95 #include "OSGConfig.h"
99 #include "OSGGLFuncProtos.h"
101 #include "OSGWindow.h"
103 #include "OSGFrameBufferObject.h"
104 #include "OSGDrawEnv.h"
105 #include "OSGFrameBufferAttachment.h"
106 #include "OSGTextureBuffer.h"
107 #include "OSGTextureObjChunk.h"
108 #include "OSGRenderBuffer.h"
112 UInt32
FrameBufferObject::_uiFramebufferObjectArb
=
113 Window::invalidExtensionID
;
115 UInt32
FrameBufferObject::_uiFramebufferBlitExt
=
116 Window::invalidExtensionID
;
118 UInt32
FrameBufferObject::_uiPackedDepthStencilExt
=
119 Window::invalidExtensionID
;
121 UInt32
FrameBufferObject::_uiFuncGenFramebuffers
=
122 Window::invalidFunctionID
;
124 UInt32
FrameBufferObject::_uiFuncCheckFramebufferStatus
=
125 Window::invalidFunctionID
;
127 UInt32
FrameBufferObject::_uiFuncBindFramebuffer
=
128 Window::invalidFunctionID
;
130 UInt32
FrameBufferObject::_uiFuncDeleteFramebuffers
=
131 Window::invalidFunctionID
;
133 UInt32
FrameBufferObject::_uiFuncFramebufferRenderbuffer
=
134 Window::invalidFunctionID
;
136 UInt32
FrameBufferObject::_uiFuncDrawBuffers
=
137 Window::invalidFunctionID
;
139 UInt32
FrameBufferObject::_uiFuncBlitFramebuffer
=
140 Window::invalidFunctionID
;
142 // Documentation for this class is emited in the
143 // OSGFrameBufferObjectBase.cpp file.
144 // To modify it, please change the .fcd file (OSGFrameBufferObject.fcd) and
145 // regenerate the base file.
147 void FrameBufferObject::setColorAttachment(
148 FrameBufferAttachment
*pAttachment
,
151 if(uiSlot
>= GL_COLOR_ATTACHMENT0
)
153 uiSlot
-= GL_COLOR_ATTACHMENT0
;
156 editMField(ColorAttachmentsFieldMask
, _mfColorAttachments
);
158 if(uiSlot
>= _mfColorAttachments
.size())
160 _mfColorAttachments
.resize(uiSlot
+ 1, NULL
);
163 _mfColorAttachments
.replace(uiSlot
, pAttachment
);
166 void FrameBufferObject::setSize(UInt32 uiWidth
, UInt32 uiHeight
)
172 void FrameBufferObject::resizeAll(UInt32 uiWidth
, UInt32 uiHeight
)
176 MFUnrecFrameBufferAttachmentPtr::const_iterator attIt
=
177 _mfColorAttachments
.begin();
178 MFUnrecFrameBufferAttachmentPtr::const_iterator attEnd
=
179 _mfColorAttachments
.end ();
181 for(; attIt
!= attEnd
; ++attIt
)
186 (*attIt
)->resizeBuffers(uiWidth
, uiHeight
);
189 if(_sfDepthAttachment
.getValue() != NULL
)
191 _sfDepthAttachment
.getValue()->resizeBuffers(uiWidth
, uiHeight
);
194 if(_sfStencilAttachment
.getValue() != NULL
)
196 _sfStencilAttachment
.getValue()->resizeBuffers(uiWidth
, uiHeight
);
200 // multi-sample buffer
202 attIt
= _mfMsaaColorAttachments
.begin();
203 attEnd
= _mfMsaaColorAttachments
.end ();
205 for(; attIt
!= attEnd
; ++attIt
)
210 (*attIt
)->resizeBuffers(uiWidth
, uiHeight
);
213 if(_sfMsaaDepthAttachment
.getValue() != NULL
)
215 _sfMsaaDepthAttachment
.getValue()->resizeBuffers(uiWidth
, uiHeight
);
218 if(_sfMsaaStencilAttachment
.getValue() != NULL
)
220 _sfMsaaStencilAttachment
.getValue()->resizeBuffers(uiWidth
, uiHeight
);
224 this->setSize(uiWidth
, uiHeight
);
226 Window::refreshGLObject(getGLId());
227 Window::refreshGLObject(getMultiSampleGLId());
230 /*----------------------- constructors & destructors ----------------------*/
232 FrameBufferObject::FrameBufferObject(void) :
237 FrameBufferObject::FrameBufferObject(const FrameBufferObject
&source
) :
242 FrameBufferObject::~FrameBufferObject(void)
246 /*----------------------------- class specific ----------------------------*/
248 void FrameBufferObject::initMethod(InitPhase ePhase
)
250 Inherited::initMethod(ePhase
);
252 if(ePhase
== TypeObject::SystemPost
)
254 _uiFramebufferObjectArb
=
255 Window::registerExtension("GL_ARB_framebuffer_object");
256 _uiFramebufferBlitExt
=
257 Window::registerExtension("GL_EXT_framebuffer_blit");
258 _uiPackedDepthStencilExt
=
259 Window::registerExtension("GL_EXT_packed_depth_stencil");
261 _uiFuncGenFramebuffers
=
262 Window::registerFunction (
263 OSG_DLSYM_UNDERSCORE
"glGenFramebuffers",
264 _uiFramebufferObjectArb
);
266 _uiFuncCheckFramebufferStatus
=
267 Window::registerFunction (
268 OSG_DLSYM_UNDERSCORE
"glCheckFramebufferStatus",
269 _uiFramebufferObjectArb
);
271 _uiFuncBindFramebuffer
=
272 Window::registerFunction (
273 OSG_DLSYM_UNDERSCORE
"glBindFramebuffer",
274 _uiFramebufferObjectArb
);
276 _uiFuncDeleteFramebuffers
=
277 Window::registerFunction (
278 OSG_DLSYM_UNDERSCORE
"glDeleteFramebuffers",
279 _uiFramebufferObjectArb
);
281 _uiFuncFramebufferRenderbuffer
=
282 Window::registerFunction (
283 OSG_DLSYM_UNDERSCORE
"glFramebufferRenderbuffer",
284 _uiFramebufferObjectArb
);
287 Window::registerFunction (
288 OSG_DLSYM_UNDERSCORE
"glDrawBuffers",
289 _uiFramebufferObjectArb
);
291 _uiFuncBlitFramebuffer
=
292 Window::registerFunction (
293 OSG_DLSYM_UNDERSCORE
"glBlitFramebufferEXT",
294 _uiFramebufferBlitExt
);
299 void FrameBufferObject::onCreate(const FrameBufferObject
*source
)
301 if(GlobalSystemState
== Startup
)
305 Window::registerGLObject(
306 boost::bind(&FrameBufferObject::handleGL
,
307 FrameBufferObjectMTUncountedPtr(this),
309 &FrameBufferObject::handleDestroyGL
));
312 Window::registerGLObject(
313 boost::bind(&FrameBufferObject::handleMultiSampleGL
,
314 FrameBufferObjectMTUncountedPtr(this),
316 &FrameBufferObject::handleDestroyGL
));
319 void FrameBufferObject::onDestroy(UInt32 uiContainerId
)
322 Window::destroyGLObject(getGLId(), 1);
324 if(getMultiSampleGLId() > 0)
325 Window::destroyGLObject(getMultiSampleGLId(), 1);
327 Inherited::onDestroy(uiContainerId
);
330 void FrameBufferObject::changed(ConstFieldMaskArg whichField
,
334 Inherited::changed(whichField
, origin
, details
);
336 if(0x0000 != (whichField
& (WidthFieldMask
| HeightFieldMask
)))
340 MFUnrecFrameBufferAttachmentPtr::const_iterator attIt
=
341 _mfColorAttachments
.begin();
342 MFUnrecFrameBufferAttachmentPtr::const_iterator attEnd
=
343 _mfColorAttachments
.end ();
345 for(; attIt
!= attEnd
; ++attIt
)
350 (*attIt
)->resize(getWidth(), getHeight());
353 if(_sfDepthAttachment
.getValue() != NULL
)
355 _sfDepthAttachment
.getValue()->resize(getWidth (),
359 if(_sfStencilAttachment
.getValue() != NULL
)
361 _sfStencilAttachment
.getValue()->resize(getWidth (),
365 Window::refreshGLObject(getGLId());
368 // multi-sample buffer
370 attIt
= _mfMsaaColorAttachments
.begin();
371 attEnd
= _mfMsaaColorAttachments
.end ();
373 for(; attIt
!= attEnd
; ++attIt
)
378 (*attIt
)->resize(getWidth(), getHeight());
381 if(_sfMsaaDepthAttachment
.getValue() != NULL
)
383 _sfMsaaDepthAttachment
.getValue()->resize(getWidth (),
387 if(_sfMsaaStencilAttachment
.getValue() != NULL
)
389 _sfMsaaStencilAttachment
.getValue()->resize(getWidth (),
393 Window::refreshGLObject(getMultiSampleGLId());
396 if(0x0000 != (whichField
& DepthAttachmentFieldMask
))
398 if(_sfDepthAttachment
.getValue() != NULL
)
400 _sfDepthAttachment
.getValue()->resize(getWidth (),
403 if(_sfMsaaDepthAttachment
.getValue() != NULL
)
405 _sfMsaaDepthAttachment
.getValue()->resize(getWidth (),
408 else if(_sfEnableMultiSample
.getValue() == true)
410 FrameBufferAttachmentUnrecPtr pMsaaBuffer
=
411 this->createMultiSampleBufferFrom(
412 _sfDepthAttachment
.getValue());
414 this->setMsaaDepthAttachment(pMsaaBuffer
);
419 this->setMsaaDepthAttachment(NULL
);
422 Window::reinitializeGLObject(getGLId ());
423 Window::reinitializeGLObject(getMultiSampleGLId());
426 if(0x0000 != (whichField
& StencilAttachmentFieldMask
))
428 if(_sfStencilAttachment
.getValue() != NULL
)
430 _sfStencilAttachment
.getValue()->resize(getWidth (),
433 if(_sfMsaaStencilAttachment
.getValue() != NULL
)
435 _sfMsaaStencilAttachment
.getValue()->resize(getWidth (),
438 else if(_sfEnableMultiSample
.getValue() == true)
440 FrameBufferAttachmentUnrecPtr pMsaaBuffer
=
441 this->createMultiSampleBufferFrom(
442 _sfStencilAttachment
.getValue());
444 this->setMsaaStencilAttachment(pMsaaBuffer
);
449 this->setMsaaStencilAttachment(NULL
);
452 Window::reinitializeGLObject(getGLId ());
453 Window::reinitializeGLObject(getMultiSampleGLId());
456 if(0x0000 != (whichField
& ColorAttachmentsFieldMask
))
458 MFUnrecFrameBufferAttachmentPtr::const_iterator attIt
=
459 _mfColorAttachments
.begin();
460 MFUnrecFrameBufferAttachmentPtr::const_iterator attEnd
=
461 _mfColorAttachments
.end ();
463 if(_mfMsaaColorAttachments
.size() != _mfColorAttachments
.size())
465 editMField(MsaaColorAttachmentsFieldMask
, _mfMsaaColorAttachments
);
467 _mfMsaaColorAttachments
.resize(_mfColorAttachments
.size(),
471 MFUnrecFrameBufferAttachmentPtr::iterator msaaAttIt
=
472 _mfMsaaColorAttachments
.begin_nc();
474 for(; attIt
!= attEnd
; ++attIt
, ++msaaAttIt
)
478 if(*msaaAttIt
!= NULL
)
480 editMField( MsaaColorAttachmentsFieldMask
,
481 _mfMsaaColorAttachments
);
483 _mfMsaaColorAttachments
.replace(msaaAttIt
, NULL
);
489 (*attIt
)->resize(getWidth(), getHeight());
491 if(*msaaAttIt
!= NULL
)
493 (*msaaAttIt
)->resize(getWidth(), getHeight());
495 else if(_sfEnableMultiSample
.getValue() == true)
497 FrameBufferAttachmentUnrecPtr pMsaaBuffer
=
498 this->createMultiSampleBufferFrom(*attIt
);
500 editMField( MsaaColorAttachmentsFieldMask
,
501 _mfMsaaColorAttachments
);
503 _mfMsaaColorAttachments
.replace(msaaAttIt
, pMsaaBuffer
);
507 Window::reinitializeGLObject(getGLId ());
508 Window::reinitializeGLObject(getMultiSampleGLId());
511 if(0x0000 != (whichField
& EnableMultiSampleFieldMask
))
513 if(_sfDepthAttachment
.getValue() != NULL
&&
514 _sfMsaaDepthAttachment
.getValue() == NULL
)
516 FrameBufferAttachmentUnrecPtr pMsaaBuffer
=
517 this->createMultiSampleBufferFrom(
518 _sfDepthAttachment
.getValue());
520 this->setMsaaDepthAttachment(pMsaaBuffer
);
523 if(_sfStencilAttachment
.getValue() != NULL
&&
524 _sfMsaaStencilAttachment
.getValue() == NULL
)
526 FrameBufferAttachmentUnrecPtr pMsaaBuffer
=
527 this->createMultiSampleBufferFrom(
528 _sfStencilAttachment
.getValue());
530 this->setMsaaStencilAttachment(pMsaaBuffer
);
533 MFUnrecFrameBufferAttachmentPtr::const_iterator attIt
=
534 _mfColorAttachments
.begin();
535 MFUnrecFrameBufferAttachmentPtr::const_iterator attEnd
=
536 _mfColorAttachments
.end ();
538 if(_mfMsaaColorAttachments
.size() != _mfColorAttachments
.size())
540 editMField(MsaaColorAttachmentsFieldMask
, _mfMsaaColorAttachments
);
542 _mfMsaaColorAttachments
.resize(_mfColorAttachments
.size(),
546 MFUnrecFrameBufferAttachmentPtr::iterator msaaAttIt
=
547 _mfMsaaColorAttachments
.begin_nc();
549 for(; attIt
!= attEnd
; ++attIt
, ++msaaAttIt
)
554 if(*msaaAttIt
== NULL
)
556 FrameBufferAttachmentUnrecPtr pMsaaBuffer
=
557 this->createMultiSampleBufferFrom(*attIt
);
559 editMField( MsaaColorAttachmentsFieldMask
,
560 _mfMsaaColorAttachments
);
562 _mfMsaaColorAttachments
.replace(msaaAttIt
, pMsaaBuffer
);
566 Window::reinitializeGLObject(getMultiSampleGLId());
570 void FrameBufferObject::dump( UInt32
,
571 const BitVector
) const
573 SLOG
<< "Dump FrameBufferObject NI" << std::endl
;
576 void FrameBufferObject::activate(DrawEnv
*pEnv
,
579 Window
*win
= pEnv
->getWindow();
581 if(win
->hasExtOrVersion(_uiFramebufferObjectArb
, 0x0300, 0x0200) == false)
583 FNOTICE(("Framebuffer objects not supported on Window %p!\n",
584 static_cast<void *>(win
)));
588 // FLOG(("FBO Activate %p\n", this));
590 UInt32 glId
= getGLId();
592 win
->validateGLObject(getGLId(), pEnv
);
594 if(_sfEnableMultiSample
.getValue() == true &&
595 win
->hasExtOrVersion(_uiFramebufferBlitExt
, 0x0300) == true )
597 win
->validateGLObject(getMultiSampleGLId(), pEnv
);
599 glId
= getMultiSampleGLId();
601 glEnable(GL_MULTISAMPLE
);
604 OSGGETGLFUNCBYID_GL3_ES( glBindFramebuffer
,
605 osgGlBindFramebuffer
,
606 _uiFuncBindFramebuffer
,
609 osgGlBindFramebuffer(GL_FRAMEBUFFER
,
610 win
->getGLObjectId(glId
));
612 pEnv
->setActiveFBO(glId
);
614 glErr("FrameBufferObject::activate::bind");
616 glErr("FrameBufferObject::activate");
619 if(eDrawBuffer
== GL_NONE
)
621 if(_mfDrawBuffers
.size() != 0)
623 OSGGETGLFUNCBYID_GL3( glDrawBuffers
,
628 osgGlDrawBuffers(GLsizei(_mfDrawBuffers
.size()),
629 &(_mfDrawBuffers
[0]) );
633 glDrawBuffer(GL_NONE
);
634 glReadBuffer(GL_NONE
);
639 OSGGETGLFUNCBYID_GL3( glDrawBuffers
,
644 osgGlDrawBuffers(1, &eDrawBuffer
);
648 CHECK_FRAMEBUFFER_STATUS();
651 void FrameBufferObject::deactivate (DrawEnv
*pEnv
)
653 Window
*win
= pEnv
->getWindow();
655 if(win
->hasExtOrVersion(_uiFramebufferObjectArb
, 0x0300, 0x0200) == false)
657 FNOTICE(("Framebuffer objects not supported on Window %p!\n",
658 static_cast<void *>(win
)));
662 // FLOG(("FBO DeActivate %p\n", this));
664 OSGGETGLFUNCBYID_GL3_ES( glBindFramebuffer
,
665 osgGlBindFramebuffer
,
666 _uiFuncBindFramebuffer
,
669 if(_sfEnableMultiSample
.getValue() == true &&
670 win
->hasExtOrVersion(_uiFramebufferBlitExt
, 0x0300) == true )
672 OSGGETGLFUNCBYID_GL3( glBlitFramebuffer
,
673 osgGlBlitFramebuffer
,
674 _uiFuncBlitFramebuffer
,
677 // GLbitfield bufferMask = GL_COLOR_BUFFER_BIT;
678 glDisable(GL_MULTISAMPLE
);
680 osgGlBindFramebuffer(GL_READ_FRAMEBUFFER
,
681 win
->getGLObjectId(getMultiSampleGLId()));
682 osgGlBindFramebuffer(GL_DRAW_FRAMEBUFFER
,
683 win
->getGLObjectId(getGLId ()));
685 osgGlBlitFramebuffer(0, 0, getWidth(), getHeight(),
686 0, 0, getWidth(), getHeight(),
687 (GL_COLOR_BUFFER_BIT
|
688 GL_DEPTH_BUFFER_BIT
|
689 GL_STENCIL_BUFFER_BIT
),
692 osgGlBindFramebuffer(GL_FRAMEBUFFER
, win
->getGLObjectId(getGLId()));
695 if(_sfPostProcessOnDeactivate
.getValue() == true)
697 MFUnrecFrameBufferAttachmentPtr::const_iterator attIt
=
698 _mfColorAttachments
.begin();
699 MFUnrecFrameBufferAttachmentPtr::const_iterator attEnd
=
700 _mfColorAttachments
.end ();
702 UInt32 index
= GL_COLOR_ATTACHMENT0
;
704 for(; attIt
!= attEnd
; ++attIt
, ++index
)
709 (*attIt
)->processPreDeactivate(pEnv
, index
);
712 if(_sfDepthAttachment
.getValue() != NULL
&&
713 _sfStencilAttachment
.getValue() != NULL
)
715 if(_sfDepthAttachment
.getValue() == _sfStencilAttachment
.getValue())
717 _sfDepthAttachment
.getValue()->processPreDeactivate(
722 _sfDepthAttachment
.getValue()->processPreDeactivate(
724 _sfStencilAttachment
.getValue()->processPreDeactivate(
728 else if(_sfDepthAttachment
.getValue() != NULL
)
730 _sfDepthAttachment
.getValue()->processPreDeactivate(
733 else if(_sfStencilAttachment
.getValue() != NULL
)
735 _sfStencilAttachment
.getValue()->processPreDeactivate(
740 osgGlBindFramebuffer(GL_FRAMEBUFFER
, 0);
742 pEnv
->setActiveFBO(0);
744 if(_sfPostProcessOnDeactivate
.getValue() == true)
746 MFUnrecFrameBufferAttachmentPtr::const_iterator attIt
=
747 _mfColorAttachments
.begin();
748 MFUnrecFrameBufferAttachmentPtr::const_iterator attEnd
=
749 _mfColorAttachments
.end ();
751 for(; attIt
!= attEnd
; ++attIt
)
756 (*attIt
)->processPostDeactivate(pEnv
);
761 UInt32
FrameBufferObject::handleGL(DrawEnv
*pEnv
,
763 Window::GLObjectStatusE mode
,
766 Window
*win
= pEnv
->getWindow();
769 if(mode
== Window::initialize
|| mode
== Window::reinitialize
||
770 mode
== Window::needrefresh
)
772 if(mode
== Window::initialize
)
774 OSGGETGLFUNCBYID_GL3_ES( glGenFramebuffers
,
775 osgGlGenFramebuffers
,
776 _uiFuncGenFramebuffers
,
779 osgGlGenFramebuffers(1, &uiFBOId
);
781 win
->setGLObjectId(osgid
, uiFBOId
);
785 // already has an GLid
786 uiFBOId
= win
->getGLObjectId(osgid
);
791 if(mode
== Window::initialize
|| mode
== Window::reinitialize
)
793 OSGGETGLFUNCBYID_GL3_ES( glBindFramebuffer
,
794 osgGlBindFramebuffer
,
795 _uiFuncBindFramebuffer
,
798 OSGGETGLFUNCBYID_GL3_ES( glFramebufferRenderbuffer
,
799 osgGlFramebufferRenderbuffer
,
800 _uiFuncFramebufferRenderbuffer
,
803 osgGlBindFramebuffer(GL_FRAMEBUFFER
, uiFBOId
);
805 MFUnrecFrameBufferAttachmentPtr::const_iterator attIt
=
806 _mfColorAttachments
.begin();
807 MFUnrecFrameBufferAttachmentPtr::const_iterator attEnd
=
808 _mfColorAttachments
.end ();
810 GLint iMaxColorAttachments
;
812 glGetIntegerv(GL_MAX_COLOR_ATTACHMENTS
, &iMaxColorAttachments
);
814 Int32 index
= GL_COLOR_ATTACHMENT0
;
816 iMaxColorAttachments
+= GL_COLOR_ATTACHMENT0
;
818 while(attIt
!= attEnd
&& index
< iMaxColorAttachments
)
822 (*attIt
)->bind(pEnv
, index
);
826 osgGlFramebufferRenderbuffer(GL_FRAMEBUFFER
,
832 glErr("FrameBufferObject::color");
838 while(index
< iMaxColorAttachments
)
840 osgGlFramebufferRenderbuffer(GL_FRAMEBUFFER
,
845 glErr("FrameBufferObject::coloroff");
850 if(_sfDepthAttachment
.getValue() != NULL
)
852 _sfDepthAttachment
.getValue()->bind(pEnv
,
853 GL_DEPTH_ATTACHMENT
);
857 osgGlFramebufferRenderbuffer(GL_FRAMEBUFFER
,
863 glErr("FrameBufferObject::depth");
865 if(_sfStencilAttachment
.getValue() != NULL
)
867 _sfStencilAttachment
.getValue()->bind(pEnv
,
868 GL_STENCIL_ATTACHMENT
);
872 osgGlFramebufferRenderbuffer(GL_FRAMEBUFFER
,
873 GL_STENCIL_ATTACHMENT
,
878 glErr("FrameBufferObject::stencil");
880 else if(mode
== Window::needrefresh
)
882 MFUnrecFrameBufferAttachmentPtr::const_iterator attIt
=
883 _mfColorAttachments
.begin();
884 MFUnrecFrameBufferAttachmentPtr::const_iterator attEnd
=
885 _mfColorAttachments
.end ();
887 while(attIt
!= attEnd
)
891 (*attIt
)->validate(pEnv
);
894 glErr("FrameBufferObject::refresh");
899 if(_sfDepthAttachment
.getValue() != NULL
)
901 _sfDepthAttachment
.getValue()->validate(pEnv
);
904 if(_sfStencilAttachment
.getValue() != NULL
)
906 _sfStencilAttachment
.getValue()->validate(pEnv
);
913 void FrameBufferObject::handleDestroyGL(DrawEnv
*pEnv
,
915 Window::GLObjectStatusE mode
)
917 Window
*win
= pEnv
->getWindow();
919 if(mode
== Window::destroy
)
921 GLuint uiFBOId
= win
->getGLObjectId(osgid
);
923 if(win
->hasExtOrVersion(_uiFramebufferObjectArb
,
927 OSGGETGLFUNCBYID_GL3_ES( glDeleteFramebuffers
,
928 osgGlDeleteFramebuffers
,
929 _uiFuncDeleteFramebuffers
,
932 osgGlDeleteFramebuffers(1, &uiFBOId
);
937 UInt32
FrameBufferObject::handleMultiSampleGL(
940 Window::GLObjectStatusE mode
,
943 Window
*win
= pEnv
->getWindow();
946 if(mode
== Window::initialize
|| mode
== Window::reinitialize
||
947 mode
== Window::needrefresh
)
949 if(mode
== Window::initialize
)
951 OSGGETGLFUNCBYID_GL3_ES( glGenFramebuffers
,
952 osgGlGenFramebuffers
,
953 _uiFuncGenFramebuffers
,
956 osgGlGenFramebuffers(1, &uiFBOId
);
958 win
->setGLObjectId(osgid
, uiFBOId
);
962 // already has an GLid
963 uiFBOId
= win
->getGLObjectId(osgid
);
968 if(mode
== Window::initialize
|| mode
== Window::reinitialize
)
970 OSGGETGLFUNCBYID_GL3_ES( glBindFramebuffer
,
971 osgGlBindFramebuffer
,
972 _uiFuncBindFramebuffer
,
975 OSGGETGLFUNCBYID_GL3_ES( glFramebufferRenderbuffer
,
976 osgGlFramebufferRenderbuffer
,
977 _uiFuncFramebufferRenderbuffer
,
980 osgGlBindFramebuffer(GL_FRAMEBUFFER
, uiFBOId
);
982 MFUnrecFrameBufferAttachmentPtr::const_iterator attIt
=
983 _mfMsaaColorAttachments
.begin();
984 MFUnrecFrameBufferAttachmentPtr::const_iterator attEnd
=
985 _mfMsaaColorAttachments
.end ();
987 GLint iMaxColorAttachments
;
989 glGetIntegerv(GL_MAX_COLOR_ATTACHMENTS
, &iMaxColorAttachments
);
991 Int32 index
= GL_COLOR_ATTACHMENT0
;
993 iMaxColorAttachments
+= GL_COLOR_ATTACHMENT0
;
995 while(attIt
!= attEnd
&& index
< iMaxColorAttachments
)
999 (*attIt
)->bind(pEnv
, index
);
1003 osgGlFramebufferRenderbuffer(GL_FRAMEBUFFER
,
1009 glErr("FrameBufferObject::color");
1015 while(index
< iMaxColorAttachments
)
1017 osgGlFramebufferRenderbuffer(GL_FRAMEBUFFER
,
1022 glErr("FrameBufferObject::coloroff");
1027 if(_sfMsaaDepthAttachment
.getValue() != NULL
)
1029 _sfMsaaDepthAttachment
.getValue()->bind(pEnv
,
1030 GL_DEPTH_ATTACHMENT
);
1034 osgGlFramebufferRenderbuffer(GL_FRAMEBUFFER
,
1035 GL_DEPTH_ATTACHMENT
,
1040 glErr("FrameBufferObject::depth");
1042 if(_sfMsaaStencilAttachment
.getValue() != NULL
)
1044 _sfMsaaStencilAttachment
.getValue()->bind(
1046 GL_STENCIL_ATTACHMENT
);
1050 osgGlFramebufferRenderbuffer(GL_FRAMEBUFFER
,
1051 GL_STENCIL_ATTACHMENT
,
1056 glErr("FrameBufferObject::stencil");
1058 else if(mode
== Window::needrefresh
)
1060 MFUnrecFrameBufferAttachmentPtr::const_iterator attIt
=
1061 _mfMsaaColorAttachments
.begin();
1062 MFUnrecFrameBufferAttachmentPtr::const_iterator attEnd
=
1063 _mfMsaaColorAttachments
.end ();
1065 while(attIt
!= attEnd
)
1069 (*attIt
)->validate(pEnv
);
1072 glErr("FrameBufferObject::refresh");
1077 if(_sfMsaaDepthAttachment
.getValue() != NULL
)
1079 _sfMsaaDepthAttachment
.getValue()->validate(pEnv
);
1082 if(_sfMsaaStencilAttachment
.getValue() != NULL
)
1084 _sfMsaaStencilAttachment
.getValue()->validate(pEnv
);
1092 FrameBufferAttachmentTransitPtr
1093 FrameBufferObject::createMultiSampleBufferFrom(FrameBufferAttachment
*pSrc
)
1095 RenderBufferUnrecPtr returnValue
= NULL
;
1098 return FrameBufferAttachmentTransitPtr(returnValue
);
1101 returnValue
= RenderBuffer::create();
1103 returnValue
->setInternalFormat(pSrc
->getBufferFormat());
1105 returnValue
->setWidth (pSrc
->getWidth ());
1106 returnValue
->setHeight(pSrc
->getHeight());
1108 returnValue
->setColorSamples (this->getColorSamples ());
1109 returnValue
->setCoverageSamples (this->getCoverageSamples ());
1110 returnValue
->setFixedSampleLocation(this->getFixedSampleLocation());
1112 return FrameBufferAttachmentTransitPtr(returnValue
);
1115 void FrameBufferObject::activateFBOById(DrawEnv
*pEnv
, UInt32 uiOSGId
)
1120 Window
*win
= pEnv
->getWindow();
1122 if(win
->hasExtOrVersion(_uiFramebufferObjectArb
, 0x0300, 0x0200) == false)
1124 FNOTICE(("Framebuffer objects not supported on Window %p!\n",
1125 static_cast<void *>(win
)));
1129 OSGGETGLFUNCBYID_GL3_ES( glBindFramebuffer
,
1130 osgGlBindFramebuffer
,
1131 _uiFuncBindFramebuffer
,
1134 win
->validateGLObject(uiOSGId
, pEnv
);
1136 osgGlBindFramebuffer(GL_FRAMEBUFFER
,
1137 win
->getGLObjectId(uiOSGId
));
1139 pEnv
->setActiveFBO(uiOSGId
);
1142 void FrameBufferObject::deactivateFBOById(DrawEnv
*pEnv
)
1144 Window
*win
= pEnv
->getWindow();
1146 if(win
->hasExtOrVersion(_uiFramebufferObjectArb
, 0x0300, 0x0200) == false)
1148 FNOTICE(("Framebuffer objects not supported on Window %p!\n",
1149 static_cast<void *>(win
)));
1153 OSGGETGLFUNCBYID_GL3_ES( glBindFramebuffer
,
1154 osgGlBindFramebuffer
,
1155 _uiFuncBindFramebuffer
,
1158 osgGlBindFramebuffer(GL_FRAMEBUFFER
,
1161 pEnv
->setActiveFBO(0);