From 80e6ea3e871fa9f0e5a21d48ad893d4ec59c5c1c Mon Sep 17 00:00:00 2001 From: Rhys Weatherley Date: Thu, 7 Jan 2010 08:38:35 +1000 Subject: Avoid a deep copy of QImage::bits() in the png writer Task-number: QTBUG-7161 Reviewed-by: Daniel Pope --- src/gui/image/qpnghandler.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/gui/image/qpnghandler.cpp b/src/gui/image/qpnghandler.cpp index 1de0f32..42c48a9 100644 --- a/src/gui/image/qpnghandler.cpp +++ b/src/gui/image/qpnghandler.cpp @@ -855,7 +855,7 @@ bool Q_INTERNAL_WIN_NO_THROW QPNGImageWriter::writeImage(const QImage& image_in, png_get_IHDR(png_ptr, info_ptr, &width, &height, &bit_depth, &color_type, 0, 0, 0); - const uchar *data = image.bits(); + const uchar *data = (static_cast(&image))->bits(); int bpl = image.bytesPerLine(); row_pointers = new png_bytep[height]; uint y; -- cgit v0.12 From 2e4c7797144ff2487eadd4c4ae076943c1b7d409 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Trond=20Kjern=C3=A5sen?= Date: Thu, 7 Jan 2010 10:34:14 +0100 Subject: Remove unnecessary call to QWidget::setAttribute(). This is already done in the QGLWidget constructor. Reviewed-by: Kim --- src/opengl/qgl.cpp | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/opengl/qgl.cpp b/src/opengl/qgl.cpp index c3e4a2e..4a79427 100644 --- a/src/opengl/qgl.cpp +++ b/src/opengl/qgl.cpp @@ -4952,8 +4952,6 @@ void QGLWidgetPrivate::initContext(QGLContext *context, const QGLWidget* shareWi if (!glcx) glcx = new QGLContext(QGLFormat::defaultFormat(), q); - - q->setAttribute(Qt::WA_NoSystemBackground); } #if defined(Q_WS_X11) || defined(Q_WS_MAC) || defined(Q_WS_QWS) -- cgit v0.12 From 443d2f28f5ee83c4ab8353c2c8608139735e1f48 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Samuel=20R=C3=B8dal?= Date: Thu, 7 Jan 2010 12:26:38 +0100 Subject: Fixed bug in boxes demo occuring with certain OpenGL drivers. Apparently glLoadMatrixf doesn't load the supplied data synchronously in certain drivers, so we make the arrays static to work around this issue. Really a GL driver bug but it's quite simple to work around it in this case. Reviewed-by: Kim --- demos/boxes/scene.cpp | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/demos/boxes/scene.cpp b/demos/boxes/scene.cpp index 452f4ef..9b36b81 100644 --- a/demos/boxes/scene.cpp +++ b/demos/boxes/scene.cpp @@ -653,7 +653,8 @@ void Scene::initGL() static void loadMatrix(const QMatrix4x4& m) { - GLfloat mat[16]; + // static to prevent glLoadMatrixf to fail on certain drivers + static GLfloat mat[16]; const qreal *data = m.constData(); for (int index = 0; index < 16; ++index) mat[index] = data[index]; @@ -662,7 +663,8 @@ static void loadMatrix(const QMatrix4x4& m) static void multMatrix(const QMatrix4x4& m) { - GLfloat mat[16]; + // static to prevent glMultMatrixf to fail on certain drivers + static GLfloat mat[16]; const qreal *data = m.constData(); for (int index = 0; index < 16; ++index) mat[index] = data[index]; -- cgit v0.12 From f4e633af484b1016bed5935e29f99a49dc403e3c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Trond=20Kjern=C3=A5sen?= Date: Thu, 7 Jan 2010 14:48:34 +0100 Subject: Fixed indentation and typo. Reviewed-by: TrustMe --- src/opengl/qgl_x11egl.cpp | 134 +++++++++++++++++++++++----------------------- 1 file changed, 67 insertions(+), 67 deletions(-) diff --git a/src/opengl/qgl_x11egl.cpp b/src/opengl/qgl_x11egl.cpp index 271f4de..d6281f7 100644 --- a/src/opengl/qgl_x11egl.cpp +++ b/src/opengl/qgl_x11egl.cpp @@ -56,9 +56,9 @@ QT_BEGIN_NAMESPACE bool qt_egl_setup_x11_visual(XVisualInfo &vi, EGLDisplay display, EGLConfig config, const QX11Info &x11Info, bool useArgbVisual); // -// QGLTempContext is a lass for creating a temporary GL context (which is -// needed during QGLWidget initialization to retrieve GL extension info). -// Faster to construct than a full QGLWidget. +// QGLTempContext is a class for creating a temporary GL context +// (which is needed during QGLWidget initialization to retrieve GL +// extension info). Faster to construct than a full QGLWidget. // class QGLTempContext { @@ -68,82 +68,82 @@ public: window(0), context(0), surface(0) - { - display = eglGetDisplay(EGLNativeDisplayType(X11->display)); + { + display = eglGetDisplay(EGLNativeDisplayType(X11->display)); - if (!eglInitialize(display, NULL, NULL)) { - qWarning("QGLTempContext: Unable to initialize EGL display."); - return; - } + if (!eglInitialize(display, NULL, NULL)) { + qWarning("QGLTempContext: Unable to initialize EGL display."); + return; + } - EGLConfig config; - int numConfigs = 0; - EGLint attribs[] = { - EGL_SURFACE_TYPE, EGL_WINDOW_BIT, + EGLConfig config; + int numConfigs = 0; + EGLint attribs[] = { + EGL_SURFACE_TYPE, EGL_WINDOW_BIT, #ifdef QT_OPENGL_ES_2 - EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, + EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, #endif - EGL_NONE - }; + EGL_NONE + }; - eglChooseConfig(display, attribs, &config, 1, &numConfigs); - if (!numConfigs) { - qWarning("QGLTempContext: No EGL configurations available."); - return; - } + eglChooseConfig(display, attribs, &config, 1, &numConfigs); + if (!numConfigs) { + qWarning("QGLTempContext: No EGL configurations available."); + return; + } - XVisualInfo visualInfo; - XVisualInfo *vi; - int numVisuals; - EGLint id = 0; - - eglGetConfigAttrib(display, config, EGL_NATIVE_VISUAL_ID, &id); - if (id == 0) { - // EGL_NATIVE_VISUAL_ID is optional and might not be supported - // on some implementations - we'll have to do it the hard way - QX11Info xinfo; - qt_egl_setup_x11_visual(visualInfo, display, config, xinfo, false); - } else { - visualInfo.visualid = id; - } - vi = XGetVisualInfo(X11->display, VisualIDMask, &visualInfo, &numVisuals); - if (!vi || numVisuals < 1) { - qWarning("QGLTempContext: Unable to get X11 visual info id."); - return; - } + XVisualInfo visualInfo; + XVisualInfo *vi; + int numVisuals; + EGLint id = 0; + + eglGetConfigAttrib(display, config, EGL_NATIVE_VISUAL_ID, &id); + if (id == 0) { + // EGL_NATIVE_VISUAL_ID is optional and might not be supported + // on some implementations - we'll have to do it the hard way + QX11Info xinfo; + qt_egl_setup_x11_visual(visualInfo, display, config, xinfo, false); + } else { + visualInfo.visualid = id; + } + vi = XGetVisualInfo(X11->display, VisualIDMask, &visualInfo, &numVisuals); + if (!vi || numVisuals < 1) { + qWarning("QGLTempContext: Unable to get X11 visual info id."); + return; + } - window = XCreateWindow(X11->display, RootWindow(X11->display, screen), - 0, 0, 1, 1, 0, - vi->depth, InputOutput, vi->visual, - 0, 0); + window = XCreateWindow(X11->display, RootWindow(X11->display, screen), + 0, 0, 1, 1, 0, + vi->depth, InputOutput, vi->visual, + 0, 0); - surface = eglCreateWindowSurface(display, config, (EGLNativeWindowType) window, NULL); + surface = eglCreateWindowSurface(display, config, (EGLNativeWindowType) window, NULL); - if (surface == EGL_NO_SURFACE) { - qWarning("QGLTempContext: Error creating EGL surface."); - XFree(vi); - XDestroyWindow(X11->display, window); - return; - } + if (surface == EGL_NO_SURFACE) { + qWarning("QGLTempContext: Error creating EGL surface."); + XFree(vi); + XDestroyWindow(X11->display, window); + return; + } - EGLint contextAttribs[] = { + EGLint contextAttribs[] = { #ifdef QT_OPENGL_ES_2 - EGL_CONTEXT_CLIENT_VERSION, 2, + EGL_CONTEXT_CLIENT_VERSION, 2, #endif - EGL_NONE - }; - context = eglCreateContext(display, config, 0, contextAttribs); - if (context != EGL_NO_CONTEXT - && eglMakeCurrent(display, surface, surface, context)) - { - initialized = true; - } else { - qWarning("QGLTempContext: Error creating EGL context."); - eglDestroySurface(display, surface); - XDestroyWindow(X11->display, window); - } - XFree(vi); + EGL_NONE + }; + context = eglCreateContext(display, config, 0, contextAttribs); + if (context != EGL_NO_CONTEXT + && eglMakeCurrent(display, surface, surface, context)) + { + initialized = true; + } else { + qWarning("QGLTempContext: Error creating EGL context."); + eglDestroySurface(display, surface); + XDestroyWindow(X11->display, window); } + XFree(vi); + } ~QGLTempContext() { if (initialized) { @@ -349,7 +349,7 @@ bool qt_egl_setup_x11_visual(XVisualInfo &vi, EGLDisplay display, EGLConfig conf // If EGL does not know the visual ID, so try to select an appropriate one ourselves, first // using XRender if we're supposed to have an alpha, then falling back to XGetVisualInfo - + #if !defined(QT_NO_XRENDER) if (vi.visualid == 0 && useArgbVisual) { // Try to use XRender to find an ARGB visual we can use -- cgit v0.12 From 6026436f0de6020252410c021e0745a22599b159 Mon Sep 17 00:00:00 2001 From: Alexis Menard Date: Thu, 7 Jan 2010 16:13:14 +0100 Subject: Fix performance regression in _q_polishItems. QSet is a hash internally, using Iterator::begin while erasing elements inside the set might create holes and then the complexity increase. We now use the return value of erase (the next element) so the complexity is linear. For those who create/delete item in the polish event (BAD), _q_polishItem might be slower than the normal call. Task-number:QTBUG-6958 Reviewed-by:olivier --- src/gui/graphicsview/qgraphicsscene.cpp | 17 +++++++++++------ src/gui/graphicsview/qgraphicsscene_p.h | 1 + tests/benchmarks/qgraphicsscene/tst_qgraphicsscene.cpp | 17 +++++++++++++++++ 3 files changed, 29 insertions(+), 6 deletions(-) diff --git a/src/gui/graphicsview/qgraphicsscene.cpp b/src/gui/graphicsview/qgraphicsscene.cpp index 774a6d3..ceb810b 100644 --- a/src/gui/graphicsview/qgraphicsscene.cpp +++ b/src/gui/graphicsview/qgraphicsscene.cpp @@ -292,6 +292,7 @@ QGraphicsScenePrivate::QGraphicsScenePrivate() processDirtyItemsEmitted(false), selectionChanging(0), needSortTopLevelItems(true), + unpolishedItemsModified(true), holesInTopLevelSiblingIndex(false), topLevelSequentialOrdering(true), scenePosDescendantsUpdatePending(false), @@ -428,12 +429,12 @@ void QGraphicsScenePrivate::unregisterTopLevelItem(QGraphicsItem *item) */ void QGraphicsScenePrivate::_q_polishItems() { - QSet::Iterator it; + QSet::Iterator it = unpolishedItems.begin(); const QVariant booleanTrueVariant(true); while (!unpolishedItems.isEmpty()) { - it = unpolishedItems.begin(); QGraphicsItem *item = *it; - unpolishedItems.erase(it); + it = unpolishedItems.erase(it); + unpolishedItemsModified = false; if (!item->d_ptr->explicitlyHidden) { item->itemChange(QGraphicsItem::ItemVisibleChange, booleanTrueVariant); item->itemChange(QGraphicsItem::ItemVisibleHasChanged, booleanTrueVariant); @@ -442,6 +443,8 @@ void QGraphicsScenePrivate::_q_polishItems() QEvent event(QEvent::Polish); QApplication::sendEvent((QGraphicsWidget *)item, &event); } + if (unpolishedItemsModified) + it = unpolishedItems.begin(); } } @@ -636,6 +639,7 @@ void QGraphicsScenePrivate::removeItemHelper(QGraphicsItem *item) hoverItems.removeAll(item); cachedItemsUnderMouse.removeAll(item); unpolishedItems.remove(item); + unpolishedItemsModified = true; resetDirtyItem(item); //We remove all references of item from the sceneEventFilter arrays @@ -2577,9 +2581,10 @@ void QGraphicsScene::addItem(QGraphicsItem *item) item->d_ptr->resolveFont(d->font.resolve()); item->d_ptr->resolvePalette(d->palette.resolve()); - if (d->unpolishedItems.isEmpty()) - QMetaObject::invokeMethod(this, "_q_polishItems", Qt::QueuedConnection); - d->unpolishedItems.insert(item); + if (d->unpolishedItems.isEmpty()) + QMetaObject::invokeMethod(this, "_q_polishItems", Qt::QueuedConnection); + d->unpolishedItems.insert(item); + d->unpolishedItemsModified = true; // Reenable selectionChanged() for individual items --d->selectionChanging; diff --git a/src/gui/graphicsview/qgraphicsscene_p.h b/src/gui/graphicsview/qgraphicsscene_p.h index 69e4d5b..f6ec0aa 100644 --- a/src/gui/graphicsview/qgraphicsscene_p.h +++ b/src/gui/graphicsview/qgraphicsscene_p.h @@ -111,6 +111,7 @@ public: QSet unpolishedItems; QList topLevelItems; bool needSortTopLevelItems; + bool unpolishedItemsModified; bool holesInTopLevelSiblingIndex; bool topLevelSequentialOrdering; diff --git a/tests/benchmarks/qgraphicsscene/tst_qgraphicsscene.cpp b/tests/benchmarks/qgraphicsscene/tst_qgraphicsscene.cpp index 1944219..53fd9b6 100644 --- a/tests/benchmarks/qgraphicsscene/tst_qgraphicsscene.cpp +++ b/tests/benchmarks/qgraphicsscene/tst_qgraphicsscene.cpp @@ -64,6 +64,7 @@ private slots: void addItem(); void itemAt_data(); void itemAt(); + void initialShow(); }; tst_QGraphicsScene::tst_QGraphicsScene() @@ -227,5 +228,21 @@ void tst_QGraphicsScene::itemAt() qApp->processEvents(); } +void tst_QGraphicsScene::initialShow() +{ + QGraphicsScene scene; + + QBENCHMARK { + for (int y = 0; y < 30000; ++y) { + QGraphicsRectItem *item = new QGraphicsRectItem(0, 0, 50, 50); + item->setPos((y/2) * item->rect().width(), (y/2) * item->rect().height()); + scene.addItem(item); + } + scene.itemAt(0, 0); // triggers indexing + //This call polish the items so we bench their processing too. + qApp->processEvents(); + } +} + QTEST_MAIN(tst_QGraphicsScene) #include "tst_qgraphicsscene.moc" -- cgit v0.12 From f8e08419c78e94d32273c8b039dd48dc9d5e3433 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Trond=20Kjern=C3=A5sen?= Date: Thu, 7 Jan 2010 16:14:07 +0100 Subject: Reset the GL stencil mask, op and function in resetGLState(). Task-number: QTBUG-7203 Reviewed-by: Samuel --- src/opengl/gl2paintengineex/qpaintengineex_opengl2.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/opengl/gl2paintengineex/qpaintengineex_opengl2.cpp b/src/opengl/gl2paintengineex/qpaintengineex_opengl2.cpp index 5901601..ff096c2 100644 --- a/src/opengl/gl2paintengineex/qpaintengineex_opengl2.cpp +++ b/src/opengl/gl2paintengineex/qpaintengineex_opengl2.cpp @@ -559,6 +559,9 @@ void QGL2PaintEngineExPrivate::resetGLState() glDepthMask(true); glDepthFunc(GL_LESS); glClearDepth(1); + glStencilMask(0xff); + glStencilOp(GL_KEEP, GL_KEEP, GL_KEEP); + glStencilFunc(GL_ALWAYS, 0, 0xff); } void QGL2PaintEngineEx::endNativePainting() -- cgit v0.12