1/* This file is part of the KDE project
2 Copyright (C) 2005 - 2007 Dag Andersen <danders@get2net.dk>
3 Copyright (C) 2011 Dag Andersen <danders@get2net.dk>
4
5 This library is free software; you can redistribute it and/or
6 modify it under the terms of the GNU Library General Public
7 License as published by the Free Software Foundation; either
8 version 2 of the License, or (at your option) any later version.
9
10 This library is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 Library General Public License for more details.
14
15 You should have received a copy of the GNU Library General Public License
16 along with this library; see the file COPYING.LIB. If not, write to
17 the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
18 * Boston, MA 02110-1301, USA.
19*/
20
21#ifndef KPTACCOUNT_H
22#define KPTACCOUNT_H
23
24#include "kplatokernel_export.h"
25
26#include <QDateTime>
27#include <QMap>
28#include <QList>
29#include <QStringList>
30
31#include "kptglobal.h"
32#include "kpteffortcostmap.h"
33#include "kptnode.h"
34#include "kptresource.h"
35
36#include <kdebug.h>
37
38#include <KoXmlReader.h>
39
40class QDomElement;
41class QString;
42
43namespace KPlato
44{
45
46class Accounts;
47class Account;
48
49
50/**
51 * Account holds one account.
52 * An account can have any number of sub-accounts.
53 * Account names must be unique.
54 */
55class KPLATOKERNEL_EXPORT Account
56{
57public:
58
59 /**
60 * Constructor.
61 */
62 Account();
63
64 /**
65 *
66 */
67 explicit Account(const QString& name, const QString& description=QString());
68
69 /**
70 * Destructor.
71 */
72 ~Account();
73
74
75 QString name() const { return m_name; }
76 void setName(const QString& name);
77
78 QString description() const { return m_description; }
79 void setDescription(const QString& desc);
80
81 bool isElement() const { return m_accountList.isEmpty(); }
82 bool isDefaultAccount() const;
83
84 Accounts *list() const { return m_list; }
85 void setList(Accounts *list) { m_list = list; }
86 Account *parent() const { return m_parent; }
87 void setParent(Account *parent) { m_parent = parent; }
88 void clear() { m_accountList.clear(); }
89 void insert(Account *account, int index = -1);
90 void take(Account *account);
91 bool isChildOf( const Account *account ) const;
92 void insertChildren();
93 int indexOf( Account *account ) const { return m_accountList.indexOf( account ); }
94
95 bool isBaselined( long id = BASELINESCHEDULE ) const;
96
97 bool load(KoXmlElement &element, Project &project);
98 void save(QDomElement &element) const;
99
100 const QList<Account*> &accountList() const { return m_accountList; }
101 int childCount() const { return m_accountList.count(); }
102 Account *childAt( int index ) const { return m_accountList.value( index ); }
103
104 Account *findAccount() const { return findAccount(m_name); }
105 Account *findAccount(const QString &id) const;
106 bool removeId() { return removeId(m_name); }
107 bool removeId(const QString &id);
108 bool insertId();
109 bool insertId(Account *account);
110
111 void changed();
112
113 class CostPlace {
114 public:
115 /// Create an empty cost place
116 CostPlace()
117 : m_account(0), m_objectId(), m_node(0), m_resource(0), m_running(false), m_startup(false), m_shutdown(false)
118 {}
119 /// Create an empty cost place for account @p acc
120 explicit CostPlace(Account *acc)
121 : m_account(acc), m_objectId(), m_node(0), m_resource(0), m_running(false), m_startup(false), m_shutdown(false)
122 {}
123 /// Create a cost place for a task
124 CostPlace(Account *acc, Node *node, bool running=false, bool strtup=false, bool shutdown=false);
125
126 /// Create a cost place for a resource
127 CostPlace(Account *acc, Resource *resource, bool running=false);
128
129 explicit CostPlace(CostPlace *cp) {
130 m_account = cp->m_account;
131 m_objectId = cp->m_objectId;
132 m_node = cp->m_node;
133 m_resource = cp->m_resource;
134 m_running = cp->m_running;
135 m_startup = cp->m_startup;
136 m_shutdown = cp->m_shutdown;
137 }
138 ~CostPlace();
139
140 bool isBaselined( long id = BASELINESCHEDULE ) const;
141
142 bool isEmpty() { return !(m_running || m_startup || m_shutdown); }
143 Node *node() const { return m_node; }
144 void setNode( Node *node );
145
146 Resource *resource() const { return m_resource; }
147 void setResource( Resource *resource );
148
149 bool running() const { return m_running; }
150 void setRunning(bool on );
151 bool startup() const { return m_startup; }
152 void setStartup(bool on);
153 bool shutdown() const { return m_shutdown; }
154 void setShutdown(bool on);
155
156 bool load(KoXmlElement &element, Project &project);
157 void save(QDomElement &element) const;
158 // for loading xml
159 void setObjectId( const QString &id );
160 QString objectId() const;
161
162 private:
163 Account *m_account;
164 QString m_objectId;
165 Node *m_node;
166 Resource *m_resource;
167 bool m_running;
168 bool m_startup;
169 bool m_shutdown;
170 };
171
172 void append(CostPlace *cp) { m_costPlaces.append(cp); }
173 const QList<CostPlace*> &costPlaces() const {return m_costPlaces; }
174 Account::CostPlace *findCostPlace(const Node &node) const;
175
176 Account::CostPlace *findCostPlace(const Resource &resource) const;
177 CostPlace *findRunning(const Resource &resource) const;
178 void removeRunning(const Resource &resource);
179 void addRunning(Resource &resource);
180
181 CostPlace *findRunning(const Node &node) const;
182 void removeRunning(const Node &node);
183 void addRunning(Node &node);
184 CostPlace *findStartup(const Node &node) const;
185 void removeStartup(const Node &node);
186 void addStartup(Node &node);
187 CostPlace *findShutdown(const Node &node) const;
188 void removeShutdown(const Node &node);
189 void addShutdown(Node &node);
190 void deleteCostPlace(CostPlace *cp);
191
192 EffortCostMap plannedCost(long id = BASELINESCHEDULE) const;
193 EffortCostMap plannedCost(const QDate &start, const QDate &end, long id = BASELINESCHEDULE) const;
194
195 EffortCostMap actualCost(long id = BASELINESCHEDULE) const;
196 EffortCostMap actualCost(const QDate &start, const QDate &end, long id = BASELINESCHEDULE) const;
197
198protected:
199 EffortCostMap plannedCost(const CostPlace &cp, const QDate &start, const QDate &end, long id ) const;
200 EffortCostMap actualCost(const Account::CostPlace &cp, const QDate &start, const QDate &end, long id) const;
201
202private:
203 QString m_name;
204 QString m_description;
205 Accounts *m_list;
206 Account *m_parent;
207 QList<Account*> m_accountList;
208 QList<CostPlace*> m_costPlaces;
209
210#ifndef NDEBUG
211public:
212 void printDebug(const QString& indent);
213#endif
214};
215
216typedef QList<Account*> AccountList;
217typedef QListIterator<Account*> AccountListIterator;
218
219/**
220 * Accounts administrates all accounts.
221 */
222
223class KPLATOKERNEL_EXPORT Accounts : public QObject
224{
225 Q_OBJECT
226public:
227 explicit Accounts(Project &project);
228 ~Accounts();
229
230 Account *defaultAccount() const { return m_defaultAccount; }
231 void setDefaultAccount(Account *account);
232
233 /// Return the planned cost from all cost places of this account added to cost from all sub-accounts
234 EffortCostMap plannedCost(const Account &account, long id = BASELINESCHEDULE) const;
235
236 /// Return the planned cost from all cost places of this account added to cost from all sub-accounts
237 /// for the interval @p start to @p end inclusive
238 EffortCostMap plannedCost(const Account &account, const QDate &start, const QDate &end, long id = BASELINESCHEDULE) const;
239
240 /// Return the actual cost from all cost places of this account added to cost from all sub-accounts
241 EffortCostMap actualCost(const Account &account, long id = BASELINESCHEDULE) const;
242
243 /// Return the actual cost from all cost places of this account added to cost from all sub-accounts
244 /// for the interval @p start to @p end inclusive
245 EffortCostMap actualCost(const Account &account, const QDate &start, const QDate &end, long id = BASELINESCHEDULE) const;
246
247 void clear() { m_accountList.clear(); m_idDict.clear(); }
248 void insert(Account *account, Account *parent=0, int index = -1);
249 void take(Account *account);
250
251 bool load(KoXmlElement &element, Project &project);
252 void save(QDomElement &element) const;
253
254 QStringList costElements() const;
255 QStringList nameList() const;
256
257 const AccountList &accountList() const { return m_accountList; }
258 int accountCount() const { return m_accountList.count(); }
259 Account *accountAt( int index ) const { return m_accountList.value( index ); }
260 int indexOf( Account *account ) const { return m_accountList.indexOf( account ); }
261
262 Account *findRunningAccount(const Resource &resource) const;
263
264 Account *findRunningAccount(const Node &node) const;
265 Account *findStartupAccount(const Node &node) const;
266 Account *findShutdownAccount(const Node &node) const;
267 Account *findAccount(const QString &id) const;
268 bool insertId(Account *account);
269 bool removeId(const QString &id);
270 QString uniqueId( const QString &seed ) const;
271
272 void accountDeleted(Account *account)
273 { if (account == m_defaultAccount) m_defaultAccount = 0; }
274
275 void accountChanged( Account *account );
276 QList<Account*> allAccounts() const { return m_idDict.values(); }
277 QList<Node*> allNodes() const;
278
279signals:
280 void accountAdded( const Account * );
281 void accountToBeAdded( const Account *, int );
282 void accountRemoved( const Account * );
283 void accountToBeRemoved( const Account * );
284 void changed( Account *);
285 void defaultAccountChanged();
286
287private:
288 Project &m_project;
289 AccountList m_accountList;
290 QMap<QString, Account*> m_idDict;
291
292 Account *m_defaultAccount;
293
294#ifndef NDEBUG
295public:
296 void printDebug(const QString& indent);
297#endif
298};
299
300} //namespace KPlato
301
302#endif
303