Я пишу для своего приложения средство визуализации векторной графики на основе OpenGL. Он должен отображаться в объекте фреймбуфера, а не непосредственно на экране. Поскольку я пишу приложение на Qt, я использую QGLFramebufferObject, который является классом-оболочкой для объекта фреймбуфера OpenGL.
Я создал минимальный пример, который показывает неправильный результат, который я также получаю при рендеринге более сложных вещей (например, с использованием фрагментного шейдера, который устанавливает цвета с не равным единице альфа-значением). Я просто визуализирую красный кружок и полупрозрачный зеленый кружок на черном экране, а затем то же самое в FBO:
void MainWidget::initializeGL()
{
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
glClearColor(0, 0, 0, 0);
}
void MainWidget::resizeGL(int w, int h)
{
glViewport(0, 0, w, h);
}
void MainWidget::paintGL()
{
// DRAW ON THE SCREEN
{
glClear(GL_COLOR_BUFFER_BIT);
glPointSize(100);
glEnable(GL_POINT_SMOOTH);
glBegin(GL_POINTS);
glColor4f(1, 0, 0, 1);
glVertex2f(-.2, 0);
glColor4f(0, 1, 0, .5);
glVertex2f( .2, 0);
glEnd();
}
QGLFramebufferObject fbo(width(), height());
fbo.bind();
// DRAW ON THE FBO USING THE SAME CODE AND THE SAME CONTEXT
{
glClear(GL_COLOR_BUFFER_BIT);
glPointSize(100);
glEnable(GL_POINT_SMOOTH);
glBegin(GL_POINTS);
glColor4f(1, 0, 0, 1);
glVertex2f(-.2, 0);
glColor4f(0, 1, 0, .5);
glVertex2f( .2, 0);
glEnd();
}
fbo.release();
fbo.toImage().save("debug.png");
}
Результат на экране (масштаб 400%) выглядит так:
Рендеринг QGLFramebufferObject выглядит следующим образом (также масштабируется на 400%):
Обратите внимание, что это изображение не полностью непрозрачно, поэтому здесь это то же изображение с добавленной за ним шахматной доской:
Даже область, в которой два круга перекрываются, не полностью непрозрачна. Да и сглаживание выглядит довольно некрасиво.
Как это происходит? И как я могу это исправить?
Я уже пробовал:
- Различные функции наложения.
- Явное отключение буфера глубины, буфера трафарета и выборки в QGLFramebufferObject. Я не уверен, добавляет ли формат по умолчанию QGLFramebufferObject то, что мне не нужно.