There are some mysteries, implementing a simple colorPicking with QOpenGL in-built tools.
Context : I've an application, owning its own OGL widget. For some reasons (multi-widgets), I had to change my QGLWidget by a QOpenGLWidget which allows me easily to have many OpenGL contexts without (a priori) any problems. This change actually broke my color Picking and I'm then investigating:
I previously did this so as to get my object:
glClear(GL_DEPTH_BUFFER_BIT | GL_COLOR_BUFFER_BIT);
// render every object in our scene
ShaderLib::bindShader(ShaderLib::PICKING_SHADER);
{
for(auto const& _3dobject : model_->getObjects())
_3dobject.second->draw(projection_, cameraview_, true);
}
ShaderLib::unbind();
glFlush();
glFinish();
// get color information from frame buffer
float pixel[4];
GLint viewport[4];
glGetIntegerv(GL_VIEWPORT, viewport);
glReadPixels(event->x(), viewport[3] - event->y(), 1, 1, GL_RGBA, GL_FLOAT, pixel)
This perfectly worked with the QGLWidget. I could get the pixel, then the matching object. I saved my pixels in QImage to confirm and I exactly had what was expected.
After changing QGLWidget by QOpenGLWidget :
Then, with the QOpenGLWidget, the above code didn't work. Worst : glReadPixels seems to not reading in the back framebuffer. How do I know ? I simply displayed the whole supposed buffer read via glReadPixels, as before, and it gives me a partial screenshot of my application but not my QOPenGLWidget :O, what means that now, glReadPixels has a different behavior according to QGLWidget or QOpenGLWidget !
Well. Never give up !
I try to get the framebuffer through QOpenGLWidget::grabFrameBuffer(); It creates a QImage of the... I don't know what buffer.
glClear(GL_DEPTH_BUFFER_BIT | GL_COLOR_BUFFER_BIT);
// render every object in our scene
ShaderLib::bindShader(ShaderLib::PICKING_SHADER);
{
for(auto const& _3dobject : model_->getObjects())
_3dobject.second->draw(projection_, cameraview_, true);
}
ShaderLib::unbind();
glFlush();
glFinish();
QImage fb = grabFramebuffer();
This prints me an image of the framebuffer drawn in my paintGL() function, which is different from the one rendered in my MousePressEvent() (where I render with a specific 'picking' shader...
Hoped you followed everything. To sum up :
- Does anyone understand why glReadPixels gives a different result between the two 'painters' used ? I certainly missed something
- Does anyone gets how double-buffering is working with QOpenGLWidget ? It seems that the user cannot really choose what's happening.