1/* This file is part of the KDE project
2 Copyright 2007 Stefan Nikolaus <stefan.nikolaus@kdemail.net>
3 Copyright 2007 Thorsten Zachmann <zachmann@kde.org>
4 Copyright 2005-2006 Inge Wallin <inge@lysator.liu.se>
5 Copyright 2004 Ariya Hidayat <ariya@kde.org>
6 Copyright 2002-2003 Norbert Andres <nandres@web.de>
7 Copyright 2000-2002 Laurent Montel <montel@kde.org>
8 Copyright 2002 John Dailey <dailey@vt.edu>
9 Copyright 2002 Phillip Mueller <philipp.mueller@gmx.de>
10 Copyright 2000 Werner Trobin <trobin@kde.org>
11 Copyright 1999-2000 Simon Hausmann <hausmann@kde.org>
12 Copyright 1999 David Faure <faure@kde.org>
13 Copyright 1998-2000 Torben Weis <weis@kde.org>
14
15 This library is free software; you can redistribute it and/or
16 modify it under the terms of the GNU Library General Public
17 License as published by the Free Software Foundation; either
18 version 2 of the License, or (at your option) any later version.
19
20 This library is distributed in the hope that it will be useful,
21 but WITHOUT ANY WARRANTY; without even the implied warranty of
22 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
23 Library General Public License for more details.
24
25 You should have received a copy of the GNU Library General Public License
26 along with this library; see the file COPYING.LIB. If not, write to
27 the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
28 Boston, MA 02110-1301, USA.
29*/
30
31// Local
32#include "CalculationSettings.h"
33
34#include "Localization.h"
35
36#include <KoXmlNS.h>
37#include <KoXmlWriter.h>
38
39#include <kdebug.h>
40
41using namespace Calligra::Sheets;
42
43class CalculationSettings::Private
44{
45public:
46 KLocale* locale;
47 bool caseSensitiveComparisons : 1;
48 bool precisionAsShown : 1;
49 bool wholeCellSearchCriteria : 1;
50 bool automaticFindLabels : 1;
51 bool useRegularExpressions : 1;
52 bool useWildcards : 1;
53 bool automaticCalculation : 1;
54 int refYear; // the reference year two-digit years are relative to
55 QDate refDate; // the reference date all dates are relative to
56 // The precision used for decimal numbers, if the default cell style's
57 // precision is set to arbitrary.
58 int precision;
59 QString fileName;
60};
61
62/*****************************************************************************
63 *
64 * CalculationSettings
65 *
66 *****************************************************************************/
67
68CalculationSettings::CalculationSettings()
69 : d(new Private)
70{
71 d->locale = new Localization();
72 d->caseSensitiveComparisons = true;
73 d->precisionAsShown = false;
74 d->wholeCellSearchCriteria = true;
75 d->automaticFindLabels = true;
76 d->useRegularExpressions = true;
77 d->useWildcards = false;
78 d->automaticCalculation = true;
79 d->refYear = 1930;
80 d->refDate = QDate(1899, 12, 30);
81 d->precision = -1;
82}
83
84CalculationSettings::~CalculationSettings()
85{
86 delete d->locale;
87 delete d;
88}
89
90void CalculationSettings::loadOdf(const KoXmlElement& body)
91{
92 KoXmlNode settings = KoXml::namedItemNS(body, KoXmlNS::table, "calculation-settings");
93 kDebug() << "Calculation settings found?" << !settings.isNull();
94 if (!settings.isNull()) {
95 KoXmlElement element = settings.toElement();
96 if (element.hasAttributeNS(KoXmlNS::table, "case-sensitive")) {
97 d->caseSensitiveComparisons = true;
98 QString value = element.attributeNS(KoXmlNS::table, "case-sensitive", "true");
99 if (value == "false")
100 d->caseSensitiveComparisons = false;
101 } else if (element.hasAttributeNS(KoXmlNS::table, "precision-as-shown")) {
102 d->precisionAsShown = false;
103 QString value = element.attributeNS(KoXmlNS::table, "precision-as-shown", "false");
104 if (value == "true")
105 d->precisionAsShown = true;
106 } else if (element.hasAttributeNS(KoXmlNS::table, "search-criteria-must-apply-to-whole-cell")) {
107 d->wholeCellSearchCriteria = true;
108 QString value = element.attributeNS(KoXmlNS::table, "search-criteria-must-apply-to-whole-cell", "true");
109 if (value == "false")
110 d->wholeCellSearchCriteria = false;
111 } else if (element.hasAttributeNS(KoXmlNS::table, "automatic-find-labels")) {
112 d->automaticFindLabels = true;
113 QString value = element.attributeNS(KoXmlNS::table, "automatic-find-labels", "true");
114 if (value == "false")
115 d->automaticFindLabels = false;
116 } else if (element.hasAttributeNS(KoXmlNS::table, "use-regular-expressions")) {
117 d->useRegularExpressions = true;
118 QString value = element.attributeNS(KoXmlNS::table, "use-regular-expressions", "true");
119 if (value == "false")
120 d->useRegularExpressions = false;
121 } else if (element.hasAttributeNS(KoXmlNS::table, "use-wildcards")) {
122 d->useWildcards = false;
123 QString value = element.attributeNS(KoXmlNS::table, "use-wildcards", "false");
124 if (value == "true")
125 d->useWildcards = true;
126 } else if (element.hasAttributeNS(KoXmlNS::table, "null-year")) {
127 d->refYear = 1930;
128 QString value = element.attributeNS(KoXmlNS::table, "null-year", "1930");
129 if (!value.isEmpty() && value != "1930") {
130 bool ok;
131 int refYear = value.toInt(&ok);
132 if (ok)
133 d->refYear = refYear;
134 }
135 }
136
137 forEachElement(element, settings) {
138 if (element.namespaceURI() != KoXmlNS::table)
139 continue;
140 else if (element.tagName() == "null-date") {
141 d->refDate = QDate(1899, 12, 30);
142 QString valueType = element.attributeNS(KoXmlNS::table, "value-type", "date");
143 if (valueType == "date") {
144 QString value = element.attributeNS(KoXmlNS::table, "date-value", "1899-12-30");
145 QDate date = QDate::fromString(value, Qt::ISODate);
146 if (date.isValid())
147 d->refDate = date;
148 } else {
149 kDebug() << "CalculationSettings: Error on loading null date."
150 << "Value type """ << valueType << """ not handled"
151 << ", falling back to default." << endl;
152 // NOTE Stefan: I don't know why different types are possible here!
153 // sebsauer: because according to ODF-specs a zero null date can
154 // mean QDate::currentDate(). Still unclear what a numeric value !=0
155 // means through :-/
156 }
157 } else if (element.tagName() == "iteration") {
158 // TODO
159 }
160 }
161 }
162}
163
164bool CalculationSettings::saveOdf(KoXmlWriter &xmlWriter) const
165{
166 xmlWriter.startElement("table:calculation-settings");
167 if (!d->caseSensitiveComparisons)
168 xmlWriter.addAttribute("table:case-sensitive", "false");
169 if (d->precisionAsShown)
170 xmlWriter.addAttribute("table:precision-as-shown", "true");
171 if (!d->wholeCellSearchCriteria)
172 xmlWriter.addAttribute("table:search-criteria-must-apply-to-whole-cell", "false");
173 if (!d->automaticFindLabels)
174 xmlWriter.addAttribute("table:automatic-find-labels", "false");
175 if (!d->useRegularExpressions)
176 xmlWriter.addAttribute("table:use-regular-expressions", "false");
177 if (d->useWildcards)
178 xmlWriter.addAttribute("table:use-wildcards", "true");
179 if (d->refYear != 1930)
180 xmlWriter.addAttribute("table:null-year", QString::number(d->refYear));
181 xmlWriter.endElement();
182 return true;
183}
184
185KLocale* CalculationSettings::locale() const
186{
187 return d->locale;
188}
189
190void CalculationSettings::setReferenceYear(int year)
191{
192 d->refYear = year;
193}
194
195int CalculationSettings::referenceYear() const
196{
197 return d->refYear;
198}
199
200void CalculationSettings::setReferenceDate(const QDate& date)
201{
202 if (!date.isValid()) return;
203 d->refDate.setDate(date.year(), date.month(), date.day());
204}
205
206QDate CalculationSettings::referenceDate() const
207{
208 return d->refDate;
209}
210
211void CalculationSettings::setPrecisionAsShown(bool enable)
212{
213 d->precisionAsShown = enable;
214}
215
216bool CalculationSettings::precisionAsShown() const
217{
218 return d->precisionAsShown;
219}
220
221void CalculationSettings::setDefaultDecimalPrecision(int precision)
222{
223 d->precision = precision;
224}
225
226int CalculationSettings::defaultDecimalPrecision() const
227{
228 return d->precision;
229}
230
231void CalculationSettings::setFileName(const QString& fileName)
232{
233 d->fileName = fileName;
234}
235
236const QString& CalculationSettings::fileName() const
237{
238 return d->fileName;
239}
240
241void CalculationSettings::setAutoCalculationEnabled(bool enable)
242{
243 d->automaticCalculation = enable;
244}
245
246bool CalculationSettings::isAutoCalculationEnabled() const
247{
248 return d->automaticCalculation;
249}
250
251void CalculationSettings::setAutomaticFindLabels(bool enabled)
252{
253 d->automaticFindLabels = enabled;
254}
255
256bool CalculationSettings::automaticFindLabels() const
257{
258 return d->automaticFindLabels;
259}
260
261void CalculationSettings::setCaseSensitiveComparisons(Qt::CaseSensitivity caseSensitive)
262{
263 d->caseSensitiveComparisons = caseSensitive == Qt::CaseSensitive;
264}
265
266Qt::CaseSensitivity CalculationSettings::caseSensitiveComparisons() const
267{
268 return d->caseSensitiveComparisons ? Qt::CaseSensitive : Qt::CaseInsensitive;
269}
270
271void CalculationSettings::setWholeCellSearchCriteria(bool enabled)
272{
273 d->wholeCellSearchCriteria = enabled;
274}
275
276bool CalculationSettings::wholeCellSearchCriteria() const
277{
278 return d->wholeCellSearchCriteria;
279}
280
281void CalculationSettings::setUseRegularExpressions(bool enabled)
282{
283 d->useRegularExpressions = enabled;
284}
285
286bool CalculationSettings::useRegularExpressions() const
287{
288 return d->useRegularExpressions;
289}
290
291void CalculationSettings::setUseWildcards(bool enabled)
292{
293 d->useWildcards = enabled;
294}
295
296bool CalculationSettings::useWildcards() const
297{
298 return d->useWildcards;
299}
300