• Skip to content
  • Skip to link menu
KDE API Reference
  • KDE API Reference
  • kde-runtime API Reference
  • KDE Home
  • Contact Us
 

KNotify

  • sources
  • kde-4.14
  • kde-runtime
  • knotify
knotify.cpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2005-2009 by Olivier Goffart <ogoffart at kde.org>
3 
4 
5  This program is free software; you can redistribute it and/or modify
6  it under the terms of the GNU General Public License as published by
7  the Free Software Foundation; either version 2, or (at your option)
8  any later version.
9 
10  This program is distributed in the hope that it will be useful,
11  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  GNU General Public License for more details.
14 
15  You should have received a copy of the GNU General Public License
16  along with this program; if not, write to the Free Software
17  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
18 
19  */
20 
21 #include "knotify.h"
22 
23 // KDE headers
24 #include <kapplication.h>
25 #include <kconfig.h>
26 #include <kdebug.h>
27 #include <kglobal.h>
28 #include <klocale.h>
29 #include <kservicetypetrader.h>
30 
31 #include <config-runtime.h>
32 
33 #include "knotifyconfig.h"
34 #include "ksolidnotify.h"
35 #include "notifybysound.h"
36 #include "notifybypopup.h"
37 #include "notifybyexecute.h"
38 #include "notifybylogfile.h"
39 #include "notifybytaskbar.h"
40 #include "notifybyktts.h"
41 
42 
43 
44 KNotify::KNotify( QObject *parent )
45  : QObject( parent ),
46  m_counter(0)
47 {
48  loadConfig();
49  (void)new KNotifyAdaptor(this);
50  (void)new KSolidNotify(this);
51  QDBusConnection::sessionBus().registerObject("/Notify", this, QDBusConnection::ExportAdaptors
52  /*| QDBusConnection::ExportScriptableSlots | QDBusConnection::ExportScriptableSignals*/ );
53 }
54 
55 KNotify::~KNotify()
56 {
57  qDeleteAll(m_notifications);
58 }
59 
60 
61 void KNotify::loadConfig()
62 {
63  qDeleteAll(m_plugins);
64  m_plugins.clear();
65  addPlugin(new NotifyBySound(this));
66  addPlugin(new NotifyByPopup(this));
67  addPlugin(new NotifyByExecute(this));
68  addPlugin(new NotifyByLogfile(this));
69  //TODO reactivate on Mac/Win when KWindowSystem::demandAttention will implemented on this system.
70 #ifndef Q_WS_MAC
71  addPlugin(new NotifyByTaskbar(this));
72 #endif
73  addPlugin(new NotifyByKTTS(this));
74 
75  KService::List offers = KServiceTypeTrader::self()->query("KNotify/NotifyMethod");
76 
77  QVariantList args;
78  QString error;
79 
80  foreach (const KService::Ptr service, offers)
81  {
82  KNotifyPlugin *plugin = service->createInstance<KNotifyPlugin>(this, args, &error);
83  if (plugin)
84  {
85  addPlugin(plugin);
86  }
87  else
88  {
89  kDebug() << "Could not load plugin" << service->name() << "due to:" << error;
90  }
91  }
92 }
93 
94 void KNotify::addPlugin( KNotifyPlugin * p )
95 {
96  m_plugins[p->optionName()]=p;
97  connect(p,SIGNAL(finished( int )) , this , SLOT(slotPluginFinished( int ) ));
98  connect(p,SIGNAL(actionInvoked( int , int )) , this , SIGNAL(notificationActivated( int , int ) ));
99 }
100 
101 
102 
103 void KNotify::reconfigure()
104 {
105  KGlobal::config()->reparseConfiguration();
106  KNotifyConfig::reparseConfiguration();
107  loadConfig();
108 }
109 
110 void KNotify::closeNotification(int id)
111 {
112  if(!m_notifications.contains(id))
113  return;
114  Event *e=m_notifications[id];
115 
116  kDebug() << e->id << " ref=" << e->ref;
117 
118  //this has to be called before plugin->close or we will get double deletion because of slotPluginFinished
119  m_notifications.remove(id);
120 
121  if(e->ref>0)
122  {
123  e->ref++;
124  KNotifyPlugin *plugin;
125  foreach(plugin , m_plugins)
126  {
127  plugin->close( id );
128  }
129  }
130  notificationClosed(id);
131  delete e;
132 }
133 
134 int KNotify::event( const QString & event, const QString & appname, const ContextList & contexts, const QString & title, const QString & text, const KNotifyImage & image, const QStringList & actions, int timeout, WId winId )
135 {
136  m_counter++;
137  Event *e=new Event(appname , contexts , event );
138  e->id = m_counter;
139  e->ref = 1;
140 
141  e->config.title=title;
142  e->config.text=text;
143  e->config.actions=actions;
144  e->config.image=image;
145  e->config.timeout=timeout;
146  e->config.winId=(WId)winId;
147 
148  m_notifications.insert(m_counter,e);
149  emitEvent(e);
150 
151  e->ref--;
152  kDebug() << e->id << " ref=" << e->ref;
153  if(e->ref==0)
154  {
155  m_notifications.remove(e->id);
156  delete e;
157  return 0;
158  }
159  return m_counter;
160 }
161 
162 void KNotify::update(int id, const QString &title, const QString &text, const KNotifyImage& image, const QStringList& actions)
163 {
164  if(!m_notifications.contains(id))
165  return;
166 
167  Event *e=m_notifications[id];
168 
169  e->config.title=title;
170  e->config.text=text;
171  e->config.image = image;
172  e->config.actions = actions;
173 
174  foreach(KNotifyPlugin *p, m_plugins)
175  {
176  p->update(id, &e->config);
177  }
178 }
179 void KNotify::reemit(int id, const ContextList& contexts)
180 {
181  if(!m_notifications.contains(id))
182  return;
183  Event *e=m_notifications[id];
184  e->config.contexts=contexts;
185 
186  emitEvent(e);
187 }
188 
189 void KNotify::emitEvent(Event *e)
190 {
191  QString presentstring=e->config.readEntry("Action");
192  QStringList presents=presentstring.split ('|');
193 
194  if (!e->config.contexts.isEmpty() && !presents.first().isEmpty())
195  {
196  //Check whether the present actions are absolute, relative or invalid
197  bool relative = presents.first().startsWith('+') || presents.first().startsWith('-');
198  bool valid = true;
199  foreach (const QString & presentAction, presents)
200  valid &= ((presentAction.startsWith('+') || presentAction.startsWith('-')) == relative);
201  if (!valid)
202  {
203  kDebug() << "Context " << e->config.contexts << "present actions are invalid! Fallback to default present actions";
204  Event defaultEvent = Event(e->config.appname, ContextList(), e->config.eventid);
205  QString defaultPresentstring=defaultEvent.config.readEntry("Action");
206  presents = defaultPresentstring.split ('|');
207  } else if (relative)
208  {
209  // Obtain the list of present actions without context
210  Event noContextEvent = Event(e->config.appname, ContextList(), e->config.eventid);
211  QString noContextPresentstring = noContextEvent.config.readEntry("Action");
212  QSet<QString> noContextPresents = noContextPresentstring.split ('|').toSet();
213  foreach (const QString & presentAction, presents)
214  {
215  if (presentAction.startsWith('+'))
216  noContextPresents << presentAction.mid(1);
217  else
218  noContextPresents.remove(presentAction.mid(1));
219  }
220  presents = noContextPresents.toList();
221  }
222  }
223 
224  foreach(const QString & action , presents)
225  {
226  if(!m_plugins.contains(action))
227  continue;
228  KNotifyPlugin *p=m_plugins[action];
229  e->ref++;
230  p->notify(e->id,&e->config);
231  }
232 }
233 
234 void KNotify::slotPluginFinished( int id )
235 {
236  if(!m_notifications.contains(id))
237  return;
238  Event *e=m_notifications[id];
239  kDebug() << e->id << " ref=" << e->ref ;
240  e->ref--;
241  if(e->ref==0)
242  closeNotification( id );
243 }
244 
245 KNotifyAdaptor::KNotifyAdaptor(QObject *parent)
246  : QDBusAbstractAdaptor(parent)
247 {
248  setAutoRelaySignals(true);
249 }
250 
251 void KNotifyAdaptor::reconfigure()
252 {
253  static_cast<KNotify *>(parent())->reconfigure();
254 }
255 
256 void KNotifyAdaptor::closeNotification(int id)
257 {
258  static_cast<KNotify *>(parent())->closeNotification(id);
259 }
260 
261 int KNotifyAdaptor::event(const QString &event, const QString &fromApp, const QVariantList& contexts,
262  const QString &title, const QString &text, const QByteArray& image, const QStringList& actions,
263  int timeout, qlonglong winId)
264 // const QDBusMessage & , int _return )
265 
266 {
267  /* I'm not sure this is the right way to read a a(ss) type, but it seems to work */
268  ContextList contextlist;
269  QString context_key;
270  foreach( const QVariant &v , contexts)
271  {
272  /* this code doesn't work
273  QVariantList vl=v.toList();
274  if(vl.count() != 2)
275  {
276  kWarning() << "Bad structure passed as argument" ;
277  continue;
278  }
279  contextlist << qMakePair(vl[0].toString() , vl[1].toString());*/
280  QString s=v.toString();
281  if(context_key.isEmpty())
282  context_key=s;
283  else {
284  contextlist << qMakePair(context_key , s);
285  context_key = "";
286  }
287  }
288 
289  return static_cast<KNotify *>(parent())->event(event, fromApp, contextlist, title, text, image, actions, timeout, WId(winId));
290 }
291 
292 void KNotifyAdaptor::reemit(int id, const QVariantList& contexts)
293 {
294  ContextList contextlist;
295  QString context_key;
296  foreach( const QVariant &v , contexts)
297  {
298  QString s=v.toString();
299  if(context_key.isEmpty())
300  context_key=s;
301  else {
302  contextlist << qMakePair(context_key , s);
303  context_key = "";
304  }
305  }
306  static_cast<KNotify *>(parent())->reemit(id, contextlist);
307 }
308 
309 
310 void KNotifyAdaptor::update(int id, const QString &title, const QString &text, const QByteArray& image, const QStringList& actions )
311 {
312  static_cast<KNotify *>(parent())->update(id, title, text, image, actions);
313 }
314 
315 #include "knotify.moc"
316 
317 // vim: sw=4 sts=4 ts=8 et
318 
319 
KNotifyAdaptor::reemit
void reemit(int id, const QVariantList &contexts)
Definition: knotify.cpp:292
QHash::insert
iterator insert(const Key &key, const T &value)
NotifyByTaskbar
Definition: notifybytaskbar.h:29
QByteArray
KNotifyAdaptor::event
int event(const QString &event, const QString &fromApp, const QVariantList &contexts, const QString &title, const QString &text, const QByteArray &pixmap, const QStringList &actions, int timeout, qlonglong winId)
Definition: knotify.cpp:261
notifybysound.h
QString::split
QStringList split(const QString &sep, SplitBehavior behavior, Qt::CaseSensitivity cs) const
NotifyBySound
Definition: notifybysound.h:29
KNotifyPlugin
abstract class for KNotify actions
Definition: knotifyplugin.h:44
KNotifyConfig::reparseConfiguration
static void reparseConfiguration()
reparse the cached configs.
Definition: knotifyconfig.cpp:43
QDBusConnection::registerObject
bool registerObject(const QString &path, QObject *object, QFlags< QDBusConnection::RegisterOption > options)
KNotifyAdaptor::update
void update(int id, const QString &title, const QString &text, const QByteArray &pixmap, const QStringList &actions)
Definition: knotify.cpp:310
KNotify::update
void update(int id, const QString &title, const QString &text, const KNotifyImage &image, const QStringList &actions)
Definition: knotify.cpp:162
QDBusConnection::sessionBus
QDBusConnection sessionBus()
QList::toSet
QSet< T > toSet() const
knotifyconfig.h
NotifyByKTTS
Definition: notifybyktts.h:30
KNotifyPlugin::update
virtual void update(int id, KNotifyConfig *config)
This function is called when the notification has changed (such as the text or the icon) ...
Definition: knotifyplugin.cpp:38
KNotifyAdaptor::reconfigure
void reconfigure()
Definition: knotify.cpp:251
notifybylogfile.h
QDBusAbstractAdaptor
KNotifyImage
An image with lazy loading from the byte array.
Definition: knotifyconfig.h:37
KNotify::notificationClosed
void notificationClosed(int id)
knotify.h
KNotifyAdaptor
Definition: knotify.h:85
notifybypopup.h
QObject
notifybytaskbar.h
notifybyktts.h
KNotifyPlugin::notify
virtual void notify(int id, KNotifyConfig *config)=0
This function is called when the notification is sent.
QString::isEmpty
bool isEmpty() const
QString::startsWith
bool startsWith(const QString &s, Qt::CaseSensitivity cs) const
QSet
QList::first
T & first()
QString
QList< QPair< QString, QString > >
QHash::remove
int remove(const Key &key)
NotifyByLogfile
Definition: notifybylogfile.h:29
QStringList
QHash::clear
void clear()
KNotify
Definition: knotify.h:40
NotifyByPopup
Definition: notifybypopup.h:33
KNotify::notificationActivated
void notificationActivated(int id, int action)
KNotify::addPlugin
void addPlugin(KNotifyPlugin *p)
Definition: knotify.cpp:94
KNotify::reconfigure
void reconfigure()
Definition: knotify.cpp:103
KNotify::reemit
void reemit(int id, const ContextList &contexts)
Definition: knotify.cpp:179
KNotify::closeNotification
void closeNotification(int id)
Definition: knotify.cpp:110
KNotifyPlugin::close
virtual void close(int id)
This function is called when the notification has been closed.
Definition: knotifyplugin.cpp:44
ksolidnotify.h
QString::mid
QString mid(int position, int n) const
QSet::remove
bool remove(const T &value)
KNotify::~KNotify
~KNotify()
Definition: knotify.cpp:55
NotifyByExecute
Definition: notifybyexecute.h:29
KSolidNotify
Class which triggers solid notifications.
Definition: ksolidnotify.h:43
notifybyexecute.h
QSet::toList
QList< T > toList() const
KNotifyPlugin::optionName
virtual QString optionName()=0
return the name of this plugin.
QHash::contains
bool contains(const Key &key) const
KNotify::KNotify
KNotify(QObject *parent=0l)
Definition: knotify.cpp:44
KNotifyAdaptor::closeNotification
void closeNotification(int id)
Definition: knotify.cpp:256
QObject::connect
bool connect(const QObject *sender, const char *signal, const QObject *receiver, const char *method, Qt::ConnectionType type)
QObject::parent
QObject * parent() const
QVariant::toString
QString toString() const
KNotify::event
int event(const QString &event, const QString &fromApp, const ContextList &contexts, const QString &title, const QString &text, const KNotifyImage &image, const QStringList &actions, int timeout, WId winId=0)
Definition: knotify.cpp:134
QVariant
This file is part of the KDE documentation.
Documentation copyright © 1996-2020 The KDE developers.
Generated on Mon Jun 22 2020 13:08:23 by doxygen 1.8.7 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.

KNotify

Skip menu "KNotify"
  • Main Page
  • Namespace List
  • Namespace Members
  • Alphabetical List
  • Class List
  • Class Hierarchy
  • Class Members
  • File List
  • File Members
  • Related Pages

kde-runtime API Reference

Skip menu "kde-runtime API Reference"
  • KCMShell
  • KNotify
  • Plasma Runtime
  •     PlasmaCore
  •     DragAndDrop
  •     PlasmaComponents
  •     PlasmaExtraComponents
  •     QtExtraComponents

Search



Report problems with this website to our bug tracking system.
Contact the specific authors with questions and comments about the page contents.

KDE® and the K Desktop Environment® logo are registered trademarks of KDE e.V. | Legal