Класс QOpenGLWindow
Класс QOpenGLWindow — это удобное подклассовое расширение класса QWindow для выполнения отрисовки OpenGL. Подробнее...
| Заголовок: | #include <QOpenGLWindow> |
| qmake: | QT += gui |
| С момента: | Qt 5.4 |
| Наследует: | QPaintDeviceWindow |
Открытые типы
| Перечисление | UpdateBehavior { NoPartialUpdate, PartialUpdateBlit, PartialUpdateBlend } |
Открытые функции
| QOpenGLWindow(QOpenGLWindow::UpdateBehavior updateBehavior = NoPartialUpdate, QWindow *parent = nullptr) | |
| QOpenGLWindow(QOpenGLContext *shareContext, QOpenGLWindow::UpdateBehavior updateBehavior = NoPartialUpdate, QWindow *parent = nullptr) | |
| виртуальный | ~QOpenGLWindow() |
| QOpenGLContext * | context() const |
| GLuint | defaultFramebufferObject() const |
| void | doneCurrent() |
| QImage | grabFramebuffer() |
| bool | isValid() const |
| void | makeCurrent() |
| QOpenGLContext * | shareContext() const |
| QOpenGLWindow::UpdateBehavior | updateBehavior() const |
- 2 открытые функции, унаследованные от QPaintDeviceWindow
- 82 открытые функции, унаследованные от QWindow
- 14 открытых функций, унаследованных от QPaintDevice
- 31 открытая функция, унаследованная от QObject
- 6 открытых функций, унаследованных от QSurface
Сигналы
| void | frameSwapped() |
Статические открытые члены
| const QMetaObject | staticMetaObject |
- 1 статический открытый член, унаследованный от QWindow
- 9 статических открытых членов, унаследованных от QObject
Защищенные функции
| виртуальный void | initializeGL() |
| виртуальный void | paintGL() |
| виртуальный void | paintOverGL() |
| виртуальный void | paintUnderGL() |
| виртуальный void | resizeGL(int w, int h) |
Переопределенные защищенные функции
| виртуальный void | paintEvent(QPaintEvent *event) override |
| виртуальный void | resizeEvent(QResizeEvent *event) override |
- 1 защищенная функция, унаследованная от QPaintDeviceWindow
- 18 защищенных функций, унаследованных от QWindow
- 1 защищенная функция, унаследованная от QPaintDevice
- 9 защищенных функций, унаследованных от QObject
Дополнительные унаследованные члены
- 16 свойств, унаследованных от QWindow
- 1 свойство, унаследованное от QObject
- 1 открытый слот, унаследованный от QPaintDeviceWindow
- 24 открытых слота, унаследованных от QWindow
- 1 открытый слот, унаследованный от QObject
Подробное описание
Класс QOpenGLWindow — это удобное подклассовое расширение класса QWindow для выполнения отрисовки OpenGL.
QOpenGLWindow — это расширенный класс QWindow, который позволяет легко создавать окна, выполняющие отрисовку OpenGL с помощью API, совместимого с QOpenGLWidget и аналогичного устаревшему QGLWidget. В отличие от QOpenGLWidget, QOpenGLWindow не зависит от модуля виджетов и предлагает лучшую производительность.
Типичное приложение подклассирует QOpenGLWindow и переопределяет следующие виртуальные функции:
- initializeGL() для инициализации ресурсов OpenGL
- resizeGL() для настройки матриц преобразования и других ресурсов, зависящих от размера окна
- paintGL() для выполнения команд OpenGL или рисования с помощью QPainter
Для планирования перерисовки вызовите функцию update(). Обратите внимание, что это не приведет к немедленному вызову paintGL(). Вызов update() несколько раз подряд не изменит поведение никоим образом.
Это слот, поэтому он может быть подключен к сигналу QTimer::timeout() для выполнения анимации. Однако в современном мире OpenGL гораздо лучшим выбором является использование синхронизации с частотой вертикальной развертки дисплея. См. setSwapInterval() для описания интервала переключения. При интервале переключения 1, который по умолчанию используется на большинстве систем, вызов swapBuffers(), который выполняется внутри QOpenGLWindow после каждой перерисовки, будет блокировать и ожидать vsync. Это означает, что всякий раз, когда происходит переключение, обновление можно запланировать снова, вызвав update(), не полагаясь на таймеры.
Для запроса определенной конфигурации контекста используйте setFormat() как для любого другого QWindow. Это позволяет, среди прочего, запросить определенную версию и профиль OpenGL, или включить буферы глубины и трафарета.
В отличие от QWindow, QOpenGLWindow позволяет открыть painter на себе и выполнять рисование на основе QPainter.
QOpenGLWindow поддерживает несколько вариантов поведения обновления. По умолчанию, NoPartialUpdate эквивалентен стандартному, OpenGL-основанному QWindow или устаревшему QGLWidget. В отличие от этого, PartialUpdateBlit и PartialUpdateBlend более соответствуют способу работы QOpenGLWidget, где всегда присутствует дополнительный, выделенный объект framebuffer. Эти режимы позволяют, жертвуя некоторой производительностью, перерисовывать только меньшую область при каждой отрисовке и сохранять остальное содержимое из предыдущего кадра. Это полезно для приложений, которые рисуют по частям с помощью QPainter, поскольку таким образом им не нужно перерисовывать всё содержимое окна при каждом вызове paintGL().
Аналогично QOpenGLWidget, QOpenGLWindow поддерживает атрибут Qt::AA_ShareOpenGLContexts. При включении, контексты OpenGL всех экземпляров QOpenGLWindow будут совместно использоваться. Это позволяет обращаться к общим ресурсам OpenGL друг друга.
Дополнительную информацию об графике в Qt см. в разделе Графика.
Документация по типу членов
перечисление QOpenGLWindow::UpdateBehavior
Этот перечисление описывает стратегию обновления окна QOpenGLWindow.
| Постоянная | Значение | Описание |
|---|---|---|
QOpenGLWindow::NoPartialUpdate |
0 |
Указывает, что вся поверхность окна будет перерисована при каждом обновлении, и поэтому дополнительные буферы кадров не нужны. Это значение используется в большинстве случаев и эквивалентно способу рисования непосредственно через QWindow. |
QOpenGLWindow::PartialUpdateBlit |
1 |
Указывает, что отрисовка, выполненная в paintGL(), не охватывает всё окно. В этом случае под капотом создаётся дополнительный буфер кадра, и отрисовка, выполненная в paintGL(), будет нацелена на этот буфер. Затем этот буфер копируется в основной буфер поверхности окна после каждого отрисовки. Это позволяет использовать код рисования на основе QPainter в paintGL(), который перерисовывает только меньшую область за раз, потому что, в отличие от NoPartialUpdate, предыдущее содержимое сохраняется. |
QOpenGLWindow::PartialUpdateBlend |
2 |
Аналогично PartialUpdateBlit, но вместо копирования буфера кадра используется отрисовка текстурированного квадрата с включённым смешением. Это, в отличие от PartialUpdateBlit, позволяет использовать альфа-смешение и работает даже при отсутствии glBlitFramebuffer. С точки зрения производительности, это значение, вероятно, будет несколько медленнее, чем PartialUpdateBlit. |
Документация по членам-функциям
QOpenGLWindow::QOpenGLWindow(QOpenGLWindow::UpdateBehavior updateBehavior = NoPartialUpdate, QWindow *parent = nullptr)
Создаёт новый объект QOpenGLWindow с заданным parent и updateBehavior.
См. также QOpenGLWindow::UpdateBehavior.
QOpenGLWindow::QOpenGLWindow(QOpenGLContext *shareContext, QOpenGLWindow::UpdateBehavior updateBehavior = NoPartialUpdate, QWindow *parent = nullptr)
Создаёт новый объект QOpenGLWindow с заданным parent и updateBehavior. Контекст QOpenGLWindow будет совместно использоваться с shareContext.
См. также QOpenGLWindow::UpdateBehavior и shareContext.
[virtual] QOpenGLWindow::~QOpenGLWindow()
Удаляет экземпляр QOpenGLWindow, освобождая его ресурсы.
Контекст OpenGLWindow становится текущим в деструкторе, что позволяет безопасно удалить любой дочерний объект, которому может потребоваться освободить ресурсы OpenGL, принадлежащие контексту, предоставляемому этим окном.
Предупреждение: если у вас есть объекты, обертывающие ресурсы OpenGL (например, QOpenGLBuffer, QOpenGLShaderProgram и т.д.) в качестве членов подкласса QOpenGLWindow, вам может потребоваться добавить вызов makeCurrent() также в деструкторе этого подкласса. Из-за правил уничтожения объектов C++, эти объекты будут уничтожены *до* вызова этой функции (но после того, как выполнится деструктор подкласса), поэтому сделать контекст OpenGL текущим в этой функции произойдёт слишком поздно для их безопасного удаления.
Эта функция была добавлена в Qt 5.5.
См. также makeCurrent.
QOpenGLContext *QOpenGLWindow::context() const
Возвращает QOpenGLContext, используемый этим окном, или 0, если он ещё не инициализирован.
GLuint QOpenGLWindow::defaultFramebufferObject() const
Обработчик буфера кадра, используемого этим окном.
Когда поведение обновления установлено в NoPartialUpdate, нет отдельного буфера кадра. В этом случае возвращаемое значение — идентификатор основного буфера кадра.
В противном случае значение — идентификатор буфера кадра или 0, если он ещё не инициализирован.
void QOpenGLWindow::doneCurrent()
Освобождает контекст.
В большинстве случаев вызывать эту функцию не обязательно, так как виджет позаботится о том, чтобы контекст был привязан и высвобождён должным образом при вызове paintGL().
См. также makeCurrent().
[signal] void QOpenGLWindow::frameSwapped()
Этот сигнал излучается после потенциально блокирующего обмена буферами буферов. Приложения, которые хотят непрерывно перерисовывать, синхронизируясь с вертикальной разверткой, должны вызвать update() при поступлении этого сигнала. Это позволяет добиться гораздо более плавной работы по сравнению с традиционным использованием таймеров.
QImage QOpenGLWindow::grabFramebuffer()
Возвращает копию буфера кадра.
Примечание: это потенциально дорогостоящая операция, так как она полагается на glReadPixels() для считывания пикселей. Это может быть медленным и может блокировать обработку графического процессора.
Примечание: При использовании с поведением обновления NoPartialUpdate, возвращаемый образ может не содержать необходимого содержимого, если вызывается после обмена переднего и заднего буферов (если включена сохраняемая замена в интерфейсе оконной системы). В этом режиме функция считывает данные из заднего буфера, и содержимое этого буфера может не совпадать с содержимым на экране (передний буфер). В этом случае единственным местом, где эта функция может безопасно использоваться, является paintGL() или paintOverGL().
[virtual protected] void QOpenGLWindow::initializeGL()
Эта виртуальная функция вызывается один раз перед первым вызовом paintGL() или resizeGL(). Переопределите её в подклассе.
В этой функции должны быть настроены необходимые ресурсы и состояние OpenGL.
Вызывать makeCurrent() не нужно, так как это уже сделано при вызове этой функции. Однако обратите внимание, что буфер кадра в случае использования режима частичного обновления ещё недоступен на этом этапе, поэтому избегайте вызова команд отрисовки отсюда. Отложите такие вызовы до paintGL() вместо этого.
См. также paintGL() и resizeGL().
bool QOpenGLWindow::isValid() const
Возвращает true, если ресурсы OpenGL окна, такие как контекст, были успешно инициализированы. Обратите внимание, что возвращаемое значение всегда false до тех пор, пока окно не станет видимым.
void QOpenGLWindow::makeCurrent()
Подготавливает отображение содержимого OpenGL для этого окна, сделав соответствующий контекст текущим и привязав буфер кадра, если он есть, в этом контексте.
В большинстве случаев вызывать эту функцию не нужно, так как она вызывается автоматически перед вызовом paintGL(). Она предоставляется, чтобы поддерживать сложные, многопоточные сценарии, когда поток, отличный от потока пользовательского интерфейса или основного потока, может захотеть обновить содержимое поверхности или буфера кадра. Подробнее о проблемах, связанных с потоками, см. в QOpenGLContext.
Эта функция подходит для вызова также и тогда, когда базовое оконное приложение уже уничтожено. Это означает, что эту функцию безопасно вызывать из деструктора подкласса QOpenGLWindow. Если более нет нативного окна, вместо него используется поверхностный буфер. Это гарантирует, что операции по очистке ресурсов OpenGL в деструкторе всегда будут работать, если сначала вызывается эта функция.
См. также QOpenGLContext, context(), paintGL() и doneCurrent().
[override virtual protected] void QOpenGLWindow::paintEvent(QPaintEvent *event)
Переопределяет метод QPaintDeviceWindow::paintEvent().
Обработчик события рисования event. Вызывает paintGL().
См. также paintGL().
[virtual protected] void QOpenGLWindow::paintGL()
Эта виртуальная функция вызывается всякий раз, когда требуется перерисовать содержимое окна. Переопределите её в подклассе.
Вызывать makeCurrent() не нужно, так как это уже сделано при вызове этой функции.
Перед вызовом этой функции контекст и буфер кадра, если он есть, привязываются, и область просмотра настраивается с помощью вызова glViewport(). Никакие другие состояния не устанавливаются, и никакое очищение или отрисовка не выполняются фреймворком.
Примечание: При использовании поведения частичного обновления, такого как PartialUpdateBlend, результат предыдущего вызова paintGL() сохраняется, и после дополнительной отрисовки, выполненной в текущем вызове функции, содержимое копируется или накладывается поверх содержимого, нарисованного напрямую в окне в paintUnderGL().
См. также initializeGL(), resizeGL(), paintUnderGL(), paintOverGL() и UpdateBehavior.
[virtual protected] void QOpenGLWindow::paintOverGL()
Эта виртуальная функция вызывается после каждого вызова paintGL().
Когда режим обновления установлен в NoPartialUpdate, между этой функцией и paintGL() нет разницы; выполнение отрисовки в любой из них приводит к одному результату.
Как и paintUnderGL(), отрисовка в этой функции направлена на буфер кадров по умолчанию окна, независимо от режима обновления. Она вызывается после того, как paintGL() вернула управление и выполнено перемещение (PartialUpdateBlit) или построение квадриков (PartialUpdateBlend).
См. также paintGL(), paintUnderGL() и UpdateBehavior.
[virtual protected] void QOpenGLWindow::paintUnderGL()
Виртуальная функция вызывается перед каждым вызовом paintGL().
Когда режим обновления установлен в NoPartialUpdate, между этой функцией и paintGL() нет разницы; выполнение отрисовки в любой из них приводит к одному результату.
Разница становится значимой при использовании PartialUpdateBlend, где используется дополнительный объект буфера кадров. Там paintGL() направлена на этот дополнительный объект буфера кадров, сохраняя его содержимое, в то время как paintUnderGL() и paintOverGL() направлены на буфер кадров по умолчанию, то есть непосредственно на поверхность окна, содержимое которого теряется после каждого отображенного кадра.
Примечание: Избегайте полагаться на эту функцию, когда режим обновления равен PartialUpdateBlit. Этот режим включает перемещение дополнительного буфера кадров, используемого paintGL(), на буфер кадров по умолчанию после каждого вызова paintGL(), тем самым перезаписывая всю отрисовку, сгенерированную в этой функции.
См. также paintGL(), paintOverGL() и UpdateBehavior.
[override virtual protected] void QOpenGLWindow::resizeEvent(QResizeEvent *event)
Переопределено из QWindow::resizeEvent().
Обработчик события изменения размера. Вызывает resizeGL().
См. также resizeGL().
[virtual protected] void QOpenGLWindow::resizeGL(int w, int h)
Эта виртуальная функция вызывается всякий раз, когда виджет был изменён по размеру. Переопределите её в подклассе. Новый размер передаётся в w и h.
Примечание: Это просто вспомогательная функция, чтобы обеспечить API, совместимый с QOpenGLWidget. В отличие от QOpenGLWidget, производные классы могут выбрать переопределение resizeEvent() вместо этой функции.
Примечание: Избегайте выполнения команд OpenGL из этой функции, так как контекст может быть не активным во время её вызова. Если этого избежать невозможно, вызовите makeCurrent().
Примечание: Планирование обновлений отсюда не требуется. Системы оконного интерфейса отправят события expose, которые автоматически заставят произвести обновление.
См. также initializeGL() и paintGL().
QOpenGLContext *QOpenGLWindow::shareContext() const
Возвращает QOpenGLContext, который запрошено поделиться с QOpenGLContext этого окна.
QOpenGLWindow::UpdateBehavior QOpenGLWindow::updateBehavior() const
Возвращает режим обновления для этого QOpenGLWindow.
© The Qt Company Ltd
Licensed under the GNU Free Documentation License, Version 1.3.
https://doc.qt.io/qt-5.12/qopenglwindow.html