From a76b8bf67696ae69888cc6237417e7c8f07f8da6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Samuel=20R=C3=B8dal?= Date: Tue, 17 Aug 2010 10:29:03 +0200 Subject: Prevented Xorg crash in qtdemo when running corkboards example. The crash happens in the Nvidia driver in glXReleaseTexImageEXT when scrolling the corkboard using the mouse. To work around it we detect the Nvidia driver versions where this is known to be a problem and skip using the texture from pixmap extension in those cases. Task-number: QTBUG-12914 Reviewed-by: Trond --- src/opengl/qgl.cpp | 30 +++++++++++++++++++++++++----- src/opengl/qgl_p.h | 3 +++ 2 files changed, 28 insertions(+), 5 deletions(-) diff --git a/src/opengl/qgl.cpp b/src/opengl/qgl.cpp index 4daa866..74bde36 100644 --- a/src/opengl/qgl.cpp +++ b/src/opengl/qgl.cpp @@ -1688,6 +1688,10 @@ void QGLContextPrivate::init(QPaintDevice *dev, const QGLFormat &format) workaround_needsFullClearOnEveryFrame = false; workaround_brokenFBOReadBack = false; workaroundsCached = false; + + workaround_brokenTextureFromPixmap = false; + workaround_brokenTextureFromPixmap_init = false; + for (int i = 0; i < QT_GL_VERTEX_ARRAY_TRACKED_COUNT; ++i) vertexAttributeArraysEnabledState[i] = false; } @@ -2570,11 +2574,27 @@ QGLTexture *QGLContextPrivate::bindTexture(const QPixmap &pixmap, GLenum target, && xinfo && xinfo->screen() == pixmap.x11Info().screen() && target == GL_TEXTURE_2D) { - texture = bindTextureFromNativePixmap(const_cast(&pixmap), key, options); - if (texture) { - texture->options |= QGLContext::MemoryManagedBindOption; - texture->boundPixmap = pd; - boundPixmaps.insert(pd, QPixmap(pixmap)); + if (!workaround_brokenTextureFromPixmap_init) { + workaround_brokenTextureFromPixmap_init = true; + + const QByteArray versionString(reinterpret_cast(glGetString(GL_VERSION))); + const int pos = versionString.indexOf("NVIDIA "); + + if (pos >= 0) { + const QByteArray nvidiaVersionString = versionString.mid(pos + strlen("NVIDIA ")); + + if (nvidiaVersionString.startsWith("195") || nvidiaVersionString.startsWith("256")) + workaround_brokenTextureFromPixmap = true; + } + } + + if (!workaround_brokenTextureFromPixmap) { + texture = bindTextureFromNativePixmap(const_cast(&pixmap), key, options); + if (texture) { + texture->options |= QGLContext::MemoryManagedBindOption; + texture->boundPixmap = pd; + boundPixmaps.insert(pd, QPixmap(pixmap)); + } } } #endif diff --git a/src/opengl/qgl_p.h b/src/opengl/qgl_p.h index 32feacd..ca0d3fa 100644 --- a/src/opengl/qgl_p.h +++ b/src/opengl/qgl_p.h @@ -393,6 +393,9 @@ public: uint workaround_brokenFBOReadBack : 1; uint workaroundsCached : 1; + uint workaround_brokenTextureFromPixmap : 1; + uint workaround_brokenTextureFromPixmap_init : 1; + QPaintDevice *paintDevice; QColor transpColor; QGLContext *q_ptr; -- cgit v0.12 From cc6dc0aeefde881a95f5fea2b26f2f3d7bdc6e15 Mon Sep 17 00:00:00 2001 From: Richard Moe Gustavsen Date: Tue, 17 Aug 2010 10:08:20 +0200 Subject: Cocoa: parent windows shows on screen when they should be hidden The reason is the cocoa method that adds a window as a child of another, it ends up showing both the parent and the child window regardless. And this could in some cases also cause a crash. So we therefore need to be careful when calling that function, and be sure that the parent is actually visible. In addition, addChildWindow reset the stacking level of the child window, and made e.g. normal child windows pop in front of tool child windows. This could easily be seen in e.g. Designer. Task-number: QTBUG-12866 Reviewed-by: prasanth --- src/gui/kernel/qwidget_mac.mm | 22 ++++++++++++++++------ 1 file changed, 16 insertions(+), 6 deletions(-) diff --git a/src/gui/kernel/qwidget_mac.mm b/src/gui/kernel/qwidget_mac.mm index 8ae6a99..4ed4ccc 100644 --- a/src/gui/kernel/qwidget_mac.mm +++ b/src/gui/kernel/qwidget_mac.mm @@ -2796,10 +2796,16 @@ void QWidgetPrivate::setSubWindowStacking(bool set) if (QWidget *parent = q->parentWidget()) { if (parent->testAttribute(Qt::WA_WState_Created)) { - if (set) - [qt_mac_window_for(parent) addChildWindow:qt_mac_window_for(q) ordered:NSWindowAbove]; - else + if (set) { + if (parent->isVisible()) { + NSWindow *childwin = qt_mac_window_for(q); + int childLevel = [childwin level]; + [qt_mac_window_for(parent) addChildWindow:childwin ordered:NSWindowAbove]; + [childwin setLevel:childLevel]; + } + } else { [qt_mac_window_for(parent) removeChildWindow:qt_mac_window_for(q)]; + } } } @@ -2807,10 +2813,14 @@ void QWidgetPrivate::setSubWindowStacking(bool set) for (int i=0; iisWindow() && child->testAttribute(Qt::WA_WState_Created) && child->isVisibleTo(q)) { - if (set) - [qt_mac_window_for(q) addChildWindow:qt_mac_window_for(child) ordered:NSWindowAbove]; - else + if (set) { + NSWindow *childwin = qt_mac_window_for(child); + int childLevel = [childwin level]; + [qt_mac_window_for(q) addChildWindow:childwin ordered:NSWindowAbove]; + [childwin setLevel:childLevel]; + } else { [qt_mac_window_for(q) removeChildWindow:qt_mac_window_for(child)]; + } } } } -- cgit v0.12 From ff405f5623d7ed18c881c097368e3e9afd2e9443 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Samuel=20R=C3=B8dal?= Date: Tue, 17 Aug 2010 10:45:17 +0200 Subject: Outline / fill inconsistency in X11 paint engine. Change ebbab30af417dfbf3df47dec15c0e2f8d6a30fa6 broke outline / fill consistency in the X11 engine. Since the positioning of lines is more important we'll round the fill coordinates the same way. The bug was visible in the filltest.qps arthur test. Reviewed-by: Gunnar Sletta --- src/gui/painting/qpaintengine_x11.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/gui/painting/qpaintengine_x11.cpp b/src/gui/painting/qpaintengine_x11.cpp index e521e01..5307142 100644 --- a/src/gui/painting/qpaintengine_x11.cpp +++ b/src/gui/painting/qpaintengine_x11.cpp @@ -1516,8 +1516,8 @@ void QX11PaintEnginePrivate::fillPolygon_translated(const QPointF *polygonPoints for (int i = 0; i < pointCount; ++i) { translated_points[i] = polygonPoints[i] + offset; - translated_points[i].rx() = qRound(translated_points[i].x()) + offs; - translated_points[i].ry() = qRound(translated_points[i].y()) + offs; + translated_points[i].rx() = qFloor(translated_points[i].x()) + offs; + translated_points[i].ry() = qFloor(translated_points[i].y()) + offs; } fillPolygon_dev(translated_points.data(), pointCount, gcMode, mode); @@ -1754,8 +1754,8 @@ void QX11PaintEnginePrivate::fillPath(const QPainterPath &path, QX11PaintEngineP for (int j = 0; j < polys.at(i).size(); ++j) { translated_points[j] = polys.at(i).at(j); if (!X11->use_xrender || !(render_hints & QPainter::Antialiasing)) { - translated_points[j].rx() = qRound(translated_points[j].rx() + aliasedCoordinateDelta) + offs; - translated_points[j].ry() = qRound(translated_points[j].ry() + aliasedCoordinateDelta) + offs; + translated_points[j].rx() = qFloor(translated_points[j].rx() + aliasedCoordinateDelta) + offs; + translated_points[j].ry() = qFloor(translated_points[j].ry() + aliasedCoordinateDelta) + offs; } } -- cgit v0.12