From b55ed97e7967fca675fa43a8c0cd7445bbbbb493 Mon Sep 17 00:00:00 2001 From: Frederik Gladhorn Date: Wed, 7 Mar 2012 13:39:57 +0100 Subject: Call updateAccessibility with the right index. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit In Qt 4 index 0 was the widget itself. With the cleanup of child index this now changed. The default constructor uses -1 as parameter to signify that the widget is the cause, not a child. Change-Id: I329a1cc91bf2d1d1d8534739acbddfe107f40364 Reviewed-by: Jan-Arve Sæther --- src/widgets/dialogs/qdialog.cpp | 4 ++-- src/widgets/dialogs/qmessagebox.cpp | 2 +- src/widgets/graphicsview/qgraphicsscene.cpp | 2 +- src/widgets/kernel/qwhatsthis.cpp | 4 ++-- src/widgets/kernel/qwidget.cpp | 14 +++++++------- src/widgets/widgets/qabstractbutton.cpp | 2 +- src/widgets/widgets/qabstractslider.cpp | 2 +- src/widgets/widgets/qabstractspinbox.cpp | 4 ++-- src/widgets/widgets/qlineedit_p.cpp | 2 +- src/widgets/widgets/qmenu.cpp | 2 +- src/widgets/widgets/qprogressbar.cpp | 2 +- src/widgets/widgets/qwidgetlinecontrol.cpp | 4 ++-- 12 files changed, 22 insertions(+), 22 deletions(-) (limited to 'src/widgets') diff --git a/src/widgets/dialogs/qdialog.cpp b/src/widgets/dialogs/qdialog.cpp index 4170df4799..f1a6a294d2 100644 --- a/src/widgets/dialogs/qdialog.cpp +++ b/src/widgets/dialogs/qdialog.cpp @@ -754,7 +754,7 @@ void QDialog::setVisible(bool visible) } #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::DialogStart, this, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::DialogStart, this)); #endif } else { @@ -763,7 +763,7 @@ void QDialog::setVisible(bool visible) #ifndef QT_NO_ACCESSIBILITY if (isVisible()) - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::DialogEnd, this, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::DialogEnd, this)); #endif // Reimplemented to exit a modal event loop when the dialog is hidden. diff --git a/src/widgets/dialogs/qmessagebox.cpp b/src/widgets/dialogs/qmessagebox.cpp index 3909125fe7..e1b134ee48 100644 --- a/src/widgets/dialogs/qmessagebox.cpp +++ b/src/widgets/dialogs/qmessagebox.cpp @@ -1463,7 +1463,7 @@ void QMessageBox::showEvent(QShowEvent *e) d->updateSize(); #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::Alert, this, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::Alert, this)); #endif #ifdef Q_OS_WIN if (const HMENU systemMenu = qt_getWindowsSystemMenu(this)) { diff --git a/src/widgets/graphicsview/qgraphicsscene.cpp b/src/widgets/graphicsview/qgraphicsscene.cpp index 015cd254d4..830853094a 100644 --- a/src/widgets/graphicsview/qgraphicsscene.cpp +++ b/src/widgets/graphicsview/qgraphicsscene.cpp @@ -843,7 +843,7 @@ void QGraphicsScenePrivate::setFocusItemHelper(QGraphicsItem *item, #ifndef QT_NO_ACCESSIBILITY if (focusItem) { if (QGraphicsObject *focusObj = focusItem->toGraphicsObject()) { - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::Focus, focusObj, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::Focus, focusObj)); } } #endif diff --git a/src/widgets/kernel/qwhatsthis.cpp b/src/widgets/kernel/qwhatsthis.cpp index 4a6f3518d0..1c20b98139 100644 --- a/src/widgets/kernel/qwhatsthis.cpp +++ b/src/widgets/kernel/qwhatsthis.cpp @@ -412,7 +412,7 @@ QWhatsThisPrivate::QWhatsThisPrivate() #endif } #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ContextHelpStart, this, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ContextHelpStart, this)); #endif } @@ -424,7 +424,7 @@ QWhatsThisPrivate::~QWhatsThisPrivate() QApplication::restoreOverrideCursor(); #endif #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ContextHelpEnd, this, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ContextHelpEnd, this)); #endif instance = 0; } diff --git a/src/widgets/kernel/qwidget.cpp b/src/widgets/kernel/qwidget.cpp index bf864503a4..03ada1ac7a 100644 --- a/src/widgets/kernel/qwidget.cpp +++ b/src/widgets/kernel/qwidget.cpp @@ -5965,7 +5965,7 @@ void QWidget::setFocus(Qt::FocusReason reason) // menus update the focus manually and this would create bogus events if (!(f->inherits("QMenuBar") || f->inherits("QMenu") || f->inherits("QMenuItem"))) # endif - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::Focus, f, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::Focus, f)); #endif #ifndef QT_NO_GRAPHICSVIEW if (QWExtra *topData = window()->d_func()->extra) { @@ -6045,7 +6045,7 @@ void QWidget::clearFocus() #endif { #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::Focus, this, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::Focus, this)); #endif } } @@ -7052,7 +7052,7 @@ void QWidgetPrivate::show_helper() #ifndef QT_NO_ACCESSIBILITY if (q->windowType() != Qt::ToolTip) // Tooltips are read aloud twice in MS narrator. - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ObjectShow, q, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ObjectShow, q)); #endif if (QApplicationPrivate::hidden_focus_widget == q) { @@ -7143,7 +7143,7 @@ void QWidgetPrivate::hide_helper() #ifndef QT_NO_ACCESSIBILITY if (wasVisible) - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ObjectHide, q, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ObjectHide, q)); #endif } @@ -7375,7 +7375,7 @@ void QWidgetPrivate::hideChildren(bool spontaneous) qApp->d_func()->sendSyntheticEnterLeave(widget); #ifndef QT_NO_ACCESSIBILITY if (!spontaneous) - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ObjectHide, widget, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ObjectHide, widget)); #endif } } @@ -10386,7 +10386,7 @@ void QWidget::setAccessibleName(const QString &name) { Q_D(QWidget); d->accessibleName = name; - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::NameChanged, this, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::NameChanged, this)); } QString QWidget::accessibleName() const @@ -10408,7 +10408,7 @@ void QWidget::setAccessibleDescription(const QString &description) { Q_D(QWidget); d->accessibleDescription = description; - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::DescriptionChanged, this, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::DescriptionChanged, this)); } QString QWidget::accessibleDescription() const diff --git a/src/widgets/widgets/qabstractbutton.cpp b/src/widgets/widgets/qabstractbutton.cpp index 80e125947e..f7c8ad7773 100644 --- a/src/widgets/widgets/qabstractbutton.cpp +++ b/src/widgets/widgets/qabstractbutton.cpp @@ -647,7 +647,7 @@ void QAbstractButton::setText(const QString &text) update(); updateGeometry(); #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::NameChanged, this, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::NameChanged, this)); #endif } diff --git a/src/widgets/widgets/qabstractslider.cpp b/src/widgets/widgets/qabstractslider.cpp index 6aff2e9077..b0216e5277 100644 --- a/src/widgets/widgets/qabstractslider.cpp +++ b/src/widgets/widgets/qabstractslider.cpp @@ -538,7 +538,7 @@ void QAbstractSlider::setValue(int value) emit sliderMoved((d->position = value)); } #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ValueChanged, this, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ValueChanged, this)); #endif sliderChange(SliderValueChange); emit valueChanged(value); diff --git a/src/widgets/widgets/qabstractspinbox.cpp b/src/widgets/widgets/qabstractspinbox.cpp index e9652a9869..c083369136 100644 --- a/src/widgets/widgets/qabstractspinbox.cpp +++ b/src/widgets/widgets/qabstractspinbox.cpp @@ -976,7 +976,7 @@ void QAbstractSpinBox::keyPressEvent(QKeyEvent *event) } } #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ValueChanged, this, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ValueChanged, this)); #endif return; } @@ -1595,7 +1595,7 @@ void QAbstractSpinBoxPrivate::updateState(bool up, bool fromKeyboard /* = false buttonState = (up ? Up : Down) | (fromKeyboard ? Keyboard : Mouse); q->stepBy(up ? 1 : -1); #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ValueChanged, q, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ValueChanged, q)); #endif } } diff --git a/src/widgets/widgets/qlineedit_p.cpp b/src/widgets/widgets/qlineedit_p.cpp index e3404a62de..d06e98e31a 100644 --- a/src/widgets/widgets/qlineedit_p.cpp +++ b/src/widgets/widgets/qlineedit_p.cpp @@ -144,7 +144,7 @@ void QLineEditPrivate::_q_selectionChanged() emit q->selectionChanged(); #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::TextSelectionChanged, q, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::TextSelectionChanged, q)); #endif } diff --git a/src/widgets/widgets/qmenu.cpp b/src/widgets/widgets/qmenu.cpp index fd030a5383..af4a87e282 100644 --- a/src/widgets/widgets/qmenu.cpp +++ b/src/widgets/widgets/qmenu.cpp @@ -2091,7 +2091,7 @@ void QMenu::hideEvent(QHideEvent *) d->eventLoop->exit(); d->setCurrentAction(0); #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::PopupMenuEnd, this, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::PopupMenuEnd, this)); #endif #ifndef QT_NO_MENUBAR if (QMenuBar *mb = qobject_cast(d->causedPopup.widget)) diff --git a/src/widgets/widgets/qprogressbar.cpp b/src/widgets/widgets/qprogressbar.cpp index 816b847cf5..c1a34bfb7a 100644 --- a/src/widgets/widgets/qprogressbar.cpp +++ b/src/widgets/widgets/qprogressbar.cpp @@ -314,7 +314,7 @@ void QProgressBar::setValue(int value) d->value = value; emit valueChanged(value); #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ValueChanged, this, 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::ValueChanged, this)); #endif if (d->repaintRequired()) repaint(); diff --git a/src/widgets/widgets/qwidgetlinecontrol.cpp b/src/widgets/widgets/qwidgetlinecontrol.cpp index 73c3d14f9b..a04339f864 100644 --- a/src/widgets/widgets/qwidgetlinecontrol.cpp +++ b/src/widgets/widgets/qwidgetlinecontrol.cpp @@ -768,7 +768,7 @@ void QWidgetLineControl::internalSetText(const QString &txt, int pos, bool edite #ifndef QT_NO_ACCESSIBILITY if (changed) - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::TextUpdated, parent(), 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::TextUpdated, parent())); #endif } @@ -1367,7 +1367,7 @@ void QWidgetLineControl::emitCursorPositionChanged() m_lastCursorPos = m_cursor; cursorPositionChanged(oldLast, m_cursor); #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::TextCaretMoved, parent(), 0)); + QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::TextCaretMoved, parent())); #endif } } -- cgit v1.2.3 From 816893d91d550c08297ebcdfc3306bb3d9c0c2f6 Mon Sep 17 00:00:00 2001 From: David Faure Date: Wed, 7 Mar 2012 22:52:42 +0100 Subject: Fix some duplication between QGuiApplication and QApplication, MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit for the mouseButtons and keyboardModifiers vars and methods. Implement queryKeyboardModifiers with a new virtual in QPlatformIntegration. Task-number: QTBUG-11243 Change-Id: I9e95841542ac61c73ff72d7682ad962ea8aada42 Reviewed-by: Friedemann Kleint Reviewed-by: Samuel Rødal --- src/widgets/kernel/qapplication.cpp | 65 ------------------------------------- src/widgets/kernel/qapplication.h | 4 --- src/widgets/kernel/qapplication_p.h | 3 -- 3 files changed, 72 deletions(-) (limited to 'src/widgets') diff --git a/src/widgets/kernel/qapplication.cpp b/src/widgets/kernel/qapplication.cpp index 90b64db579..348eb2f343 100644 --- a/src/widgets/kernel/qapplication.cpp +++ b/src/widgets/kernel/qapplication.cpp @@ -371,9 +371,6 @@ void qt_init(QApplicationPrivate *priv, int type ); void qt_cleanup(); -Qt::MouseButtons QApplicationPrivate::mouse_buttons = Qt::NoButton; -Qt::KeyboardModifiers QApplicationPrivate::modifier_buttons = Qt::NoModifier; - QStyle *QApplicationPrivate::app_style = 0; // default application style QString QApplicationPrivate::styleOverride; // style override @@ -2665,68 +2662,6 @@ QDesktopWidget *QApplication::desktop() return qt_desktopWidget; } -/*! - Returns the current state of the modifier keys on the keyboard. The current - state is updated sychronously as the event queue is emptied of events that - will spontaneously change the keyboard state (QEvent::KeyPress and - QEvent::KeyRelease events). - - It should be noted this may not reflect the actual keys held on the input - device at the time of calling but rather the modifiers as last reported in - one of the above events. If no keys are being held Qt::NoModifier is - returned. - - \sa mouseButtons(), queryKeyboardModifiers() -*/ - -Qt::KeyboardModifiers QApplication::keyboardModifiers() -{ - return QApplicationPrivate::modifier_buttons; -} - -/*! - \fn Qt::KeyboardModifiers QApplication::queryKeyboardModifiers() - - Queries and returns the state of the modifier keys on the keyboard. - Unlike keyboardModifiers, this method returns the actual keys held - on the input device at the time of calling the method. - - It does not rely on the keypress events having been received by this - process, which makes it possible to check the modifiers while moving - a window, for instance. Note that in most cases, you should use - keyboardModifiers(), which is faster and more accurate since it contains - the state of the modifiers as they were when the currently processed - event was received. - - \sa keyboardModifiers() - - \since 4.8 -*/ - -Qt::KeyboardModifiers QApplication::queryKeyboardModifiers() -{ - qWarning("queryKeyboardModifiers() doesn't have a QPA implementation"); - return QApplicationPrivate::modifier_buttons; -} - -/*! - Returns the current state of the buttons on the mouse. The current state is - updated syncronously as the event queue is emptied of events that will - spontaneously change the mouse state (QEvent::MouseButtonPress and - QEvent::MouseButtonRelease events). - - It should be noted this may not reflect the actual buttons held on the - input device at the time of calling but rather the mouse buttons as last - reported in one of the above events. If no mouse buttons are being held - Qt::NoButton is returned. - - \sa keyboardModifiers() -*/ - -Qt::MouseButtons QApplication::mouseButtons() -{ - return QApplicationPrivate::mouse_buttons; -} /*! \fn bool QApplication::isSessionRestored() const diff --git a/src/widgets/kernel/qapplication.h b/src/widgets/kernel/qapplication.h index 060765969f..55ed6998fa 100644 --- a/src/widgets/kernel/qapplication.h +++ b/src/widgets/kernel/qapplication.h @@ -150,10 +150,6 @@ public: static void beep(); static void alert(QWidget *widget, int duration = 0); - static Qt::KeyboardModifiers keyboardModifiers(); - static Qt::KeyboardModifiers queryKeyboardModifiers(); - static Qt::MouseButtons mouseButtons(); - static void setCursorFlashTime(int); static int cursorFlashTime(); diff --git a/src/widgets/kernel/qapplication_p.h b/src/widgets/kernel/qapplication_p.h index 2d639172e2..74af3bca6d 100644 --- a/src/widgets/kernel/qapplication_p.h +++ b/src/widgets/kernel/qapplication_p.h @@ -247,9 +247,6 @@ public: QPoint toolTipPos, toolTipGlobalPos, hoverGlobalPos; QPointer toolTipWidget; - static Qt::MouseButtons mouse_buttons; - static Qt::KeyboardModifiers modifier_buttons; - static QSize app_strut; static QWidgetList *popupWidgets; static QStyle *app_style; -- cgit v1.2.3 From 70cb55bc6df486b51addf0c622bf3e77d324abf5 Mon Sep 17 00:00:00 2001 From: Robin Burchell Date: Mon, 5 Mar 2012 15:05:16 +0100 Subject: Force properties to be applied in the order in which they are specified. Previously, property setting was randomized in order, which means that things like: qproperty-foo: 4; qproperty-bar: 5; where foo may affect bar worked by chance - or not at all - depending on the hash function. Change-Id: Ifb9813ee72842cefb278cbedb644f24b91113f3f Reviewed-by: Olivier Goffart --- src/widgets/styles/qstylesheetstyle.cpp | 17 +++++++++++++++-- 1 file changed, 15 insertions(+), 2 deletions(-) (limited to 'src/widgets') diff --git a/src/widgets/styles/qstylesheetstyle.cpp b/src/widgets/styles/qstylesheetstyle.cpp index 5c0ee254d4..7a0cc09452 100644 --- a/src/widgets/styles/qstylesheetstyle.cpp +++ b/src/widgets/styles/qstylesheetstyle.cpp @@ -2498,7 +2498,13 @@ void QStyleSheetStyle::setGeometry(QWidget *w) void QStyleSheetStyle::setProperties(QWidget *w) { + // we have two data structures here: a hash of property -> value for lookup, + // and a vector giving properties in the order they are specified. + // + // this means we only set a property once (thanks to the hash) but we set + // properties in the order they are specified. QHash propertyHash; + QVector properties; QVector decls = declarations(styleRules(w), QString()); // run through the declarations in order @@ -2535,10 +2541,17 @@ void QStyleSheetStyle::setProperties(QWidget *w) #endif default: v = decl.d->values.at(0).variant; break; } + + if (propertyHash.contains(property)) { + // we're ignoring the original appearance of this property + properties.remove(properties.indexOf(property)); + } + propertyHash[property] = v; + properties.append(property); } - // apply the values - const QList properties = propertyHash.keys(); + + // apply the values from left to right order for (int i = 0; i < properties.count(); i++) { const QString &property = properties.at(i); w->setProperty(property.toLatin1(), propertyHash[property]); -- cgit v1.2.3 From 37546c563e32960fbf50d4a692993721ae2da273 Mon Sep 17 00:00:00 2001 From: Vincent A Date: Wed, 7 Mar 2012 19:24:29 +0100 Subject: Support Growl >=1.3 in QSystemTrayIcon MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The app name has changed in Growl 1.3, but the id stays the same. Also don't send notifications if Growl is not running to follow recommendations. Change-Id: I31ff7df272b4af1b4f1e4db80c47e7ba75038dec Reviewed-by: Morten Johan Sørvig --- src/widgets/util/qsystemtrayicon_mac.mm | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) (limited to 'src/widgets') diff --git a/src/widgets/util/qsystemtrayicon_mac.mm b/src/widgets/util/qsystemtrayicon_mac.mm index 59342cb8a4..7f7d7cdc6a 100644 --- a/src/widgets/util/qsystemtrayicon_mac.mm +++ b/src/widgets/util/qsystemtrayicon_mac.mm @@ -260,7 +260,11 @@ void QSystemTrayIconPrivate::showMessage_sys(const QString &title, const QString notificationIcon = QLatin1String("image from location \"file://") + notificationIconFile.fileName() + QLatin1String("\""); } const QString script(QLatin1String( - "tell application \"GrowlHelperApp\"\n" + "tell application \"System Events\"\n" + "set isRunning to (count of (every process whose bundle identifier is \"com.Growl.GrowlHelperApp\")) > 0\n" + "end tell\n" + "if isRunning\n" + "tell application id \"com.Growl.GrowlHelperApp\"\n" "-- Make a list of all the notification types (all)\n" "set the allNotificationsList to {\"") + notificationType + QLatin1String("\"}\n" @@ -276,7 +280,7 @@ void QSystemTrayIconPrivate::showMessage_sys(const QString &title, const QString QLatin1String("\" description \"") + message + QLatin1String("\" application name \"") + notificationApp + QLatin1String("\" ") + notificationIcon + - QLatin1String("\nend tell")); + QLatin1String("\nend tell\nend if")); qt_mac_execute_apple_script(script, 0); #elif 0 Q_Q(QSystemTrayIcon); -- cgit v1.2.3 From eb57da5b3ff9915d2254fdbf57992fa0320d9041 Mon Sep 17 00:00:00 2001 From: Frederik Gladhorn Date: Wed, 7 Mar 2012 13:51:31 +0100 Subject: Update accessibility StateChange by custom event. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Subclass QAccessibleEvent to give details what changed in the state change. Change-Id: I9005d311e85a3c8bfa6e062833fa6a8a7dc6a4a4 Reviewed-by: Jan-Arve Sæther --- src/widgets/kernel/qwidget.cpp | 14 +++++--------- src/widgets/widgets/qabstractbutton.cpp | 10 +++++++--- src/widgets/widgets/qpushbutton.cpp | 4 +++- 3 files changed, 15 insertions(+), 13 deletions(-) (limited to 'src/widgets') diff --git a/src/widgets/kernel/qwidget.cpp b/src/widgets/kernel/qwidget.cpp index 03ada1ac7a..1493f61972 100644 --- a/src/widgets/kernel/qwidget.cpp +++ b/src/widgets/kernel/qwidget.cpp @@ -8245,12 +8245,15 @@ bool QWidget::event(QEvent *event) void QWidget::changeEvent(QEvent * event) { switch(event->type()) { - case QEvent::EnabledChange: + case QEvent::EnabledChange: { update(); #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::StateChanged, this, 0)); + QAccessible::State s; + s.disabled = true; + QAccessible::updateAccessibility(QAccessibleStateChangeEvent(s, this)); #endif break; + } case QEvent::FontChange: case QEvent::StyleChange: { @@ -10515,13 +10518,6 @@ void QWidget::updateMicroFocus() { // updating everything since this is currently called for any kind of state change qApp->inputMethod()->update(Qt::ImQueryAll); - -#ifndef QT_NO_ACCESSIBILITY - if (isVisible()) { - // ##### is this correct - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::StateChanged, this, 0)); - } -#endif } /*! diff --git a/src/widgets/widgets/qabstractbutton.cpp b/src/widgets/widgets/qabstractbutton.cpp index f7c8ad7773..aebef8ddc9 100644 --- a/src/widgets/widgets/qabstractbutton.cpp +++ b/src/widgets/widgets/qabstractbutton.cpp @@ -504,9 +504,6 @@ void QAbstractButtonPrivate::refresh() if (blockRefresh) return; q->update(); -#ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::StateChanged, q, 0)); -#endif } void QAbstractButtonPrivate::click() @@ -767,6 +764,13 @@ void QAbstractButton::setChecked(bool checked) d->notifyChecked(); if (guard) emit toggled(checked); + + +#ifndef QT_NO_ACCESSIBILITY + QAccessible::State s; + s.checked = true; + QAccessible::updateAccessibility(QAccessibleStateChangeEvent(s, this)); +#endif } bool QAbstractButton::isChecked() const diff --git a/src/widgets/widgets/qpushbutton.cpp b/src/widgets/widgets/qpushbutton.cpp index 7ca5dcb486..059b0f801c 100644 --- a/src/widgets/widgets/qpushbutton.cpp +++ b/src/widgets/widgets/qpushbutton.cpp @@ -376,7 +376,9 @@ void QPushButton::setDefault(bool enable) } update(); #ifndef QT_NO_ACCESSIBILITY - QAccessible::updateAccessibility(QAccessibleEvent(QAccessible::StateChanged, this, 0)); + QAccessible::State s; + s.defaultButton = true; + QAccessible::updateAccessibility(QAccessibleStateChangeEvent(s, this)); #endif } -- cgit v1.2.3 From 6e278b868824db8e24b68d48fa0f6e154de1b2f6 Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Fri, 9 Mar 2012 09:53:10 +0100 Subject: Implement QSystemTrayIcon for Windows. No longer base the implementation on a QWidget which is not necessary when all that is required is a message window listening to task-tray messages. Export a service function creating a message window from the Windows native interface and use that. Task-number: QTBUG-20978 Change-Id: I01d0faeac777df4eee802c51d2bc722fce814080 Reviewed-by: Friedemann Kleint --- src/widgets/util/qsystemtrayicon_win.cpp | 227 ++++++++++++++++++------------- src/widgets/util/util.pri | 9 +- 2 files changed, 136 insertions(+), 100 deletions(-) (limited to 'src/widgets') diff --git a/src/widgets/util/qsystemtrayicon_win.cpp b/src/widgets/util/qsystemtrayicon_win.cpp index fdb308c3d6..f3d4347986 100644 --- a/src/widgets/util/qsystemtrayicon_win.cpp +++ b/src/widgets/util/qsystemtrayicon_win.cpp @@ -50,13 +50,16 @@ #define _WIN32_IE 0x600 #endif -#include -#include -#include - #include -#include +#include +#include #include +#include +#include + +#include +#include +#include QT_BEGIN_NAMESPACE @@ -72,28 +75,12 @@ struct Q_NOTIFYICONIDENTIFIER { GUID guidItem; }; -#ifndef NOTIFYICON_VERSION_4 -#define NOTIFYICON_VERSION_4 4 -#endif - -#ifndef NIN_SELECT -#define NIN_SELECT (WM_USER + 0) -#endif - -#ifndef NIN_KEYSELECT -#define NIN_KEYSELECT (WM_USER + 1) -#endif - -#ifndef NIN_BALLOONTIMEOUT -#define NIN_BALLOONTIMEOUT (WM_USER + 4) -#endif - -#ifndef NIN_BALLOONUSERCLICK -#define NIN_BALLOONUSERCLICK (WM_USER + 5) -#endif - -#ifndef NIF_SHOWTIP -#define NIF_SHOWTIP 0x00000080 +#ifdef Q_CC_MINGW +# define NIN_SELECT (WM_USER + 0) +# define NIN_KEYSELECT (WM_USER + 1) +# define NIN_BALLOONTIMEOUT (WM_USER + 4) +# define NIN_BALLOONUSERCLICK (WM_USER + 5) +# define NIF_SHOWTIP 0x00000080 #endif #define Q_MSGFLT_ALLOW 1 @@ -102,23 +89,34 @@ typedef HRESULT (WINAPI *PtrShell_NotifyIconGetRect)(const Q_NOTIFYICONIDENTIFIE typedef BOOL (WINAPI *PtrChangeWindowMessageFilter)(UINT message, DWORD dwFlag); typedef BOOL (WINAPI *PtrChangeWindowMessageFilterEx)(HWND hWnd, UINT message, DWORD action, void* pChangeFilterStruct); -class QSystemTrayIconSys : QWidget +// Copy QString data to a limited wchar_t array including \0. +static inline void qStringToLimitedWCharArray(QString in, wchar_t *target, int maxLength) +{ + const int length = qMin(maxLength - 1, in.size()); + if (length < in.size()) + in.truncate(length); + in.toWCharArray(target); + target[length] = wchar_t(0); +} + +class QSystemTrayIconSys { public: - QSystemTrayIconSys(QSystemTrayIcon *object); + QSystemTrayIconSys(HWND hwnd, QSystemTrayIcon *object); ~QSystemTrayIconSys(); - bool winEvent( MSG *m, long *result ); bool trayMessage(DWORD msg); void setIconContents(NOTIFYICONDATA &data); bool showMessage(const QString &title, const QString &message, QSystemTrayIcon::MessageIcon type, uint uSecs); QRect findIconGeometry(const int a_iButtonID); - void createIcon(); + HICON createIcon(); + bool winEvent(MSG *m, long *result); + +private: + const HWND m_hwnd; HICON hIcon; QPoint globalPos; QSystemTrayIcon *q; -private: uint notifyIconSize; - int maxTipLength; int version; bool ignoreNextMouseRelease; }; @@ -126,28 +124,68 @@ private: static bool allowsMessages() { #ifndef QT_NO_SETTINGS - QSettings settings(QLatin1String("HKEY_CURRENT_USER\\Software\\Microsoft" - "\\Windows\\CurrentVersion\\Explorer\\Advanced"), QSettings::NativeFormat); - return settings.value(QLatin1String("EnableBalloonTips"), true).toBool(); + const QString key = QStringLiteral("HKEY_CURRENT_USER\\Software\\Microsoft\\Windows\\CurrentVersion\\Explorer\\Advanced"); + const QSettings settings(key, QSettings::NativeFormat); + return settings.value(QStringLiteral("EnableBalloonTips"), true).toBool(); #else return false; #endif } -QSystemTrayIconSys::QSystemTrayIconSys(QSystemTrayIcon *object) - : hIcon(0), q(object), ignoreNextMouseRelease(false) +typedef QHash HandleTrayIconHash; +Q_GLOBAL_STATIC(HandleTrayIconHash, handleTrayIconHash) + +extern "C" LRESULT QT_WIN_CALLBACK qWindowsTrayconWndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { - if (QSysInfo::windowsVersion() >= QSysInfo::WV_VISTA) { - notifyIconSize = sizeof(NOTIFYICONDATA); - version = NOTIFYICON_VERSION_4; - } else { + if (message == MYWM_TASKBARCREATED || message == MYWM_NOTIFYICON) { + if (QSystemTrayIconSys *trayIcon = handleTrayIconHash()->value(hwnd)) { + MSG msg; + msg.hwnd = hwnd; // re-create MSG structure + msg.message = message; // time and pt fields ignored + msg.wParam = wParam; + msg.lParam = lParam; + msg.pt.x = GET_X_LPARAM(lParam); + msg.pt.y = GET_Y_LPARAM(lParam); + long result = 0; + if (trayIcon->winEvent(&msg, &result)) + return result; + } + } + return DefWindowProc(hwnd, message, wParam, lParam); +} + +// Invoke a service of the native Windows interface to create +// a non-visible message window. +static inline HWND createTrayIconMessageWindow() +{ + if (QPlatformNativeInterface *ni = QGuiApplication::platformNativeInterface()) { + void *hwnd = 0; + void *wndProc = reinterpret_cast(qWindowsTrayconWndProc); + if (QMetaObject::invokeMethod(ni, "createMessageWindow", Qt::DirectConnection, + Q_RETURN_ARG(void *, hwnd), + Q_ARG(QString, QStringLiteral("QTrayIconMessageWindowClass")), + Q_ARG(QString, QStringLiteral("QTrayIconMessageWindow")), + Q_ARG(void *, wndProc)) && hwnd) { + return reinterpret_cast(hwnd); + } + } + return 0; +} + +QSystemTrayIconSys::QSystemTrayIconSys(HWND hwnd, QSystemTrayIcon *object) + : m_hwnd(hwnd), hIcon(0), q(object) + , notifyIconSize(NOTIFYICONDATA_V2_SIZE), version(NOTIFYICON_VERSION) + , ignoreNextMouseRelease(false) + +{ + handleTrayIconHash()->insert(m_hwnd, this); + + if (QSysInfo::windowsVersion() < QSysInfo::WV_VISTA) { notifyIconSize = NOTIFYICONDATA_V2_SIZE; version = NOTIFYICON_VERSION; } - maxTipLength = 128; - // For restoring the tray icon after explorer crashes if (!MYWM_TASKBARCREATED) { MYWM_TASKBARCREATED = RegisterWindowMessage(L"TaskbarCreated"); @@ -158,8 +196,8 @@ QSystemTrayIconSys::QSystemTrayIconSys(QSystemTrayIcon *object) (PtrChangeWindowMessageFilterEx)QSystemLibrary::resolve(QLatin1String("user32"), "ChangeWindowMessageFilterEx"); if (pChangeWindowMessageFilterEx) { - // Call the safer ChangeWindowMessageFilterEx API if available - pChangeWindowMessageFilterEx(winId(), MYWM_TASKBARCREATED, Q_MSGFLT_ALLOW, 0); + // Call the safer ChangeWindowMessageFilterEx API if available (Windows 7 onwards) + pChangeWindowMessageFilterEx(m_hwnd, MYWM_TASKBARCREATED, Q_MSGFLT_ALLOW, 0); } else { static PtrChangeWindowMessageFilter pChangeWindowMessageFilter = (PtrChangeWindowMessageFilter)QSystemLibrary::resolve(QLatin1String("user32"), "ChangeWindowMessageFilter"); @@ -173,8 +211,10 @@ QSystemTrayIconSys::QSystemTrayIconSys(QSystemTrayIcon *object) QSystemTrayIconSys::~QSystemTrayIconSys() { + handleTrayIconHash()->remove(m_hwnd); if (hIcon) DestroyIcon(hIcon); + DestroyWindow(m_hwnd); } void QSystemTrayIconSys::setIconContents(NOTIFYICONDATA &tnd) @@ -182,12 +222,9 @@ void QSystemTrayIconSys::setIconContents(NOTIFYICONDATA &tnd) tnd.uFlags |= NIF_MESSAGE | NIF_ICON | NIF_TIP; tnd.uCallbackMessage = MYWM_NOTIFYICON; tnd.hIcon = hIcon; - QString tip = q->toolTip(); - - if (!tip.isNull()) { - tip = tip.left(maxTipLength - 1) + QChar(); - memcpy(tnd.szTip, tip.utf16(), qMin(tip.length() + 1, maxTipLength) * sizeof(wchar_t)); - } + const QString tip = q->toolTip(); + if (!tip.isNull()) + qStringToLimitedWCharArray(tip, tnd.szTip, 64); } static int iconFlag( QSystemTrayIcon::MessageIcon icon ) @@ -211,19 +248,16 @@ bool QSystemTrayIconSys::showMessage(const QString &title, const QString &messag { NOTIFYICONDATA tnd; memset(&tnd, 0, notifyIconSize); - - memcpy(tnd.szInfo, message.utf16(), qMin(message.length() + 1, 256) * sizeof(wchar_t)); - memcpy(tnd.szInfoTitle, title.utf16(), qMin(title.length() + 1, 64) * sizeof(wchar_t)); + qStringToLimitedWCharArray(message, tnd.szInfo, 256); + qStringToLimitedWCharArray(title, tnd.szInfoTitle, 64); tnd.uID = q_uNOTIFYICONID; tnd.dwInfoFlags = iconFlag(type); tnd.cbSize = notifyIconSize; - tnd.hWnd = winId(); + tnd.hWnd = m_hwnd; tnd.uTimeout = uSecs; tnd.uFlags = NIF_INFO | NIF_SHOWTIP; - Q_ASSERT(testAttribute(Qt::WA_WState_Created)); - return Shell_NotifyIcon(NIM_MODIFY, &tnd); } @@ -234,12 +268,10 @@ bool QSystemTrayIconSys::trayMessage(DWORD msg) tnd.uID = q_uNOTIFYICONID; tnd.cbSize = notifyIconSize; - tnd.hWnd = winId(); + tnd.hWnd = m_hwnd; tnd.uFlags = NIF_SHOWTIP; tnd.uVersion = version; - Q_ASSERT(testAttribute(Qt::WA_WState_Created)); - if (msg == NIM_ADD || msg == NIM_MODIFY) { setIconContents(tnd); } @@ -252,25 +284,28 @@ bool QSystemTrayIconSys::trayMessage(DWORD msg) return success; } -void QSystemTrayIconSys::createIcon() +Q_GUI_EXPORT HICON qt_pixmapToWinHICON(const QPixmap &); + +HICON QSystemTrayIconSys::createIcon() { + const HICON oldIcon = hIcon; hIcon = 0; - QIcon icon = q->icon(); + const QIcon icon = q->icon(); if (icon.isNull()) - return; - + return oldIcon; const int iconSizeX = GetSystemMetrics(SM_CXSMICON); const int iconSizeY = GetSystemMetrics(SM_CYSMICON); - QSize size = icon.actualSize(QSize(iconSizeX, iconSizeY)); - QPixmap pm = icon.pixmap(size); + const QSize size = icon.actualSize(QSize(iconSizeX, iconSizeY)); + const QPixmap pm = icon.pixmap(size); if (pm.isNull()) - return; - - hIcon = pm.toWinHICON(); + return oldIcon; + hIcon = qt_pixmapToWinHICON(pm); + return oldIcon; } bool QSystemTrayIconSys::winEvent( MSG *m, long *result ) { + *result = 0; switch(m->message) { case MYWM_NOTIFYICON: { @@ -324,22 +359,24 @@ bool QSystemTrayIconSys::winEvent( MSG *m, long *result ) break; } default: - if (m->message == MYWM_TASKBARCREATED) + if (m->message == MYWM_TASKBARCREATED) // self-registered message id. trayMessage(NIM_ADD); - else - return QWidget::winEvent(m, result); break; } - return 0; + return false; } void QSystemTrayIconPrivate::install_sys() { Q_Q(QSystemTrayIcon); if (!sys) { - sys = new QSystemTrayIconSys(q); - sys->createIcon(); - sys->trayMessage(NIM_ADD); + if (const HWND hwnd = createTrayIconMessageWindow()) { + sys = new QSystemTrayIconSys(hwnd, q); + sys->createIcon(); + sys->trayMessage(NIM_ADD); + } else { + qWarning("%s: The platform plugin failed to create a message window.", Q_FUNC_INFO); + } } } @@ -351,13 +388,14 @@ void QSystemTrayIconPrivate::install_sys() QRect QSystemTrayIconSys::findIconGeometry(const int iconId) { static PtrShell_NotifyIconGetRect Shell_NotifyIconGetRect = - (PtrShell_NotifyIconGetRect)QSystemLibrary::resolve(QLatin1String("shell32"), "Shell_NotifyIconGetRect"); + (PtrShell_NotifyIconGetRect)QSystemLibrary::resolve(QLatin1String("shell32"), + "Shell_NotifyIconGetRect"); if (Shell_NotifyIconGetRect) { Q_NOTIFYICONIDENTIFIER nid; memset(&nid, 0, sizeof(nid)); nid.cbSize = sizeof(nid); - nid.hWnd = winId(); + nid.hWnd = m_hwnd; nid.uID = iconId; RECT rect; @@ -421,7 +459,7 @@ QRect QSystemTrayIconSys::findIconGeometry(const int iconId) HWND currentIconHandle = (HWND) appData[0]; bool isHidden = buttonData.fsState & TBSTATE_HIDDEN; - if (currentIconHandle == winId() && + if (currentIconHandle == m_hwnd && currentIconId == iconId && !isHidden) { SendMessage(trayHandle, TB_GETITEMRECT, toolbarButton , (LPARAM)data); RECT iconRect = {0, 0}; @@ -441,27 +479,22 @@ QRect QSystemTrayIconSys::findIconGeometry(const int iconId) return ret; } -void QSystemTrayIconPrivate::showMessage_sys(const QString &title, const QString &message, QSystemTrayIcon::MessageIcon type, int timeOut) +void QSystemTrayIconPrivate::showMessage_sys(const QString &title, + const QString &messageIn, + QSystemTrayIcon::MessageIcon type, + int timeOut) { if (!sys || !allowsMessages()) return; - uint uSecs = 0; - if ( timeOut < 0) - uSecs = 10000; //10 sec default - else uSecs = (int)timeOut; - - //message is limited to 255 chars + NULL - QString messageString; + // 10 sec default + const uint uSecs = timeOut < 0 ? uint(10000) : uint(timeOut); + // For empty messages, ensures that they show when only title is set + QString message = messageIn; if (message.isEmpty() && !title.isEmpty()) - messageString = QLatin1Char(' '); //ensures that the message shows when only title is set - else - messageString = message.left(255) + QChar(); - - //title is limited to 63 chars + NULL - QString titleString = title.left(63) + QChar(); + message.append(QLatin1Char(' ')); - sys->showMessage(titleString, messageString, type, uSecs); + sys->showMessage(title, message, type, uSecs); } QRect QSystemTrayIconPrivate::geometry_sys() const @@ -487,9 +520,7 @@ void QSystemTrayIconPrivate::updateIcon_sys() if (!sys) return; - HICON hIconToDestroy = sys->hIcon; - - sys->createIcon(); + const HICON hIconToDestroy = sys->createIcon(); sys->trayMessage(NIM_MODIFY); if (hIconToDestroy) diff --git a/src/widgets/util/util.pri b/src/widgets/util/util.pri index abfb1d86fe..16765558f6 100644 --- a/src/widgets/util/util.pri +++ b/src/widgets/util/util.pri @@ -25,8 +25,13 @@ SOURCES += \ util/qflickgesture.cpp \ util/qundogroup.cpp \ util/qundostack.cpp \ - util/qundoview.cpp \ - util/qsystemtrayicon_qpa.cpp + util/qundoview.cpp + +win32:!wince* { + SOURCES += util/qsystemtrayicon_win.cpp +} else { + SOURCES += util/qsystemtrayicon_qpa.cpp +} # TODO false:!x11:mac { -- cgit v1.2.3