diff options
author | Samuel Gaist <samuel.gaist@edeltech.ch> | 2014-07-20 14:41:27 (GMT) |
---|---|---|
committer | Morten Johan Sørvig <morten.sorvig@theqtcompany.com> | 2015-02-12 20:35:35 (GMT) |
commit | 6555ba030a29d995b2f53814b7999b81920fa0ce (patch) | |
tree | c71d8b143054efd6fd6be0927b8957913635de06 /src/gui | |
parent | 97b85f4f4e7fc14ff47cd92e4525f7a56864bff4 (diff) | |
download | Qt-6555ba030a29d995b2f53814b7999b81920fa0ce.zip Qt-6555ba030a29d995b2f53814b7999b81920fa0ce.tar.gz Qt-6555ba030a29d995b2f53814b7999b81920fa0ce.tar.bz2 |
Backport implementation of OS X QSystemTrayIcon from Qt 5
This patch aims to bring support of OS X >= 10.8 notification center and
update the growl support code.
[ChangeLog][OS X][Nofication] Added support for OS X 10.8 and upper
notification center.
Task-number: QTBUG-21830
Change-Id: Iad19c5e3a915e2caf15730a27ac762c9c11e493c
Reviewed-by: Morten Johan Sørvig <morten.sorvig@theqtcompany.com>
Diffstat (limited to 'src/gui')
-rw-r--r-- | src/gui/util/qsystemtrayicon_mac.mm | 172 |
1 files changed, 110 insertions, 62 deletions
diff --git a/src/gui/util/qsystemtrayicon_mac.mm b/src/gui/util/qsystemtrayicon_mac.mm index bcb3e07..7f8647c 100644 --- a/src/gui/util/qsystemtrayicon_mac.mm +++ b/src/gui/util/qsystemtrayicon_mac.mm @@ -99,7 +99,11 @@ QT_USE_NAMESPACE @class QT_MANGLE_NAMESPACE(QNSMenu); @class QT_MANGLE_NAMESPACE(QNSImageView); -@interface QT_MANGLE_NAMESPACE(QNSStatusItem) : NSObject { +@interface QT_MANGLE_NAMESPACE(QNSStatusItem) : NSObject +#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_8 + <NSUserNotificationCenterDelegate> +#endif +{ NSStatusItem *item; QSystemTrayIcon *icon; QSystemTrayIconPrivate *iconPrivate; @@ -112,6 +116,11 @@ QT_USE_NAMESPACE -(QRectF)geometry; - (void)triggerSelector:(id)sender button:(Qt::MouseButton)mouseButton; - (void)doubleClickSelector:(id)sender; + +#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_8 +- (BOOL)userNotificationCenter:(NSUserNotificationCenter *)center shouldPresentNotification:(NSUserNotification *)notification; +- (void)userNotificationCenter:(NSUserNotificationCenter *)center didActivateNotification:(NSUserNotification *)notification; +#endif @end @interface QT_MANGLE_NAMESPACE(QNSImageView) : NSImageView { @@ -148,12 +157,27 @@ public: QSystemTrayIconSys(QSystemTrayIcon *icon, QSystemTrayIconPrivate *d) { QMacCocoaAutoReleasePool pool; item = [[QT_MANGLE_NAMESPACE(QNSStatusItem) alloc] initWithIcon:icon iconPrivate:d]; +#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_8 + if (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_8) { + [[NSUserNotificationCenter defaultUserNotificationCenter] setDelegate:item]; + } +#endif } ~QSystemTrayIconSys() { QMacCocoaAutoReleasePool pool; [[[item item] view] setHidden: YES]; +#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_8 + if (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_8) { + [[NSUserNotificationCenter defaultUserNotificationCenter] setDelegate:nil]; + } +#endif [item release]; } + + void emitMessageClicked() { + emit [item icon]->messageClicked(); + } + QT_MANGLE_NAMESPACE(QNSStatusItem) *item; }; @@ -233,70 +257,80 @@ bool QSystemTrayIconPrivate::supportsMessages_sys() void QSystemTrayIconPrivate::showMessage_sys(const QString &title, const QString &message, QSystemTrayIcon::MessageIcon icon, int) { + if (!sys) + return; + +#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_8 + if (QSysInfo::MacintoshVersion >= QSysInfo::MV_10_8) { + NSUserNotification *notification = [[NSUserNotification alloc] init]; + notification.title = [NSString stringWithUTF8String:title.toUtf8().data()]; + notification.informativeText = [NSString stringWithUTF8String:message.toUtf8().data()]; + + [[NSUserNotificationCenter defaultUserNotificationCenter] deliverNotification:notification]; + + return; + } +#endif - if(sys) { #ifdef QT_MAC_SYSTEMTRAY_USE_GROWL - // Make sure that we have Growl installed on the machine we are running on. - QCFType<CFURLRef> cfurl; - OSStatus status = LSGetApplicationForInfo(kLSUnknownType, kLSUnknownCreator, - CFSTR("growlTicket"), kLSRolesAll, 0, &cfurl); - if (status == kLSApplicationNotFoundErr) - return; - QCFType<CFBundleRef> bundle = CFBundleCreate(0, cfurl); - - if (CFStringCompare(CFBundleGetIdentifier(bundle), CFSTR("com.Growl.GrowlHelperApp"), - kCFCompareCaseInsensitive | kCFCompareBackwards) != kCFCompareEqualTo) - return; - QPixmap notificationIconPixmap; - if(icon == QSystemTrayIcon::Information) - notificationIconPixmap = QApplication::style()->standardPixmap(QStyle::SP_MessageBoxInformation); - else if(icon == QSystemTrayIcon::Warning) - notificationIconPixmap = QApplication::style()->standardPixmap(QStyle::SP_MessageBoxWarning); - else if(icon == QSystemTrayIcon::Critical) - notificationIconPixmap = QApplication::style()->standardPixmap(QStyle::SP_MessageBoxCritical); - QTemporaryFile notificationIconFile; - QString notificationType(QLatin1String("Notification")), notificationIcon, notificationApp(QApplication::applicationName()); - if(notificationApp.isEmpty()) - notificationApp = QLatin1String("Application"); - if(!notificationIconPixmap.isNull() && notificationIconFile.open()) { - QImageWriter writer(¬ificationIconFile, "PNG"); - if(writer.write(notificationIconPixmap.toImage())) - notificationIcon = QLatin1String("image from location \"file://") + notificationIconFile.fileName() + QLatin1String("\""); - } - const QString script(QLatin1String( - "tell application \"GrowlHelperApp\"\n" - "-- Make a list of all the notification types (all)\n" - "set the allNotificationsList to {\"") + notificationType + QLatin1String("\"}\n" - - "-- Make a list of the notifications (enabled)\n" - "set the enabledNotificationsList to {\"") + notificationType + QLatin1String("\"}\n" - - "-- Register our script with growl.\n" - "register as application \"") + notificationApp + QLatin1String("\" all notifications allNotificationsList default notifications enabledNotificationsList\n" - - "-- Send a Notification...\n") + - QLatin1String("notify with name \"") + notificationType + - QLatin1String("\" title \"") + title + - QLatin1String("\" description \"") + message + - QLatin1String("\" application name \"") + notificationApp + - QLatin1String("\" ") + notificationIcon + - QLatin1String("\nend tell")); - qt_mac_execute_apple_script(script, 0); -#elif 0 - Q_Q(QSystemTrayIcon); - NSView *v = [[sys->item item] view]; - NSWindow *w = [v window]; - w = [[sys->item item] window]; - qDebug() << w << v; - QPoint p(qRound([w frame].origin.x), qRound([w frame].origin.y)); - qDebug() << p; - QBalloonTip::showBalloon(icon, message, title, q, QPoint(0, 0), msecs); + // Make sure that we have Growl installed on the machine we are running on. + QCFType<CFURLRef> cfurl; + OSStatus status = LSGetApplicationForInfo(kLSUnknownType, kLSUnknownCreator, + CFSTR("growlTicket"), kLSRolesAll, 0, &cfurl); + if (status == kLSApplicationNotFoundErr) + return; + QCFType<CFBundleRef> bundle = CFBundleCreate(0, cfurl); + + if (CFStringCompare(CFBundleGetIdentifier(bundle), CFSTR("com.Growl.GrowlHelperApp"), + kCFCompareCaseInsensitive | kCFCompareBackwards) != kCFCompareEqualTo) + return; + + QPixmap notificationIconPixmap; + if (icon == QSystemTrayIcon::Information) + notificationIconPixmap = QApplication::style()->standardPixmap(QStyle::SP_MessageBoxInformation); + else if (icon == QSystemTrayIcon::Warning) + notificationIconPixmap = QApplication::style()->standardPixmap(QStyle::SP_MessageBoxWarning); + else if (icon == QSystemTrayIcon::Critical) + notificationIconPixmap = QApplication::style()->standardPixmap(QStyle::SP_MessageBoxCritical); + + QTemporaryFile notificationIconFile; + QString notificationType(QLatin1String("Notification")), notificationIcon, notificationApp(QApplication::applicationName()); + if (notificationApp.isEmpty()) + notificationApp = QLatin1String("Application"); + if (!notificationIconPixmap.isNull() && notificationIconFile.open()) { + QImageWriter writer(¬ificationIconFile, "PNG"); + if (writer.write(notificationIconPixmap.toImage())) + notificationIcon = QLatin1String("image from location \"file://") + notificationIconFile.fileName() + QLatin1String("\""); + } + const QString script(QLatin1String( + "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" + + "-- Make a list of the notifications (enabled)\n" + "set the enabledNotificationsList to {\"") + notificationType + QLatin1String("\"}\n" + + "-- Register our script with growl.\n" + "register as application \"") + notificationApp + QLatin1String("\" all notifications allNotificationsList default notifications enabledNotificationsList\n" + + "-- Send a Notification...\n") + + QLatin1String("notify with name \"") + notificationType + + QLatin1String("\" title \"") + title + + QLatin1String("\" description \"") + message + + QLatin1String("\" application name \"") + notificationApp + + QLatin1String("\" ") + notificationIcon + + QLatin1String("\nend tell\nend if")); + qt_mac_execute_apple_script(script, 0); #else - Q_UNUSED(icon); - Q_UNUSED(title); - Q_UNUSED(message); + Q_UNUSED(icon); + Q_UNUSED(title); + Q_UNUSED(message); #endif - } + } QT_END_NAMESPACE @@ -357,7 +391,7 @@ QT_END_NAMESPACE [nsaltimage release]; } - if ((clickCount == 2)) { + if (clickCount == 2) { [self menuTrackingDone:nil]; [parent doubleClickSelector:self]; } else { @@ -475,6 +509,20 @@ QT_END_NAMESPACE qtsystray_sendActivated(icon, QSystemTrayIcon::DoubleClick); } +#if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_8 +- (BOOL)userNotificationCenter:(NSUserNotificationCenter *)center shouldPresentNotification:(NSUserNotification *)notification { + Q_UNUSED(center); + Q_UNUSED(notification); + return YES; +} + +- (void)userNotificationCenter:(NSUserNotificationCenter *)center didActivateNotification:(NSUserNotification *)notification { + Q_UNUSED(center); + Q_UNUSED(notification); + emit iconPrivate->sys->emitMessageClicked(); +} +#endif + @end class QSystemTrayIconQMenu : public QMenu |