Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
5 : * This Source Code Form is subject to the terms of the Mozilla Public
6 : * License, v. 2.0. If a copy of the MPL was not distributed with this
7 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
11 : * Licensed to the Apache Software Foundation (ASF) under one or more
12 : * contributor license agreements. See the NOTICE file distributed
13 : * with this work for additional information regarding copyright
14 : * ownership. The ASF licenses this file to you under the Apache
15 : * License, Version 2.0 (the "License"); you may not use this file
16 : * except in compliance with the License. You may obtain a copy of
17 : * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 : */
19 :
20 : #include "XMLExportIterator.hxx"
21 : #include <com/sun/star/text/XSimpleText.hpp>
22 : #include <com/sun/star/sheet/XCellAddressable.hpp>
23 : #include <com/sun/star/sheet/CellFlags.hpp>
24 : #include <com/sun/star/sheet/XSheetAnnotationsSupplier.hpp>
25 : #include <com/sun/star/container/XEnumerationAccess.hpp>
26 : #include <xmloff/xmlnmspe.hxx>
27 : #include "dociter.hxx"
28 : #include "convuno.hxx"
29 : #include "xmlexprt.hxx"
30 : #include "XMLExportSharedData.hxx"
31 : #include "XMLStylesExportHelper.hxx"
32 : #include "document.hxx"
33 :
34 : #include <algorithm>
35 :
36 : using namespace ::com::sun::star;
37 :
38 95 : ScMyIteratorBase::ScMyIteratorBase()
39 : {
40 95 : }
41 :
42 95 : ScMyIteratorBase::~ScMyIteratorBase()
43 : {
44 95 : }
45 :
46 1682 : void ScMyIteratorBase::UpdateAddress( table::CellAddress& rCellAddress )
47 : {
48 1682 : table::CellAddress aNewAddr( rCellAddress );
49 1682 : if( GetFirstAddress( aNewAddr ) )
50 : {
51 8 : if( (aNewAddr.Sheet == rCellAddress.Sheet) &&
52 4 : ((aNewAddr.Row < rCellAddress.Row) ||
53 0 : ((aNewAddr.Row == rCellAddress.Row) && (aNewAddr.Column < rCellAddress.Column))) )
54 4 : rCellAddress = aNewAddr;
55 : }
56 1682 : }
57 :
58 :
59 0 : bool ScMyShape::operator<(const ScMyShape& aShape) const
60 : {
61 0 : if( aAddress.Tab() != aShape.aAddress.Tab() )
62 0 : return (aAddress.Tab() < aShape.aAddress.Tab());
63 0 : else if( aAddress.Row() != aShape.aAddress.Row() )
64 0 : return (aAddress.Row() < aShape.aAddress.Row());
65 : else
66 0 : return (aAddress.Col() < aShape.aAddress.Col());
67 : }
68 :
69 2 : ScMyShapesContainer::ScMyShapesContainer()
70 2 : : aShapeList()
71 : {
72 2 : }
73 :
74 4 : ScMyShapesContainer::~ScMyShapesContainer()
75 : {
76 4 : }
77 :
78 2 : void ScMyShapesContainer::AddNewShape( const ScMyShape& aShape )
79 : {
80 2 : aShapeList.push_back(aShape);
81 2 : }
82 :
83 4 : bool ScMyShapesContainer::GetFirstAddress( table::CellAddress& rCellAddress )
84 : {
85 4 : sal_Int32 nTable(rCellAddress.Sheet);
86 4 : if( !aShapeList.empty() )
87 : {
88 2 : ScUnoConversion::FillApiAddress( rCellAddress, aShapeList.begin()->aAddress );
89 2 : return (nTable == rCellAddress.Sheet);
90 : }
91 2 : return false;
92 : }
93 :
94 2 : void ScMyShapesContainer::SetCellData( ScMyCell& rMyCell )
95 : {
96 2 : rMyCell.aShapeList.clear();
97 2 : ScAddress aAddress;
98 2 : ScUnoConversion::FillScAddress( aAddress, rMyCell.aCellAddress );
99 :
100 2 : ScMyShapeList::iterator aItr(aShapeList.begin());
101 2 : ScMyShapeList::iterator aEndItr(aShapeList.end());
102 6 : while( (aItr != aEndItr) && (aItr->aAddress == aAddress) )
103 : {
104 2 : rMyCell.aShapeList.push_back(*aItr);
105 2 : aItr = aShapeList.erase(aItr);
106 : }
107 2 : rMyCell.bHasShape = !rMyCell.aShapeList.empty();
108 2 : }
109 :
110 0 : void ScMyShapesContainer::SkipTable(SCTAB nSkip)
111 : {
112 0 : ScMyShapeList::iterator aItr = aShapeList.begin();
113 0 : while( (aItr != aShapeList.end()) && (aItr->aAddress.Tab() == nSkip) )
114 0 : aItr = aShapeList.erase(aItr);
115 0 : }
116 :
117 2 : void ScMyShapesContainer::Sort()
118 : {
119 2 : aShapeList.sort();
120 2 : }
121 :
122 2 : bool ScMyNoteShape::operator<(const ScMyNoteShape& aNote) const
123 : {
124 2 : if( aPos.Tab() != aNote.aPos.Tab() )
125 0 : return (aPos.Tab() < aNote.aPos.Tab());
126 2 : else if( aPos.Row() != aNote.aPos.Row() )
127 2 : return (aPos.Row() < aNote.aPos.Row());
128 : else
129 0 : return (aPos.Col() < aNote.aPos.Col());
130 : }
131 :
132 1 : ScMyNoteShapesContainer::ScMyNoteShapesContainer()
133 1 : : aNoteShapeList()
134 : {
135 1 : }
136 :
137 2 : ScMyNoteShapesContainer::~ScMyNoteShapesContainer()
138 : {
139 2 : }
140 :
141 2 : void ScMyNoteShapesContainer::AddNewNote( const ScMyNoteShape& aNote )
142 : {
143 2 : aNoteShapeList.push_back(aNote);
144 2 : }
145 :
146 3 : bool ScMyNoteShapesContainer::GetFirstAddress( table::CellAddress& rCellAddress )
147 : {
148 3 : sal_Int16 nTable = rCellAddress.Sheet;
149 3 : if( !aNoteShapeList.empty() )
150 : {
151 2 : ScUnoConversion::FillApiAddress( rCellAddress, aNoteShapeList.begin()->aPos );
152 2 : return (nTable == rCellAddress.Sheet);
153 : }
154 1 : return false;
155 : }
156 :
157 2 : void ScMyNoteShapesContainer::SetCellData( ScMyCell& rMyCell )
158 : {
159 2 : ScAddress aAddress;
160 2 : ScUnoConversion::FillScAddress( aAddress, rMyCell.aCellAddress );
161 :
162 2 : ScMyNoteShapeList::iterator aItr = aNoteShapeList.begin();
163 6 : while( (aItr != aNoteShapeList.end()) && (aItr->aPos == aAddress) )
164 : {
165 2 : aItr = aNoteShapeList.erase(aItr);
166 : }
167 2 : }
168 :
169 0 : void ScMyNoteShapesContainer::SkipTable(SCTAB nSkip)
170 : {
171 0 : ScMyNoteShapeList::iterator aItr = aNoteShapeList.begin();
172 0 : while( (aItr != aNoteShapeList.end()) && (aItr->aPos.Tab() == nSkip) )
173 0 : aItr = aNoteShapeList.erase(aItr);
174 0 : }
175 :
176 2 : void ScMyNoteShapesContainer::Sort()
177 : {
178 2 : aNoteShapeList.sort();
179 2 : }
180 :
181 0 : bool ScMyMergedRange::operator<(const ScMyMergedRange& aRange) const
182 : {
183 0 : if( aCellRange.Sheet != aRange.aCellRange.Sheet )
184 0 : return (aCellRange.Sheet < aRange.aCellRange.Sheet);
185 0 : else if( aCellRange.StartRow != aRange.aCellRange.StartRow )
186 0 : return (aCellRange.StartRow < aRange.aCellRange.StartRow);
187 : else
188 0 : return (aCellRange.StartColumn < aRange.aCellRange.StartColumn);
189 : }
190 :
191 :
192 20 : ScMyMergedRangesContainer::ScMyMergedRangesContainer()
193 20 : : aRangeList()
194 : {
195 20 : }
196 :
197 40 : ScMyMergedRangesContainer::~ScMyMergedRangesContainer()
198 : {
199 40 : }
200 :
201 0 : void ScMyMergedRangesContainer::AddRange(const table::CellRangeAddress aMergedRange)
202 : {
203 0 : sal_Int32 nStartRow(aMergedRange.StartRow);
204 0 : sal_Int32 nEndRow(aMergedRange.EndRow);
205 :
206 0 : ScMyMergedRange aRange;
207 0 : aRange.bIsFirst = true;
208 0 : aRange.aCellRange = aMergedRange;
209 0 : aRange.aCellRange.EndRow = nStartRow;
210 0 : aRange.nRows = nEndRow - nStartRow + 1;
211 0 : aRangeList.push_back( aRange );
212 :
213 0 : aRange.bIsFirst = false;
214 0 : aRange.nRows = 0;
215 0 : for( sal_Int32 nRow = nStartRow + 1; nRow <= nEndRow; ++nRow )
216 : {
217 0 : aRange.aCellRange.StartRow = aRange.aCellRange.EndRow = nRow;
218 0 : aRangeList.push_back(aRange);
219 : }
220 0 : }
221 :
222 335 : bool ScMyMergedRangesContainer::GetFirstAddress( table::CellAddress& rCellAddress )
223 : {
224 335 : sal_Int32 nTable(rCellAddress.Sheet);
225 335 : if( !aRangeList.empty() )
226 : {
227 0 : ScUnoConversion::FillApiStartAddress( rCellAddress, aRangeList.begin()->aCellRange );
228 0 : return (nTable == rCellAddress.Sheet);
229 : }
230 335 : return false;
231 : }
232 :
233 313 : void ScMyMergedRangesContainer::SetCellData( ScMyCell& rMyCell )
234 : {
235 313 : rMyCell.bIsMergedBase = rMyCell.bIsCovered = false;
236 313 : ScMyMergedRangeList::iterator aItr(aRangeList.begin());
237 313 : if( aItr != aRangeList.end() )
238 : {
239 0 : table::CellAddress aFirstAddress;
240 0 : ScUnoConversion::FillApiStartAddress( aFirstAddress, aItr->aCellRange );
241 0 : if( aFirstAddress == rMyCell.aCellAddress )
242 : {
243 0 : rMyCell.aMergeRange = aItr->aCellRange;
244 0 : if (aItr->bIsFirst)
245 0 : rMyCell.aMergeRange.EndRow = rMyCell.aMergeRange.StartRow + aItr->nRows - 1;
246 0 : rMyCell.bIsMergedBase = aItr->bIsFirst;
247 0 : rMyCell.bIsCovered = !aItr->bIsFirst;
248 0 : if( aItr->aCellRange.StartColumn < aItr->aCellRange.EndColumn )
249 : {
250 0 : ++(aItr->aCellRange.StartColumn);
251 0 : aItr->bIsFirst = false;
252 : }
253 : else
254 0 : aRangeList.erase(aItr);
255 : }
256 : }
257 313 : }
258 :
259 0 : void ScMyMergedRangesContainer::SkipTable(SCTAB nSkip)
260 : {
261 0 : ScMyMergedRangeList::iterator aItr = aRangeList.begin();
262 0 : while( (aItr != aRangeList.end()) && (aItr->aCellRange.Sheet == nSkip) )
263 0 : aItr = aRangeList.erase(aItr);
264 0 : }
265 :
266 18 : void ScMyMergedRangesContainer::Sort()
267 : {
268 18 : aRangeList.sort();
269 18 : }
270 :
271 0 : bool ScMyAreaLink::Compare( const ScMyAreaLink& rAreaLink ) const
272 : {
273 0 : return (GetRowCount() == rAreaLink.GetRowCount()) &&
274 0 : (sFilter == rAreaLink.sFilter) &&
275 0 : (sFilterOptions == rAreaLink.sFilterOptions) &&
276 0 : (sURL == rAreaLink.sURL) &&
277 0 : (sSourceStr == rAreaLink.sSourceStr);
278 : }
279 :
280 0 : bool ScMyAreaLink::operator<(const ScMyAreaLink& rAreaLink ) const
281 : {
282 0 : if( aDestRange.Sheet != rAreaLink.aDestRange.Sheet )
283 0 : return (aDestRange.Sheet < rAreaLink.aDestRange.Sheet);
284 0 : else if( aDestRange.StartRow != rAreaLink.aDestRange.StartRow )
285 0 : return (aDestRange.StartRow < rAreaLink.aDestRange.StartRow);
286 : else
287 0 : return (aDestRange.StartColumn < rAreaLink.aDestRange.StartColumn);
288 : }
289 :
290 18 : ScMyAreaLinksContainer::ScMyAreaLinksContainer() :
291 18 : aAreaLinkList()
292 : {
293 18 : }
294 :
295 18 : ScMyAreaLinksContainer::~ScMyAreaLinksContainer()
296 : {
297 18 : }
298 :
299 335 : bool ScMyAreaLinksContainer::GetFirstAddress( table::CellAddress& rCellAddress )
300 : {
301 335 : sal_Int32 nTable(rCellAddress.Sheet);
302 335 : if( !aAreaLinkList.empty() )
303 : {
304 0 : ScUnoConversion::FillApiStartAddress( rCellAddress, aAreaLinkList.begin()->aDestRange );
305 0 : return (nTable == rCellAddress.Sheet);
306 : }
307 335 : return false;
308 : }
309 :
310 313 : void ScMyAreaLinksContainer::SetCellData( ScMyCell& rMyCell )
311 : {
312 313 : rMyCell.bHasAreaLink = false;
313 313 : ScMyAreaLinkList::iterator aItr(aAreaLinkList.begin());
314 313 : if( aItr != aAreaLinkList.end() )
315 : {
316 0 : table::CellAddress aAddress;
317 0 : ScUnoConversion::FillApiStartAddress( aAddress, aItr->aDestRange );
318 0 : if( aAddress == rMyCell.aCellAddress )
319 : {
320 0 : rMyCell.bHasAreaLink = true;
321 0 : rMyCell.aAreaLink = *aItr;
322 0 : aItr = aAreaLinkList.erase( aItr );
323 0 : bool bFound = true;
324 0 : while (aItr != aAreaLinkList.end() && bFound)
325 : {
326 0 : ScUnoConversion::FillApiStartAddress( aAddress, aItr->aDestRange );
327 0 : if (aAddress == rMyCell.aCellAddress)
328 : {
329 : OSL_FAIL("more than one linked range on one cell");
330 0 : aItr = aAreaLinkList.erase( aItr );
331 : }
332 : else
333 0 : bFound = false;
334 : }
335 : }
336 : }
337 313 : }
338 :
339 0 : void ScMyAreaLinksContainer::SkipTable(SCTAB nSkip)
340 : {
341 0 : ScMyAreaLinkList::iterator aItr = aAreaLinkList.begin();
342 0 : while( (aItr != aAreaLinkList.end()) && (aItr->aDestRange.Sheet == nSkip) )
343 0 : aItr = aAreaLinkList.erase(aItr);
344 0 : }
345 :
346 18 : void ScMyAreaLinksContainer::Sort()
347 : {
348 18 : aAreaLinkList.sort();
349 18 : }
350 :
351 0 : ScMyCellRangeAddress::ScMyCellRangeAddress(const table::CellRangeAddress& rRange)
352 0 : : table::CellRangeAddress(rRange)
353 : {
354 0 : }
355 :
356 0 : bool ScMyCellRangeAddress::operator<(const ScMyCellRangeAddress& rRange ) const
357 : {
358 0 : if( Sheet != rRange.Sheet )
359 0 : return (Sheet < rRange.Sheet);
360 0 : else if( StartRow != rRange.StartRow )
361 0 : return (StartRow < rRange.StartRow);
362 : else
363 0 : return (StartColumn < rRange.StartColumn);
364 : }
365 :
366 18 : ScMyEmptyDatabaseRangesContainer::ScMyEmptyDatabaseRangesContainer()
367 18 : : aDatabaseList()
368 : {
369 18 : }
370 :
371 18 : ScMyEmptyDatabaseRangesContainer::~ScMyEmptyDatabaseRangesContainer()
372 : {
373 18 : }
374 :
375 0 : void ScMyEmptyDatabaseRangesContainer::AddNewEmptyDatabaseRange(const table::CellRangeAddress& aCellRange)
376 : {
377 0 : sal_Int32 nStartRow(aCellRange.StartRow);
378 0 : sal_Int32 nEndRow(aCellRange.EndRow);
379 0 : ScMyCellRangeAddress aRange( aCellRange );
380 0 : for( sal_Int32 nRow = nStartRow; nRow <= nEndRow; ++nRow )
381 : {
382 0 : aRange.StartRow = aRange.EndRow = nRow;
383 0 : aDatabaseList.push_back( aRange );
384 : }
385 0 : }
386 :
387 335 : bool ScMyEmptyDatabaseRangesContainer::GetFirstAddress( table::CellAddress& rCellAddress )
388 : {
389 335 : sal_Int32 nTable(rCellAddress.Sheet);
390 335 : if( !aDatabaseList.empty() )
391 : {
392 0 : ScUnoConversion::FillApiStartAddress( rCellAddress, *(aDatabaseList.begin()) );
393 0 : return (nTable == rCellAddress.Sheet);
394 : }
395 335 : return false;
396 : }
397 :
398 313 : void ScMyEmptyDatabaseRangesContainer::SetCellData( ScMyCell& rMyCell )
399 : {
400 313 : rMyCell.bHasEmptyDatabase = false;
401 313 : ScMyEmptyDatabaseRangeList::iterator aItr(aDatabaseList.begin());
402 313 : if( aItr != aDatabaseList.end() )
403 : {
404 0 : table::CellAddress aFirstAddress;
405 0 : ScUnoConversion::FillApiStartAddress( aFirstAddress, *aItr );
406 0 : if( aFirstAddress == rMyCell.aCellAddress )
407 : {
408 0 : rMyCell.bHasEmptyDatabase = true;
409 0 : if( aItr->StartColumn < aItr->EndColumn )
410 0 : ++(aItr->StartColumn);
411 : else
412 0 : aDatabaseList.erase(aItr);
413 : }
414 : }
415 313 : }
416 :
417 0 : void ScMyEmptyDatabaseRangesContainer::SkipTable(SCTAB nSkip)
418 : {
419 0 : ScMyEmptyDatabaseRangeList::iterator aItr = aDatabaseList.begin();
420 0 : while( (aItr != aDatabaseList.end()) && (aItr->Sheet == nSkip) )
421 0 : aItr = aDatabaseList.erase(aItr);
422 0 : }
423 :
424 0 : void ScMyEmptyDatabaseRangesContainer::Sort()
425 : {
426 0 : aDatabaseList.sort();
427 0 : }
428 :
429 0 : bool ScMyDetectiveObj::operator<( const ScMyDetectiveObj& rDetObj) const
430 : {
431 0 : if( aPosition.Sheet != rDetObj.aPosition.Sheet )
432 0 : return (aPosition.Sheet < rDetObj.aPosition.Sheet);
433 0 : else if( aPosition.Row != rDetObj.aPosition.Row )
434 0 : return (aPosition.Row < rDetObj.aPosition.Row);
435 : else
436 0 : return (aPosition.Column < rDetObj.aPosition.Column);
437 : }
438 :
439 18 : ScMyDetectiveObjContainer::ScMyDetectiveObjContainer() :
440 18 : aDetectiveObjList()
441 : {
442 18 : }
443 :
444 36 : ScMyDetectiveObjContainer::~ScMyDetectiveObjContainer()
445 : {
446 36 : }
447 :
448 0 : void ScMyDetectiveObjContainer::AddObject( ScDetectiveObjType eObjType, const SCTAB nSheet,
449 : const ScAddress& rPosition, const ScRange& rSourceRange,
450 : bool bHasError )
451 : {
452 0 : if( (eObjType == SC_DETOBJ_ARROW) ||
453 0 : (eObjType == SC_DETOBJ_FROMOTHERTAB) ||
454 0 : (eObjType == SC_DETOBJ_TOOTHERTAB) ||
455 : (eObjType == SC_DETOBJ_CIRCLE) )
456 : {
457 0 : ScMyDetectiveObj aDetObj;
458 0 : aDetObj.eObjType = eObjType;
459 0 : if( eObjType == SC_DETOBJ_TOOTHERTAB )
460 0 : ScUnoConversion::FillApiAddress( aDetObj.aPosition, rSourceRange.aStart );
461 : else
462 0 : ScUnoConversion::FillApiAddress( aDetObj.aPosition, rPosition );
463 0 : ScUnoConversion::FillApiRange( aDetObj.aSourceRange, rSourceRange );
464 :
465 : // #111064#; take the sheet where the object is found and not the sheet given in the ranges, because they are not always true
466 0 : if (eObjType != SC_DETOBJ_FROMOTHERTAB)
467 : {
468 : // if the ObjType == SC_DETOBJ_FROMOTHERTAB then the SourceRange is not used and so it has not to be tested and changed
469 : OSL_ENSURE(aDetObj.aPosition.Sheet == aDetObj.aSourceRange.Sheet, "It seems to be possible to have different sheets");
470 0 : aDetObj.aSourceRange.Sheet = nSheet;
471 : }
472 0 : aDetObj.aPosition.Sheet = nSheet;
473 :
474 0 : aDetObj.bHasError = bHasError;
475 0 : aDetectiveObjList.push_back( aDetObj );
476 : }
477 0 : }
478 :
479 335 : bool ScMyDetectiveObjContainer::GetFirstAddress( table::CellAddress& rCellAddress )
480 : {
481 335 : sal_Int32 nTable(rCellAddress.Sheet);
482 335 : if( !aDetectiveObjList.empty() )
483 : {
484 0 : rCellAddress = aDetectiveObjList.begin()->aPosition;
485 0 : return (nTable == rCellAddress.Sheet);
486 : }
487 335 : return false;
488 : }
489 :
490 313 : void ScMyDetectiveObjContainer::SetCellData( ScMyCell& rMyCell )
491 : {
492 313 : rMyCell.aDetectiveObjVec.clear();
493 313 : ScMyDetectiveObjList::iterator aItr(aDetectiveObjList.begin());
494 313 : ScMyDetectiveObjList::iterator aEndItr(aDetectiveObjList.end());
495 626 : while( (aItr != aEndItr) && (aItr->aPosition == rMyCell.aCellAddress) )
496 : {
497 0 : rMyCell.aDetectiveObjVec.push_back( *aItr );
498 0 : aItr = aDetectiveObjList.erase( aItr );
499 : }
500 313 : rMyCell.bHasDetectiveObj = (rMyCell.aDetectiveObjVec.size() != 0);
501 313 : }
502 :
503 0 : void ScMyDetectiveObjContainer::SkipTable(SCTAB nSkip)
504 : {
505 0 : ScMyDetectiveObjList::iterator aItr = aDetectiveObjList.begin();
506 0 : while( (aItr != aDetectiveObjList.end()) && (aItr->aPosition.Sheet == nSkip) )
507 0 : aItr = aDetectiveObjList.erase(aItr);
508 0 : }
509 :
510 18 : void ScMyDetectiveObjContainer::Sort()
511 : {
512 18 : aDetectiveObjList.sort();
513 18 : }
514 :
515 0 : bool ScMyDetectiveOp::operator<( const ScMyDetectiveOp& rDetOp) const
516 : {
517 0 : if( aPosition.Sheet != rDetOp.aPosition.Sheet )
518 0 : return (aPosition.Sheet < rDetOp.aPosition.Sheet);
519 0 : else if( aPosition.Row != rDetOp.aPosition.Row )
520 0 : return (aPosition.Row < rDetOp.aPosition.Row);
521 : else
522 0 : return (aPosition.Column < rDetOp.aPosition.Column);
523 : }
524 :
525 18 : ScMyDetectiveOpContainer::ScMyDetectiveOpContainer() :
526 18 : aDetectiveOpList()
527 : {
528 18 : }
529 :
530 18 : ScMyDetectiveOpContainer::~ScMyDetectiveOpContainer()
531 : {
532 18 : }
533 :
534 0 : void ScMyDetectiveOpContainer::AddOperation( ScDetOpType eOpType, const ScAddress& rPosition, sal_uInt32 nIndex )
535 : {
536 0 : ScMyDetectiveOp aDetOp;
537 0 : aDetOp.eOpType = eOpType;
538 0 : ScUnoConversion::FillApiAddress( aDetOp.aPosition, rPosition );
539 0 : aDetOp.nIndex = nIndex;
540 0 : aDetectiveOpList.push_back( aDetOp );
541 0 : }
542 :
543 335 : bool ScMyDetectiveOpContainer::GetFirstAddress( table::CellAddress& rCellAddress )
544 : {
545 335 : sal_Int32 nTable(rCellAddress.Sheet);
546 335 : if( !aDetectiveOpList.empty() )
547 : {
548 0 : rCellAddress = aDetectiveOpList.begin()->aPosition;
549 0 : return (nTable == rCellAddress.Sheet);
550 : }
551 335 : return false;
552 : }
553 :
554 313 : void ScMyDetectiveOpContainer::SetCellData( ScMyCell& rMyCell )
555 : {
556 313 : rMyCell.aDetectiveOpVec.clear();
557 313 : ScMyDetectiveOpList::iterator aItr(aDetectiveOpList.begin());
558 313 : ScMyDetectiveOpList::iterator aEndItr(aDetectiveOpList.end());
559 626 : while( (aItr != aEndItr) && (aItr->aPosition == rMyCell.aCellAddress) )
560 : {
561 0 : rMyCell.aDetectiveOpVec.push_back( *aItr );
562 0 : aItr = aDetectiveOpList.erase( aItr );
563 : }
564 313 : rMyCell.bHasDetectiveOp = (rMyCell.aDetectiveOpVec.size() != 0);
565 313 : }
566 :
567 0 : void ScMyDetectiveOpContainer::SkipTable(SCTAB nSkip)
568 : {
569 0 : ScMyDetectiveOpList::iterator aItr = aDetectiveOpList.begin();
570 0 : while( (aItr != aDetectiveOpList.end()) && (aItr->aPosition.Sheet == nSkip) )
571 0 : aItr = aDetectiveOpList.erase(aItr);
572 0 : }
573 :
574 0 : void ScMyDetectiveOpContainer::Sort()
575 : {
576 0 : aDetectiveOpList.sort();
577 0 : }
578 :
579 44 : ScMyCell::ScMyCell() :
580 : aShapeList(),
581 : aDetectiveObjVec(),
582 : pNote(NULL),
583 : nValidationIndex(-1),
584 : nStyleIndex(-1),
585 : nNumberFormat(-1),
586 : bIsAutoStyle( false ),
587 : bHasShape( false ),
588 : bIsMergedBase( false ),
589 : bIsCovered( false ),
590 : bHasAreaLink( false ),
591 : bHasEmptyDatabase( false ),
592 : bHasDetectiveObj( false ),
593 : bHasDetectiveOp( false ),
594 : bIsMatrixBase( false ),
595 : bIsMatrixCovered( false ),
596 44 : bHasAnnotation( false )
597 : {
598 44 : }
599 :
600 44 : ScMyCell::~ScMyCell()
601 : {
602 44 : }
603 :
604 20 : ScMyNotEmptyCellsIterator::ScMyNotEmptyCellsIterator(ScXMLExport& rTempXMLExport)
605 : : pShapes(NULL),
606 : pNoteShapes(NULL),
607 : pEmptyDatabaseRanges(NULL),
608 : pMergedRanges(NULL),
609 : pAreaLinks(NULL),
610 : pDetectiveObj(NULL),
611 : pDetectiveOp(NULL),
612 : rExport(rTempXMLExport),
613 20 : nCurrentTable(SCTAB_MAX)
614 : {
615 20 : }
616 :
617 40 : ScMyNotEmptyCellsIterator::~ScMyNotEmptyCellsIterator()
618 : {
619 20 : Clear();
620 20 : }
621 :
622 38 : void ScMyNotEmptyCellsIterator::Clear()
623 : {
624 38 : mpCellItr.reset();
625 38 : pShapes = NULL;
626 38 : pNoteShapes = NULL;
627 38 : pMergedRanges = NULL;
628 38 : pAreaLinks = NULL;
629 38 : pEmptyDatabaseRanges = NULL;
630 38 : pDetectiveObj = NULL;
631 38 : pDetectiveOp = NULL;
632 38 : nCurrentTable = SCTAB_MAX;
633 38 : }
634 :
635 335 : void ScMyNotEmptyCellsIterator::UpdateAddress( table::CellAddress& rAddress )
636 : {
637 335 : if (mpCellItr->GetPos(nCellCol, nCellRow))
638 : {
639 309 : rAddress.Column = nCellCol;
640 309 : rAddress.Row = nCellRow;
641 : }
642 335 : }
643 :
644 313 : void ScMyNotEmptyCellsIterator::SetCellData( ScMyCell& rMyCell, table::CellAddress& rAddress )
645 : {
646 313 : rMyCell.maBaseCell.clear();
647 313 : rMyCell.aCellAddress = rAddress;
648 :
649 313 : if( (nCellCol == rAddress.Column) && (nCellRow == rAddress.Row) )
650 : {
651 310 : const ScRefCellValue* pCell = mpCellItr->GetNext(nCellCol, nCellRow);
652 310 : if (pCell)
653 309 : rMyCell.maBaseCell = *pCell;
654 : }
655 :
656 313 : rMyCell.bIsMatrixCovered = false;
657 313 : rMyCell.bIsMatrixBase = false;
658 :
659 313 : bool bIsMatrixBase = false;
660 :
661 313 : ScAddress aScAddress;
662 313 : ScUnoConversion::FillScAddress( aScAddress, rMyCell.aCellAddress );
663 313 : switch (rMyCell.maBaseCell.meType)
664 : {
665 : case CELLTYPE_VALUE:
666 261 : rMyCell.nType = table::CellContentType_VALUE;
667 261 : break;
668 : case CELLTYPE_STRING:
669 : case CELLTYPE_EDIT:
670 44 : rMyCell.nType = table::CellContentType_TEXT;
671 44 : break;
672 : case CELLTYPE_FORMULA:
673 4 : rMyCell.nType = table::CellContentType_FORMULA;
674 4 : break;
675 : default:
676 4 : rMyCell.nType = table::CellContentType_EMPTY;
677 : }
678 :
679 313 : if (rMyCell.maBaseCell.meType == CELLTYPE_FORMULA)
680 4 : if( rExport.IsMatrix( aScAddress, rMyCell.aMatrixRange, bIsMatrixBase ) )
681 : {
682 0 : rMyCell.bIsMatrixBase = bIsMatrixBase;
683 0 : rMyCell.bIsMatrixCovered = !bIsMatrixBase;
684 : }
685 313 : }
686 :
687 313 : void ScMyNotEmptyCellsIterator::HasAnnotation(ScMyCell& aCell)
688 : {
689 313 : aCell.bHasAnnotation = false;
690 313 : ScAddress aAddress;
691 313 : ScUnoConversion::FillScAddress( aAddress, aCell.aCellAddress );
692 :
693 313 : ScPostIt* pNote = rExport.GetDocument()->GetNote(aAddress);
694 :
695 313 : if(pNote)
696 : {
697 2 : aCell.bHasAnnotation = true;
698 2 : aCell.pNote = pNote;
699 : }
700 313 : }
701 :
702 :
703 22 : void ScMyNotEmptyCellsIterator::SetCurrentTable(const SCTAB nTable,
704 : uno::Reference<sheet::XSpreadsheet>& rxTable)
705 : {
706 22 : aLastAddress.Row = 0;
707 22 : aLastAddress.Column = 0;
708 22 : aLastAddress.Sheet = nTable;
709 22 : if (nCurrentTable != nTable)
710 : {
711 22 : nCurrentTable = nTable;
712 :
713 : mpCellItr.reset(
714 : new ScHorizontalCellIterator(
715 22 : rExport.GetDocument(), nCurrentTable, 0, 0,
716 22 : static_cast<SCCOL>(rExport.GetSharedData()->GetLastColumn(nCurrentTable)),
717 44 : static_cast<SCROW>(rExport.GetSharedData()->GetLastRow(nCurrentTable))));
718 :
719 22 : xTable.set(rxTable);
720 22 : xCellRange.set(xTable, uno::UNO_QUERY);
721 : }
722 22 : }
723 :
724 0 : void ScMyNotEmptyCellsIterator::SkipTable(SCTAB nSkip)
725 : {
726 : // Skip entries for a sheet that is copied instead of saving normally.
727 : // Cells are handled separately in SetCurrentTable.
728 :
729 0 : if( pShapes )
730 0 : pShapes->SkipTable(nSkip);
731 0 : if( pNoteShapes )
732 0 : pNoteShapes->SkipTable(nSkip);
733 0 : if( pEmptyDatabaseRanges )
734 0 : pEmptyDatabaseRanges->SkipTable(nSkip);
735 0 : if( pMergedRanges )
736 0 : pMergedRanges->SkipTable(nSkip);
737 0 : if( pAreaLinks )
738 0 : pAreaLinks->SkipTable(nSkip);
739 0 : if( pDetectiveObj )
740 0 : pDetectiveObj->SkipTable(nSkip);
741 0 : if( pDetectiveOp )
742 0 : pDetectiveOp->SkipTable(nSkip);
743 0 : }
744 :
745 335 : bool ScMyNotEmptyCellsIterator::GetNext(ScMyCell& aCell, ScFormatRangeStyles* pCellStyles)
746 : {
747 335 : table::CellAddress aAddress( nCurrentTable, MAXCOL + 1, MAXROW + 1 );
748 :
749 335 : UpdateAddress( aAddress );
750 :
751 335 : if( pShapes )
752 4 : pShapes->UpdateAddress( aAddress );
753 335 : if( pNoteShapes )
754 3 : pNoteShapes->UpdateAddress( aAddress );
755 335 : if( pEmptyDatabaseRanges )
756 335 : pEmptyDatabaseRanges->UpdateAddress( aAddress );
757 335 : if( pMergedRanges )
758 335 : pMergedRanges->UpdateAddress( aAddress );
759 335 : if( pAreaLinks )
760 335 : pAreaLinks->UpdateAddress( aAddress );
761 335 : if( pDetectiveObj )
762 335 : pDetectiveObj->UpdateAddress( aAddress );
763 335 : if( pDetectiveOp )
764 335 : pDetectiveOp->UpdateAddress( aAddress );
765 :
766 335 : bool bFoundCell((aAddress.Column <= MAXCOL) && (aAddress.Row <= MAXROW));
767 335 : if( bFoundCell )
768 : {
769 313 : SetCellData( aCell, aAddress );
770 313 : if( pShapes )
771 2 : pShapes->SetCellData( aCell );
772 313 : if( pNoteShapes )
773 2 : pNoteShapes->SetCellData( aCell );
774 313 : if( pEmptyDatabaseRanges )
775 313 : pEmptyDatabaseRanges->SetCellData( aCell );
776 313 : if( pMergedRanges )
777 313 : pMergedRanges->SetCellData( aCell );
778 313 : if( pAreaLinks )
779 313 : pAreaLinks->SetCellData( aCell );
780 313 : if( pDetectiveObj )
781 313 : pDetectiveObj->SetCellData( aCell );
782 313 : if( pDetectiveOp )
783 313 : pDetectiveOp->SetCellData( aCell );
784 :
785 313 : HasAnnotation( aCell );
786 : bool bIsAutoStyle;
787 : // Ranges before the previous cell are not needed by ExportFormatRanges anymore and can be removed
788 313 : sal_Int32 nRemoveBeforeRow = aLastAddress.Row;
789 : aCell.nStyleIndex = pCellStyles->GetStyleNameIndex(aCell.aCellAddress.Sheet,
790 : aCell.aCellAddress.Column, aCell.aCellAddress.Row,
791 313 : bIsAutoStyle, aCell.nValidationIndex, aCell.nNumberFormat, nRemoveBeforeRow);
792 313 : aLastAddress = aCell.aCellAddress;
793 313 : aCell.bIsAutoStyle = bIsAutoStyle;
794 :
795 : //#102799#; if the cell is in a DatabaseRange which should saved empty, the cell should have the type empty
796 313 : if (aCell.bHasEmptyDatabase)
797 0 : aCell.nType = table::CellContentType_EMPTY;
798 : }
799 335 : return bFoundCell;
800 102 : }
801 :
802 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|