1/* This file is part of the KDE project
2 Copyright 2006-2007 Stefan Nikolaus <stefan.nikolaus@kdemail.net>
3 Copyright 2004 Tomas Mecir <mecirt@gmail.com>
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 KSPREAD_DEPENDENCY_MANAGER_P
22#define KSPREAD_DEPENDENCY_MANAGER_P
23
24// Local
25#include "DependencyManager.h"
26
27#include <QHash>
28#include <QList>
29
30#include "Cell.h"
31#include "Region.h"
32#include "RTree.h"
33
34namespace Calligra
35{
36namespace Sheets
37{
38class Formula;
39class Map;
40class Sheet;
41
42class DependencyManager::Private
43{
44public:
45 /**
46 * Clears internal structures.
47 */
48 void reset();
49
50 /**
51 * Generates the dependencies of \p cell .
52 * First, it removes the old providing region. Then, the new providing
53 * region is computed. Finally, adds \p cell as consumer and the new
54 * providing region to the data structures.
55 * \see removeDependencies
56 * \see computeDependencies
57 */
58 void generateDependencies(const Cell& cell, const Formula& formula);
59
60 /**
61 * Computes the reference depth.
62 * Depth means the maximum depth of all cells this cell depends on plus one,
63 * while a cell, which do not refer to other cells, has a depth
64 * of zero.
65 *
66 * Examples:
67 * \li A1: '=1.0'
68 * \li A2: '=A1+A1'
69 * \li A3: '=A1+A1+A2'
70 *
71 * \li depth(A1) = 0
72 * \li depth(A2) = 1
73 * \li depth(A3) = 2
74 */
75 int computeDepth(Cell cell) const;
76
77 /**
78 * Used in the recalculation events for changed regions.
79 * Determines the reference depth for each position in \p region .
80 *
81 * \see computeDepth
82 * \see generateDepths(Cell cell)
83 */
84 void generateDepths(const Region& region);
85
86 /**
87 * Generates the depth of cell and all of its consumers.
88 * Calls itself recursively for the cell's consuming cells.
89 */
90 void generateDepths(Cell cell, QSet<Cell>& computedDepths);
91
92 /**
93 * Returns the region, that consumes the value of \p cell.
94 * \see DependencyManager::consumingRegion(const Cell&)
95 * \return region consuming \p cell 's value
96 */
97 Region consumingRegion(const Cell& cell) const;
98
99 void namedAreaModified(const QString& name);
100
101 /**
102 * Removes all dependencies of \p cell .
103 */
104 void removeDependencies(const Cell& cell);
105
106 /**
107 * Removes the depths of \p cell and all its consumers.
108 */
109 void removeDepths(const Cell& cell);
110
111 /**
112 * Computes and stores the dependencies.
113 *
114 * Parses \p formula and adds each contained reference to a
115 * cell, a cell range or a named area to the providing regions
116 * of \p cell.
117 * Additionally, the opposite direction is also stored:
118 * Each consumed region, i.e. each reference, points to \p cell.
119 *
120 * The \p formula has to belong to \p cell. It would have been
121 * possible to look it up from \p cell, but is passed separately
122 * for performance reasons.
123 * Do not call this method for a \p cell not containing a \p formula.
124 */
125 void computeDependencies(const Cell& cell, const Formula& formula);
126
127 enum Direction { Forward, Backward };
128 /**
129 * Removes the circular dependency flag from \p region and all their dependencies.
130 */
131 void removeCircularDependencyFlags(const Region& region, Direction direction);
132
133 /**
134 * For debugging/testing purposes.
135 */
136 void dump() const;
137
138 const Map* map;
139 // stores providing regions ordered by their consuming cell locations
140 // use QMap rather then QHash cause it's faster for our use-case
141 QMap<Cell, Region> providers;
142 // stores consuming cell locations ordered by their providing regions
143 QHash<Sheet*, RTree<Cell>*> consumers;
144 // stores consuming cell locations ordered by their providing named area
145 // (in addition to the general storage of the consuming cell locations)
146 QHash<QString, QList<Cell> > namedAreaConsumers;
147 /*
148 * Stores cells with its reference depth.
149 * Depth means the maximum depth of all cells this cell depends on plus one,
150 * while a cell which has a formula without cell references has a depth
151 * of zero.
152 *
153 * Examples:
154 * \li A1: '=1.0'
155 * \li A2: '=A1+A1'
156 * \li A3: '=A1+A1+A2'
157 *
158 * \li depth(A1) = 0
159 * \li depth(A2) = 1
160 * \li depth(A3) = 2
161 */
162 // use QMap rather then QHash cause it's faster for our use-case
163 QMap<Cell, int> depths;
164};
165
166} // namespace Sheets
167} // namespace Calligra
168
169#endif // KSPREAD_DEPENDENCY_MANAGER_P
170