From 465e93aa95d99f799300867b07f81bdd5162c9f1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?B=C5=82a=C5=BCej=20Szczygie=C5=82?= Date: Mon, 11 Jan 2016 15:25:12 +0100 Subject: [PATCH] QtWidgets: Improve native and top-level OpenGL widget performance Since 7c6625b105511191f739d07dc658094ff6f682ac native OpenGL widgets are able to render, but performance is very low. It also slows down rendering for top-level OpenGL widgets. Render-to-texture widgets prevent triggering unnecessary backingstore painting when only the OpenGL content changes. This patch makes possible to use that feature for native and top-level widgets by calling "markDirtyOnScreen()" function only when necessary. This patch also prevents native and top-level OpenGL widgets from flickering during resizing. Task-number: QTBUG-50381 Task-number: QTBUG-49620 Change-Id: I0c16ea644fb869a00772fd74e1709611e627bff3 Reviewed-by: Laszlo Agocs --- src/widgets/kernel/qwidgetbackingstore.cpp | 26 +++++++++++++--------- 1 file changed, 15 insertions(+), 11 deletions(-) diff --git a/src/widgets/kernel/qwidgetbackingstore.cpp b/src/widgets/kernel/qwidgetbackingstore.cpp index 3f7f9291b6..d9d1c887c1 100644 --- a/src/widgets/kernel/qwidgetbackingstore.cpp +++ b/src/widgets/kernel/qwidgetbackingstore.cpp @@ -1079,7 +1079,8 @@ void QWidgetBackingStore::sync(QWidget *exposedWidget, const QRegion &exposedReg // Nothing to repaint. if (!isDirty() && store->size().isValid()) { - qt_flush(exposedWidget, exposedRegion, store, tlw, tlwOffset, widgetTexturesFor(tlw, tlw), this); + QPlatformTextureList *tl = widgetTexturesFor(tlw, exposedWidget); + qt_flush(exposedWidget, tl ? QRegion() : exposedRegion, store, tlw, tlwOffset, tl, this); return; } @@ -1250,9 +1251,17 @@ void QWidgetBackingStore::doSync() for (int i = 0; i < paintPending.count(); ++i) { QWidget *w = paintPending[i]; w->d_func()->sendPaintEvent(w->rect()); - QWidget *npw = w->nativeParentWidget(); - if (w->internalWinId() || (npw && npw != tlw)) - markDirtyOnScreen(w->rect(), w, w->mapTo(tlw, QPoint())); + if (w != tlw) { + QWidget *npw = w->nativeParentWidget(); + if (w->internalWinId() || (npw && npw != tlw)) { + if (!w->internalWinId()) + w = npw; + QWidgetPrivate *wPrivate = w->d_func(); + if (!wPrivate->needsFlush) + wPrivate->needsFlush = new QRegion; + appendDirtyOnScreenWidget(w); + } + } } // We might have newly exposed areas on the screen if this function was @@ -1277,13 +1286,8 @@ void QWidgetBackingStore::doSync() } } } - for (int i = 0; i < dirtyRenderToTextureWidgets.count(); ++i) { - QWidget *w = dirtyRenderToTextureWidgets.at(i); - resetWidget(w); - QWidget *npw = w->nativeParentWidget(); - if (w->internalWinId() || (npw && npw != tlw)) - markDirtyOnScreen(w->rect(), w, w->mapTo(tlw, QPoint())); - } + for (int i = 0; i < dirtyRenderToTextureWidgets.count(); ++i) + resetWidget(dirtyRenderToTextureWidgets.at(i)); dirtyRenderToTextureWidgets.clear(); #endif