[osg-users] QtQuickFrameBufferObject and GraphicsContexts
Antoine Rennuit
antoinerennuit at hotmail.com
Tue Aug 22 09:52:07 PDT 2017
Hi all
I have integrated OSG within QQuick 2 via QtQuickFramebufferObject, it is working great with complex scenes and within a complex application behind the hood, except for 1 point: I sometimes observe flickering of the whole window (it is not only the 3d view that flickers but the whole application window - check the video here (https://youtu.be/NlAxvTAVpl0)). It is not periodic, only every now and then, it can get crazy for a few seconds and then calms down.
In QtQuick the windowing system is actually rendered in OpenGL (hence the complexity). QtQuickFramebufferObject provides you with the tools to design a custom 3d item, and is thus the preferred way to implement a 3d view.
QtQuickFramebufferObject has you define a renderer and create a Qt compatible GL framebuffer in a function called by the QtQuick framework
Code:
QOpenGLFramebufferObject* OsgRenderer::createFramebufferObject(const QSize &size)
{
QOpenGLFramebufferObjectFormat format;
format.setAttachment(QOpenGLFramebufferObject::CombinedDepthStencil);
return new QOpenGLFramebufferObject(size, format);
}
it then has you write a render function also called by the QtQuick 2 framework, this is where I call my OSG rendering
Code:
void OsgRenderer::render()
{
assert(m_osgItem);
if ( !m_osgItem->getViewer() )
return;
// Without this line the model is not displayed in the second
// and subsequent frames.
QOpenGLContext::currentContext()->functions()->glUseProgram(0);
// Ask OSG to render.
m_osgItem->getViewer()->frame(); // WARNING: non-blocking (executed in a thread of its own - in a thread-safe way).
// Reset OpenGl state for QtQuick.
m_osgItem->window()->resetOpenGLState();
}
The QtQuick framework then merges the framebuffer in which I rendered with its own rendering to display the final image.
Now I suspect my flickering issue comes from a problem of GL context mix-up between QtQuick and OSG.
So I have inherited osgViewer::GraphicsWindowEmbedded to use as custom GraphicsContext which binds and releases the framebuffer created above:
Code:
bool OsgWindow::makeCurrentImplementation()
{
if (!m_renderer)
return false;
if (!m_renderer->framebufferObject())
return false;
return m_renderer->framebufferObject()->bind();
}
bool OsgWindow::releaseContextImplementation()
{
if (!m_renderer)
return false;
if (!m_renderer->framebufferObject())
return false;
return m_renderer->framebufferObject()->release();
}
Does that ensure me that the OSG rendering in frame() is written to this FBO?
Also as far as I know, the GL context is kept in OsgWindow (it inherits osgViewer::GraphicsWindowEmbedded as stated above), but is it reapplied at each frame? i.e. the GL context is modified by QtQuick's own GL rendering but am I sure that it is put back in place for OSG's correct rendering when I call frame()? If not, is there a way for me to enforce OSG's GL context is not modified by QtQuick?
Thanks a lot,
Antoine
------------------
Read this topic online here:
http://forum.openscenegraph.org/viewtopic.php?p=71500#71500
More information about the osg-users
mailing list