8 #include "tdeaccelmenuwatch.h"
9 #include <dcopclient.h>
11 #include <tdeaction.h>
12 #include <tdeapplication.h>
13 #include <tdeconfig.h>
15 #include <tdeglobal.h>
16 #include <kkeydialog.h>
17 #include <tdelocale.h>
18 #include <tdemessagebox.h>
19 #include <kstatusbar.h>
20 #include <kstdaction.h>
21 #include <tqkeycode.h>
22 #include <tqpopupmenu.h>
23 #include <tqptrlist.h>
26 #include "karmerrors.h"
27 #include "karmutility.h"
28 #include "mainwindow.h"
29 #include "preferences.h"
37 MainWindow::MainWindow(
const TQString &icsfile )
38 : DCOPObject (
"KarmDCOPIface" ),
39 KParts::MainWindow(0,TQt::WStyle_ContextHelp),
40 _accel ( new TDEAccel( this ) ),
46 _taskView =
new TaskView(
this, 0, icsfile );
48 setCentralWidget( _taskView );
53 _preferences = Preferences::instance();
57 _watcher->updateMenus();
60 connect( _taskView, TQ_SIGNAL( totalTimesChanged(
long,
long ) ),
61 this, TQ_SLOT( updateTime(
long,
long ) ) );
62 connect( _taskView, TQ_SIGNAL( selectionChanged ( TQListViewItem * )),
63 this, TQ_SLOT(slotSelectionChanged()));
64 connect( _taskView, TQ_SIGNAL( updateButtons() ),
65 this, TQ_SLOT(slotSelectionChanged()));
66 connect( _taskView, TQ_SIGNAL( setStatusBar( TQString ) ),
67 this, TQ_SLOT(setStatusBar( TQString )));
73 TQ_SIGNAL( contextMenuRequested( TQListViewItem*,
const TQPoint&,
int )),
75 TQ_SLOT( contextMenuRequest( TQListViewItem*,
const TQPoint&,
int )));
77 _tray =
new KarmTray(
this );
79 connect( _tray, TQ_SIGNAL( quitSelected() ), TQ_SLOT( quit() ) );
81 connect( _taskView, TQ_SIGNAL( timersActive() ), _tray, TQ_SLOT( startClock() ) );
82 connect( _taskView, TQ_SIGNAL( timersActive() ),
this, TQ_SLOT( enableStopAll() ));
83 connect( _taskView, TQ_SIGNAL( timersInactive() ), _tray, TQ_SLOT( stopClock() ) );
84 connect( _taskView, TQ_SIGNAL( timersInactive() ),
this, TQ_SLOT( disableStopAll()));
85 connect( _taskView, TQ_SIGNAL( tasksChanged( TQPtrList<Task> ) ),
86 _tray, TQ_SLOT( updateToolTip( TQPtrList<Task> ) ));
92 _preferences->emitSignals();
93 slotSelectionChanged();
96 if ( !kapp->dcopClient()->isRegistered() )
98 kapp->dcopClient()->registerAs(
"karm" );
99 kapp->dcopClient()->setDefaultObject( objId() );
103 m_error[ KARM_ERR_GENERIC_SAVE_FAILED ] =
104 i18n(
"Save failed, most likely because the file could not be locked." );
105 m_error[ KARM_ERR_COULD_NOT_MODIFY_RESOURCE ] =
106 i18n(
"Could not modify calendar resource." );
107 m_error[ KARM_ERR_MEMORY_EXHAUSTED ] =
108 i18n(
"Out of memory--could not create object." );
109 m_error[ KARM_ERR_UID_NOT_FOUND ] =
110 i18n(
"UID not found." );
111 m_error[ KARM_ERR_INVALID_DATE ] =
112 i18n(
"Invalidate date--format is YYYY-MM-DD." );
113 m_error[ KARM_ERR_INVALID_TIME ] =
114 i18n(
"Invalid time--format is YYYY-MM-DDTHH:MM:SS." );
115 m_error[ KARM_ERR_INVALID_DURATION ] =
116 i18n(
"Invalid task duration--must be greater than zero." );
119 void MainWindow::slotSelectionChanged()
121 Task* item= _taskView->current_item();
122 actionDelete->setEnabled(item);
123 actionEdit->setEnabled(item);
125 actionStop->setEnabled(item && item->
isRunning());
126 actionMarkAsComplete->setEnabled(item && !item->
isComplete());
127 actionMarkAsIncomplete->setEnabled(item && item->
isComplete());
137 void MainWindow::setStatusBar(TQString qs)
139 statusBar()->message(qs.isEmpty() ?
"" : i18n(qs.ascii()));
142 bool MainWindow::save()
144 kdDebug(5970) <<
"Saving time data to disk." << endl;
145 TQString err=_taskView->save();
146 if (err.isEmpty()) statusBar()->message(i18n(
"Successfully saved tasks and history"),1807);
147 else statusBar()->message(i18n(err.ascii()),7707);
152 void MainWindow::exportcsvHistory()
154 kdDebug(5970) <<
"Exporting History to disk." << endl;
155 TQString err=_taskView->exportcsvHistory();
156 if (err.isEmpty()) statusBar()->message(i18n(
"Successfully exported History to CSV-file"),1807);
157 else KMessageBox::error(
this, err.ascii());
162 void MainWindow::quit()
168 MainWindow::~MainWindow()
170 kdDebug(5970) <<
"MainWindow::~MainWindows: Quitting karm." << endl;
171 _taskView->stopAllTimers();
173 _taskView->closeStorage();
176 void MainWindow::enableStopAll()
178 actionStopAll->setEnabled(
true);
181 void MainWindow::disableStopAll()
183 actionStopAll->setEnabled(
false);
194 _sessionSum += sessionDiff;
195 _totalSum += totalDiff;
200 void MainWindow::updateStatusBar( )
204 time = formatTime( _sessionSum );
205 statusBar()->changeItem( i18n(
"Session: %1").arg(time), 0 );
207 time = formatTime( _totalSum );
208 statusBar()->changeItem( i18n(
"Total: %1" ).arg(time), 1);
211 void MainWindow::startStatusBar()
213 statusBar()->insertItem( i18n(
"Session"), 0, 0,
true );
214 statusBar()->insertItem( i18n(
"Total" ), 1, 0,
true );
217 void MainWindow::saveProperties( TDEConfig* cfg )
219 _taskView->stopAllTimers();
221 cfg->writeEntry(
"WindowShown", isVisible());
224 void MainWindow::readProperties( TDEConfig* cfg )
226 if( cfg->readBoolEntry(
"WindowShown",
true ))
230 void MainWindow::keyBindings()
232 KKeyDialog::configure( actionCollection(),
this );
235 void MainWindow::startNewSession()
237 _taskView->startNewSession();
240 void MainWindow::resetAllTimes()
242 if ( KMessageBox::warningContinueCancel(
this, i18n(
"Do you really want to reset the time to zero for all tasks?" ),
243 i18n(
"Confirmation Required" ), KGuiItem( i18n(
"Reset All Times" ) ) ) == KMessageBox::Continue )
244 _taskView->resetTimeForAllTasks();
247 void MainWindow::makeMenus()
254 (void) KStdAction::quit(
this, TQ_SLOT( quit() ), actionCollection());
255 (void) KStdAction::print(
this, TQ_SLOT( print() ), actionCollection());
256 actionKeyBindings = KStdAction::keyBindings(
this, TQ_SLOT( keyBindings() ),
257 actionCollection() );
258 actionPreferences = KStdAction::preferences(_preferences,
259 TQ_SLOT(showDialog()),
260 actionCollection() );
261 (void) KStdAction::save(
this, TQ_SLOT( save() ), actionCollection() );
262 TDEAction* actionStartNewSession =
new TDEAction( i18n(
"Start &New Session"),
265 TQ_SLOT( startNewSession() ),
267 "start_new_session");
268 TDEAction* actionResetAll =
new TDEAction( i18n(
"&Reset All Times"),
271 TQ_SLOT( resetAllTimes() ),
274 actionStart =
new TDEAction( i18n(
"&Start"),
275 TQString::fromLatin1(
"1rightarrow"), Key_S,
277 TQ_SLOT( startCurrentTimer() ), actionCollection(),
279 actionStop =
new TDEAction( i18n(
"S&top"),
280 TQString::fromLatin1(
"process-stop"), Key_S,
282 TQ_SLOT( stopCurrentTimer() ), actionCollection(),
284 actionStopAll =
new TDEAction( i18n(
"Stop &All Timers"),
287 TQ_SLOT( stopAllTimers() ), actionCollection(),
289 actionStopAll->setEnabled(
false);
291 actionNew =
new TDEAction( i18n(
"&New..."),
292 TQString::fromLatin1(
"document-new"), CTRL+Key_N,
294 TQ_SLOT( newTask() ), actionCollection(),
296 actionNewSub =
new TDEAction( i18n(
"New &Subtask..."),
297 TQString::fromLatin1(
"application-vnd.tde.tdemultiple"), CTRL+ALT+Key_N,
299 TQ_SLOT( newSubTask() ), actionCollection(),
301 actionDelete =
new TDEAction( i18n(
"&Delete"),
302 TQString::fromLatin1(
"edit-delete"), Key_Delete,
304 TQ_SLOT( deleteTask() ), actionCollection(),
306 actionEdit =
new TDEAction( i18n(
"&Edit..."),
307 TQString::fromLatin1(
"edit"), CTRL + Key_E,
309 TQ_SLOT( editTask() ), actionCollection(),
318 actionMarkAsComplete =
new TDEAction( i18n(
"&Mark as Complete"),
319 TQString::fromLatin1(
"text-x-generic"),
322 TQ_SLOT( markTaskAsComplete() ),
325 actionMarkAsIncomplete =
new TDEAction( i18n(
"&Mark as Incomplete"),
326 TQString::fromLatin1(
"text-x-generic"),
329 TQ_SLOT( markTaskAsIncomplete() ),
331 "mark_as_incomplete");
332 actionClipTotals =
new TDEAction( i18n(
"&Copy Totals to Clipboard"),
333 TQString::fromLatin1(
"klipper"),
336 TQ_SLOT( clipTotals() ),
340 actionClipTotals =
new TDEAction( i18n(
"&Copy Session Time to Clipboard"),
341 TQString::fromLatin1(
"klipper"),
344 TQ_SLOT( clipSession() ),
347 actionClipHistory =
new TDEAction( i18n(
"Copy &History to Clipboard"),
348 TQString::fromLatin1(
"klipper"),
351 TQ_SLOT( clipHistory() ),
355 new TDEAction( i18n(
"Import &Legacy Flat File..."), 0,
356 _taskView, TQ_SLOT(loadFromFlatFile()), actionCollection(),
358 new TDEAction( i18n(
"&Export to CSV File..."), 0,
359 _taskView, TQ_SLOT(exportcsvFile()), actionCollection(),
361 new TDEAction( i18n(
"Export &History to CSV File..."), 0,
362 this, TQ_SLOT(exportcsvHistory()), actionCollection(),
363 "export_csvhistory");
364 new TDEAction( i18n(
"Import Tasks From &Planner..."), 0,
365 _taskView, TQ_SLOT(importPlanner()), actionCollection(),
375 setXMLFile( TQString::fromLatin1(
"karmui.rc") );
379 actionKeyBindings->setToolTip( i18n(
"Configure key bindings") );
380 actionKeyBindings->setWhatsThis( i18n(
"This will let you configure key"
381 "bindings which is specific to karm") );
383 actionStartNewSession->setToolTip( i18n(
"Start a new session") );
384 actionStartNewSession->setWhatsThis( i18n(
"This will reset the session time "
385 "to 0 for all tasks, to start a "
386 "new session, without affecting "
388 actionResetAll->setToolTip( i18n(
"Reset all times") );
389 actionResetAll->setWhatsThis( i18n(
"This will reset the session and total "
390 "time to 0 for all tasks, to restart from "
393 actionStart->setToolTip( i18n(
"Start timing for selected task") );
394 actionStart->setWhatsThis( i18n(
"This will start timing for the selected "
396 "It is even possible to time several tasks "
397 "simultaneously.\n\n"
398 "You may also start timing of a tasks by "
399 "double clicking the left mouse "
400 "button on a given task. This will, however, "
401 "stop timing of other tasks."));
403 actionStop->setToolTip( i18n(
"Stop timing of the selected task") );
404 actionStop->setWhatsThis( i18n(
"Stop timing of the selected task") );
406 actionStopAll->setToolTip( i18n(
"Stop all of the active timers") );
407 actionStopAll->setWhatsThis( i18n(
"Stop all of the active timers") );
409 actionNew->setToolTip( i18n(
"Create new top level task") );
410 actionNew->setWhatsThis( i18n(
"This will create a new top level task.") );
412 actionDelete->setToolTip( i18n(
"Delete selected task") );
413 actionDelete->setWhatsThis( i18n(
"This will delete the selected task and "
414 "all its subtasks.") );
416 actionEdit->setToolTip( i18n(
"Edit name or times for selected task") );
417 actionEdit->setWhatsThis( i18n(
"This will bring up a dialog box where you "
418 "may edit the parameters for the selected "
426 actionClipTotals->setToolTip(i18n(
"Copy task totals to clipboard"));
427 actionClipHistory->setToolTip(i18n(
"Copy time card history to clipboard."));
429 slotSelectionChanged();
432 void MainWindow::print()
438 void MainWindow::loadGeometry()
440 if (initialGeometrySet()) setAutoSaveSettings();
443 TDEConfig &config = *kapp->config();
445 config.setGroup( TQString::fromLatin1(
"Main Window Geometry") );
446 int w = config.readNumEntry( TQString::fromLatin1(
"Width"), 100 );
447 int h = config.readNumEntry( TQString::fromLatin1(
"Height"), 100 );
448 w = TQMAX( w, sizeHint().width() );
449 h = TQMAX( h, sizeHint().height() );
455 void MainWindow::saveGeometry()
457 TDEConfig &config = *TDEGlobal::config();
458 config.setGroup( TQString::fromLatin1(
"Main Window Geometry"));
459 config.writeEntry( TQString::fromLatin1(
"Width"), width());
460 config.writeEntry( TQString::fromLatin1(
"Height"), height());
464 bool MainWindow::queryClose()
466 if ( !kapp->sessionSaving() ) {
470 return TDEMainWindow::queryClose();
473 void MainWindow::contextMenuRequest( TQListViewItem*,
const TQPoint& point,
int )
475 TQPopupMenu* pop =
dynamic_cast<TQPopupMenu*
>(
476 factory()->container( i18n(
"task_popup" ),
this ) );
494 _taskView->deleteTask();
500 return _preferences->promptDelete();
505 _preferences->setPromptDelete( prompt );
513 Task* task = _taskView->first_child();
514 while ( rval.isEmpty() && task )
516 rval = _hasTask( task, taskname );
517 task = task->nextSibling();
525 DesktopList desktopList;
526 TQString uid = _taskView->addTask( taskname, 0, 0, desktopList );
527 kdDebug(5970) <<
"MainWindow::addTask( " << taskname <<
" ) returns " << uid << endl;
528 if ( uid.length() > 0 )
return 0;
533 return KARM_ERR_GENERIC_SAVE_FAILED;
540 TQString err=
"no such task";
541 for (
int i=0; i<_taskView->count(); i++)
543 if ((_taskView->item_at_index(i)->name()==taskName))
546 if (err==TQString()) err=
"task name is abigious";
547 if (err==
"no such task") err=TQString();
552 _taskView->item_at_index(index)->setPercentComplete( perCent, _taskView->storage() );
558 (
const TQString& taskId,
const TQString& datetime,
long minutes )
563 TQDateTime startDateTime;
566 if ( minutes <= 0 ) rval = KARM_ERR_INVALID_DURATION;
569 task = _taskView->first_child();
573 t = _hasUid( task, taskId );
574 task = task->nextSibling();
576 if ( t == NULL ) rval = KARM_ERR_UID_NOT_FOUND;
581 startDate = TQDate::fromString( datetime, TQt::ISODate );
582 if ( datetime.length() > 10 )
584 startTime = TQTime::fromString( datetime, TQt::ISODate );
586 else startTime = TQTime( 12, 0 );
587 if ( startDate.isValid() && startTime.isValid() )
589 startDateTime = TQDateTime( startDate, startTime );
591 else rval = KARM_ERR_INVALID_DATE;
598 t->
changeTotalTimes( t->sessionTime() + minutes, t->totalTime() + minutes );
599 if ( ! _taskView->storage()->bookTime( t, startDateTime, minutes * 60 ) )
601 rval = KARM_ERR_GENERIC_SAVE_FAILED;
612 if ( mkb <= KARM_MAX_ERROR_NO )
return m_error[ mkb ];
613 else return i18n(
"Invalid error number: %1" ).arg( mkb );
621 kdDebug(5970) <<
"MainWindow::totalTimeForTask( " << taskId <<
" )" << endl;
624 task = _taskView->first_child();
628 t = _hasUid( task, taskId );
629 task = task->nextSibling();
633 rval = t->totalTime();
634 kdDebug(5970) <<
"MainWindow::totalTimeForTask - task found: rval = " << rval << endl;
638 kdDebug(5970) <<
"MainWindow::totalTimeForTask - task not found" << endl;
639 rval = KARM_ERR_UID_NOT_FOUND;
645 TQString MainWindow::_hasTask(
Task* task,
const TQString &taskname )
const
648 if ( task->
name() == taskname )
655 while ( rval.isEmpty() && nexttask )
657 rval = _hasTask( nexttask, taskname );
658 nexttask = nexttask->nextSibling();
664 Task* MainWindow::_hasUid(
Task* task,
const TQString &uid )
const
670 if ( task->
uid() == uid ) rval = task;
674 while ( !rval && nexttask )
676 rval = _hasUid( nexttask, uid );
677 nexttask = nexttask->nextSibling();
685 TQString err=
"no such task";
686 for (
int i=0; i<_taskView->count(); i++)
688 if ((_taskView->item_at_index(i)->name()==taskname))
691 if (err==TQString()) err=
"task name is abigious";
692 if (err==
"no such task") err=TQString();
695 if (err==TQString()) _taskView->startTimerFor( _taskView->item_at_index(index) );
702 TQString err=
"no such task";
703 for (
int i=0; i<_taskView->count(); i++)
705 if ((_taskView->item_at_index(i)->name()==taskname))
708 if (err==TQString()) err=
"task name is abigious";
709 if (err==
"no such task") err=TQString();
712 if (err==TQString()) _taskView->stopTimerFor( _taskView->item_at_index(index) );
716 TQString
MainWindow::exportcsvfile( TQString filename, TQString from, TQString to,
int type,
bool decimalMinutes,
bool allTasks, TQString delimiter, TQString quote )
720 rc.
from=TQDate::fromString( from );
721 if ( rc.
from.isNull() ) rc.
from=TQDate::fromString( from, TQt::ISODate );
722 kdDebug(5970) <<
"rc.from " << rc.
from << endl;
723 rc.
to=TQDate::fromString( to );
724 if ( rc.
to.isNull() ) rc.
to=TQDate::fromString( to, TQt::ISODate );
725 kdDebug(5970) <<
"rc.to " << rc.
to << endl;
731 return _taskView->report( rc );
736 return _taskView->importPlanner(fileName);
740 #include "mainwindow.moc"