From 4e69d46289047cb6ea39c9c8896837d31c7b7c2b Mon Sep 17 00:00:00 2001 From: Robert Osfield Date: Wed, 27 Jul 2005 11:27:44 +0000 Subject: [PATCH] Further work on trying to get glGenerateMipMapEXT working in conjunction with frame buffer objects. Still don't work under Linux yet through :-| --- include/osg/FrameBufferObject | 1 + include/osg/Texture | 9 +++++ include/osg/Texture1D | 6 +-- include/osg/Texture2D | 6 +-- include/osg/Texture3D | 6 +-- include/osg/TextureCubeMap | 6 +-- include/osg/TextureRectangle | 6 +-- src/osg/FrameBufferObject.cpp | 47 +++++++++++++++++++++- src/osgUtil/RenderToTextureStage.cpp | 59 ++++++++-------------------- 9 files changed, 77 insertions(+), 69 deletions(-) diff --git a/include/osg/FrameBufferObject b/include/osg/FrameBufferObject index e3132560a..ef306e46d 100644 --- a/include/osg/FrameBufferObject +++ b/include/osg/FrameBufferObject @@ -263,6 +263,7 @@ namespace osg FrameBufferAttachment &operator = (const FrameBufferAttachment ©); + void createRequiredTexturesAndApplyGenerateMipMap(State &state, const FBOExtensions* ext) const; void attach(State &state, GLenum attachment_point, const FBOExtensions* ext) const; int compare(const FrameBufferAttachment &fa) const; diff --git a/include/osg/Texture b/include/osg/Texture index 9b8388161..d3e7f156f 100644 --- a/include/osg/Texture +++ b/include/osg/Texture @@ -207,6 +207,15 @@ class OSG_EXPORT Texture : public osg::StateAttribute virtual bool isTextureAttribute() const { return true; } + + virtual GLenum getTextureTarget() const = 0; + + virtual bool getModeUsage(ModeUsage& usage) const + { + usage.usesTextureMode(getTextureTarget()); + return true; + } + enum WrapParameter { WRAP_S, WRAP_T, diff --git a/include/osg/Texture1D b/include/osg/Texture1D index 34a4ff301..912290665 100644 --- a/include/osg/Texture1D +++ b/include/osg/Texture1D @@ -38,11 +38,7 @@ class OSG_EXPORT Texture1D : public Texture /** Return -1 if *this < *rhs, 0 if *this==*rhs, 1 if *this>*rhs. */ virtual int compare(const StateAttribute& rhs) const; - virtual bool getModeUsage(ModeUsage& usage) const - { - usage.usesTextureMode(GL_TEXTURE_1D); - return true; - } + virtual GLenum getTextureTarget() const { return GL_TEXTURE_1D; } /** Sets the texture image. */ void setImage(Image* image); diff --git a/include/osg/Texture2D b/include/osg/Texture2D index dd060556a..5c0394d8b 100644 --- a/include/osg/Texture2D +++ b/include/osg/Texture2D @@ -38,11 +38,7 @@ class OSG_EXPORT Texture2D : public Texture /** Return -1 if *this < *rhs, 0 if *this==*rhs, 1 if *this>*rhs. */ virtual int compare(const StateAttribute& rhs) const; - virtual bool getModeUsage(ModeUsage& usage) const - { - usage.usesTextureMode(GL_TEXTURE_2D); - return true; - } + virtual GLenum getTextureTarget() const { return GL_TEXTURE_2D; } /** Sets the texture image. */ void setImage(Image* image); diff --git a/include/osg/Texture3D b/include/osg/Texture3D index ee60d3a11..f09ffe361 100644 --- a/include/osg/Texture3D +++ b/include/osg/Texture3D @@ -36,11 +36,7 @@ class OSG_EXPORT Texture3D : public Texture /** Return -1 if *this < *rhs, 0 if *this==*rhs, 1 if *this>*rhs. */ virtual int compare(const StateAttribute& rhs) const; - virtual bool getModeUsage(ModeUsage& usage) const - { - usage.usesTextureMode(GL_TEXTURE_3D); - return true; - } + virtual GLenum getTextureTarget() const { return GL_TEXTURE_3D; } /** Sets the texture image. */ void setImage(Image* image); diff --git a/include/osg/TextureCubeMap b/include/osg/TextureCubeMap index c62720178..6ee9f25f2 100644 --- a/include/osg/TextureCubeMap +++ b/include/osg/TextureCubeMap @@ -47,11 +47,7 @@ class OSG_EXPORT TextureCubeMap : public Texture /** Return -1 if *this < *rhs, 0 if *this==*rhs, 1 if *this>*rhs. */ virtual int compare(const StateAttribute& rhs) const; - virtual bool getModeUsage(ModeUsage& usage) const - { - usage.usesTextureMode(GL_TEXTURE_CUBE_MAP); - return true; - } + virtual GLenum getTextureTarget() const { return GL_TEXTURE_CUBE_MAP; } enum Face { POSITIVE_X=0, diff --git a/include/osg/TextureRectangle b/include/osg/TextureRectangle index 7f384597b..eef352c1c 100644 --- a/include/osg/TextureRectangle +++ b/include/osg/TextureRectangle @@ -44,11 +44,7 @@ class OSG_EXPORT TextureRectangle : public Texture /** Return -1 if *this < *rhs, 0 if *this==*rhs, 1 if *this>*rhs. */ virtual int compare(const StateAttribute& rhs) const; - virtual bool getModeUsage(ModeUsage& usage) const - { - usage.usesTextureMode(GL_TEXTURE_RECTANGLE); - return true; - } + virtual GLenum getTextureTarget() const { return GL_TEXTURE_RECTANGLE; } /** Set the texture image. */ void setImage(Image* image); diff --git a/src/osg/FrameBufferObject.cpp b/src/osg/FrameBufferObject.cpp index c436b53cc..e599c11d5 100644 --- a/src/osg/FrameBufferObject.cpp +++ b/src/osg/FrameBufferObject.cpp @@ -272,7 +272,7 @@ FrameBufferAttachment &FrameBufferAttachment::operator = (const FrameBufferAttac return *this; } -void FrameBufferAttachment::attach(State &state, GLenum attachment_point, const FBOExtensions* ext) const +void FrameBufferAttachment::createRequiredTexturesAndApplyGenerateMipMap(State &state, const FBOExtensions* ext) const { unsigned int contextID = state.getContextID(); @@ -285,11 +285,41 @@ void FrameBufferAttachment::attach(State &state, GLenum attachment_point, const { _ximpl->textureTarget->compileGLObjects(state); tobj = _ximpl->textureTarget->getTextureObject(contextID); + + } + if (!tobj || tobj->_id == 0) + return; + + Texture::FilterMode minFilter = _ximpl->textureTarget->getFilter(Texture::MIN_FILTER); + if (minFilter==Texture::LINEAR_MIPMAP_LINEAR || + minFilter==Texture::LINEAR_MIPMAP_NEAREST || + minFilter==Texture::NEAREST_MIPMAP_LINEAR || + minFilter==Texture::NEAREST_MIPMAP_NEAREST) + { + ext->glGenerateMipmapEXT(_ximpl->textureTarget->getTextureTarget()); + } + + } +} + +void FrameBufferAttachment::attach(State &state, GLenum attachment_point, const FBOExtensions* ext) const +{ + unsigned int contextID = state.getContextID(); + + Texture::TextureObject *tobj = 0; + if (_ximpl->textureTarget.valid()) + { + tobj = _ximpl->textureTarget->getTextureObject(contextID); + if (!tobj || tobj->_id == 0) + { + _ximpl->textureTarget->compileGLObjects(state); + tobj = _ximpl->textureTarget->getTextureObject(contextID); + } if (!tobj || tobj->_id == 0) return; } - + switch (_ximpl->targetType) { default: @@ -379,9 +409,22 @@ void FrameBufferObject::apply(State &state) const notify(WARN) << "Warning: FrameBufferObject: could not create the FBO" << std::endl; return; } + dirtyAttachmentList = 1; + } + if (dirtyAttachmentList) + { + // create textures and mipmaps before we bind the frame buffer object + for (AttachmentMap::const_iterator i=_attachments.begin(); i!=_attachments.end(); ++i) + { + const FrameBufferAttachment &fa = i->second; + fa.createRequiredTexturesAndApplyGenerateMipMap(state, ext); + } + + } + ext->glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, fboID); if (dirtyAttachmentList) diff --git a/src/osgUtil/RenderToTextureStage.cpp b/src/osgUtil/RenderToTextureStage.cpp index f6d7234b4..d8bb748d2 100644 --- a/src/osgUtil/RenderToTextureStage.cpp +++ b/src/osgUtil/RenderToTextureStage.cpp @@ -16,6 +16,7 @@ #include #include #include +#include using namespace osg; using namespace osgUtil; @@ -43,35 +44,12 @@ void RenderToTextureStage::reset() RenderStage::reset(); } -class GenerateMipMapHelper : public StateAttribute::ModeUsage -{ - public: - GenerateMipMapHelper(osg::FBOExtensions* fbo_ext): - _fbo_ext(fbo_ext) {} - - virtual ~GenerateMipMapHelper() {} - - virtual void usesMode(StateAttribute::GLMode) - { - } - - virtual void usesTextureMode(StateAttribute::GLMode mode) - { - _fbo_ext->glGenerateMipmapEXT((GLenum)mode); - } - - osg::FBOExtensions* _fbo_ext; - -}; - void RenderToTextureStage::draw(osg::State& state,RenderLeaf*& previous) { if (_stageDrawnThisFrame) return; - state.checkGLErrors("beginning of RenderToTextureStage::draw()"); - //cout << "begining RTTS draw "<x()<<","<< _viewport->y()<<","<< _viewport->width()<<","<< _viewport->height()<readPixels(_viewport->x(),_viewport->y(),_viewport->width(),_viewport->height(),_imageReadPixelFormat,_imageReadPixelDataType); } - if (fbo_supported && _camera) - { - // now generate mipmaps if they are required. - const osg::CameraNode::BufferAttachmentMap& bufferAttachements = _camera->getBufferAttachmentMap(); - for(osg::CameraNode::BufferAttachmentMap::const_iterator itr = bufferAttachements.begin(); - itr != bufferAttachements.end(); - ++itr) - { - if (itr->second._texture.valid() && itr->second._mipMapGeneration) - { - itr->second._texture->apply(*useState); - GenerateMipMapHelper generateMipMap(fbo_ext); - itr->second._texture->getModeUsage(generateMipMap); - } - } - } if (_camera && _camera->getPostDrawCallback()) { @@ -176,6 +138,22 @@ void RenderToTextureStage::draw(osg::State& state,RenderLeaf*& previous) // switch of the frame buffer object fbo_ext->glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0); } + + if (fbo_supported && _camera) + { + // now generate mipmaps if they are required. + const osg::CameraNode::BufferAttachmentMap& bufferAttachements = _camera->getBufferAttachmentMap(); + for(osg::CameraNode::BufferAttachmentMap::const_iterator itr = bufferAttachements.begin(); + itr != bufferAttachements.end(); + ++itr) + { + if (itr->second._texture.valid() && itr->second._mipMapGeneration) + { + itr->second._texture->apply(*useState); + // fbo_ext->glGenerateMipmapEXT(itr->second._texture->getTextureTarget()); + } + } + } if (callingContext && useContext != callingContext) { @@ -184,8 +162,5 @@ void RenderToTextureStage::draw(osg::State& state,RenderLeaf*& previous) glReadBuffer(GL_BACK); } - - state.checkGLErrors("end of RenderToTextureStage::draw()"); - }