Commit 6e7d440c authored by Juzef's avatar Juzef

Fix notification lifecycle

parent b8e9f6b2
......@@ -39,8 +39,6 @@ WindowNotifierWindow::WindowNotifierWindow(Notification *notification, QWidget *
setWindowRole("kadu-window-notifier");
CurrentNotification->acquire();
setWindowTitle(CurrentNotification->title());
setAttribute(Qt::WA_DeleteOnClose);
......@@ -49,7 +47,7 @@ WindowNotifierWindow::WindowNotifierWindow(Notification *notification, QWidget *
WindowNotifierWindow::~WindowNotifierWindow()
{
CurrentNotification->release();
emit closed(CurrentNotification);
}
void WindowNotifierWindow::createGui()
......
......@@ -42,6 +42,9 @@ public:
explicit WindowNotifierWindow(Notification *notification, QWidget *parent = 0);
virtual ~WindowNotifierWindow();
signals:
void closed(Notification *notification);
};
#endif // WINDOW_NOTIFIER_WINDOW_H
......@@ -181,8 +181,6 @@ void NotificationManager::notify(Notification *rawNotification)
bool foundNotifier = false;
bool foundNotifierWithCallbackSupported = !rawNotification->requireCallback();
notification->acquire();
foreach (Notifier *notifier, Notifiers)
{
if (config_file.readBoolEntry("Notify", notifyType + '_' + notifier->name()))
......@@ -209,8 +207,6 @@ void NotificationManager::notify(Notification *rawNotification)
if (!foundNotifier)
notification->callbackDiscard();
notification->release();
if (!foundNotifierWithCallbackSupported)
MessageDialog::show(KaduIcon("dialog-warning"), tr("Kadu"), tr("Unable to find notifier for %1 event").arg(rawNotification->type()));
......@@ -231,7 +227,7 @@ Notification * NotificationManager::findGroup(Notification *rawNotification)
connect(aggregate, SIGNAL(closed(Notification*)), this, SLOT(removeGrouped(Notification*)));
}
ActiveNotifications.insert(rawNotification->identifier(), aggregate);
ActiveNotifications.insert(aggregate->identifier(), aggregate);
return aggregate;
}
......
......@@ -26,34 +26,32 @@ AggregateNotification::AggregateNotification(Notification *firstNotification)
: Notification("aggregate", firstNotification->icon()), GroupKey(firstNotification->groupKey())
{
Notifications = QList<Notification *>();
Notifications.append(firstNotification);
addNotification(firstNotification);
}
void AggregateNotification::addNotification(Notification* notification)
{
Notifications.append(notification);
emit updated(this);
}
void AggregateNotification::acquire()
{
Notification::acquire();
connect(notification, SIGNAL(partialClosed(Notification *)), this, SLOT(partialNotificationClosed(Notification *)));
foreach (Notification *n, Notifications)
{
n->acquire();
}
emit updated(this);
}
void AggregateNotification::close()
{
foreach (Notification *n, Notifications)
if (!Closing)
{
n->close();
}
Closing = true;
foreach (Notification *n, Notifications)
{
n->partialClose();
}
Notification::close();
emit closed(this);
deleteLater();
}
}
const QString AggregateNotification::title() const
......@@ -104,15 +102,11 @@ bool AggregateNotification::requireCallback()
void AggregateNotification::callbackAccept()
{
close();
Notifications.first()->callbackAccept();
}
void AggregateNotification::callbackDiscard()
{
close();
Notifications.first()->callbackDiscard();
}
......@@ -121,3 +115,10 @@ void AggregateNotification::clearDefaultCallback()
Notifications.first()->clearDefaultCallback();
}
void AggregateNotification::partialNotificationClosed(Notification *notification)
{
Notifications.removeAll(notification);
close();
}
......@@ -45,7 +45,6 @@ public:
QList<Notification *> & notifications() { return Notifications; }
virtual void acquire();
virtual void close();
const QList<Callback> & getCallbacks() { return Notifications.first()->getCallbacks(); }
......@@ -61,6 +60,9 @@ public:
virtual bool isPeriodic() { return Notifications.first()->isPeriodic(); }
virtual int period() { return Notifications.first()->period(); }
protected slots:
void partialNotificationClosed(Notification *notification);
public slots:
virtual void callbackAccept();
virtual void callbackDiscard();
......
......@@ -23,6 +23,7 @@
#include "icons/kadu-icon.h"
#include "notify/notification-manager.h"
#include "notify/notifier.h"
#include "parser/parser.h"
#include "debug.h"
......@@ -50,8 +51,7 @@ void Notification::unregisterParserTags()
}
Notification::Notification(const QString &type, const KaduIcon &icon) :
Type(type), Icon(icon), DefaultCallbackTimer(0),
ReferencesCount(0), Closing(false)
Type(type), Icon(icon), DefaultCallbackTimer(0), Closing(false)
{
}
......@@ -59,20 +59,20 @@ Notification::~Notification()
{
}
void Notification::acquire()
void Notification::acquire(Notifier *notifier)
{
kdebugf();
ReferencesCount++;
Notifiers.insert(notifier);
}
void Notification::release()
void Notification::release(Notifier *notifier)
{
kdebugf();
ReferencesCount--;
Notifiers.remove(notifier);
if (ReferencesCount <= 0)
if (Notifiers.size() <= 0)
close();
}
......@@ -80,6 +80,13 @@ void Notification::close()
{
kdebugf();
emit closed(this);
}
void Notification::partialClose()
{
kdebugf();
if (!Closing)
{
Closing = true;
......
......@@ -32,6 +32,8 @@
class QTimer;
class Notifier;
/**
@class Notification
@author Rafa� 'Vogel' Malinowski
......@@ -122,7 +124,8 @@ private:
QList<Callback> Callbacks;
QTimer *DefaultCallbackTimer;
int ReferencesCount;
protected:
QSet<Notifier *> Notifiers;
bool Closing;
public:
......@@ -143,20 +146,22 @@ public:
/**
Wywo�ywane przez notyfikator, kt�ry zajmuje si� danym zdarzeniem.
**/
virtual void acquire();
virtual void acquire(Notifier *notifier);
/**
Wywo�ywane przez notyfikator, kt�ry przestaje zajmowa� si� danym zdarzeniem.
Gdy �aden notyfikator nie zajmuje si� danym zdarzeniem, zdarzenie jest zwalniane.
Wyst�puje to na przyk�ad w przypadku modu��w d�wi�kowych czy modu�u hints, gdy
dymek zniknie po up�ywie okre�lonego czasu a nie przez zdarzenie wywo�ane przez u�ytkownika.
**/
virtual void release();
virtual void release(Notifier *notifier);
/**
Zamyka zdarzenie. Wywo�uje sygna� closed() i usuwa obiekt.
**/
virtual void close();
void partialClose();
/**
Usuwa akcje u�ytkownika
**/
......@@ -263,7 +268,7 @@ public slots:
signals:
void updated(Notification *);
void partialClosed(Notification *);
void closed(Notification *);
......
......@@ -22,6 +22,7 @@
*/
#include "gui/windows/window-notifier-window.h"
#include "notify/notification/notification.h"
#include "notify/notification-manager.h"
#include "configuration/configuration-file.h"
......@@ -60,13 +61,21 @@ void WindowNotifier::notify(Notification *notification)
{
kdebugf();
notification->acquire(this);
WindowNotifierWindow *window = new WindowNotifierWindow(notification);
connect(window, SIGNAL(closed(Notification *)), this, SLOT(notificationClosed(Notification *)));
window->show();
_activateWindow(window);
kdebugf2();
}
void WindowNotifier::notificationClosed(Notification *notification)
{
notification->release(this);
}
void WindowNotifier::import_0_6_5_configuration()
{
config_file.addVariable("Notify", "StatusChanged/ToAway_Window", config_file.readEntry("Notify", "StatusChanged/ToBusy_Window"));
......
......@@ -37,6 +37,9 @@ class WindowNotifier : public Notifier
void import_0_6_5_configuration();
void createDefaultConfiguration();
private slots:
void notificationClosed(Notification *notification);
public:
explicit WindowNotifier(QObject *parent = 0);
virtual ~WindowNotifier();
......
......@@ -35,6 +35,7 @@
#include "icons/kadu-icon.h"
#include "misc/kadu-paths.h"
#include "notify/notification-manager.h"
#include "notify/notification/aggregate-notification.h"
#include "notify/notification/notification.h"
#include "notify/notify-event.h"
#include "url-handlers/url-handler-manager.h"
......@@ -162,7 +163,17 @@ void FreedesktopNotify::notify(Notification *notification)
QList<QVariant> args;
args.append("Kadu");
args.append(0U);
unsigned int replacedNotificationId = 0U;
unsigned int notificationUid = NotificationMap.key(notification);
if (notificationUid)
{
notificationClosed(notification);
replacedNotificationId = notificationUid;
}
args.append(replacedNotificationId);
KaduIcon icon(notification->icon());
if (icon.isNull())
......@@ -227,7 +238,15 @@ void FreedesktopNotify::notify(Notification *notification)
QStringList actions;
if (ServerSupportsActions)
{
foreach (const Notification::Callback &callback, notification->getCallbacks())
Notification *firstNotification = notification;
AggregateNotification *aggregateNotification = qobject_cast<AggregateNotification *>(notification);
if (aggregateNotification)
{
firstNotification = aggregateNotification->notifications().first();
}
foreach (const Notification::Callback &callback, firstNotification->getCallbacks())
{
actions << callback.Signature;
actions << callback.Caption;
......@@ -248,7 +267,7 @@ void FreedesktopNotify::notify(Notification *notification)
QDBusReply<unsigned int> reply = KNotify->callWithArgumentList(QDBus::Block, "Notify", args);
if (reply.isValid())
{
notification->acquire(); // do not remove now
notification->acquire(this); // do not remove now
connect(notification, SIGNAL(closed(Notification*)), this, SLOT(notificationClosed(Notification*)));
......@@ -284,7 +303,7 @@ void FreedesktopNotify::notificationClosed(unsigned int id, unsigned int reason)
Notification *notification = NotificationMap.take(id);
disconnect(notification, SIGNAL(closed(Notification*)), this, SLOT(notificationClosed(Notification*)));
notification->release();
notification->release(this);
}
void FreedesktopNotify::slotServiceOwnerChanged(const QString &serviceName, const QString &oldOwner, const QString &newOwner)
......@@ -298,7 +317,7 @@ void FreedesktopNotify::slotServiceOwnerChanged(const QString &serviceName, cons
{
Notification *notification = i.value();
disconnect(notification, SIGNAL(closed(Notification*)), this, SLOT(notificationClosed(Notification*)));
notification->release();
notification->release(this);
}
NotificationMap.clear();
......
......@@ -56,8 +56,6 @@ Hint::Hint(QWidget *parent, Notification *notification)
if (notification->type() == "Preview")
requireCallbacks = true;
notification->acquire();
AggregateNotification *aggregateNotification = qobject_cast<AggregateNotification *>(notification);
if (aggregateNotification)
{
......@@ -112,7 +110,6 @@ Hint::~Hint()
kdebugf();
disconnect(notification, 0, this, 0);
notification->release();
kdebugf2();
}
......
......@@ -262,11 +262,15 @@ void HintManager::deleteHint(Hint *hint)
{
kdebugf();
Notification *notification = hint->getNotification();
DisplayedNotifications.removeAll(hint->getNotification()->identifier());
hints.removeAll(hint);
layout->removeWidget(hint);
hint->deleteLater();
notification->release(this);
if (hints.isEmpty())
{
......@@ -433,6 +437,8 @@ Hint *HintManager::addHint(Notification *notification)
}
else
{
notification->acquire(this);
connect(notification, SIGNAL(closed(Notification *)), this, SLOT(notificationClosed(Notification *)));
hint = new Hint(frame, notification);
......
......@@ -145,13 +145,13 @@ NotifierConfigurationWidget *PCSpeaker::createConfigurationWidget(QWidget *paren
void PCSpeaker::notify(Notification *notification)
{
kdebugf();
notification->acquire();
notification->acquire(this);
#ifdef Q_OS_MACX
SysBeep(1);
#else
parseAndPlay(config_file.readEntry("PC Speaker", notification->type() + "_Sound"));
#endif
notification->release();
notification->release(this);
kdebugf2();
}
......
......@@ -115,7 +115,7 @@ void Qt4Notify::notify(Notification *notification)
if (Qt4TrayIcon::instance())
{
notification->acquire();
notification->acquire(this);
unsigned int timeout = config_file.readNumEntry("Qt4DockingNotify", QString("Event_") + notification->key() + "_timeout");
unsigned int icon = config_file.readNumEntry("Qt4DockingNotify", QString("Event_") + notification->key() + "_icon");
......@@ -126,7 +126,7 @@ void Qt4Notify::notify(Notification *notification)
parseText(syntax, notification, notification->details().join(QLatin1String("\n"))),
(QSystemTrayIcon::MessageIcon)icon, timeout * 1000);
notification->release();
notification->release(this);
}
kdebugf2();
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment