00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #include "kalarm.h"
00022 #include "functions.h"
00023
00024 #include "alarmcalendar.h"
00025 #include "alarmevent.h"
00026 #include "alarmlistview.h"
00027 #include "daemon.h"
00028 #include "kalarmapp.h"
00029 #include "kamail.h"
00030 #include "mainwindow.h"
00031 #include "messagewin.h"
00032 #include "preferences.h"
00033 #include "shellprocess.h"
00034 #include "templatelistview.h"
00035 #include "templatemenuaction.h"
00036
00037 #include <qdeepcopy.h>
00038 #include <qdir.h>
00039 #include <qregexp.h>
00040
00041 #include <kconfig.h>
00042 #include <kaction.h>
00043 #include <kglobal.h>
00044 #include <klocale.h>
00045 #include <kstdguiitem.h>
00046 #include <kstdaccel.h>
00047 #include <kmessagebox.h>
00048 #include <kfiledialog.h>
00049 #include <dcopclient.h>
00050 #include <dcopref.h>
00051 #include <kdcopservicestarter.h>
00052 #include <kdebug.h>
00053
00054 #include <libkcal/event.h>
00055 #include <libkcal/icalformat.h>
00056 #include <libkpimidentities/identitymanager.h>
00057 #include <libkpimidentities/identity.h>
00058 #include <libkcal/person.h>
00059
00060
00061 namespace
00062 {
00063 bool resetDaemonQueued = false;
00064 QCString korganizerName = "korganizer";
00065 QString korgStartError;
00066 #define KORG_DCOP_OBJECT "KOrganizerIface"
00067 const char* KORG_DCOP_WINDOW = "KOrganizer MainWindow";
00068 const char* KMAIL_DCOP_WINDOW = "kmail-mainwindow#1";
00069
00070 bool sendToKOrganizer(const KAEvent&);
00071 bool deleteFromKOrganizer(const QString& eventID);
00072 bool runKOrganizer();
00073 }
00074 #ifdef HAVE_XTEST
00075 void x11_cancelScreenSaver();
00076 #endif
00077
00078
00079 namespace KAlarm
00080 {
00081
00082
00083
00084
00085 MainWindow* displayMainWindowSelected(const QString& eventID)
00086 {
00087 MainWindow* win = MainWindow::firstWindow();
00088 if (!win)
00089 {
00090 if (theApp()->checkCalendarDaemon())
00091 {
00092 win = MainWindow::create();
00093 win->show();
00094 }
00095 }
00096 else
00097 {
00098
00099 bool visible = win->isVisible();
00100 if (visible)
00101 win->hide();
00102 if (!visible || win->isMinimized())
00103 win->showNormal();
00104 win->raise();
00105 win->setActiveWindow();
00106 }
00107 if (win && !eventID.isEmpty())
00108 win->selectEvent(eventID);
00109 return win;
00110 }
00111
00112
00113
00114
00115 KAction* createNewAlarmAction(const QString& label, QObject* receiver, const char* slot, KActionCollection* actions, const char* name)
00116 {
00117 return new KAction(label, "filenew", KStdAccel::openNew(), receiver, slot, actions, name);
00118 }
00119
00120
00121
00122
00123 TemplateMenuAction* createNewFromTemplateAction(const QString& label, QObject* receiver, const char* slot, KActionCollection* actions, const char* name)
00124 {
00125 return new TemplateMenuAction(label, "new_from_template", receiver, slot, actions, name);
00126 }
00127
00128
00129
00130
00131
00132
00133
00134
00135 UpdateStatus addEvent(KAEvent& event, AlarmListView* selectionView, QWidget* errmsgParent, bool useEventID, bool allowKOrgUpdate)
00136 {
00137 kdDebug(5950) << "KAlarm::addEvent(): " << event.id() << endl;
00138 UpdateStatus status = UPDATE_OK;
00139 if (!theApp()->checkCalendarDaemon())
00140 return UPDATE_FAILED;
00141 else
00142 {
00143
00144 AlarmCalendar* cal = AlarmCalendar::activeCalendar();
00145 if (!cal->addEvent(event, useEventID))
00146 status = UPDATE_FAILED;
00147 else if (!cal->save())
00148 status = SAVE_FAILED;
00149 }
00150 if (status == UPDATE_OK)
00151 {
00152 if (allowKOrgUpdate && event.copyToKOrganizer())
00153 {
00154 if (!sendToKOrganizer(event))
00155 status = UPDATE_KORG_ERR;
00156 }
00157
00158
00159 AlarmListView::addEvent(event, selectionView);
00160 return status;
00161 }
00162
00163 if (errmsgParent)
00164 displayUpdateError(errmsgParent, status, ERR_ADD, 1);
00165 return status;
00166 }
00167
00168
00169
00170
00171
00172 bool addExpiredEvent(KAEvent& event)
00173 {
00174 kdDebug(5950) << "KAlarm::addExpiredEvent(" << event.id() << ")\n";
00175 AlarmCalendar* cal = AlarmCalendar::expiredCalendarOpen();
00176 if (!cal)
00177 return false;
00178 bool archiving = (KAEvent::uidStatus(event.id()) == KAEvent::ACTIVE);
00179 if (archiving)
00180 event.setSaveDateTime(QDateTime::currentDateTime());
00181 KCal::Event* kcalEvent = cal->addEvent(event);
00182 cal->save();
00183
00184
00185 if (!archiving)
00186 AlarmListView::addEvent(event, 0);
00187 else if (kcalEvent)
00188 AlarmListView::modifyEvent(KAEvent(*kcalEvent), 0);
00189 return true;
00190 }
00191
00192
00193
00194
00195
00196
00197
00198
00199 UpdateStatus addTemplate(KAEvent& event, TemplateListView* selectionView, QWidget* errmsgParent)
00200 {
00201 kdDebug(5950) << "KAlarm::addTemplate(): " << event.id() << endl;
00202 UpdateStatus status = UPDATE_OK;
00203
00204
00205 AlarmCalendar* cal = AlarmCalendar::templateCalendarOpen();
00206 if (!cal || !cal->addEvent(event))
00207 status = UPDATE_FAILED;
00208 else if (!cal->save())
00209 status = SAVE_FAILED;
00210 else
00211 {
00212 cal->emitEmptyStatus();
00213
00214
00215 TemplateListView::addEvent(event, selectionView);
00216 return UPDATE_OK;
00217 }
00218
00219 if (errmsgParent)
00220 displayUpdateError(errmsgParent, status, ERR_TEMPLATE, 1);
00221 return status;
00222 }
00223
00224
00225
00226
00227
00228
00229
00230
00231 UpdateStatus modifyEvent(KAEvent& oldEvent, const KAEvent& newEvent, AlarmListView* selectionView, QWidget* errmsgParent)
00232 {
00233 kdDebug(5950) << "KAlarm::modifyEvent(): '" << oldEvent.id() << endl;
00234
00235 UpdateStatus status = UPDATE_OK;
00236 if (!newEvent.valid())
00237 {
00238 deleteEvent(oldEvent, true);
00239 status = UPDATE_FAILED;
00240 }
00241 else
00242 {
00243 if (oldEvent.copyToKOrganizer())
00244 {
00245
00246
00247
00248 deleteFromKOrganizer(oldEvent.id());
00249 }
00250
00251
00252 AlarmCalendar* cal = AlarmCalendar::activeCalendar();
00253 if (!cal->deleteEvent(oldEvent.id())
00254 || !cal->addEvent(const_cast<KAEvent&>(newEvent), true))
00255 status = UPDATE_FAILED;
00256 else if (!cal->save())
00257 status = SAVE_FAILED;
00258 if (status == UPDATE_OK)
00259 {
00260 if (newEvent.copyToKOrganizer())
00261 {
00262 if (!sendToKOrganizer(newEvent))
00263 status = UPDATE_KORG_ERR;
00264 }
00265
00266
00267 AlarmListView::modifyEvent(oldEvent.id(), newEvent, selectionView);
00268 return status;
00269 }
00270 }
00271
00272 if (errmsgParent)
00273 displayUpdateError(errmsgParent, status, ERR_ADD, 1);
00274 return status;
00275 }
00276
00277
00278
00279
00280
00281
00282
00283
00284
00285
00286 UpdateStatus updateEvent(KAEvent& event, AlarmListView* selectionView, QWidget* errmsgParent, bool archiveOnDelete, bool incRevision)
00287 {
00288 kdDebug(5950) << "KAlarm::updateEvent(): " << event.id() << endl;
00289
00290 if (!event.valid())
00291 deleteEvent(event, archiveOnDelete);
00292 else
00293 {
00294
00295 if (incRevision)
00296 event.incrementRevision();
00297 AlarmCalendar* cal = AlarmCalendar::activeCalendar();
00298 cal->updateEvent(event);
00299 if (!cal->save())
00300 {
00301 if (errmsgParent)
00302 displayUpdateError(errmsgParent, SAVE_FAILED, ERR_ADD, 1);
00303 return SAVE_FAILED;
00304 }
00305
00306
00307 AlarmListView::modifyEvent(event, selectionView);
00308 }
00309 return UPDATE_OK;
00310 }
00311
00312
00313
00314
00315
00316
00317 UpdateStatus updateTemplate(const KAEvent& event, TemplateListView* selectionView, QWidget* errmsgParent)
00318 {
00319 UpdateStatus status = UPDATE_OK;
00320 AlarmCalendar* cal = AlarmCalendar::templateCalendarOpen();
00321 if (!cal)
00322 status = UPDATE_FAILED;
00323 else
00324 {
00325 cal->updateEvent(event);
00326 if (!cal->save())
00327 status = SAVE_FAILED;
00328 else
00329 {
00330 TemplateListView::modifyEvent(event.id(), event, selectionView);
00331 return UPDATE_OK;
00332 }
00333 }
00334
00335 if (errmsgParent)
00336 displayUpdateError(errmsgParent, SAVE_FAILED, ERR_TEMPLATE, 1);
00337 return status;
00338 }
00339
00340
00341
00342
00343
00344 UpdateStatus deleteEvent(KAEvent& event, bool archive, QWidget* errmsgParent)
00345 {
00346 QString id = event.id();
00347 kdDebug(5950) << "KAlarm::deleteEvent(): " << id << endl;
00348
00349
00350 AlarmListView::deleteEvent(id);
00351
00352 UpdateStatus status = UPDATE_OK;
00353 AlarmCalendar* cal;
00354
00355
00356 if (KAEvent::uidStatus(id) == KAEvent::EXPIRED)
00357 {
00358 cal = AlarmCalendar::expiredCalendarOpen();
00359 if (!cal)
00360 status = UPDATE_FAILED;
00361 }
00362 else
00363 {
00364 if (event.copyToKOrganizer())
00365 {
00366
00367
00368
00369 if (!deleteFromKOrganizer(event.id()))
00370 status = UPDATE_KORG_ERR;
00371 }
00372 if (archive && event.toBeArchived())
00373 addExpiredEvent(event);
00374 cal = AlarmCalendar::activeCalendar();
00375 }
00376 if (status != UPDATE_FAILED)
00377 {
00378 if (!cal->deleteEvent(id, true))
00379 status = SAVE_FAILED;
00380 }
00381 if (status > UPDATE_KORG_ERR && errmsgParent)
00382 displayUpdateError(errmsgParent, SAVE_FAILED, ERR_DELETE, 1);
00383 return status;
00384 }
00385
00386
00387
00388
00389 UpdateStatus deleteTemplate(const KAEvent& event)
00390 {
00391 QString id = event.id();
00392
00393
00394 AlarmCalendar* cal = AlarmCalendar::templateCalendarOpen();
00395 if (!cal)
00396 return UPDATE_FAILED;
00397 if (!cal->deleteEvent(id, true))
00398 return SAVE_FAILED;
00399 cal->emitEmptyStatus();
00400
00401
00402 TemplateListView::deleteEvent(id);
00403 return UPDATE_OK;
00404 }
00405
00406
00407
00408
00409 void deleteDisplayEvent(const QString& eventID)
00410 {
00411 kdDebug(5950) << "KAlarm::deleteDisplayEvent(" << eventID << ")\n";
00412
00413 if (KAEvent::uidStatus(eventID) == KAEvent::DISPLAYING)
00414 {
00415 AlarmCalendar* cal = AlarmCalendar::displayCalendarOpen();
00416 if (cal)
00417 cal->deleteEvent(eventID, true);
00418 }
00419 }
00420
00421
00422
00423
00424
00425
00426
00427 UpdateStatus reactivateEvent(KAEvent& event, AlarmListView* selectionView, bool useEventID)
00428 {
00429 QString id = event.id();
00430 kdDebug(5950) << "KAlarm::reactivateEvent(): " << id << endl;
00431
00432
00433 if (KAEvent::uidStatus(id) == KAEvent::EXPIRED)
00434 {
00435 QDateTime now = QDateTime::currentDateTime();
00436 if (event.occursAfter(now, true))
00437 {
00438 if (event.recurs() || event.repeatCount())
00439 event.setNextOccurrence(now);
00440 event.setArchive();
00441
00442
00443 AlarmCalendar* cal = AlarmCalendar::activeCalendar();
00444 if (!cal->addEvent(event, useEventID))
00445 return UPDATE_FAILED;
00446 if (!cal->save())
00447 return SAVE_FAILED;
00448
00449 UpdateStatus status = UPDATE_OK;
00450 if (event.copyToKOrganizer())
00451 {
00452 if (!sendToKOrganizer(event))
00453 status = UPDATE_KORG_ERR;
00454 }
00455
00456
00457 AlarmListView::undeleteEvent(id, event, selectionView);
00458
00459 cal = AlarmCalendar::expiredCalendarOpen();
00460 if (cal)
00461 cal->deleteEvent(id, true);
00462 return status;
00463 }
00464 }
00465 return UPDATE_FAILED;
00466 }
00467
00468
00469
00470
00471
00472
00473
00474 UpdateStatus enableEvent(KAEvent& event, AlarmListView* selectionView, bool enable)
00475 {
00476 kdDebug(5950) << "KAlarm::enableEvent(" << enable << "): " << event.id() << endl;
00477
00478 if (enable != event.enabled())
00479 {
00480 event.setEnabled(enable);
00481
00482
00483 AlarmCalendar* cal = AlarmCalendar::activeCalendar();
00484 cal->updateEvent(event);
00485 if (!cal->save())
00486 return SAVE_FAILED;
00487
00488
00489 if (!enable && event.displayAction())
00490 {
00491 MessageWin* win = MessageWin::findEvent(event.id());
00492 delete win;
00493 }
00494
00495
00496 AlarmListView::modifyEvent(event, selectionView);
00497 }
00498 return UPDATE_OK;
00499 }
00500
00501
00502
00503
00504 void displayUpdateError(QWidget* parent, UpdateStatus, UpdateError code, int nAlarms)
00505 {
00506 QString errmsg;
00507 switch (code)
00508 {
00509 case ERR_ADD:
00510 errmsg = (nAlarms > 1) ? i18n("Error saving alarms")
00511 : i18n("Error saving alarm");
00512 break;
00513 case ERR_DELETE:
00514 errmsg = (nAlarms > 1) ? i18n("Error deleting alarms")
00515 : i18n("Error deleting alarm");
00516 break;
00517 case ERR_REACTIVATE:
00518 errmsg = (nAlarms > 1) ? i18n("Error saving reactivated alarms")
00519 : i18n("Error saving reactivated alarm");
00520 break;
00521 case ERR_TEMPLATE:
00522 errmsg = i18n("Error saving alarm template");
00523 break;
00524 }
00525 KMessageBox::error(parent, errmsg);
00526 }
00527
00528
00529
00530
00531 void displayKOrgUpdateError(QWidget* parent, KOrgUpdateError code, int nAlarms)
00532 {
00533 QString errmsg;
00534 switch (code)
00535 {
00536 case KORG_ERR_ADD:
00537 errmsg = (nAlarms > 1) ? i18n("Unable to show alarms in KOrganizer")
00538 : i18n("Unable to show alarm in KOrganizer");
00539 break;
00540 case KORG_ERR_MODIFY:
00541 errmsg = i18n("Unable to update alarm in KOrganizer");
00542 break;
00543 case KORG_ERR_DELETE:
00544 errmsg = (nAlarms > 1) ? i18n("Unable to delete alarms from KOrganizer")
00545 : i18n("Unable to delete alarm from KOrganizer");
00546 break;
00547 }
00548 KMessageBox::error(parent, errmsg);
00549 }
00550
00551
00552
00553
00554 bool edit(const QString& eventID)
00555 {
00556 AlarmCalendar* cal;
00557 switch (KAEvent::uidStatus(eventID))
00558 {
00559 case KAEvent::ACTIVE:
00560 cal = AlarmCalendar::activeCalendar();
00561 break;
00562 case KAEvent::TEMPLATE:
00563 cal = AlarmCalendar::templateCalendarOpen();
00564 break;
00565 default:
00566 kdError(5950) << "KAlarm::edit(" << eventID << "): event not active or template" << endl;
00567 return false;
00568 }
00569 KCal::Event* kcalEvent = cal->event(eventID);
00570 if (!kcalEvent)
00571 {
00572 kdError(5950) << "KAlarm::edit(): event ID not found: " << eventID << endl;
00573 return false;
00574 }
00575 KAEvent event(*kcalEvent);
00576 MainWindow::executeEdit(event);
00577 return true;
00578 }
00579
00580
00581
00582
00583
00584 bool editNew(const QString& templateName)
00585 {
00586 bool result = true;
00587 if (!templateName.isEmpty())
00588 {
00589 AlarmCalendar* cal = AlarmCalendar::templateCalendarOpen();
00590 if (cal)
00591 {
00592 KAEvent templateEvent = KAEvent::findTemplateName(*cal, templateName);
00593 if (templateEvent.valid())
00594 {
00595 MainWindow::executeNew(templateEvent);
00596 return true;
00597 }
00598 kdWarning(5950) << "KAlarm::editNew(" << templateName << "): template not found" << endl;
00599 }
00600 result = false;
00601 }
00602 MainWindow::executeNew();
00603 return result;
00604 }
00605
00606
00607
00608
00609
00610 QValueList<KAEvent> templateList()
00611 {
00612 QValueList<KAEvent> templates;
00613 AlarmCalendar* cal = AlarmCalendar::templateCalendarOpen();
00614 if (cal)
00615 {
00616 bool includeCmdAlarms = ShellProcess::authorised();
00617 KCal::Event::List events = cal->events();
00618 for (KCal::Event::List::ConstIterator it = events.begin(); it != events.end(); ++it)
00619 {
00620 KCal::Event* kcalEvent = *it;
00621 KAEvent event(*kcalEvent);
00622 if (includeCmdAlarms || event.action() != KAEvent::COMMAND)
00623 templates.append(event);
00624 }
00625 }
00626 return templates;
00627 }
00628
00629
00630
00631
00632
00633
00634 void outputAlarmWarnings(QWidget* parent, const KAEvent* event)
00635 {
00636 if (event && event->action() == KAEvent::EMAIL
00637 && Preferences::emailAddress().isEmpty())
00638 KMessageBox::information(parent, i18n("Please set the 'From' email address...",
00639 "%1\nPlease set it in the Preferences dialog.").arg(KAMail::i18n_NeedFromEmailAddress()));
00640
00641 if (!Daemon::monitoringAlarms())
00642 {
00643 if (KMessageBox::warningYesNo(parent, i18n("Alarms are currently disabled.\nDo you want to enable alarms now?"),
00644 QString::null, i18n("Enable"), i18n("Keep Disabled"),
00645 QString::fromLatin1("EditEnableAlarms"))
00646 == KMessageBox::Yes)
00647 Daemon::setAlarmsEnabled();
00648 }
00649 }
00650
00651
00652
00653
00654
00655 void resetDaemon()
00656 {
00657 kdDebug(5950) << "KAlarm::resetDaemon()" << endl;
00658 if (!resetDaemonQueued)
00659 {
00660 resetDaemonQueued = true;
00661 theApp()->processQueue();
00662 }
00663 }
00664
00665
00666
00667
00668
00669
00670
00671
00672 void resetDaemonIfQueued()
00673 {
00674 if (resetDaemonQueued)
00675 {
00676 kdDebug(5950) << "KAlarm::resetDaemonIfNeeded()" << endl;
00677 AlarmCalendar::activeCalendar()->reload();
00678 AlarmCalendar::expiredCalendar()->reload();
00679
00680
00681 KAEvent event;
00682 KCal::Event::List events = AlarmCalendar::activeCalendar()->events();
00683 for (KCal::Event::List::ConstIterator it = events.begin(); it != events.end(); ++it)
00684 {
00685 KCal::Event* kcalEvent = *it;
00686 event.set(*kcalEvent);
00687 if (!event.enabled() && event.displayAction())
00688 {
00689 MessageWin* win = MessageWin::findEvent(event.id());
00690 delete win;
00691 }
00692 }
00693
00694 MainWindow::refresh();
00695 if (!Daemon::reset())
00696 Daemon::start();
00697 resetDaemonQueued = false;
00698 }
00699 }
00700
00701
00702
00703
00704
00705
00706 QString runKMail(bool minimise)
00707 {
00708 QCString dcopName;
00709 QString errmsg;
00710 if (!runProgram("kmail", (minimise ? KMAIL_DCOP_WINDOW : ""), dcopName, errmsg))
00711 return i18n("Unable to start KMail\n(%1)").arg(errmsg);
00712 return QString::null;
00713 }
00714
00715
00716
00717
00718
00719
00720
00721
00722 bool runProgram(const QCString& program, const QCString& windowName, QCString& dcopName, QString& errorMessage)
00723 {
00724 if (!kapp->dcopClient()->isApplicationRegistered(program))
00725 {
00726
00727 if (KApplication::startServiceByDesktopName(QString::fromLatin1(program), QString::null, &errorMessage, &dcopName))
00728 {
00729 kdError(5950) << "runProgram(): couldn't start " << program << " (" << errorMessage << ")\n";
00730 return false;
00731 }
00732
00733
00734
00735 kapp->dcopClient()->send(dcopName, windowName, "minimize()", QString::null);
00736 }
00737 else if (dcopName.isEmpty())
00738 dcopName = program;
00739 errorMessage = QString::null;
00740 return true;
00741 }
00742
00743
00744
00745
00746
00747
00748
00749 bool readConfigWindowSize(const char* window, QSize& result)
00750 {
00751 KConfig* config = KGlobal::config();
00752 config->setGroup(QString::fromLatin1(window));
00753 QWidget* desktop = KApplication::desktop();
00754 QSize s = QSize(config->readNumEntry(QString::fromLatin1("Width %1").arg(desktop->width()), 0),
00755 config->readNumEntry(QString::fromLatin1("Height %1").arg(desktop->height()), 0));
00756 if (s.isEmpty())
00757 return false;
00758 result = s;
00759 return true;
00760 }
00761
00762
00763
00764
00765
00766 void writeConfigWindowSize(const char* window, const QSize& size)
00767 {
00768 KConfig* config = KGlobal::config();
00769 config->setGroup(QString::fromLatin1(window));
00770 QWidget* desktop = KApplication::desktop();
00771 config->writeEntry(QString::fromLatin1("Width %1").arg(desktop->width()), size.width());
00772 config->writeEntry(QString::fromLatin1("Height %1").arg(desktop->height()), size.height());
00773 config->sync();
00774 }
00775
00776
00777
00778
00779 int Version()
00780 {
00781 static int version = 0;
00782 if (!version)
00783 version = getVersionNumber(KALARM_VERSION);
00784 return version;
00785 }
00786
00787
00788
00789
00790
00791
00792
00793 int getVersionNumber(const QString& version, QString* subVersion)
00794 {
00795
00796
00797 if (subVersion)
00798 *subVersion = QString::null;
00799 int count = version.contains('.') + 1;
00800 if (count < 2)
00801 return 0;
00802 bool ok;
00803 unsigned vernum = version.section('.', 0, 0).toUInt(&ok) * 10000;
00804 if (!ok)
00805 return 0;
00806 unsigned v = version.section('.', 1, 1).toUInt(&ok);
00807 if (!ok)
00808 return 0;
00809 vernum += (v < 99 ? v : 99) * 100;
00810 if (count >= 3)
00811 {
00812
00813 QString issue = version.section('.', 2);
00814 if (!issue.at(0).isDigit())
00815 return 0;
00816 int n = issue.length();
00817 int i;
00818 for (i = 0; i < n && issue.at(i).isDigit(); ++i) ;
00819 if (subVersion)
00820 *subVersion = issue.mid(i);
00821 v = issue.left(i).toUInt();
00822 vernum += (v < 99 ? v : 99);
00823 }
00824 return vernum;
00825 }
00826
00827
00828
00829
00830
00831
00832 FileType fileType(const QString& mimetype)
00833 {
00834 static const char* applicationTypes[] = {
00835 "x-shellscript", "x-nawk", "x-awk", "x-perl", "x-python",
00836 "x-desktop", "x-troff", 0 };
00837 static const char* formattedTextTypes[] = {
00838 "html", "xml", 0 };
00839
00840 if (mimetype.startsWith(QString::fromLatin1("image/")))
00841 return Image;
00842 int slash = mimetype.find('/');
00843 if (slash < 0)
00844 return Unknown;
00845 QString type = mimetype.mid(slash + 1);
00846 const char* typel = type.latin1();
00847 if (mimetype.startsWith(QString::fromLatin1("application")))
00848 {
00849 for (int i = 0; applicationTypes[i]; ++i)
00850 if (!strcmp(typel, applicationTypes[i]))
00851 return TextApplication;
00852 }
00853 else if (mimetype.startsWith(QString::fromLatin1("text")))
00854 {
00855 for (int i = 0; formattedTextTypes[i]; ++i)
00856 if (!strcmp(typel, formattedTextTypes[i]))
00857 return TextFormatted;
00858 return TextPlain;
00859 }
00860 return Unknown;
00861 }
00862
00863
00864
00865
00866
00867
00868
00869
00870
00871
00872
00873 QString browseFile(const QString& caption, QString& defaultDir, const QString& initialFile,
00874 const QString& filter, int mode, QWidget* parent, const char* name)
00875 {
00876 QString initialDir = !initialFile.isEmpty() ? QString(initialFile).remove(QRegExp("/[^/]*$"))
00877 : !defaultDir.isEmpty() ? defaultDir
00878 : QDir::homeDirPath();
00879 KFileDialog fileDlg(initialDir, filter, parent, name, true);
00880 fileDlg.setOperationMode(mode & KFile::ExistingOnly ? KFileDialog::Opening : KFileDialog::Saving);
00881 fileDlg.setMode(KFile::File | mode);
00882 fileDlg.setCaption(caption);
00883 if (!initialFile.isEmpty())
00884 fileDlg.setSelection(initialFile);
00885 if (fileDlg.exec() != QDialog::Accepted)
00886 return QString::null;
00887 KURL url = fileDlg.selectedURL();
00888 defaultDir = url.path();
00889 return (mode & KFile::LocalOnly) ? url.path() : url.prettyURL();
00890 }
00891
00892
00893
00894
00895
00896 int localeFirstDayOfWeek()
00897 {
00898 static int firstDay = 0;
00899 if (!firstDay)
00900 firstDay = KGlobal::locale()->weekStartDay();
00901 return firstDay;
00902 }
00903
00904
00905
00906
00907 QString stripAccel(const QString& text)
00908 {
00909 unsigned len = text.length();
00910 QString out = QDeepCopy<QString>(text);
00911 QChar *corig = (QChar*)out.unicode();
00912 QChar *cout = corig;
00913 QChar *cin = cout;
00914 while (len)
00915 {
00916 if ( *cin == '&' )
00917 {
00918 ++cin;
00919 --len;
00920 if ( !len )
00921 break;
00922 }
00923 *cout = *cin;
00924 ++cout;
00925 ++cin;
00926 --len;
00927 }
00928 unsigned newlen = cout - corig;
00929 if (newlen != out.length())
00930 out.truncate(newlen);
00931 return out;
00932 }
00933
00934
00935
00936
00937
00938 void cancelScreenSaver()
00939 {
00940 #ifdef HAVE_XTEST
00941 x11_cancelScreenSaver();
00942 #endif // HAVE_XTEST
00943 }
00944
00945 }
00946
00947
00948 namespace {
00949
00950
00951
00952
00953
00954
00955 bool sendToKOrganizer(const KAEvent& event)
00956 {
00957 KCal::Event* kcalEvent = event.event();
00958 QString uid = KAEvent::uid(event.id(), KAEvent::KORGANIZER);
00959 kcalEvent->setUid(uid);
00960 kcalEvent->clearAlarms();
00961 QString userEmail;
00962 switch (event.action())
00963 {
00964 case KAEvent::MESSAGE:
00965 case KAEvent::FILE:
00966 case KAEvent::COMMAND:
00967 kcalEvent->setSummary(event.cleanText());
00968 userEmail = Preferences::emailAddress();
00969 break;
00970 case KAEvent::EMAIL:
00971 {
00972 QString from = event.emailFromId()
00973 ? KAMail::identityManager()->identityForUoid(event.emailFromId()).fullEmailAddr()
00974 : Preferences::emailAddress();
00975 AlarmText atext;
00976 atext.setEmail(event.emailAddresses(", "), from, QString::null, QString::null, event.emailSubject(), QString::null);
00977 kcalEvent->setSummary(atext.displayText());
00978 userEmail = from;
00979 break;
00980 }
00981 }
00982 kcalEvent->setOrganizer(KCal::Person(QString::null, userEmail));
00983
00984
00985 KCal::ICalFormat format;
00986 format.setTimeZone(QString::null, false);
00987 QString iCal = format.toICalString(kcalEvent);
00988 kdDebug(5950)<<"Korg->"<<iCal<<endl;
00989 delete kcalEvent;
00990
00991
00992 if (!runKOrganizer())
00993 return false;
00994 QByteArray data, replyData;
00995 QCString replyType;
00996 QDataStream arg(data, IO_WriteOnly);
00997 arg << iCal;
00998 if (kapp->dcopClient()->call(korganizerName, KORG_DCOP_OBJECT, "addIncidence(QString)", data, replyType, replyData)
00999 && replyType == "bool")
01000 {
01001 bool result;
01002 QDataStream reply(replyData, IO_ReadOnly);
01003 reply >> result;
01004 if (result)
01005 {
01006 kdDebug(5950) << "sendToKOrganizer(" << uid << "): success\n";
01007 return true;
01008 }
01009 }
01010 kdError(5950) << "sendToKOrganizer(): KOrganizer addEvent(" << uid << ") dcop call failed\n";
01011 return false;
01012 }
01013
01014
01015
01016
01017 bool deleteFromKOrganizer(const QString& eventID)
01018 {
01019 if (!runKOrganizer())
01020 return false;
01021 QString newID = KAEvent::uid(eventID, KAEvent::KORGANIZER);
01022 QByteArray data, replyData;
01023 QCString replyType;
01024 QDataStream arg(data, IO_WriteOnly);
01025 arg << newID << true;
01026 if (kapp->dcopClient()->call(korganizerName, KORG_DCOP_OBJECT, "deleteIncidence(QString,bool)", data, replyType, replyData)
01027 && replyType == "bool")
01028 {
01029 bool result;
01030 QDataStream reply(replyData, IO_ReadOnly);
01031 reply >> result;
01032 if (result)
01033 {
01034 kdDebug(5950) << "deleteFromKOrganizer(" << newID << "): success\n";
01035 return true;
01036 }
01037 }
01038 kdError(5950) << "sendToKOrganizer(): KOrganizer deleteEvent(" << newID << ") dcop call failed\n";
01039 return false;
01040 }
01041
01042
01043
01044
01045 bool runKOrganizer()
01046 {
01047 QString error;
01048 QCString dcopService;
01049 int result = KDCOPServiceStarter::self()->findServiceFor("DCOP/Organizer", QString::null, QString::null, &error, &dcopService);
01050 if (result)
01051 {
01052 kdDebug(5950) << "Unable to start DCOP/Organizer: " << dcopService << " " << error << endl;
01053 return false;
01054 }
01055
01056
01057
01058 QCString dummy;
01059 if (!kapp->dcopClient()->findObject(dcopService, KORG_DCOP_OBJECT, "", QByteArray(), dummy, dummy))
01060 {
01061 DCOPRef ref(dcopService, dcopService);
01062 DCOPReply reply = ref.call("load()");
01063 if (!reply.isValid() || !(bool)reply)
01064 {
01065 kdWarning(5950) << "Error loading " << dcopService << endl;
01066 return false;
01067 }
01068 if (!kapp->dcopClient()->findObject(dcopService, KORG_DCOP_OBJECT, "", QByteArray(), dummy, dummy))
01069 {
01070 kdWarning(5950) << "Unable to access KOrganizer's "KORG_DCOP_OBJECT" DCOP object" << endl;
01071 return false;
01072 }
01073 }
01074 return true;
01075 }
01076
01077 }
01078
01079 #ifdef HAVE_XTEST
01080 #include <X11/keysym.h>
01081 #include <X11/extensions/XTest.h>
01082 #include <qwindowdefs.h>
01083
01084
01085
01086
01087
01088 void x11_cancelScreenSaver()
01089 {
01090 kdDebug(5950) << "KAlarm::cancelScreenSaver()" << endl;
01091 Display* display = qt_xdisplay();
01092 static int XTestKeyCode = 0;
01093 if (!XTestKeyCode)
01094 XTestKeyCode = XKeysymToKeycode(display, XK_Shift_L);
01095 XTestFakeKeyEvent(display, XTestKeyCode, true, CurrentTime);
01096 XTestFakeKeyEvent(display, XTestKeyCode, false, CurrentTime);
01097 XSync(display, false);
01098 }
01099 #endif // HAVE_XTEST