summaryrefslogtreecommitdiffstats
path: root/karm/karmstorage.h
diff options
context:
space:
mode:
authortoma <toma@283d02a7-25f6-0310-bc7c-ecb5cbfe19da>2009-11-25 17:56:58 +0000
committertoma <toma@283d02a7-25f6-0310-bc7c-ecb5cbfe19da>2009-11-25 17:56:58 +0000
commit460c52653ab0dcca6f19a4f492ed2c5e4e963ab0 (patch)
tree67208f7c145782a7e90b123b982ca78d88cc2c87 /karm/karmstorage.h
downloadtdepim-460c52653ab0dcca6f19a4f492ed2c5e4e963ab0.tar.gz
tdepim-460c52653ab0dcca6f19a4f492ed2c5e4e963ab0.zip
Copy the KDE 3.5 branch to branches/trinity for new KDE 3.5 features.
BUG:215923 git-svn-id: svn://anonsvn.kde.org/home/kde/branches/trinity/kdepim@1054174 283d02a7-25f6-0310-bc7c-ecb5cbfe19da
Diffstat (limited to 'karm/karmstorage.h')
-rw-r--r--karm/karmstorage.h381
1 files changed, 381 insertions, 0 deletions
diff --git a/karm/karmstorage.h b/karm/karmstorage.h
new file mode 100644
index 000000000..c84658297
--- /dev/null
+++ b/karm/karmstorage.h
@@ -0,0 +1,381 @@
+/*
+ * This file only:
+ * Copyright (C) 2003 Mark Bucciarelli <mark@hubcapconsutling.com>
+ *
+ * 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 KARM_STORAGE_H
+#define KARM_STORAGE_H
+
+#include <qdict.h>
+#include <qptrstack.h>
+
+#include "journal.h"
+#include "reportcriteria.h"
+
+#include "desktoplist.h"
+
+#include <calendarresources.h>
+#include <vector>
+#include "resourcecalendar.h"
+#include <kdepimmacros.h>
+
+class QDateTime;
+class Preferences;
+class Task;
+class TaskView;
+class HistoryEvent;
+class KCal::Todo;
+
+/**
+ * Singleton to store/retrieve KArm data to/from persistent storage.
+ *
+ * The storage is an iCalendar file. Also included are methods to
+ * import KArm data from the two legacy file formats.
+ *
+ * All logic that deals with getting and saving data should go here. The
+ * storage logic has changed at least twice already in KArm's history, and
+ * chances are good it will change again (for example, allowing KOrganizer and
+ * KArm to access the same iCalendar file simultaneously).
+ *
+ * Prior to KDE 3.2, KArm just stored totals for each task--a session total
+ * and a task total. The session total was reset to zero each time KArm
+ * started up or after the user reset the session times to zero. With the
+ * release of KDE 3.2, KArm now stores these task totals as well as logging
+ * the history of each start/stop event; that is, every time you start a timer
+ * and then stop a timer on a task, KArm records this as an iCalendar event.
+ *
+ * @short Logic that gets and stores KArm data to disk.
+ * @author Mark Bucciarelli <mark@hubcapconsulting.com>
+ */
+
+class KarmStorage
+{
+ public:
+ /*
+ * Return reference to storage singleton.
+ *
+ * The constructors are private, so this must be used to create a
+ * KarmStorage instance.
+ */
+ static KarmStorage *instance();
+
+ /*
+ * Load the list view with tasks read from iCalendar file.
+ *
+ * Parses iCalendar file, builds list view items in the proper
+ * hierarchy, and loads them into the list view widget.
+ *
+ * If the file name passed in is the same as the last file name that was
+ * loaded, this method does nothing.
+ *
+ * This method considers any of the following conditions errors:
+ *
+ * @li the iCalendar file does not exist
+ * @li the iCalendar file is not readable
+ * @li the list group currently has list items
+ * @li an iCalendar todo has no related to attribute
+ * @li a todo is related to another todo which does not exist
+ *
+ * @param taskview The list group used in the TaskView
+ * @param preferences The current KArm preferences.
+ * @param fileName Override preferences' filename
+ *
+ * @return empty string if success, error message if error.
+ *
+ */
+ QString load(TaskView* taskview, const Preferences* preferences, QString fileName="" );
+
+ /*
+ * Return the name of the iCal file
+ */
+ QString icalfile();
+
+ /*
+ * Build up the taskview.
+ *
+ * This is needed if the iCal file has been modified
+ */
+ QString buildTaskView(KCal::ResourceCalendar *rc, TaskView *view);
+
+ /* Close calendar and clear view. Release lock if holding one. */
+ void closeStorage(TaskView* view);
+
+ /*
+ * Save all tasks and their totals to an iCalendar file.
+ *
+ * All tasks must have an associated VTODO object already created in the
+ * calendar file; that is, the task->uid() must refer to a valid VTODO in
+ * the calender.
+ * Delivers empty string if successful, else error msg.
+ *
+ * @param taskview The list group used in the TaskView
+ */
+ QString save(TaskView* taskview);
+
+ /**
+ * Read tasks and their total times from a text file (legacy storage).
+ *
+ * This reads from one of the two legacy file formats. In this version,
+ * the parent task times do not include the sum of all their children's
+ * times.
+ *
+ * The format of the file is zero or more lines of:
+ * 1 task id (a number)
+ * time in minutes
+ * string task name
+ * [string] desktops, in which to count. e.g. "1,2,5" (optional)
+ */
+ QString loadFromFlatFile(TaskView* taskview, const QString& filename);
+
+ /**
+ * Reads tasks and their total times from text file (legacy).
+ *
+ * This is the older legacy format, where the task totals included the
+ * children totals.
+ *
+ * @see loadFromFlatFile
+ */
+ QString loadFromFlatFileCumulative(TaskView* taskview,
+ const QString& filename);
+
+ /**
+ Output a report based on contents of ReportCriteria.
+ */
+ QString report( TaskView *taskview, const ReportCriteria &rc );
+
+ /**
+ * Log the change in a task's time.
+ *
+ * We create an iCalendar event to store each change. The event start
+ * date is set to the current datetime. If time is added to the task, the
+ * task end date is set to start time + delta. If the time is negative,
+ * the end date is set to the start time.
+ *
+ * In both cases (postive or negative delta), we create a custom iCalendar
+ * property that stores the delta (in seconds). This property is called
+ * X-KDE-karm-duration.
+ *
+ * Note that the KArm UI allows the user to change both the session and
+ * the total task time, and this routine does not account for all posibile
+ * cases. For example, it is possible for the user to do something crazy
+ * like add 10 minutes to the session time and subtract 50 minutes from
+ * the total time. Although this change violates a basic law of physics,
+ * it is allowed.
+ *
+ * For now, you should pass in the change to the total task time.
+ * Eventually, the UI should be changed.
+ *
+ * @param task The task the change is for.
+ * @param delta Change in task time, in seconds. Can be negative.
+ */
+ void changeTime(const Task* task, const long deltaSeconds);
+
+ /**
+ * Book time to a task.
+ *
+ * Creates an iCalendar event and adds it to the calendar. Does not write
+ * calender to disk, just adds event to calendar in memory. However, the
+ * resource framework does try to get a lock on the file. After a
+ * succesful lock, the calendar marks this incidence as modified and then
+ * releases the lock.
+ *
+ * @param task Task
+ * @param startDateTime Date and time the booking starts.
+ * @param durationInSeconds Duration of time to book, in seconds.
+ *
+ * @return true if event was added, false if not (if, for example, the
+ * attempted file lock failed).
+ */
+ bool bookTime(const Task* task, const QDateTime& startDateTime,
+ long durationInSeconds);
+
+ /**
+ * Log a change to a task name.
+ *
+ * For iCalendar storage, there is no need to log an Event for this event,
+ * since unique id's are used to link Events to Todos. No matter how many
+ * times you change a task's name, the uid stays the same.
+ *
+ * @param task The task
+ * @param oldname The old name of the task. The new name is in the task
+ * object already.
+ */
+ void setName(const Task* task, const QString& oldname) { Q_UNUSED(task); Q_UNUSED(oldname); }
+
+
+ /**
+ * Log the event that a timer has started for a task.
+ *
+ * For the iCalendar storage, there is no need to log anything for this
+ * event. We log an event when the timer is stopped.
+ *
+ * @param task The task the timer was started for.
+ */
+ void startTimer(const Task* task) { Q_UNUSED(task); }
+
+ /**
+ * Log the event that the timer has stopped for this task.
+ *
+ * The task stores the last time a timer was started, so we log a new iCal
+ * Event with the start and end times for this task.
+ * @see KarmStorage::changeTime
+ *
+ * @param task The task the timer was stopped for.
+ */
+ void stopTimer(const Task* task, QDateTime when=QDateTime::currentDateTime());
+
+ /**
+ * Log a new comment for this task.
+ *
+ * iCal allows multiple comment tags. So we just add a new comment to the
+ * todo for this task and write the calendar.
+ *
+ * @param task The task that gets the comment
+ * @param comment The comment
+ */
+ void addComment(const Task* task, const QString& comment);
+
+
+ /**
+ * Remove this task from iCalendar file.
+ *
+ * Removes task as well as all event history for this task.
+ *
+ * @param task The task to be removed.
+ * @return true if change was saved, false otherwise
+ */
+ bool removeTask(Task* task);
+
+ /**
+ * Add this task from iCalendar file.
+ *
+ * Create a new KCal::Todo object and load with task information. If
+ * parent is not zero, then set the RELATED-TO attribute for this Todo.
+ *
+ * @param task The task to be removed.
+ * @param parent The parent of this task. Must have a uid() that is in
+ * the existing calendar. If zero, this task is considered a root task.
+ * @return The unique ID for the new VTODO. Return an null QString if
+ * there was an error creating the new calendar object.
+ */
+ QString addTask(const Task* task, const Task* parent);
+
+ /**
+ * Check if the iCalendar file currently loaded has any Todos in it.
+ *
+ * @return true if iCalendar file has any todos
+ */
+ bool isEmpty();
+
+ /**
+ * Check if iCalendar file name in the preferences has changed since the
+ * last call to load. If there is no calendar file currently loaded,
+ * return false.
+ *
+ * @param preferences Set of KArm preferences.
+ *
+ * @return true if a previous file has been loaded and the iCalendar file
+ * specified in the preferences is different.
+ */
+ bool isNewStorage(const Preferences* preferences) const;
+
+ /** Return a list of start/stop events for the given date range. */
+ QValueList<HistoryEvent> getHistory(const QDate& from, const QDate& to);
+
+ private:
+ static KarmStorage *_instance;
+ KCal::ResourceCalendar *_calendar;
+ QString _icalfile;
+
+ KarmStorage();
+ void adjustFromLegacyFileFormat(Task* task);
+ bool parseLine(QString line, long *time, QString *name, int *level,
+ DesktopList* desktopList);
+ QString writeTaskAsTodo
+ (Task* task, const int level, QPtrStack< KCal::Todo >& parents);
+ bool saveCalendar();
+
+ KCal::Event* baseEvent(const Task*);
+ bool remoteResource( const QString& file ) const;
+
+ /**
+ * Writes all tasks and their totals to a Comma-Separated Values file.
+ *
+ * The format of this file is zero or more lines of:
+ * taskName,subtaskName,..,sessionTime,time,totalSessionTime,totalTime
+ * the number of subtasks is determined at runtime.
+ */
+ QString exportcsvFile( TaskView *taskview, const ReportCriteria &rc );
+
+ /**
+ * Write task history to file as comma-delimited data.
+ */
+ QString exportcsvHistory (
+ TaskView* taskview,
+ const QDate& from,
+ const QDate& to,
+ const ReportCriteria &rc
+ );
+
+ long printTaskHistory (
+ const Task *task,
+ const QMap<QString,long>& taskdaytotals,
+ QMap<QString,long>& daytotals,
+ const QDate& from,
+ const QDate& to,
+ const int level,
+ std::vector <QString> &matrix,
+ const ReportCriteria &rc
+ );
+};
+
+/**
+ * One start/stop event that has been logged.
+ *
+ * When a task is running and the user stops it, KArm logs this event and
+ * saves it in the history. This class represents such an event read from
+ * storage, and abstracts it from the specific storage used.
+ */
+class HistoryEvent
+{
+ public:
+ /** Needed to be used in a value list. */
+ HistoryEvent() {}
+ HistoryEvent(QString uid, QString name, long duration,
+ QDateTime start, QDateTime stop, QString todoUid);
+ QString uid() {return _uid; }
+ QString name() {return _name; }
+ /** In seconds. */
+ long duration() {return _duration; }
+ QDateTime start() {return _start; }
+ QDateTime stop() { return _stop; }
+ QString todoUid() {return _todoUid; }
+
+ private:
+ QString _uid;
+ QString _todoUid;
+ QString _name;
+ long _duration;
+ QDateTime _start;
+ QDateTime _stop;
+
+};
+
+#endif // KARM_STORAGE_H