diff options
Diffstat (limited to 'kalarm/kalarmd')
-rw-r--r-- | kalarm/kalarmd/Makefile.am | 28 | ||||
-rw-r--r-- | kalarm/kalarmd/adapp.cpp | 71 | ||||
-rw-r--r-- | kalarm/kalarmd/adapp.h | 42 | ||||
-rw-r--r-- | kalarm/kalarmd/adcalendar.cpp | 253 | ||||
-rw-r--r-- | kalarm/kalarmd/adcalendar.h | 120 | ||||
-rw-r--r-- | kalarm/kalarmd/adconfigdata.cpp | 146 | ||||
-rw-r--r-- | kalarm/kalarmd/adconfigdata.h | 41 | ||||
-rw-r--r-- | kalarm/kalarmd/admain.cpp | 59 | ||||
-rw-r--r-- | kalarm/kalarmd/alarmdaemon.cpp | 614 | ||||
-rw-r--r-- | kalarm/kalarmd/alarmdaemon.h | 79 | ||||
-rw-r--r-- | kalarm/kalarmd/alarmdaemoniface.h | 45 | ||||
-rw-r--r-- | kalarm/kalarmd/alarmguiiface.h | 71 | ||||
-rw-r--r-- | kalarm/kalarmd/clientinfo.cpp | 110 | ||||
-rw-r--r-- | kalarm/kalarmd/clientinfo.h | 72 | ||||
-rw-r--r-- | kalarm/kalarmd/kalarmd.autostart.desktop | 103 | ||||
-rw-r--r-- | kalarm/kalarmd/kalarmd.desktop | 55 | ||||
-rw-r--r-- | kalarm/kalarmd/kalarmd.h | 40 |
17 files changed, 1949 insertions, 0 deletions
diff --git a/kalarm/kalarmd/Makefile.am b/kalarm/kalarmd/Makefile.am new file mode 100644 index 000000000..7770c6816 --- /dev/null +++ b/kalarm/kalarmd/Makefile.am @@ -0,0 +1,28 @@ +INCLUDES= -I$(top_srcdir) -I$(top_srcdir)/kalarm $(all_includes) + +noinst_LTLIBRARIES = libkalarmd.la + +libkalarmd_la_LDFLAGS = $(all_libraries) $(KDE_RPATH) +libkalarmd_la_LIBADD = $(LIB_KDECORE) $(top_builddir)/libkcal/libkcal.la +libkalarmd_la_SOURCES = alarmdaemoniface.stub alarmguiiface.stub + +bin_PROGRAMS = kalarmd + +kalarmd_LDFLAGS = $(all_libraries) $(KDE_RPATH) +kalarmd_LDADD = $(LIB_KDEUI) $(top_builddir)/libkcal/libkcal.la libkalarmd.la +kalarmd_SOURCES = alarmdaemon.cpp admain.cpp adapp.cpp \ + adcalendar.cpp adconfigdata.cpp clientinfo.cpp \ + alarmdaemoniface.skel +kalarmd_COMPILE_FIRST = alarmguiiface_stub.h + +noinst_HEADERS = adapp.h alarmdaemon.h alarmdaemoniface.h alarmguiiface.h \ + adcalendar.h adconfigdata.h clientinfo.h kalarmd.h + +METASOURCES = AUTO + +autostart_DATA = kalarmd.autostart.desktop +autostartdir = $(datadir)/autostart + +app_DATA = kalarmd.desktop +appdir = $(kde_appsdir)/.hidden + diff --git a/kalarm/kalarmd/adapp.cpp b/kalarm/kalarmd/adapp.cpp new file mode 100644 index 000000000..77f31e4f0 --- /dev/null +++ b/kalarm/kalarmd/adapp.cpp @@ -0,0 +1,71 @@ +/* + * adapp.cpp - kalarmd application + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright (c) 2001, 2004, 2005 by David Jarvie <software@astrojar.org.uk> + * Copyright (c) 2000,2001 Cornelius Schumacher <schumacher@kde.org> + * Copyright (c) 1997-1999 Preston Brown <pbrown@kde.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#include "kalarmd.h" + +#include <kcmdlineargs.h> +#include <kdebug.h> + +#include "alarmdaemon.h" +#include "adapp.moc" + + +AlarmDaemonApp::AlarmDaemonApp() + : KUniqueApplication(false, false), + mAd(0) +{ + disableSessionManagement(); +} + +int AlarmDaemonApp::newInstance() +{ + kdDebug(5900) << "AlarmDaemonApp::newInstance()" << endl; + + /* Prevent the application being restored automatically by the session manager + * at session startup. Instead, the KDE autostart facility is used to start + * the application. This allows the user to configure whether or not it is to + * be started automatically, and also ensures that it is started in the correct + * phase of session startup, i.e. after clients have been restored by the + * session manager. + */ + disableSessionManagement(); + + // Check if we already have a running alarm daemon widget + if (mAd) + return 0; + + // Check if we are starting up at session startup + static bool restored = false; + bool autostart = false; + if (!restored && isRestored()) + restored = true; // make sure we restore only once + else + { + KCmdLineArgs* args = KCmdLineArgs::parsedArgs(); + autostart = args->isSet("autostart"); + args->clear(); // free up memory + } + + mAd = new AlarmDaemon(autostart, 0, DAEMON_DCOP_OBJECT); + + return 0; +} diff --git a/kalarm/kalarmd/adapp.h b/kalarm/kalarmd/adapp.h new file mode 100644 index 000000000..83d11d298 --- /dev/null +++ b/kalarm/kalarmd/adapp.h @@ -0,0 +1,42 @@ +/* + * adapp.h - kalarmd application + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright (C) 2001, 2004 by David Jarvie <software@astrojar.org.uk> + * Copyright (c) 2000,2001 Cornelius Schumacher <schumacher@kde.org> + * Copyright (c) 1997-1999 Preston Brown <pbrown@kde.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#ifndef ADAPP_H +#define ADAPP_H + +#include <kuniqueapplication.h> + +class AlarmDaemon; + + +class AlarmDaemonApp : public KUniqueApplication +{ + Q_OBJECT + public: + AlarmDaemonApp(); + virtual int newInstance(); + + private: + AlarmDaemon* mAd; +}; + +#endif // ADAPP_H diff --git a/kalarm/kalarmd/adcalendar.cpp b/kalarm/kalarmd/adcalendar.cpp new file mode 100644 index 000000000..8af97cc0b --- /dev/null +++ b/kalarm/kalarmd/adcalendar.cpp @@ -0,0 +1,253 @@ +/* + * adcalendar.cpp - calendar file access + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright (c) 2001, 2004-2006 by David Jarvie <software@astrojar.org.uk> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#include <unistd.h> +#include <assert.h> + +#include <qfile.h> + +#include <ktempfile.h> +#include <kio/job.h> +#include <kio/jobclasses.h> +#include <kdebug.h> + +#include "adcalendar.moc" + +QValueList<ADCalendar*> ADCalendar::mCalendars; +ADCalendar::EventsMap ADCalendar::mEventsHandled; +ADCalendar::EventsMap ADCalendar::mEventsPending; +QStringList ADCalendar::mCalendarUrls; // never delete or reorder anything in this list! + + +ADCalendar::ADCalendar(const QString& url, const QCString& appname) + : KCal::CalendarLocal(QString::fromLatin1("UTC")), + mUrlString(url), + mAppName(appname), + mLoaded(false), + mLoadedConnected(false), + mUnregistered(false), + mEnabled(true) +{ + ADCalendar* cal = getCalendar(url); + if (cal) + { + kdError(5900) << "ADCalendar::ADCalendar(" << url << "): calendar already exists" << endl; + assert(0); + } + mUrlIndex = mCalendarUrls.findIndex(url); // get unique index for this URL + if (mUrlIndex < 0) + { + mUrlIndex = static_cast<int>(mCalendarUrls.count()); + mCalendarUrls.append(url); + } + loadFile(false); + mCalendars.append(this); +} + +ADCalendar::~ADCalendar() +{ + clearEventsHandled(); + mCalendars.remove(this); +} + +/****************************************************************************** +* Load the calendar file. +*/ +bool ADCalendar::loadFile(bool reset) +{ + if (reset) + clearEventsHandled(); + if (!mTempFileName.isNull()) + { + // Don't try to load the file if already downloading it + kdError(5900) << "ADCalendar::loadFile(): already downloading another file\n"; + return false; + } + mLoaded = false; + KURL url(mUrlString); + if (url.isLocalFile()) + { + // It's a local file + loadLocalFile(url.path()); + emit loaded(this, mLoaded); + } + else + { + // It's a remote file. Download to a temporary file before loading it + KTempFile tempFile; + mTempFileName = tempFile.name(); + KURL dest; + dest.setPath(mTempFileName); + KIO::FileCopyJob* job = KIO::file_copy(url, dest, -1, true); + connect(job, SIGNAL(result(KIO::Job*)), SLOT(slotDownloadJobResult(KIO::Job*))); + } + return true; +} + +void ADCalendar::slotDownloadJobResult(KIO::Job *job) +{ + if (job->error()) + { + KURL url(mUrlString); + kdDebug(5900) << "Error downloading calendar from " << url.prettyURL() << endl; + job->showErrorDialog(0); + } + else + { + kdDebug(5900) << "--- Downloaded to " << mTempFileName << endl; + loadLocalFile(mTempFileName); + } + unlink(QFile::encodeName(mTempFileName)); + mTempFileName = QString::null; + emit loaded(this, mLoaded); +} + +void ADCalendar::loadLocalFile(const QString& filename) +{ + mLoaded = load(filename); + if (!mLoaded) + kdDebug(5900) << "ADCalendar::loadLocalFile(): Error loading calendar file '" << filename << "'\n"; + else + clearEventsHandled(true); // remove all events which no longer exist from handled list +} + +bool ADCalendar::setLoadedConnected() +{ + if (mLoadedConnected) + return true; + mLoadedConnected = true; + return false; +} + +/****************************************************************************** +* Check whether all the alarms for the event with the given ID have already +* been handled. +*/ +bool ADCalendar::eventHandled(const KCal::Event* event, const QValueList<QDateTime>& alarmtimes) +{ + EventsMap::ConstIterator it = mEventsHandled.find(EventKey(event->uid(), mUrlIndex)); + if (it == mEventsHandled.end()) + return false; + + int oldCount = it.data().alarmTimes.count(); + int count = alarmtimes.count(); + for (int i = 0; i < count; ++i) + { + if (alarmtimes[i].isValid() + && (i >= oldCount // is it an additional alarm? + || !it.data().alarmTimes[i].isValid() // or has it just become due? + || it.data().alarmTimes[i].isValid() // or has it changed? + && alarmtimes[i] != it.data().alarmTimes[i])) + return false; // this alarm has changed + } + return true; +} + +/****************************************************************************** +* Remember that the event with the given ID has been handled. +* It must already be in the pending list. +*/ +void ADCalendar::setEventHandled(const QString& eventID) +{ + kdDebug(5900) << "ADCalendar::setEventHandled(" << eventID << ")\n"; + EventKey key(eventID, mUrlIndex); + + // Remove it from the pending list, and add it to the handled list + EventsMap::Iterator it = mEventsPending.find(key); + if (it != mEventsPending.end()) + { + setEventInMap(mEventsHandled, key, it.data().alarmTimes, it.data().eventSequence); + mEventsPending.remove(it); + } +} + +/****************************************************************************** +* Remember that the specified alarms for the event with the given ID have been +* notified to KAlarm, but no reply has come back yet. +*/ +void ADCalendar::setEventPending(const KCal::Event* event, const QValueList<QDateTime>& alarmtimes) +{ + if (event) + { + kdDebug(5900) << "ADCalendar::setEventPending(" << event->uid() << ")\n"; + EventKey key(event->uid(), mUrlIndex); + setEventInMap(mEventsPending, key, alarmtimes, event->revision()); + } +} + +/****************************************************************************** +* Add a specified entry to the events pending or handled list. +*/ +void ADCalendar::setEventInMap(EventsMap& map, const EventKey& key, const QValueList<QDateTime>& alarmtimes, int sequence) +{ + EventsMap::Iterator it = map.find(key); + if (it != map.end()) + { + // Update the existing entry for the event + it.data().alarmTimes = alarmtimes; + it.data().eventSequence = sequence; + } + else + map.insert(key, EventItem(sequence, alarmtimes)); +} + +/****************************************************************************** +* Clear all memory of events handled for the calendar. +*/ +void ADCalendar::clearEventsHandled(bool nonexistentOnly) +{ + clearEventMap(mEventsPending, nonexistentOnly); + clearEventMap(mEventsHandled, nonexistentOnly); +} + +/****************************************************************************** +* Clear the events pending or handled list of all events handled for the calendar. +*/ +void ADCalendar::clearEventMap(EventsMap& map, bool nonexistentOnly) +{ + for (EventsMap::Iterator it = map.begin(); it != map.end(); ) + { + if (it.key().calendarIndex == mUrlIndex + && (!nonexistentOnly || !event(it.key().eventID))) + { + EventsMap::Iterator i = it; + ++it; // prevent iterator becoming invalid with remove() + map.remove(i); + } + else + ++it; + } +} + +/****************************************************************************** +* Look up the calendar with the specified full calendar URL. +*/ +ADCalendar* ADCalendar::getCalendar(const QString& calendarURL) +{ + if (!calendarURL.isEmpty()) + { + for (ConstIterator it = begin(); it != end(); ++it) + { + if ((*it)->urlString() == calendarURL) + return *it; + } + } + return 0; +} diff --git a/kalarm/kalarmd/adcalendar.h b/kalarm/kalarmd/adcalendar.h new file mode 100644 index 000000000..656070bef --- /dev/null +++ b/kalarm/kalarmd/adcalendar.h @@ -0,0 +1,120 @@ +/* + * adcalendar.h - calendar file access + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright (c) 2001, 2004-2006 by David Jarvie <software@astrojar.org.uk> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#ifndef ADCALENDAR_H +#define ADCALENDAR_H + +#include <libkcal/calendarlocal.h> +namespace KIO { class Job; } +class ADCalendar; + + +// Alarm Daemon calendar access +class ADCalendar : public KCal::CalendarLocal +{ + Q_OBJECT + public: + typedef QValueList<ADCalendar*>::ConstIterator ConstIterator; + + ~ADCalendar(); + + const QString& urlString() const { return mUrlString; } + const QCString& appName() const { return mAppName; } + + void setEnabled(bool enabled) { mEnabled = enabled; } + bool enabled() const { return mEnabled && !unregistered(); } + bool available() const { return loaded() && !unregistered(); } + + // Client has registered since calendar was constructed, but + // has not since added the calendar. Monitoring is disabled. + void setUnregistered(bool u) { mUnregistered = u; } + bool unregistered() const { return mUnregistered; } + + void setEventPending(const KCal::Event*, const QValueList<QDateTime>&); + void setEventHandled(const QString& eventID); + void clearEventsHandled(bool nonexistentOnly = false); + bool eventHandled(const KCal::Event*, const QValueList<QDateTime>&); + + bool loadFile(bool reset); + bool setLoadedConnected(); // check status of mLoadedConnected and set it to true + bool downloading() const { return !mTempFileName.isNull(); } + bool loaded() const { return mLoaded; } + + + static ConstIterator begin() { return mCalendars.begin(); } + static ConstIterator end() { return mCalendars.end(); } + static ADCalendar* getCalendar(const QString& calendarURL); + + signals: + void loaded(ADCalendar*, bool success); + + protected: + // Only ClientInfo can construct ADCalendar objects + friend class ClientInfo; + ADCalendar(const QString& url, const QCString& appname); + + private slots: + void slotDownloadJobResult(KIO::Job*); + + private: + struct EventKey + { + EventKey() : calendarIndex(-1) { } + EventKey(const QString& id, int cal) : eventID(id), calendarIndex(cal) { } + bool operator<(const EventKey& k) const + { return (calendarIndex == k.calendarIndex) + ? (eventID < k.eventID) : (calendarIndex < k.calendarIndex); + } + QString eventID; + int calendarIndex; + }; + struct EventItem + { + EventItem() : eventSequence(0) { } + EventItem(int seqno, const QValueList<QDateTime>& alarmtimes) + : eventSequence(seqno), alarmTimes(alarmtimes) {} + int eventSequence; + QValueList<QDateTime> alarmTimes; + }; + + typedef QMap<EventKey, EventItem> EventsMap; // calendar/event ID, event sequence num + static EventsMap mEventsHandled; // IDs of already triggered events which have been processed by KAlarm + static EventsMap mEventsPending; // IDs of already triggered events not yet processed by KAlarm + static QStringList mCalendarUrls; // URLs of all calendars ever opened + static QValueList<ADCalendar*> mCalendars; // list of all constructed calendars + + ADCalendar(const ADCalendar&); // prohibit copying + ADCalendar& operator=(const ADCalendar&); // prohibit copying + + void loadLocalFile(const QString& filename); + void clearEventMap(EventsMap&, bool nonexistentOnly); + void setEventInMap(EventsMap&, const EventKey&, const QValueList<QDateTime>& alarmtimes, int sequence); + + QString mUrlString; // calendar file URL + QCString mAppName; // name of application owning this calendar + QString mTempFileName; // temporary file used if currently downloading, else null + int mUrlIndex; // unique index to URL in mCalendarUrls + bool mLoaded; // true if calendar file is currently loaded + bool mLoadedConnected; // true if the loaded() signal has been connected to AlarmDaemon + bool mUnregistered; // client has registered, but has not since added the calendar + bool mEnabled; // events are currently manually enabled +}; + +#endif // ADCALENDAR_H diff --git a/kalarm/kalarmd/adconfigdata.cpp b/kalarm/kalarmd/adconfigdata.cpp new file mode 100644 index 000000000..11dc6bf67 --- /dev/null +++ b/kalarm/kalarmd/adconfigdata.cpp @@ -0,0 +1,146 @@ +/* + * adcalendar.cpp - configuration file access + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright (C) 2001, 2004 by David Jarvie <software@astrojar.org.uk> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#include "kalarmd.h" + +#include <qregexp.h> +#include <qstringlist.h> + +#include <kconfig.h> +#include <kstandarddirs.h> +#include <kdebug.h> + +#include "adcalendar.h" +#include "adconfigdata.h" + +// Config file key strings +const QString CLIENT_GROUP(QString::fromLatin1("Client ")); +const QRegExp CLIENT_GROUP_SEARCH("^Client "); +// Client data file key strings +const QString CALENDAR_KEY(QString::fromLatin1("Calendar")); +const QString TITLE_KEY(QString::fromLatin1("Title")); +const QString DCOP_OBJECT_KEY(QString::fromLatin1("DCOP object")); +const QString START_CLIENT_KEY(QString::fromLatin1("Start")); + + +/****************************************************************************** +* Read the configuration file. +* Create the client list and open all calendar files. +*/ +void ADConfigData::readConfig() +{ + kdDebug(5900) << "ADConfigData::readConfig()" << endl; + ClientInfo::clear(); + KConfig* config = KGlobal::config(); + QStringList clients = config->groupList().grep(CLIENT_GROUP_SEARCH); + for (QStringList::Iterator cl = clients.begin(); cl != clients.end(); ++cl) + { + // Read this client's configuration + config->setGroup(*cl); + QString client = *cl; + client.remove(CLIENT_GROUP_SEARCH); + QString title = config->readEntry(TITLE_KEY, client); // read app title (default = app name) + QCString dcopObject = config->readEntry(DCOP_OBJECT_KEY).local8Bit(); + bool startClient = config->readBoolEntry(START_CLIENT_KEY, false); + QString calendar = config->readPathEntry(CALENDAR_KEY); + + // Verify the configuration + bool ok = false; + if (client.isEmpty() || KStandardDirs::findExe(client).isNull()) + kdError(5900) << "ADConfigData::readConfig(): group '" << *cl << "' deleted (client app not found)\n"; + else if (calendar.isEmpty()) + kdError(5900) << "ADConfigData::readConfig(): no calendar specified for '" << client << "'\n"; + else if (dcopObject.isEmpty()) + kdError(5900) << "ADConfigData::readConfig(): no DCOP object specified for '" << client << "'\n"; + else + { + ADCalendar* cal = ADCalendar::getCalendar(calendar); + if (cal) + kdError(5900) << "ADConfigData::readConfig(): calendar registered by multiple clients: " << calendar << endl; + else + ok = true; + } + if (!ok) + { + config->deleteGroup(*cl, true); + continue; + } + + // Create the client and calendar objects + new ClientInfo(client.local8Bit(), title, dcopObject, calendar, startClient); + kdDebug(5900) << "ADConfigData::readConfig(): client " << client << " : calendar " << calendar << endl; + } + + // Remove obsolete CheckInterval entry (if it exists) + config->setGroup("General"); + config->deleteEntry("CheckInterval"); + + // Save any updates + config->sync(); +} + +/****************************************************************************** +* Write a client application's details to the config file. +*/ +void ADConfigData::writeClient(const QCString& appName, const ClientInfo* cinfo) +{ + KConfig* config = KGlobal::config(); + config->setGroup(CLIENT_GROUP + QString::fromLocal8Bit(appName)); + config->writeEntry(TITLE_KEY, cinfo->title()); + config->writeEntry(DCOP_OBJECT_KEY, QString::fromLocal8Bit(cinfo->dcopObject())); + config->writeEntry(START_CLIENT_KEY, cinfo->startClient()); + config->writePathEntry(CALENDAR_KEY, cinfo->calendar()->urlString()); + config->sync(); +} + +/****************************************************************************** +* Remove a client application's details from the config file. +*/ +void ADConfigData::removeClient(const QCString& appName) +{ + KConfig* config = KGlobal::config(); + config->deleteGroup(CLIENT_GROUP + QString::fromLocal8Bit(appName)); + config->sync(); +} + +/****************************************************************************** +* Set the calendar file URL for a specified application. +*/ +void ADConfigData::setCalendar(const QCString& appName, ADCalendar* cal) +{ + KConfig* config = KGlobal::config(); + config->setGroup(CLIENT_GROUP + QString::fromLocal8Bit(appName)); + config->writePathEntry(CALENDAR_KEY, cal->urlString()); + config->sync(); +} + +/****************************************************************************** +* DCOP call to set autostart at login on or off. +*/ +void ADConfigData::enableAutoStart(bool on) +{ + kdDebug(5900) << "ADConfigData::enableAutoStart(" << on << ")\n"; + KConfig* config = KGlobal::config(); + config->reparseConfiguration(); + config->setGroup(QString::fromLatin1(DAEMON_AUTOSTART_SECTION)); + config->writeEntry(QString::fromLatin1(DAEMON_AUTOSTART_KEY), on); + config->sync(); +} + diff --git a/kalarm/kalarmd/adconfigdata.h b/kalarm/kalarmd/adconfigdata.h new file mode 100644 index 000000000..2c841fdff --- /dev/null +++ b/kalarm/kalarmd/adconfigdata.h @@ -0,0 +1,41 @@ +/* + * adconfigdata.h - configuration file access + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright (C) 2001, 2004 by David Jarvie <software@astrojar.org.uk> + * Based on the original, (c) 1998, 1999 Preston Brown + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#ifndef ADCONFIGDATA_H +#define ADCONFIGDATA_H + +#include "clientinfo.h" + +class ADCalendar; +class ClientInfo; + + +class ADConfigData +{ + public: + static void readConfig(); + static void writeClient(const QCString& appName, const ClientInfo*); + static void removeClient(const QCString& appName); + static void setCalendar(const QCString& appName, ADCalendar*); + static void enableAutoStart(bool); +}; + +#endif // ADCONFIGDATA_H diff --git a/kalarm/kalarmd/admain.cpp b/kalarm/kalarmd/admain.cpp new file mode 100644 index 000000000..c0a7792f1 --- /dev/null +++ b/kalarm/kalarmd/admain.cpp @@ -0,0 +1,59 @@ +/* + * admain.cpp - kalarmd main program + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright (c) 2001,2004,2005 by David Jarvie <software@astrojar.org.uk> + * Copyright (c) 2000,2001 Cornelius Schumacher <schumacher@kde.org> + * Copyright (c) 1997-1999 Preston Brown <pbrown@kde.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#include "kalarmd.h" + +#include <stdlib.h> + +#include <klocale.h> +#include <kcmdlineargs.h> +#include <kaboutdata.h> +#include <kstartupinfo.h> + +#include "adapp.h" + +static const KCmdLineOptions options[] = +{ + { "autostart", "", 0 }, + KCmdLineLastOption +}; + +int main(int argc, char** argv) +{ + KAboutData aboutData(DAEMON_APP_NAME, I18N_NOOP("KAlarm Daemon"), + DAEMON_VERSION, I18N_NOOP("KAlarm Alarm Daemon"), KAboutData::License_GPL, + "Copyright 1997-1999 Preston Brown\nCopyright 2000-2001 Cornelius Schumacher\nCopyright 2001,2004-2007 David Jarvie", 0, + "http://www.astrojar.org.uk/kalarm"); + aboutData.addAuthor("David Jarvie", I18N_NOOP("Maintainer"), "software@astrojar.org.uk"); + aboutData.addAuthor("Cornelius Schumacher", I18N_NOOP("Author"), "schumacher@kde.org"); + aboutData.addAuthor("Preston Brown", I18N_NOOP("Original Author"), "pbrown@kde.org"); + + KCmdLineArgs::init(argc, argv, &aboutData); + KCmdLineArgs::addCmdLineOptions(options); + KUniqueApplication::addCmdLineOptions(); + KStartupInfo::disableAutoAppStartedSending(); + + if (!AlarmDaemonApp::start()) + exit(0); + AlarmDaemonApp app; + return app.exec(); +} diff --git a/kalarm/kalarmd/alarmdaemon.cpp b/kalarm/kalarmd/alarmdaemon.cpp new file mode 100644 index 000000000..576678574 --- /dev/null +++ b/kalarm/kalarmd/alarmdaemon.cpp @@ -0,0 +1,614 @@ +/* + * alarmdaemon.cpp - alarm daemon control routines + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright © 2001,2004-2007 by David Jarvie <software@astrojar.org.uk> + * Based on the original, (c) 1998, 1999 Preston Brown + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#include "kalarmd.h" + +#include <unistd.h> +#include <stdlib.h> + +#include <qtimer.h> +#include <qfile.h> +#include <qdatetime.h> + +#include <kapplication.h> +#include <kstandarddirs.h> +#include <kprocess.h> +#include <kio/netaccess.h> +#include <dcopclient.h> +#include <kconfig.h> +#include <kdebug.h> + +#include <libkcal/calendarlocal.h> +#include <libkcal/icalformat.h> + +#include "adcalendar.h" +#include "adconfigdata.h" +#include "alarmguiiface.h" +#include "alarmguiiface_stub.h" +#include "alarmdaemon.moc" + + +#ifdef AUTOSTART_KALARM +// Number of seconds to wait before autostarting KAlarm. +// Allow plenty of time for session restoration to happen first. +static const int KALARM_AUTOSTART_TIMEOUT = 30; +#endif +static const int SECS_PER_DAY = 3600 * 24; + +// KAlarm config file keys +static const QString START_OF_DAY(QString::fromLatin1("StartOfDay")); +static const QString AUTOSTART_TRAY(QString::fromLatin1("AutostartTray")); + + +AlarmDaemon::AlarmDaemon(bool autostart, QObject *parent, const char *name) + : DCOPObject(name), + QObject(parent, name), + mAlarmTimer(0) +{ + kdDebug(5900) << "AlarmDaemon::AlarmDaemon()" << endl; + ADConfigData::readConfig(); + + ADConfigData::enableAutoStart(true); // switch autostart on whenever the program is run + + readKAlarmConfig(); // read time-related KAlarm config items + +#ifdef AUTOSTART_KALARM + if (autostart) + { + /* The alarm daemon is being autostarted. + * Check if KAlarm needs to be autostarted in the system tray. + * This should ideally be handled internally by KAlarm, but is done by kalarmd + * for the following reason: + * KAlarm needs to be both session restored and autostarted, but KDE doesn't + * currently cater properly for this - there is no guarantee that the session + * restoration activation will come before the autostart activation. If they + * come in the wrong order, KAlarm won't know that it is supposed to restore + * itself and instead will simply open a new window. + */ + KConfig kaconfig(locate("config", "kalarmrc")); + kaconfig.setGroup(QString::fromLatin1("General")); + autostart = kaconfig.readBoolEntry(AUTOSTART_TRAY, false); + if (autostart) + { + kdDebug(5900) << "AlarmDaemon::AlarmDaemon(): wait to autostart KAlarm\n"; + QTimer::singleShot(KALARM_AUTOSTART_TIMEOUT * 1000, this, SLOT(autostartKAlarm())); + } + } + if (!autostart) +#endif + startMonitoring(); // otherwise, start monitoring alarms now +} + +/****************************************************************************** +* DCOP call to quit the program. +*/ +void AlarmDaemon::quit() +{ + kdDebug(5900) << "AlarmDaemon::quit()" << endl; + exit(0); +} + +/****************************************************************************** +* Called after a timer delay to autostart KAlarm in the system tray. +*/ +void AlarmDaemon::autostartKAlarm() +{ +#ifdef AUTOSTART_KALARM + if (mAlarmTimer) + { + kdDebug(5900) << "AlarmDaemon::autostartKAlarm(): KAlarm already registered\n"; + return; // KAlarm has already registered with us + } + kdDebug(5900) << "AlarmDaemon::autostartKAlarm(): starting KAlarm\n"; + QStringList args; + args << QString::fromLatin1("--tray"); + int ret = KApplication::kdeinitExec(QString::fromLatin1("kalarm"), args); + if (ret) + kdError(5900) << "AlarmDaemon::autostartKAlarm(): error=" << ret << endl; + else + kdDebug(5900) << "AlarmDaemon::autostartKAlarm(): success" << endl; + + startMonitoring(); +#endif +} + +/****************************************************************************** +* Start monitoring alarms. +*/ +void AlarmDaemon::startMonitoring() +{ + // Set up the alarm timer + mAlarmTimer = new QTimer(this); + connect(mAlarmTimer, SIGNAL(timeout()), SLOT(checkAlarmsSlot())); + setTimerStatus(); + + // Start monitoring calendar files. + // They are monitored until their client application registers, upon which + // monitoring ceases until KAlarm tells the daemon to monitor it. + checkAlarms(); +} + +/****************************************************************************** +* DCOP call to enable or disable monitoring of a calendar. +*/ +void AlarmDaemon::enableCal(const QString& urlString, bool enable) +{ + kdDebug(5900) << "AlarmDaemon::enableCal(" << urlString << ")" << endl; + ADCalendar* cal = ADCalendar::getCalendar(urlString); + if (cal) + { + cal->setEnabled(enable); + notifyCalStatus(cal); // notify KAlarm + } +} + +/****************************************************************************** +* DCOP call to reload, and optionally reset, the specified calendar. +*/ +void AlarmDaemon::reloadCal(const QCString& appname, const QString& urlString, bool reset) +{ + kdDebug(5900) << "AlarmDaemon::reloadCal(" << urlString << ")" << endl; + ADCalendar* cal = ADCalendar::getCalendar(urlString); + if (!cal || cal->appName() != appname) + return; + reloadCal(cal, reset); +} + +/****************************************************************************** +* Reload the specified calendar. +* If 'reset' is true, the data associated with the calendar is reset. +*/ +void AlarmDaemon::reloadCal(ADCalendar* cal, bool reset) +{ + kdDebug(5900) << "AlarmDaemon::reloadCal(): calendar" << endl; + if (!cal) + return; + if (!cal->downloading()) + { + cal->close(); + if (!cal->setLoadedConnected()) + connect(cal, SIGNAL(loaded(ADCalendar*, bool)), SLOT(calendarLoaded(ADCalendar*, bool))); + cal->loadFile(reset); + } + else if (reset) + cal->clearEventsHandled(); +} + +void AlarmDaemon::calendarLoaded(ADCalendar* cal, bool success) +{ + if (success) + kdDebug(5900) << "Calendar reloaded" << endl; + notifyCalStatus(cal); // notify KAlarm + setTimerStatus(); + checkAlarms(cal); +} + +/****************************************************************************** +* DCOP call to notify the daemon that an event has been handled, and optionally +* to tell it to reload the calendar. +*/ +void AlarmDaemon::eventHandled(const QCString& appname, const QString& calendarUrl, const QString& eventID, bool reload) +{ + QString urlString = expandURL(calendarUrl); + kdDebug(5900) << "AlarmDaemon::eventHandled(" << urlString << (reload ? "): reload" : ")") << endl; + ADCalendar* cal = ADCalendar::getCalendar(urlString); + if (!cal || cal->appName() != appname) + return; + cal->setEventHandled(eventID); + if (reload) + reloadCal(cal, false); +} + +/****************************************************************************** +* DCOP call to add an application to the list of client applications, +* and add it to the config file. +* N.B. This method must not return a bool because DCOPClient::call() can cause +* a hang if the daemon happens to send a notification to KAlarm at the +* same time as KAlarm calls this DCCOP method. +*/ +void AlarmDaemon::registerApp(const QCString& appName, const QString& appTitle, + const QCString& dcopObject, const QString& calendarUrl, + bool startClient) +{ + kdDebug(5900) << "AlarmDaemon::registerApp(" << appName << ", " << appTitle << ", " + << dcopObject << ", " << startClient << ")" << endl; + KAlarmd::RegisterResult result; + if (appName.isEmpty()) + result = KAlarmd::FAILURE; + else if (startClient && KStandardDirs::findExe(appName).isNull()) + { + kdError() << "AlarmDaemon::registerApp(): app not found" << endl; + result = KAlarmd::NOT_FOUND; + } + else + { + ADCalendar* keepCal = 0; + ClientInfo* client = ClientInfo::get(appName); + if (client) + { + // The application is already a client. + // If it's the same calendar file, don't delete its calendar object. + if (client->calendar() && client->calendar()->urlString() == calendarUrl) + { + keepCal = client->calendar(); + client->detachCalendar(); + } + ClientInfo::remove(appName); // this deletes the calendar if not detached + } + + if (keepCal) + client = new ClientInfo(appName, appTitle, dcopObject, keepCal, startClient); + else + client = new ClientInfo(appName, appTitle, dcopObject, calendarUrl, startClient); + client->calendar()->setUnregistered(false); + ADConfigData::writeClient(appName, client); + + ADConfigData::enableAutoStart(true); + setTimerStatus(); + notifyCalStatus(client->calendar()); + result = KAlarmd::SUCCESS; + } + + // Notify the client of whether the call succeeded. + AlarmGuiIface_stub stub(appName, dcopObject); + stub.registered(false, result, DAEMON_VERSION_NUM); + kdDebug(5900) << "AlarmDaemon::registerApp() -> " << result << endl; +} + +/****************************************************************************** +* DCOP call to change whether KAlarm should be started when an event needs to +* be notified to it. +* N.B. This method must not return a bool because DCOPClient::call() can cause +* a hang if the daemon happens to send a notification to KAlarm at the +* same time as KAlarm calls this DCCOP method. +*/ +void AlarmDaemon::registerChange(const QCString& appName, bool startClient) +{ + kdDebug(5900) << "AlarmDaemon::registerChange(" << appName << ", " << startClient << ")" << endl; + KAlarmd::RegisterResult result; + ClientInfo* client = ClientInfo::get(appName); + if (!client) + return; // can't access client to tell it the result + if (startClient && KStandardDirs::findExe(appName).isNull()) + { + kdError() << "AlarmDaemon::registerChange(): app not found" << endl; + result = KAlarmd::NOT_FOUND; + } + else + { + client->setStartClient(startClient); + ADConfigData::writeClient(appName, client); + result = KAlarmd::SUCCESS; + } + + // Notify the client of whether the call succeeded. + AlarmGuiIface_stub stub(appName, client->dcopObject()); + stub.registered(true, result, DAEMON_VERSION_NUM); + kdDebug(5900) << "AlarmDaemon::registerChange() -> " << result << endl; +} + +/****************************************************************************** +* DCOP call to set autostart at login on or off. +*/ +void AlarmDaemon::enableAutoStart(bool on) +{ + ADConfigData::enableAutoStart(on); +} + +/****************************************************************************** +* Check if any alarms are pending for any enabled calendar, and display the +* pending alarms. +* Called by the alarm timer. +*/ +void AlarmDaemon::checkAlarmsSlot() +{ + kdDebug(5901) << "AlarmDaemon::checkAlarmsSlot()" << endl; + if (mAlarmTimerSyncing) + { + // We've synched to the minute boundary. Now set timer to the check interval. + mAlarmTimer->changeInterval(DAEMON_CHECK_INTERVAL * 1000); + mAlarmTimerSyncing = false; + mAlarmTimerSyncCount = 10; // resynch every 10 minutes, in case of glitches + } + else if (--mAlarmTimerSyncCount <= 0) + { + int interval = DAEMON_CHECK_INTERVAL + 1 - QTime::currentTime().second(); + if (interval < DAEMON_CHECK_INTERVAL - 1) + { + // Need to re-synch to 1 second past the minute + mAlarmTimer->changeInterval(interval * 1000); + mAlarmTimerSyncing = true; + kdDebug(5900) << "Resynching alarm timer" << endl; + } + else + mAlarmTimerSyncCount = 10; + } + checkAlarms(); +} + +/****************************************************************************** +* Check if any alarms are pending for any enabled calendar, and display the +* pending alarms. +*/ +void AlarmDaemon::checkAlarms() +{ + kdDebug(5901) << "AlarmDaemon::checkAlarms()" << endl; + for (ADCalendar::ConstIterator it = ADCalendar::begin(); it != ADCalendar::end(); ++it) + checkAlarms(*it); +} + +/****************************************************************************** +* Check if any alarms are pending for a specified calendar, and display the +* pending alarms. +*/ +void AlarmDaemon::checkAlarms(ADCalendar* cal) +{ + kdDebug(5901) << "AlarmDaemons::checkAlarms(" << cal->urlString() << ")" << endl; + if (!cal->loaded() || !cal->enabled()) + return; + + QDateTime now = QDateTime::currentDateTime(); + kdDebug(5901) << " To: " << now.toString() << endl; + QValueList<KCal::Alarm*> alarms = cal->alarmsTo(now); + if (!alarms.count()) + return; + QValueList<KCal::Event*> eventsDone; + for (QValueList<KCal::Alarm*>::ConstIterator it = alarms.begin(); it != alarms.end(); ++it) + { + KCal::Event* event = dynamic_cast<KCal::Event*>((*it)->parent()); + if (!event || eventsDone.find(event) != eventsDone.end()) + continue; // either not an event, or the event has already been processed + eventsDone += event; + const QString& eventID = event->uid(); + kdDebug(5901) << "AlarmDaemon::checkAlarms(): event " << eventID << endl; + + // Check which of the alarms for this event are due. + // The times in 'alarmtimes' corresponding to due alarms are set. + // The times for non-due alarms are set invalid in 'alarmtimes'. + bool recurs = event->doesRecur(); + const QStringList cats = event->categories(); + bool floats = (cats.find(QString::fromLatin1("DATE")) != cats.end()); + QDateTime nextDateTime = event->dtStart(); + if (recurs) + { + QString prop = event->customProperty("KALARM", "NEXTRECUR"); + if (prop.length() >= 8) + { + // The next due recurrence time is specified + QDate d(prop.left(4).toInt(), prop.mid(4,2).toInt(), prop.mid(6,2).toInt()); + if (d.isValid()) + { + if (floats && prop.length() == 8) + nextDateTime = d; + else if (!floats && prop.length() == 15 && prop[8] == QChar('T')) + { + QTime t(prop.mid(9,2).toInt(), prop.mid(11,2).toInt(), prop.mid(13,2).toInt()); + if (t.isValid()) + nextDateTime = QDateTime(d, t); + } + } + } + } + if (floats) + nextDateTime.setTime(mStartOfDay); + QValueList<QDateTime> alarmtimes; + KCal::Alarm::List alarms = event->alarms(); + for (KCal::Alarm::List::ConstIterator al = alarms.begin(); al != alarms.end(); ++al) + { + KCal::Alarm* alarm = *al; + QDateTime dt; + if (alarm->enabled()) + { + QDateTime dt1; + if (!alarm->hasTime()) + { + // Find the latest recurrence for the alarm. + // Need to do this for alarms with offsets in order to detect + // reminders due for recurrences. + int offset = alarm->hasStartOffset() ? alarm->startOffset().asSeconds() + : alarm->endOffset().asSeconds() + event->dtStart().secsTo(event->dtEnd()); + if (offset) + { + dt1 = nextDateTime.addSecs(floats ? (offset/SECS_PER_DAY)*SECS_PER_DAY : offset); + if (dt1 > now) + dt1 = QDateTime(); + } + } + // Get latest due repetition, or the recurrence time if none + dt = nextDateTime; + if (nextDateTime <= now && alarm->repeatCount() > 0) + { + int snoozeSecs = alarm->snoozeTime() * 60; + int offset = alarm->repeatCount() * snoozeSecs; + QDateTime lastRepetition = nextDateTime.addSecs(floats ? (offset/SECS_PER_DAY)*SECS_PER_DAY : offset); + if (lastRepetition <= now) + dt = lastRepetition; + else + { + int repetition = nextDateTime.secsTo(now) / snoozeSecs; + int offset = repetition * snoozeSecs; + dt = nextDateTime.addSecs(floats ? (offset/SECS_PER_DAY)*SECS_PER_DAY : offset); + } + } + if (!dt.isValid() || dt > now + || dt1.isValid() && dt1 > dt) // already tested dt1 <= now + dt = dt1; + } + alarmtimes.append(dt); + } + if (!cal->eventHandled(event, alarmtimes)) + { + if (notifyEvent(cal, eventID)) + cal->setEventPending(event, alarmtimes); + } + } +} + +/****************************************************************************** +* Send a DCOP message to KAlarm telling it that an alarm should now be handled. +* Reply = false if the event should be held pending until KAlarm can be started. +*/ +bool AlarmDaemon::notifyEvent(ADCalendar* calendar, const QString& eventID) +{ + if (!calendar) + return true; + QCString appname = calendar->appName(); + const ClientInfo* client = ClientInfo::get(appname); + if (!client) + { + kdDebug(5900) << "AlarmDaemon::notifyEvent(" << appname << "): unknown client" << endl; + return false; + } + kdDebug(5900) << "AlarmDaemon::notifyEvent(" << appname << ", " << eventID << "): notification type=" << client->startClient() << endl; + QString id = QString::fromLatin1("ad:") + eventID; // prefix to indicate that the notification if from the daemon + + // Check if the client application is running and ready to receive notification + bool registered = kapp->dcopClient()->isApplicationRegistered(static_cast<const char*>(appname)); + bool ready = registered; + if (registered) + { + // It's running, but check if it has created our DCOP interface yet + QCStringList objects = kapp->dcopClient()->remoteObjects(appname); + if (objects.find(client->dcopObject()) == objects.end()) + ready = false; + } + if (!ready) + { + // KAlarm is not running, or is not yet ready to receive notifications. + if (!client->startClient()) + { + if (registered) + kdDebug(5900) << "AlarmDaemon::notifyEvent(): client not ready\n"; + else + kdDebug(5900) << "AlarmDaemon::notifyEvent(): don't start client\n"; + return false; + } + + // Start KAlarm, using the command line to specify the alarm + KProcess p; + QString cmd = locate("exe", appname); + if (cmd.isEmpty()) + { + kdDebug(5900) << "AlarmDaemon::notifyEvent(): '" << appname << "' not found" << endl; + return true; + } + p << cmd; + p << "--handleEvent" << id << "--calendarURL" << calendar->urlString(); + p.start(KProcess::DontCare); + kdDebug(5900) << "AlarmDaemon::notifyEvent(): used command line" << endl; + return true; + } + + // Notify the client by telling it the calendar URL and event ID + AlarmGuiIface_stub stub(appname, client->dcopObject()); + stub.handleEvent(calendar->urlString(), id); + if (!stub.ok()) + { + kdDebug(5900) << "AlarmDaemon::notifyEvent(): dcop send failed" << endl; + return false; + } + return true; +} + +/****************************************************************************** +* Starts or stops the alarm timer as necessary after a calendar is enabled/disabled. +*/ +void AlarmDaemon::setTimerStatus() +{ +#ifdef AUTOSTART_KALARM + if (!mAlarmTimer) + { + // KAlarm is now running, so start monitoring alarms + startMonitoring(); + return; // startMonitoring() calls this method + } + +#endif + // Count the number of currently loaded calendars whose names should be displayed + int nLoaded = 0; + for (ADCalendar::ConstIterator it = ADCalendar::begin(); it != ADCalendar::end(); ++it) + if ((*it)->loaded()) + ++nLoaded; + + // Start or stop the alarm timer if necessary + if (!mAlarmTimer->isActive() && nLoaded) + { + // Timeout every minute. + // But first synchronise to one second after the minute boundary. + int firstInterval = DAEMON_CHECK_INTERVAL + 1 - QTime::currentTime().second(); + mAlarmTimer->start(1000 * firstInterval); + mAlarmTimerSyncing = (firstInterval != DAEMON_CHECK_INTERVAL); + kdDebug(5900) << "Started alarm timer" << endl; + } + else if (mAlarmTimer->isActive() && !nLoaded) + { + mAlarmTimer->stop(); + kdDebug(5900) << "Stopped alarm timer" << endl; + } +} + +/****************************************************************************** +* Send a DCOP message to to the client which owns the specified calendar, +* notifying it of a change in calendar status. +*/ +void AlarmDaemon::notifyCalStatus(const ADCalendar* cal) +{ + ClientInfo* client = ClientInfo::get(cal); + if (!client) + return; + QCString appname = client->appName(); + if (kapp->dcopClient()->isApplicationRegistered(static_cast<const char*>(appname))) + { + KAlarmd::CalendarStatus change = cal->available() ? (cal->enabled() ? KAlarmd::CALENDAR_ENABLED : KAlarmd::CALENDAR_DISABLED) + : KAlarmd::CALENDAR_UNAVAILABLE; + kdDebug(5900) << "AlarmDaemon::notifyCalStatus() sending:" << appname << " -> " << change << endl; + AlarmGuiIface_stub stub(appname, client->dcopObject()); + stub.alarmDaemonUpdate(change, cal->urlString()); + if (!stub.ok()) + kdError(5900) << "AlarmDaemon::notifyCalStatus(): dcop send failed:" << appname << endl; + } +} + +/****************************************************************************** +* Read all relevant items from KAlarm config. +* Executed on DCOP call to notify a time related value change in the KAlarm +* config file. +*/ +void AlarmDaemon::readKAlarmConfig() +{ + KConfig config(locate("config", "kalarmrc")); + config.setGroup(QString::fromLatin1("General")); + QDateTime defTime(QDate(1900,1,1), QTime()); + mStartOfDay = config.readDateTimeEntry(START_OF_DAY, &defTime).time(); + kdDebug(5900) << "AlarmDaemon::readKAlarmConfig()" << endl; +} + +/****************************************************************************** +* Expand a DCOP call parameter URL to a full URL. +* (We must store full URLs in the calendar data since otherwise later calls to +* reload or remove calendars won't necessarily find a match.) +*/ +QString AlarmDaemon::expandURL(const QString& urlString) +{ + if (urlString.isEmpty()) + return QString(); + return KURL(urlString).url(); +} diff --git a/kalarm/kalarmd/alarmdaemon.h b/kalarm/kalarmd/alarmdaemon.h new file mode 100644 index 000000000..6ab5d0f9a --- /dev/null +++ b/kalarm/kalarmd/alarmdaemon.h @@ -0,0 +1,79 @@ +/* + * alarmdaemon.h - alarm daemon control routines + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright © 2001,2004-2007 by David Jarvie <software@astrojar.org.uk> + * Based on the original, (c) 1998, 1999 Preston Brown + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#ifndef ALARMDAEMON_H +#define ALARMDAEMON_H + +#include <libkcal/calendarlocal.h> + +#include "alarmdaemoniface.h" + +class ADCalendar; + + +class AlarmDaemon : public QObject, virtual public AlarmDaemonIface +{ + Q_OBJECT + public: + AlarmDaemon(bool autostart, QObject* parent = 0, const char* name = 0); + + private slots: +//#ifdef AUTOSTART_KALARM + void autostartKAlarm(); +//#endif + void calendarLoaded(ADCalendar*, bool success); + void checkAlarmsSlot(); + void checkAlarms(); + + private: + // DCOP interface + void enableAutoStart(bool enable); + void enableCalendar(const QString& urlString, bool enable) + { enableCal(expandURL(urlString), enable); } + void reloadCalendar(const QCString& appname, const QString& urlString) + { reloadCal(appname, expandURL(urlString), false); } + void resetCalendar(const QCString& appname, const QString& urlString) + { reloadCal(appname, expandURL(urlString), true); } + void registerApp(const QCString& appName, const QString& appTitle, const QCString& dcopObject, + const QString& calendarUrl, bool startClient); + void registerChange(const QCString& appName, bool startClient); + void eventHandled(const QCString& appname, const QString& calendarURL, const QString& eventID, bool reload); + void timeConfigChanged() { readKAlarmConfig(); } + void quit(); + // Other methods + void readKAlarmConfig(); + void startMonitoring(); + void enableCal(const QString& urlString, bool enable); + void reloadCal(const QCString& appname, const QString& urlString, bool reset); + void reloadCal(ADCalendar*, bool reset); + void checkAlarms(ADCalendar*); + bool notifyEvent(ADCalendar*, const QString& eventID); + void notifyCalStatus(const ADCalendar*); + void setTimerStatus(); + static QString expandURL(const QString& urlString); + + QTimer* mAlarmTimer; + int mAlarmTimerSyncCount; // countdown to re-synching the alarm timer + bool mAlarmTimerSyncing; // true while alarm timer interval < 1 minute + QTime mStartOfDay; // start of day for date-only alarms +}; + +#endif // ALARMDAEMON_H diff --git a/kalarm/kalarmd/alarmdaemoniface.h b/kalarm/kalarmd/alarmdaemoniface.h new file mode 100644 index 000000000..708f5b281 --- /dev/null +++ b/kalarm/kalarmd/alarmdaemoniface.h @@ -0,0 +1,45 @@ +/* + * alarmdaemoniface.h - DCOP request interface + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright © 2001,2004-2007 by David Jarvie <software@astrojar.org.uk> + * Copyright (c) 2000,2001 Cornelius Schumacher <schumacher@kde.org> + * Copyright (c) 1997-1999 Preston Brown <pbrown@kde.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#ifndef ALARMDAEMONIFACE_H +#define ALARMDAEMONIFACE_H + +#include <dcopobject.h> + + +class AlarmDaemonIface : virtual public DCOPObject +{ + K_DCOP + k_dcop: + virtual ASYNC enableAutoStart(bool enable) = 0; + virtual ASYNC enableCalendar(const QString& urlString, bool enable) = 0; + virtual ASYNC reloadCalendar(const QCString& appname, const QString& urlString) = 0; + virtual ASYNC resetCalendar(const QCString& appname, const QString& urlString) = 0; + virtual ASYNC registerApp(const QCString& appName, const QString& appTitle, const QCString& dcopObject, + const QString& calendarUrl, bool startClient) = 0; + virtual ASYNC registerChange(const QCString& appName, bool startClient) = 0; + virtual ASYNC eventHandled(const QCString& appname, const QString& calendarURL, const QString& eventID, bool reload) = 0; + virtual ASYNC timeConfigChanged() = 0; + virtual ASYNC quit() = 0; +}; + +#endif diff --git a/kalarm/kalarmd/alarmguiiface.h b/kalarm/kalarmd/alarmguiiface.h new file mode 100644 index 000000000..7e98c831d --- /dev/null +++ b/kalarm/kalarmd/alarmguiiface.h @@ -0,0 +1,71 @@ +/* + * alarmguiiface.h - DCOP interface which alarm daemon clients must implement + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright © 2001,2004,2007 by David Jarvie <software@astrojar.org.uk> + * Based on the original, (c) 1998, 1999 Preston Brown + * Copyright (c) 2000,2001 Cornelius Schumacher <schumacher@kde.org> + * Copyright (c) 1997-1999 Preston Brown <pbrown@kde.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#ifndef DAEMONGUIIFACE_H +#define DAEMONGUIIFACE_H + +#include <dcopobject.h> + +namespace KAlarmd +{ + enum RegisterResult // result code of registerApp() DCOP call + { + FAILURE = 0, + SUCCESS = 1, + NOT_FOUND = 2 // notification type requires client start, but client executable not found + }; + + enum CalendarStatus // parameters to client notification + { + CALENDAR_ENABLED, // calendar is now being monitored + CALENDAR_DISABLED, // calendar is available but not being monitored + CALENDAR_UNAVAILABLE // calendar is unavailable for monitoring + }; +} + +/*============================================================================= += Class: AlarmGuiIface += Client applications should inherit from this class to receive notifications +* from the alarm daemon. +=============================================================================*/ +class AlarmGuiIface : virtual public DCOPObject +{ + K_DCOP + k_dcop: + /** Called to notify a change in status of the calendar. + @param calendarStatus new calendar status. Value is of type CalendarStatus. + */ + virtual ASYNC alarmDaemonUpdate(int calendarStatus, const QString& calendarURL) = 0; + + /** Called to notify that an alarm is due. + */ + virtual ASYNC handleEvent(const QString& calendarURL, const QString& eventID) = 0; + + /** Called to indicate success/failure of (re)register() call. + @param result success/failure code. Value is of type RegisterResult. + @param version kalarmd version, e.g. 50101 indicates 5.1.1. + */ + virtual ASYNC registered(bool reregister, int result, int version) = 0; +}; + +#endif diff --git a/kalarm/kalarmd/clientinfo.cpp b/kalarm/kalarmd/clientinfo.cpp new file mode 100644 index 000000000..21889082e --- /dev/null +++ b/kalarm/kalarmd/clientinfo.cpp @@ -0,0 +1,110 @@ +/* + * clientinfo.cpp - client application information + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright (C) 2001, 2004 by David Jarvie <software@astrojar.org.uk> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#include "adcalendar.h" +#include "clientinfo.h" + +QMap<QCString, ClientInfo*> ClientInfo::mClients; + + +ClientInfo::ClientInfo(const QCString& appName, const QString& title, + const QCString& dcopObj, const QString& calendar, bool startClient) + : mAppName(appName), + mTitle(title), + mDcopObject(dcopObj), + mCalendar(new ADCalendar(calendar, appName)), + mStartClient(startClient) +{ + mClients[mAppName] = this; +} + +ClientInfo::ClientInfo(const QCString& appName, const QString& title, + const QCString& dcopObj, ADCalendar* calendar, bool startClient) + : mAppName(appName), + mTitle(title), + mDcopObject(dcopObj), + mCalendar(calendar), + mStartClient(startClient) +{ + mClients[mAppName] = this; +} + +ClientInfo::~ClientInfo() +{ + delete mCalendar; + mClients.remove(mAppName); +} + +/****************************************************************************** +* Set a new calendar for the specified client application. +*/ +ADCalendar* ClientInfo::setCalendar(const QString& url) +{ + if (url != mCalendar->urlString()) + { + delete mCalendar; + mCalendar = new ADCalendar(url, mAppName); + } + return mCalendar; +} + +/****************************************************************************** +* Return the ClientInfo object for the specified client application. +*/ +ClientInfo* ClientInfo::get(const QCString& appName) +{ + if (appName.isEmpty()) + return 0; + QMap<QCString, ClientInfo*>::ConstIterator it = mClients.find(appName); + if (it == mClients.end()) + return 0; + return it.data(); +} + +/****************************************************************************** +* Return the ClientInfo object for client which owns the specified calendar. +*/ +ClientInfo* ClientInfo::get(const ADCalendar* cal) +{ + for (ClientInfo::ConstIterator it = ClientInfo::begin(); it != ClientInfo::end(); ++it) + if (it.data()->calendar() == cal) + return it.data(); + return 0; +} + +/****************************************************************************** +* Delete all clients. +*/ +void ClientInfo::clear() +{ + QMap<QCString, ClientInfo*>::Iterator it; + while ((it = mClients.begin()) != mClients.end()) + delete it.data(); +} + +/****************************************************************************** +* Delete the client with the specified name. +*/ +void ClientInfo::remove(const QCString& appName) +{ + QMap<QCString, ClientInfo*>::Iterator it = mClients.find(appName); + if (it != mClients.end()) + delete it.data(); +} diff --git a/kalarm/kalarmd/clientinfo.h b/kalarm/kalarmd/clientinfo.h new file mode 100644 index 000000000..fe6491d7e --- /dev/null +++ b/kalarm/kalarmd/clientinfo.h @@ -0,0 +1,72 @@ +/* + * clientinfo.h - client application information + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright (C) 2001, 2004 by David Jarvie <software@astrojar.org.uk> + * Based on the original, (c) 1998, 1999 Preston Brown + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#ifndef _CALCLIENT_H +#define _CALCLIENT_H + +#include <qcstring.h> +#include <qstring.h> +#include <qmap.h> + +class ADCalendar; + + +/*============================================================================= += Class: ClientInfo += Details of a KAlarm client application. +=============================================================================*/ +class ClientInfo +{ + public: + typedef QMap<QCString, ClientInfo*>::ConstIterator ConstIterator; + + ClientInfo(const QCString &appName, const QString &title, const QCString &dcopObj, + const QString& calendar, bool startClient); + ClientInfo(const QCString &appName, const QString &title, const QCString &dcopObj, + ADCalendar* calendar, bool startClient); + ~ClientInfo(); + ADCalendar* setCalendar(const QString& url); + void detachCalendar() { mCalendar = 0; } + void setStartClient(bool start) { mStartClient = start; } + + QCString appName() const { return mAppName; } + QString title() const { return mTitle; } + QCString dcopObject() const { return mDcopObject; } + ADCalendar* calendar() const { return mCalendar; } + bool startClient() const { return mStartClient; } + + static ConstIterator begin() { return mClients.begin(); } + static ConstIterator end() { return mClients.end(); } + static ClientInfo* get(const QCString& appName); + static ClientInfo* get(const ADCalendar*); + static void remove(const QCString& appName); + static void clear(); + + private: + static QMap<QCString, ClientInfo*> mClients; // list of all constructed clients + QCString mAppName; // client's executable and DCOP name + QString mTitle; // application title for display purposes + QCString mDcopObject; // object to receive DCOP messages + ADCalendar* mCalendar; // this client's event calendar + bool mStartClient; // whether to notify events via command line if client app isn't running +}; + +#endif diff --git a/kalarm/kalarmd/kalarmd.autostart.desktop b/kalarm/kalarmd/kalarmd.autostart.desktop new file mode 100644 index 000000000..de5add486 --- /dev/null +++ b/kalarm/kalarmd/kalarmd.autostart.desktop @@ -0,0 +1,103 @@ +# KDE Config File +[Desktop Entry] +Name=KAlarm Daemon +Name[af]=KAlarm Bediener +Name[bg]=Демон на KAlarm +Name[br]=Diaoul KAlarm +Name[ca]=Dimoni KAlarm +Name[cs]=KAlarm démon +Name[da]=KAlarm Dæmon +Name[de]=KAlarm Erinnerungsprogramm +Name[el]=Δαίμονας KAlarm +Name[eo]=KAlarm-demono +Name[es]=Daemon de KAlarm +Name[et]=KAlarmi häiredeemon +Name[eu]=KAlarm deabrua +Name[fa]=شبح KAlarm +Name[fi]=Hälytyspalvelin +Name[fr]=Démon d'alarme +Name[ga]=Deamhan KAlarm +Name[gl]=Daemon de KAlarm +Name[he]=תהליך הרקע תזכורות +Name[hu]=KAlarm szolgáltatás +Name[is]=KAlarm þjónn +Name[it]=Demone degli avvisi +Name[ja]=KAlarm デーモン +Name[ka]=KAlarm დემონი +Name[kk]=KAlarm қызметі +Name[km]=ដេមិន KAlarm +Name[lt]=KAlarm tarnyba +Name[mk]=Даемон за КАларм +Name[ms]=Daemon KAlarm +Name[nb]=KAlarm-nisse +Name[nds]=KAlarm-Dämoon +Name[ne]=केडीई संसूचक डेइमन +Name[nn]=KAlarm-nisse +Name[pl]=Demon alarmowy +Name[pt]=Servidor do KAlarm +Name[pt_BR]=Servidor do KAlarm +Name[ru]=Служба уведомлений +Name[sk]=KAlarm démon +Name[sl]=Demon KAlarm +Name[sr]=Демон KAlarm-а +Name[sr@Latn]=Demon KAlarm-a +Name[sv]=Alarmdemon +Name[ta]=கேஅலாரம் டெமான் +Name[tr]=KAlarm Servis Programı +Name[uk]=Демон KAlarm +Name[zh_CN]=KAlarm 进程 +Name[zh_TW]=KAlarm 守護程式 +Exec=kalarmd --autostart +Icon=kalarmd +Type=Application +Comment=KAlarm alarm daemon autostart at login +Comment[af]=Begin KAlarm bediener outomaties tydens aanteken +Comment[bg]=Автоматично стартиране на процеса на алармата KAlarm при влизане в системата +Comment[ca]=Dimoni d'inici automàtic de l'alarma KAlarm en connectar +Comment[cs]=Automatické spouštění alarmovacího démona při startu +Comment[da]=KAlarm-alarmdæmon autostart ved login +Comment[de]=Autostart des KAlarm Erinnerungsprogramms von KOrganizer bei der Anmeldung +Comment[el]=Αυτόματη εκκίνηση του δαίμονα KAlarm κατά τη σύνδεση +Comment[es]=Inicio automático al ingresar del daemon de alarma de KAlarm +Comment[et]=KAlarmi häiredeemoni automaatne käivitamine +Comment[eu]=KAlarm alarma deabrua saioa hastean automatikoki abiatzen da +Comment[fa]=آغاز خودکار هشدار KAlarm در ورود +Comment[fi]=KOrganizer/KAlarm-hälytyspalvelimen automaattikäynnistys sisäänkirjautuessa +Comment[fr]=Le démon d'alarme de KOrganizer et de KAlarm démarre automatiquement lors de la connexion +Comment[fy]=KAlarm alarmdaemon automatysk begjinne by it oanmelden +Comment[gl]=Autoinicio á entrada do daemon de KAlarm +Comment[he]=הפעלה אוטומטית של תהליך הרקע תזכורות של KAlarm בעת ההפעלה +Comment[hu]=A KAlarm emlékeztető szolgáltatás automatikus elindítása +Comment[is]=Ræsa KAlarm áminningaþjónn sjálfkrafa við byrjun setu +Comment[it]=Avvio automatico del demone degli avvisi +Comment[ja]=KAlarm アラームデーモンのログイン時の自動起動 +Comment[ka]=KAlarm მაღვიძარას დემონის ავტოდაწყება შესვლისას +Comment[kk]=KAlarm қызметі жүйеге кіргенде жегіледі +Comment[km]=ចាប់ផ្ដើមដេមិនរោទ៍របស់ KAlarm ពេលចូល +Comment[lt]=KOrganizer/KAlarm priminimų tarnybos automatinis paleidimas prisiregistruojant +Comment[mk]=Даемон за аларми од КАларм - автом. старт при најава +Comment[ms]= Automula daemon penggera KAlarm semasa log masuk +Comment[nb]=start alarmnisse ved innlogging +Comment[nds]=KAlarm-Dämoon bi't Anmellen automaatsch starten +Comment[ne]=लगइनमा केडीई संसूचक संसूचक डेइमन स्वत: सुरुआत हुन्छ +Comment[nl]=KAlarm alarmdaemon automatisch starten bij login +Comment[nn]=Start alarmnisse ved innlogging +Comment[pl]=Demon alarmu KOrganizera uruchamiany przy zalogowaniu +Comment[pt]=Servidor de alarme do KAlarm auto-iniciado no arranque +Comment[pt_BR]=Servidor de alarmes do KAlarm inicia automaticamente no login +Comment[ru]=Служба уведомлений KDE +Comment[sk]=Automatické spustenie kAlarm démona pri štarte +Comment[sl]=Samodejni zagon alarmskega strežnika KAlarma ob zagonu +Comment[sr]=Аутоматско покретање алармног демона KAlarm-а по пријављивању +Comment[sr@Latn]=Automatsko pokretanje alarmnog demona KAlarm-a po prijavljivanju +Comment[sv]=Kalarm-alarmdemon, automatisk start vid inloggning +Comment[ta]=உள்நுழையும்போது கேஅலாரம் அலாரம் டெமான் தானாகவே துவங்கும் +Comment[tr]=KAlarm alarm servis programı (açılışta başlar) +Comment[uk]=Автозавантаження демона нагадувань KAlarm +Comment[zh_CN]=登录时自动启动 KAlarm 定时守护进程 +Comment[zh_TW]=登入時自動啟動 KAlarm 鬧鐘守護程式 +Terminal=false +NoDisplay=true +X-KDE-autostart-phase=2 +X-KDE-autostart-condition=kalarmdrc:General:Autostart:false +X-KDE-StartupNotify=true diff --git a/kalarm/kalarmd/kalarmd.desktop b/kalarm/kalarmd/kalarmd.desktop new file mode 100644 index 000000000..31d3a0fa7 --- /dev/null +++ b/kalarm/kalarmd/kalarmd.desktop @@ -0,0 +1,55 @@ +# KDE Config File +[Desktop Entry] +Name=KAlarm Daemon +Name[af]=KAlarm Bediener +Name[bg]=Демон на KAlarm +Name[br]=Diaoul KAlarm +Name[ca]=Dimoni KAlarm +Name[cs]=KAlarm démon +Name[da]=KAlarm Dæmon +Name[de]=KAlarm Erinnerungsprogramm +Name[el]=Δαίμονας KAlarm +Name[eo]=KAlarm-demono +Name[es]=Daemon de KAlarm +Name[et]=KAlarmi häiredeemon +Name[eu]=KAlarm deabrua +Name[fa]=شبح KAlarm +Name[fi]=Hälytyspalvelin +Name[fr]=Démon d'alarme +Name[ga]=Deamhan KAlarm +Name[gl]=Daemon de KAlarm +Name[he]=תהליך הרקע תזכורות +Name[hu]=KAlarm szolgáltatás +Name[is]=KAlarm þjónn +Name[it]=Demone degli avvisi +Name[ja]=KAlarm デーモン +Name[ka]=KAlarm დემონი +Name[kk]=KAlarm қызметі +Name[km]=ដេមិន KAlarm +Name[lt]=KAlarm tarnyba +Name[mk]=Даемон за КАларм +Name[ms]=Daemon KAlarm +Name[nb]=KAlarm-nisse +Name[nds]=KAlarm-Dämoon +Name[ne]=केडीई संसूचक डेइमन +Name[nn]=KAlarm-nisse +Name[pl]=Demon alarmowy +Name[pt]=Servidor do KAlarm +Name[pt_BR]=Servidor do KAlarm +Name[ru]=Служба уведомлений +Name[sk]=KAlarm démon +Name[sl]=Demon KAlarm +Name[sr]=Демон KAlarm-а +Name[sr@Latn]=Demon KAlarm-a +Name[sv]=Alarmdemon +Name[ta]=கேஅலாரம் டெமான் +Name[tr]=KAlarm Servis Programı +Name[uk]=Демон KAlarm +Name[zh_CN]=KAlarm 进程 +Name[zh_TW]=KAlarm 守護程式 +Exec=kalarmd +Icon=kalarmd +Type=Application +Terminal=false +X-DCOP-ServiceType=Unique +NoDisplay=true diff --git a/kalarm/kalarmd/kalarmd.h b/kalarm/kalarmd/kalarmd.h new file mode 100644 index 000000000..5e45243bf --- /dev/null +++ b/kalarm/kalarmd/kalarmd.h @@ -0,0 +1,40 @@ +/* + * kalarmd.h - global header file + * Program: KAlarm's alarm daemon (kalarmd) + * Copyright © 2004,2005,2007 by David Jarvie <software@astrojar.org.uk> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#ifndef KALARMD_H +#define KALARMD_H + +#ifdef HAVE_CONFIG_H +#include <config.h> +#endif + +#define DAEMON_VERSION "4.3" // kalarmd version number string +#define DAEMON_VERSION_NUM 40300 // kalarmd version number integer +#define DAEMON_APP_NAME "kalarmd" // DCOP name of alarm daemon application +#define DAEMON_DCOP_OBJECT "ad" // DCOP name of kalarmd's DCOP interface + +#define DAEMON_CHECK_INTERVAL 60 // the daemon checks calendar files every minute + +#define DAEMON_AUTOSTART_SECTION "General" // daemon's config file section for autostart-at-login +#define DAEMON_AUTOSTART_KEY "Autostart" // daemon's config file entry for autostart-at-login + +#define AUTOSTART_KALARM // fix for KAlarm autostart before session restoration + +#endif // KALARMD_H |