1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: table2.cxx,v $
10 * $Revision: 1.40.124.8 $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_sc.hxx"
34 // INCLUDE ---------------------------------------------------------------
36 #include "scitems.hxx"
37 #include <svx/boxitem.hxx>
38 #include <tools/urlobj.hxx>
39 #include <svtools/poolcach.hxx>
40 #include <unotools/charclass.hxx>
42 #include <svtools/PasswordHelper.hxx>
43 #include <unotools/transliterationwrapper.hxx>
45 #include "patattr.hxx"
46 #include "docpool.hxx"
48 #include "document.hxx"
49 #include "drwlayer.hxx"
50 #include "olinetab.hxx"
51 #include "rechead.hxx"
52 #include "stlpool.hxx"
53 #include "attarray.hxx" // Iterator
54 #include "markdata.hxx"
55 #include "progress.hxx"
56 #include "dociter.hxx"
57 #include "conditio.hxx"
58 #include "chartlis.hxx"
59 #include "fillinfo.hxx"
60 #include "bcaslot.hxx"
62 #include "globstr.hrc"
63 #include "segmenttree.hxx"
67 // STATIC DATA -----------------------------------------------------------
70 BOOL
ScTable::SetOutlineTable( const ScOutlineTable
* pNewOutline
)
79 nOldSizeX
= pOutlineTable
->GetColArray()->GetDepth();
80 nOldSizeY
= pOutlineTable
->GetRowArray()->GetDepth();
86 pOutlineTable
= new ScOutlineTable( *pNewOutline
);
87 nNewSizeX
= pOutlineTable
->GetColArray()->GetDepth();
88 nNewSizeY
= pOutlineTable
->GetRowArray()->GetDepth();
93 return ( nNewSizeX
!= nOldSizeX
|| nNewSizeY
!= nOldSizeY
); // Groesse geaendert ?
97 void ScTable::StartOutlineTable()
100 pOutlineTable
= new ScOutlineTable
;
104 BOOL
ScTable::TestInsertRow( SCCOL nStartCol
, SCCOL nEndCol
, SCSIZE nSize
)
108 if ( nStartCol
==0 && nEndCol
==MAXCOL
&& pOutlineTable
)
109 bTest
= pOutlineTable
->TestInsertRow(nSize
);
111 for (SCCOL i
=nStartCol
; (i
<=nEndCol
) && bTest
; i
++)
112 bTest
= aCol
[i
].TestInsertRow( nSize
);
118 void ScTable::InsertRow( SCCOL nStartCol
, SCCOL nEndCol
, SCROW nStartRow
, SCSIZE nSize
)
121 InitializeNoteCaptions();
122 if (nStartCol
==0 && nEndCol
==MAXCOL
)
124 if (pRowHeight
&& pRowFlags
)
126 pRowHeight
->Insert( nStartRow
, nSize
);
127 BYTE nNewFlags
= pRowFlags
->Insert( nStartRow
, nSize
);
128 // only copy manual size flag, clear all others
129 if (nNewFlags
&& (nNewFlags
!= CR_MANUALSIZE
))
130 pRowFlags
->SetValue( nStartRow
, nStartRow
+ nSize
- 1,
131 nNewFlags
& CR_MANUALSIZE
);
134 pOutlineTable
->InsertRow( nStartRow
, nSize
);
136 mpFilteredRows
->insertSegment(nStartRow
, nSize
, true);
137 mpHiddenRows
->insertSegment(nStartRow
, nSize
, true);
140 for (SCCOL j
=nStartCol
; j
<=nEndCol
; j
++)
141 aCol
[j
].InsertRow( nStartRow
, nSize
);
145 InvalidatePageBreaks();
149 void ScTable::DeleteRow( SCCOL nStartCol
, SCCOL nEndCol
, SCROW nStartRow
, SCSIZE nSize
,
153 InitializeNoteCaptions();
154 if (nStartCol
==0 && nEndCol
==MAXCOL
)
156 if (pRowHeight
&& pRowFlags
)
158 pRowHeight
->Remove( nStartRow
, nSize
);
159 pRowFlags
->Remove( nStartRow
, nSize
);
162 if (pOutlineTable
->DeleteRow( nStartRow
, nSize
))
164 *pUndoOutline
= TRUE
;
166 mpFilteredRows
->removeSegment(nStartRow
, nStartRow
+nSize
);
167 mpHiddenRows
->removeSegment(nStartRow
, nStartRow
+nSize
);
170 { // scope for bulk broadcast
171 ScBulkBroadcast
aBulkBroadcast( pDocument
->GetBASM());
172 for (SCCOL j
=nStartCol
; j
<=nEndCol
; j
++)
173 aCol
[j
].DeleteRow( nStartRow
, nSize
);
178 InvalidatePageBreaks();
182 BOOL
ScTable::TestInsertCol( SCROW nStartRow
, SCROW nEndRow
, SCSIZE nSize
)
186 if ( nStartRow
==0 && nEndRow
==MAXROW
&& pOutlineTable
)
187 bTest
= pOutlineTable
->TestInsertCol(nSize
);
189 if ( nSize
> static_cast<SCSIZE
>(MAXCOL
) )
192 for (SCCOL i
=MAXCOL
; (i
+static_cast<SCCOL
>(nSize
)>MAXCOL
) && bTest
; i
--)
193 bTest
= aCol
[i
].TestInsertCol(nStartRow
, nEndRow
);
199 void ScTable::InsertCol( SCCOL nStartCol
, SCROW nStartRow
, SCROW nEndRow
, SCSIZE nSize
)
202 InitializeNoteCaptions();
203 if (nStartRow
==0 && nEndRow
==MAXROW
)
205 if (pColWidth
&& pColFlags
)
207 memmove( &pColWidth
[nStartCol
+nSize
], &pColWidth
[nStartCol
],
208 (MAXCOL
- nStartCol
+ 1 - nSize
) * sizeof(pColWidth
[0]) );
209 memmove( &pColFlags
[nStartCol
+nSize
], &pColFlags
[nStartCol
],
210 (MAXCOL
- nStartCol
+ 1 - nSize
) * sizeof(pColFlags
[0]) );
213 pOutlineTable
->InsertCol( nStartCol
, nSize
);
215 mpHiddenCols
->insertSegment(nStartCol
, nSize
, true);
216 mpFilteredCols
->insertSegment(nStartCol
, nSize
, true);
220 if ((nStartRow
== 0) && (nEndRow
== MAXROW
))
222 for (SCSIZE i
=0; i
< nSize
; i
++)
223 for (SCCOL nCol
= MAXCOL
; nCol
> nStartCol
; nCol
--)
224 aCol
[nCol
].SwapCol(aCol
[nCol
-1]);
228 for (SCSIZE i
=0; static_cast<SCCOL
>(i
+nSize
)+nStartCol
<= MAXCOL
; i
++)
229 aCol
[MAXCOL
- nSize
- i
].MoveTo(nStartRow
, nEndRow
, aCol
[MAXCOL
- i
]);
232 if (nStartCol
>0) // copy old attributes
234 USHORT nWhichArray
[2];
235 nWhichArray
[0] = ATTR_MERGE
;
238 for (SCSIZE i
=0; i
<nSize
; i
++)
240 aCol
[nStartCol
-1].CopyToColumn( nStartRow
, nEndRow
, IDF_ATTRIB
,
241 FALSE
, aCol
[nStartCol
+i
] );
242 aCol
[nStartCol
+i
].RemoveFlags( nStartRow
, nEndRow
,
243 SC_MF_HOR
| SC_MF_VER
| SC_MF_AUTO
);
244 aCol
[nStartCol
+i
].ClearItems( nStartRow
, nEndRow
, nWhichArray
);
250 InvalidatePageBreaks();
254 void ScTable::DeleteCol( SCCOL nStartCol
, SCROW nStartRow
, SCROW nEndRow
, SCSIZE nSize
,
258 InitializeNoteCaptions();
259 if (nStartRow
==0 && nEndRow
==MAXROW
)
261 if (pColWidth
&& pColFlags
)
263 memmove( &pColWidth
[nStartCol
], &pColWidth
[nStartCol
+nSize
],
264 (MAXCOL
- nStartCol
+ 1 - nSize
) * sizeof(pColWidth
[0]) );
265 memmove( &pColFlags
[nStartCol
], &pColFlags
[nStartCol
+nSize
],
266 (MAXCOL
- nStartCol
+ 1 - nSize
) * sizeof(pColFlags
[0]) );
269 if (pOutlineTable
->DeleteCol( nStartCol
, nSize
))
271 *pUndoOutline
= TRUE
;
273 mpHiddenCols
->removeSegment(nStartCol
, nStartCol
+nSize
);
274 mpFilteredCols
->removeSegment(nStartCol
, nStartCol
+nSize
);
278 { // scope for bulk broadcast
279 ScBulkBroadcast
aBulkBroadcast( pDocument
->GetBASM());
280 for (SCSIZE i
= 0; i
< nSize
; i
++)
281 aCol
[nStartCol
+ i
].DeleteArea(nStartRow
, nEndRow
, IDF_ALL
);
284 if ((nStartRow
== 0) && (nEndRow
== MAXROW
))
286 for (SCSIZE i
=0; i
< nSize
; i
++)
287 for (SCCOL nCol
= nStartCol
; nCol
< MAXCOL
; nCol
++)
288 aCol
[nCol
].SwapCol(aCol
[nCol
+1]);
292 for (SCSIZE i
=0; static_cast<SCCOL
>(i
+nSize
)+nStartCol
<= MAXCOL
; i
++)
293 aCol
[nStartCol
+ nSize
+ i
].MoveTo(nStartRow
, nEndRow
, aCol
[nStartCol
+ i
]);
298 InvalidatePageBreaks();
302 void ScTable::DeleteArea(SCCOL nCol1
, SCROW nRow1
, SCCOL nCol2
, SCROW nRow2
, USHORT nDelFlag
)
304 if (nCol2
> MAXCOL
) nCol2
= MAXCOL
;
305 if (nRow2
> MAXROW
) nRow2
= MAXROW
;
306 if (ValidColRow(nCol1
, nRow1
) && ValidColRow(nCol2
, nRow2
))
310 { // scope for bulk broadcast
311 ScBulkBroadcast
aBulkBroadcast( pDocument
->GetBASM());
312 for (SCCOL i
= nCol1
; i
<= nCol2
; i
++)
313 aCol
[i
].DeleteArea(nRow1
, nRow2
, nDelFlag
);
317 // Zellschutz auf geschuetzter Tabelle nicht setzen
320 if ( IsProtected() && (nDelFlag
& IDF_ATTRIB
) )
322 ScPatternAttr
aPattern(pDocument
->GetPool());
323 aPattern
.GetItemSet().Put( ScProtectionAttr( FALSE
) );
324 ApplyPatternArea( nCol1
, nRow1
, nCol2
, nRow2
, aPattern
);
327 /* if( !--nRecalcLvl )
334 void ScTable::DeleteSelection( USHORT nDelFlag
, const ScMarkData
& rMark
)
336 { // scope for bulk broadcast
337 ScBulkBroadcast
aBulkBroadcast( pDocument
->GetBASM());
338 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
339 aCol
[i
].DeleteSelection( nDelFlag
, rMark
);
343 // Zellschutz auf geschuetzter Tabelle nicht setzen
346 if ( IsProtected() && (nDelFlag
& IDF_ATTRIB
) )
348 ScDocumentPool
* pPool
= pDocument
->GetPool();
349 SfxItemSet
aSet( *pPool
, ATTR_PATTERN_START
, ATTR_PATTERN_END
);
350 aSet
.Put( ScProtectionAttr( FALSE
) );
351 SfxItemPoolCache
aCache( pPool
, &aSet
);
352 ApplySelectionCache( &aCache
, rMark
);
357 // pTable = Clipboard
358 void ScTable::CopyToClip(SCCOL nCol1
, SCROW nRow1
, SCCOL nCol2
, SCROW nRow2
,
359 ScTable
* pTable
, BOOL bKeepScenarioFlags
, BOOL bCloneNoteCaptions
)
361 if (ValidColRow(nCol1
, nRow1
) && ValidColRow(nCol2
, nRow2
))
366 for ( i
= nCol1
; i
<= nCol2
; i
++)
367 aCol
[i
].CopyToClip(nRow1
, nRow2
, pTable
->aCol
[i
], bKeepScenarioFlags
, bCloneNoteCaptions
);
369 // copy widths/heights, and only "hidden", "filtered" and "manual" flags
370 // also for all preceding columns/rows, to have valid positions for drawing objects
372 if (pColWidth
&& pTable
->pColWidth
)
373 for (i
=0; i
<=nCol2
; i
++)
374 pTable
->pColWidth
[i
] = pColWidth
[i
];
376 pTable
->CopyColHidden(*this, 0, nCol2
);
377 pTable
->CopyColFiltered(*this, 0, nCol2
);
379 if (pRowFlags
&& pTable
->pRowFlags
&& pRowHeight
&& pTable
->pRowHeight
)
381 pTable
->pRowFlags
->CopyFromAnded( *pRowFlags
, 0, nRow2
, CR_MANUALSIZE
);
382 pTable
->pRowHeight
->CopyFrom( *pRowHeight
, 0, nRow2
);
385 pTable
->CopyRowHidden(*this, 0, nRow2
);
386 pTable
->CopyRowFiltered(*this, 0, nRow2
);
388 // ggf. Formeln durch Werte ersetzen
391 for (i
= nCol1
; i
<= nCol2
; i
++)
392 pTable
->aCol
[i
].RemoveProtected(nRow1
, nRow2
);
396 void ScTable::CopyToClip(const ScRangeList
& rRanges
, ScTable
* pTable
,
397 bool bKeepScenarioFlags
, bool bCloneNoteCaptions
)
399 ScRangeList
aRanges(rRanges
);
400 for (ScRangePtr p
= aRanges
.First(); p
; p
= aRanges
.Next())
402 CopyToClip(p
->aStart
.Col(), p
->aStart
.Row(), p
->aEnd
.Col(), p
->aEnd
.Row(),
403 pTable
, bKeepScenarioFlags
, bCloneNoteCaptions
);
407 void ScTable::CopyFromClip(SCCOL nCol1
, SCROW nRow1
, SCCOL nCol2
, SCROW nRow2
,
408 SCsCOL nDx
, SCsROW nDy
, USHORT nInsFlag
,
409 BOOL bAsLink
, BOOL bSkipAttrForEmpty
, ScTable
* pTable
)
413 if (nCol2
> MAXCOL
) nCol2
= MAXCOL
;
414 if (nRow2
> MAXROW
) nRow2
= MAXROW
;
415 if (ValidColRow(nCol1
, nRow1
) && ValidColRow(nCol2
, nRow2
))
418 for ( i
= nCol1
; i
<= nCol2
; i
++)
419 aCol
[i
].CopyFromClip(nRow1
, nRow2
, nDy
, nInsFlag
, bAsLink
, bSkipAttrForEmpty
, pTable
->aCol
[i
- nDx
]);
421 if ((nInsFlag
& IDF_ATTRIB
) != 0)
423 if (nRow1
==0 && nRow2
==MAXROW
&& pColWidth
&& pTable
->pColWidth
)
424 for (i
=nCol1
; i
<=nCol2
; i
++)
425 pColWidth
[i
] = pTable
->pColWidth
[i
-nDx
];
427 if (nCol1
==0 && nCol2
==MAXCOL
&& pRowHeight
&& pTable
->pRowHeight
&&
428 pRowFlags
&& pTable
->pRowFlags
)
430 pRowHeight
->CopyFrom( *pTable
->pRowHeight
, nRow1
, nRow2
, -nDy
);
431 // Must copy CR_MANUALSIZE bit too, otherwise pRowHeight doesn't make sense
432 for (SCROW j
=nRow1
; j
<=nRow2
; j
++)
434 if ( pTable
->pRowFlags
->GetValue(j
-nDy
) & CR_MANUALSIZE
)
435 pRowFlags
->OrValue( j
, CR_MANUALSIZE
);
437 pRowFlags
->AndValue( j
, sal::static_int_cast
<BYTE
>(~CR_MANUALSIZE
));
442 // Zellschutz auf geschuetzter Tabelle nicht setzen
445 if ( IsProtected() && (nInsFlag
& IDF_ATTRIB
) )
447 ScPatternAttr
aPattern(pDocument
->GetPool());
448 aPattern
.GetItemSet().Put( ScProtectionAttr( FALSE
) );
449 ApplyPatternArea( nCol1
, nRow1
, nCol2
, nRow2
, aPattern
);
458 void ScTable::MixData( SCCOL nCol1
, SCROW nRow1
, SCCOL nCol2
, SCROW nRow2
,
459 USHORT nFunction
, BOOL bSkipEmpty
, ScTable
* pSrcTab
)
461 for (SCCOL i
=nCol1
; i
<=nCol2
; i
++)
462 aCol
[i
].MixData( nRow1
, nRow2
, nFunction
, bSkipEmpty
, pSrcTab
->aCol
[i
] );
466 // Markierung von diesem Dokument
467 void ScTable::MixMarked( const ScMarkData
& rMark
, USHORT nFunction
,
468 BOOL bSkipEmpty
, ScTable
* pSrcTab
)
470 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
471 aCol
[i
].MixMarked( rMark
, nFunction
, bSkipEmpty
, pSrcTab
->aCol
[i
] );
475 void ScTable::TransposeClip( SCCOL nCol1
, SCROW nRow1
, SCCOL nCol2
, SCROW nRow2
,
476 ScTable
* pTransClip
, USHORT nFlags
, BOOL bAsLink
)
478 BOOL bWasCut
= pDocument
->IsCutMode();
480 ScDocument
* pDestDoc
= pTransClip
->pDocument
;
482 for (SCCOL nCol
=nCol1
; nCol
<=nCol2
; nCol
++)
487 if ( bAsLink
&& nFlags
== IDF_ALL
)
489 // #68989# with IDF_ALL, also create links (formulas) for empty cells
491 for ( nRow
=nRow1
; nRow
<=nRow2
; nRow
++ )
493 // create simple formula, as in ScColumn::CreateRefCell
495 ScAddress
aDestPos( static_cast<SCCOL
>(nRow
-nRow1
), static_cast<SCROW
>(nCol
-nCol1
), pTransClip
->nTab
);
496 ScSingleRefData aRef
;
500 aRef
.InitFlags(); // -> all absolute
501 aRef
.SetFlag3D(TRUE
);
502 aRef
.CalcRelFromAbs( aDestPos
);
504 aArr
.AddSingleReference( aRef
);
506 ScBaseCell
* pNew
= new ScFormulaCell( pDestDoc
, aDestPos
, &aArr
);
507 pTransClip
->PutCell( static_cast<SCCOL
>(nRow
-nRow1
), static_cast<SCROW
>(nCol
-nCol1
), pNew
);
512 ScColumnIterator
aIter( &aCol
[nCol
], nRow1
, nRow2
);
513 while (aIter
.Next( nRow
, pCell
))
515 ScAddress
aDestPos( static_cast<SCCOL
>(nRow
-nRow1
), static_cast<SCROW
>(nCol
-nCol1
), pTransClip
->nTab
);
517 if ( bAsLink
) // Referenz erzeugen ?
519 pNew
= aCol
[nCol
].CreateRefCell( pDestDoc
, aDestPos
, aIter
.GetIndex(), nFlags
);
523 ScAddress
aOwnPos( nCol
, nRow
, nTab
);
524 if (pCell
->GetCellType() == CELLTYPE_FORMULA
)
526 pNew
= pCell
->CloneWithNote( aOwnPos
, *pDestDoc
, aDestPos
, SC_CLONECELL_STARTLISTENING
);
529 // bei Cut werden Referenzen spaeter per UpdateTranspose angepasst
532 ((ScFormulaCell
*)pNew
)->TransposeReference();
536 pNew
= pCell
->CloneWithNote( aOwnPos
, *pDestDoc
, aDestPos
);
539 pTransClip
->PutCell( static_cast<SCCOL
>(nRow
-nRow1
), static_cast<SCROW
>(nCol
-nCol1
), pNew
);
547 const ScPatternAttr
* pPattern
;
548 ScAttrIterator
* pAttrIter
= aCol
[nCol
].CreateAttrIterator( nRow1
, nRow2
);
549 while ( (pPattern
= pAttrIter
->Next( nAttrRow1
, nAttrRow2
)) != 0 )
551 if ( !IsDefaultItem( pPattern
) )
553 const SfxItemSet
& rSet
= pPattern
->GetItemSet();
554 if ( rSet
.GetItemState( ATTR_MERGE
, FALSE
) == SFX_ITEM_DEFAULT
&&
555 rSet
.GetItemState( ATTR_MERGE_FLAG
, FALSE
) == SFX_ITEM_DEFAULT
&&
556 rSet
.GetItemState( ATTR_BORDER
, FALSE
) == SFX_ITEM_DEFAULT
)
558 // no borders or merge items involved - use pattern as-is
559 for (nRow
= nAttrRow1
; nRow
<=nAttrRow2
; nRow
++)
560 pTransClip
->SetPattern( static_cast<SCCOL
>(nRow
-nRow1
), static_cast<SCROW
>(nCol
-nCol1
), *pPattern
, TRUE
);
564 // transpose borders and merge values, remove merge flags (refreshed after pasting)
565 ScPatternAttr
aNewPattern( *pPattern
);
566 SfxItemSet
& rNewSet
= aNewPattern
.GetItemSet();
568 const SvxBoxItem
& rOldBox
= (const SvxBoxItem
&)rSet
.Get(ATTR_BORDER
);
569 if ( rOldBox
.GetTop() || rOldBox
.GetBottom() || rOldBox
.GetLeft() || rOldBox
.GetRight() )
571 SvxBoxItem
aNew( ATTR_BORDER
);
572 aNew
.SetLine( rOldBox
.GetLine( BOX_LINE_TOP
), BOX_LINE_LEFT
);
573 aNew
.SetLine( rOldBox
.GetLine( BOX_LINE_LEFT
), BOX_LINE_TOP
);
574 aNew
.SetLine( rOldBox
.GetLine( BOX_LINE_BOTTOM
), BOX_LINE_RIGHT
);
575 aNew
.SetLine( rOldBox
.GetLine( BOX_LINE_RIGHT
), BOX_LINE_BOTTOM
);
576 aNew
.SetDistance( rOldBox
.GetDistance( BOX_LINE_TOP
), BOX_LINE_LEFT
);
577 aNew
.SetDistance( rOldBox
.GetDistance( BOX_LINE_LEFT
), BOX_LINE_TOP
);
578 aNew
.SetDistance( rOldBox
.GetDistance( BOX_LINE_BOTTOM
), BOX_LINE_RIGHT
);
579 aNew
.SetDistance( rOldBox
.GetDistance( BOX_LINE_RIGHT
), BOX_LINE_BOTTOM
);
583 const ScMergeAttr
& rOldMerge
= (const ScMergeAttr
&)rSet
.Get(ATTR_MERGE
);
584 if (rOldMerge
.IsMerged())
585 rNewSet
.Put( ScMergeAttr( Min(
586 static_cast<SCsCOL
>(rOldMerge
.GetRowMerge()),
587 static_cast<SCsCOL
>(MAXCOL
+1 - (nAttrRow2
-nRow1
))),
589 static_cast<SCsROW
>(rOldMerge
.GetColMerge()),
590 static_cast<SCsROW
>(MAXROW
+1 - (nCol
-nCol1
)))));
591 const ScMergeFlagAttr
& rOldFlag
= (const ScMergeFlagAttr
&)rSet
.Get(ATTR_MERGE_FLAG
);
592 if (rOldFlag
.IsOverlapped())
594 INT16 nNewFlags
= rOldFlag
.GetValue() & ~( SC_MF_HOR
| SC_MF_VER
);
596 rNewSet
.Put( ScMergeFlagAttr( nNewFlags
) );
598 rNewSet
.ClearItem( ATTR_MERGE_FLAG
);
601 for (nRow
= nAttrRow1
; nRow
<=nAttrRow2
; nRow
++)
602 pTransClip
->SetPattern( static_cast<SCCOL
>(nRow
-nRow1
),
603 static_cast<SCROW
>(nCol
-nCol1
), aNewPattern
, TRUE
);
613 void ScTable::StartAllListeners()
615 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
616 aCol
[i
].StartAllListeners();
620 void ScTable::StartNeededListeners()
622 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
623 aCol
[i
].StartNeededListeners();
627 void ScTable::BroadcastInArea( SCCOL nCol1
, SCROW nRow1
,
628 SCCOL nCol2
, SCROW nRow2
)
630 if (nCol2
> MAXCOL
) nCol2
= MAXCOL
;
631 if (nRow2
> MAXROW
) nRow2
= MAXROW
;
632 if (ValidColRow(nCol1
, nRow1
) && ValidColRow(nCol2
, nRow2
))
633 for (SCCOL i
= nCol1
; i
<= nCol2
; i
++)
634 aCol
[i
].BroadcastInArea( nRow1
, nRow2
);
638 void ScTable::StartListeningInArea( SCCOL nCol1
, SCROW nRow1
,
639 SCCOL nCol2
, SCROW nRow2
)
641 if (nCol2
> MAXCOL
) nCol2
= MAXCOL
;
642 if (nRow2
> MAXROW
) nRow2
= MAXROW
;
643 if (ValidColRow(nCol1
, nRow1
) && ValidColRow(nCol2
, nRow2
))
644 for (SCCOL i
= nCol1
; i
<= nCol2
; i
++)
645 aCol
[i
].StartListeningInArea( nRow1
, nRow2
);
649 void ScTable::CopyToTable(SCCOL nCol1
, SCROW nRow1
, SCCOL nCol2
, SCROW nRow2
,
650 USHORT nFlags
, BOOL bMarked
, ScTable
* pDestTab
,
651 const ScMarkData
* pMarkData
,
652 BOOL bAsLink
, BOOL bColRowFlags
)
654 if (ValidColRow(nCol1
, nRow1
) && ValidColRow(nCol2
, nRow2
))
657 for (SCCOL i
= nCol1
; i
<= nCol2
; i
++)
658 aCol
[i
].CopyToColumn(nRow1
, nRow2
, nFlags
, bMarked
,
659 pDestTab
->aCol
[i
], pMarkData
, bAsLink
);
661 if (bColRowFlags
) // Spaltenbreiten/Zeilenhoehen/Flags
663 // Charts muessen beim Ein-/Ausblenden angepasst werden
664 ScChartListenerCollection
* pCharts
= pDestTab
->pDocument
->GetChartListenerCollection();
666 bool bFlagChange
= false;
668 BOOL bWidth
= (nRow1
==0 && nRow2
==MAXROW
&& pColWidth
&& pDestTab
->pColWidth
);
669 BOOL bHeight
= (nCol1
==0 && nCol2
==MAXCOL
&& pRowHeight
&& pDestTab
->pRowHeight
);
673 pDestTab
->IncRecalcLevel();
676 for (SCCOL i
=nCol1
; i
<=nCol2
; i
++)
678 bool bThisHidden
= ColHidden(i
);
679 bool bHiddenChange
= (pDestTab
->ColHidden(i
) != bThisHidden
);
680 bool bChange
= bHiddenChange
|| (pDestTab
->pColWidth
[i
] != pColWidth
[i
]);
681 pDestTab
->pColWidth
[i
] = pColWidth
[i
];
682 pDestTab
->pColFlags
[i
] = pColFlags
[i
];
683 pDestTab
->SetColHidden(i
, i
, bThisHidden
);
684 //! Aenderungen zusammenfassen?
685 if (bHiddenChange
&& pCharts
)
686 pCharts
->SetRangeDirty(ScRange( i
, 0, nTab
, i
, MAXROW
, nTab
));
694 bool bChange
= pDestTab
->pRowHeight
->SumValues(nRow1
, nRow2
) != pRowHeight
->SumValues(nRow1
, nRow2
);
699 pDestTab
->pRowHeight
->CopyFrom( *pRowHeight
, nRow1
, nRow2
);
700 pDestTab
->pRowFlags
->CopyFrom(*pRowFlags
, nRow1
, nRow2
);
702 for (SCROW i
= nRow1
; i
<= nRow2
; ++i
)
704 SCROW nThisLastRow
, nDestLastRow
;
705 bool bThisHidden
= RowHidden(i
, nThisLastRow
);
706 bool bDestHidden
= pDestTab
->RowHidden(i
, nDestLastRow
);
708 // If the segment sizes differ, we take the shorter segment of the two.
709 SCROW nLastRow
= ::std::min(nThisLastRow
, nDestLastRow
);
710 if (nLastRow
>= nRow2
)
711 // the last row shouldn't exceed the upper bound the caller specified.
714 pDestTab
->SetRowHidden(i
, nLastRow
, bThisHidden
);
716 bool bThisHiddenChange
= (bThisHidden
!= bDestHidden
);
717 if (bThisHiddenChange
&& pCharts
)
719 // Hidden flags differ.
720 pCharts
->SetRangeDirty(ScRange(0, i
, nTab
, MAXCOL
, nLastRow
, nTab
));
723 if (bThisHiddenChange
)
726 // Jump to the last row of the identical flag segment.
730 pDestTab
->DecRecalcLevel();
734 pDestTab
->InvalidatePageBreaks();
736 pDestTab
->SetOutlineTable( pOutlineTable
); // auch nur wenn bColRowFlags
742 void ScTable::UndoToTable(SCCOL nCol1
, SCROW nRow1
, SCCOL nCol2
, SCROW nRow2
,
743 USHORT nFlags
, BOOL bMarked
, ScTable
* pDestTab
,
744 const ScMarkData
* pMarkData
)
746 if (ValidColRow(nCol1
, nRow1
) && ValidColRow(nCol2
, nRow2
))
748 BOOL bWidth
= (nRow1
==0 && nRow2
==MAXROW
&& pColWidth
&& pDestTab
->pColWidth
);
749 BOOL bHeight
= (nCol1
==0 && nCol2
==MAXCOL
&& pRowHeight
&& pDestTab
->pRowHeight
);
754 for ( SCCOL i
= 0; i
<= MAXCOL
; i
++)
756 if ( i
>= nCol1
&& i
<= nCol2
)
757 aCol
[i
].UndoToColumn(nRow1
, nRow2
, nFlags
, bMarked
, pDestTab
->aCol
[i
],
760 aCol
[i
].CopyToColumn(0, MAXROW
, IDF_FORMULA
, FALSE
, pDestTab
->aCol
[i
]);
766 for (SCCOL i
=nCol1
; i
<=nCol2
; i
++)
767 pDestTab
->pColWidth
[i
] = pColWidth
[i
];
769 pDestTab
->pRowHeight
->CopyFrom( *pRowHeight
, nRow1
, nRow2
);
777 void ScTable::CopyUpdated( const ScTable
* pPosTab
, ScTable
* pDestTab
) const
779 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
780 aCol
[i
].CopyUpdated( pPosTab
->aCol
[i
], pDestTab
->aCol
[i
] );
783 void ScTable::InvalidateTableArea()
785 bTableAreaValid
= FALSE
;
788 void ScTable::InvalidatePageBreaks()
790 mbPageBreaksValid
= false;
793 void ScTable::CopyScenarioTo( ScTable
* pDestTab
) const
795 DBG_ASSERT( bScenario
, "bScenario == FALSE" );
797 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
798 aCol
[i
].CopyScenarioTo( pDestTab
->aCol
[i
] );
801 void ScTable::CopyScenarioFrom( const ScTable
* pSrcTab
)
803 DBG_ASSERT( bScenario
, "bScenario == FALSE" );
805 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
806 aCol
[i
].CopyScenarioFrom( pSrcTab
->aCol
[i
] );
809 void ScTable::MarkScenarioIn( ScMarkData
& rDestMark
, USHORT nNeededBits
) const
811 DBG_ASSERT( bScenario
, "bScenario == FALSE" );
813 if ( ( nScenarioFlags
& nNeededBits
) != nNeededBits
) // alle Bits gesetzt?
816 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
817 aCol
[i
].MarkScenarioIn( rDestMark
);
820 BOOL
ScTable::HasScenarioRange( const ScRange
& rRange
) const
822 DBG_ASSERT( bScenario
, "bScenario == FALSE" );
825 // MarkScenarioIn( aMark, 0 ); //! Bits als Parameter von HasScenarioRange?
826 // return aMark.IsAllMarked( rRange );
828 ScRange aTabRange
= rRange
;
829 aTabRange
.aStart
.SetTab( nTab
);
830 aTabRange
.aEnd
.SetTab( nTab
);
832 const ScRangeList
* pList
= GetScenarioRanges();
833 // return ( pList && pList->Find( aTabRange ) );
837 ULONG nCount
= pList
->Count();
838 for ( ULONG j
= 0; j
< nCount
; j
++ )
840 ScRange
* pR
= pList
->GetObject( j
);
841 if ( pR
->Intersects( aTabRange
) )
849 void ScTable::InvalidateScenarioRanges()
851 delete pScenarioRanges
;
852 pScenarioRanges
= NULL
;
855 const ScRangeList
* ScTable::GetScenarioRanges() const
857 DBG_ASSERT( bScenario
, "bScenario == FALSE" );
859 if (!pScenarioRanges
)
861 ((ScTable
*)this)->pScenarioRanges
= new ScRangeList
;
863 MarkScenarioIn( aMark
, 0 ); // immer
864 aMark
.FillRangeListWithMarks( pScenarioRanges
, FALSE
);
866 return pScenarioRanges
;
869 BOOL
ScTable::TestCopyScenarioTo( const ScTable
* pDestTab
) const
871 DBG_ASSERT( bScenario
, "bScenario == FALSE" );
873 if (!pDestTab
->IsProtected())
877 for (SCCOL i
=0; i
<=MAXCOL
&& bOk
; i
++)
878 bOk
= aCol
[i
].TestCopyScenarioTo( pDestTab
->aCol
[i
] );
882 void ScTable::PutCell( SCCOL nCol
, SCROW nRow
, ScBaseCell
* pCell
)
884 if (ValidColRow(nCol
,nRow
))
887 aCol
[nCol
].Insert( nRow
, pCell
);
889 aCol
[nCol
].Delete( nRow
);
894 void ScTable::PutCell( SCCOL nCol
, SCROW nRow
, ULONG nFormatIndex
, ScBaseCell
* pCell
)
896 if (ValidColRow(nCol
,nRow
))
899 aCol
[nCol
].Insert( nRow
, nFormatIndex
, pCell
);
901 aCol
[nCol
].Delete( nRow
);
906 void ScTable::PutCell( const ScAddress
& rPos
, ScBaseCell
* pCell
)
909 aCol
[rPos
.Col()].Insert( rPos
.Row(), pCell
);
911 aCol
[rPos
.Col()].Delete( rPos
.Row() );
915 //UNUSED2009-05 void ScTable::PutCell( const ScAddress& rPos, ULONG nFormatIndex, ScBaseCell* pCell )
917 //UNUSED2009-05 if (pCell)
918 //UNUSED2009-05 aCol[rPos.Col()].Insert( rPos.Row(), nFormatIndex, pCell );
920 //UNUSED2009-05 aCol[rPos.Col()].Delete( rPos.Row() );
924 BOOL
ScTable::SetString( SCCOL nCol
, SCROW nRow
, SCTAB nTabP
, const String
& rString
,
925 ScSetStringParam
* pParam
)
927 if (ValidColRow(nCol
,nRow
))
928 return aCol
[nCol
].SetString(
929 nRow
, nTabP
, rString
, pDocument
->GetAddressConvention(), pParam
);
935 void ScTable::SetValue( SCCOL nCol
, SCROW nRow
, const double& rVal
)
937 if (ValidColRow(nCol
, nRow
))
938 aCol
[nCol
].SetValue( nRow
, rVal
);
942 void ScTable::GetString( SCCOL nCol
, SCROW nRow
, String
& rString
)
944 if (ValidColRow(nCol
,nRow
))
945 aCol
[nCol
].GetString( nRow
, rString
);
951 void ScTable::GetInputString( SCCOL nCol
, SCROW nRow
, String
& rString
)
953 if (ValidColRow(nCol
,nRow
))
954 aCol
[nCol
].GetInputString( nRow
, rString
);
960 double ScTable::GetValue( SCCOL nCol
, SCROW nRow
)
962 if (ValidColRow( nCol
, nRow
))
963 return aCol
[nCol
].GetValue( nRow
);
968 void ScTable::GetFormula( SCCOL nCol
, SCROW nRow
, String
& rFormula
,
971 if (ValidColRow(nCol
,nRow
))
972 aCol
[nCol
].GetFormula( nRow
, rFormula
, bAsciiExport
);
978 ScPostIt
* ScTable::GetNote( SCCOL nCol
, SCROW nRow
)
980 return ValidColRow( nCol
, nRow
) ? aCol
[ nCol
].GetNote( nRow
) : 0;
984 void ScTable::TakeNote( SCCOL nCol
, SCROW nRow
, ScPostIt
*& rpNote
)
986 if( ValidColRow( nCol
, nRow
) )
988 aCol
[ nCol
].TakeNote( nRow
, rpNote
);
989 if( rpNote
&& rpNote
->GetNoteData().mxInitData
.get() )
991 if( !mxUninitNotes
.get() )
992 mxUninitNotes
.reset( new ScAddress2DVec
);
993 mxUninitNotes
->push_back( ScAddress2D( nCol
, nRow
) );
1001 ScPostIt
* ScTable::ReleaseNote( SCCOL nCol
, SCROW nRow
)
1003 return ValidColRow( nCol
, nRow
) ? aCol
[ nCol
].ReleaseNote( nRow
) : 0;
1007 void ScTable::DeleteNote( SCCOL nCol
, SCROW nRow
)
1009 if( ValidColRow( nCol
, nRow
) )
1010 aCol
[ nCol
].DeleteNote( nRow
);
1014 void ScTable::InitializeNoteCaptions( bool bForced
)
1016 if( mxUninitNotes
.get() && (bForced
|| pDocument
->IsUndoEnabled()) )
1018 for( ScAddress2DVec::iterator aIt
= mxUninitNotes
->begin(), aEnd
= mxUninitNotes
->end(); aIt
!= aEnd
; ++aIt
)
1019 if( ScPostIt
* pNote
= GetNote( aIt
->first
, aIt
->second
) )
1020 pNote
->GetOrCreateCaption( ScAddress( aIt
->first
, aIt
->second
, nTab
) );
1021 mxUninitNotes
.reset();
1025 CellType
ScTable::GetCellType( SCCOL nCol
, SCROW nRow
) const
1027 if (ValidColRow( nCol
, nRow
))
1028 return aCol
[nCol
].GetCellType( nRow
);
1029 return CELLTYPE_NONE
;
1033 ScBaseCell
* ScTable::GetCell( SCCOL nCol
, SCROW nRow
) const
1035 if (ValidColRow( nCol
, nRow
))
1036 return aCol
[nCol
].GetCell( nRow
);
1038 DBG_ERROR("GetCell ausserhalb");
1042 void ScTable::GetFirstDataPos(SCCOL
& rCol
, SCROW
& rRow
) const
1046 while (aCol
[rCol
].IsEmptyData() && rCol
< MAXCOL
)
1048 rRow
= aCol
[rCol
].GetFirstDataPos();
1051 void ScTable::GetLastDataPos(SCCOL
& rCol
, SCROW
& rRow
) const
1055 while (aCol
[rCol
].IsEmptyData() && (rCol
> 0))
1058 while ((SCsCOL
)nCol
>= 0)
1060 rRow
= Max(rRow
, aCol
[nCol
].GetLastDataPos());
1066 BOOL
ScTable::HasData( SCCOL nCol
, SCROW nRow
)
1068 if (ValidColRow(nCol
,nRow
))
1069 return aCol
[nCol
].HasDataAt( nRow
);
1075 BOOL
ScTable::HasStringData( SCCOL nCol
, SCROW nRow
)
1077 if (ValidColRow(nCol
,nRow
))
1078 return aCol
[nCol
].HasStringData( nRow
);
1084 BOOL
ScTable::HasValueData( SCCOL nCol
, SCROW nRow
)
1086 if (ValidColRow(nCol
,nRow
))
1087 return aCol
[nCol
].HasValueData( nRow
);
1093 BOOL
ScTable::HasStringCells( SCCOL nStartCol
, SCROW nStartRow
,
1094 SCCOL nEndCol
, SCROW nEndRow
) const
1096 if ( ValidCol(nEndCol
) )
1097 for ( SCCOL nCol
=nStartCol
; nCol
<=nEndCol
; nCol
++ )
1098 if (aCol
[nCol
].HasStringCells(nStartRow
, nEndRow
))
1105 //UNUSED2008-05 USHORT ScTable::GetErrCode( SCCOL nCol, SCROW nRow ) const
1107 //UNUSED2008-05 if (ValidColRow( nCol, nRow ))
1108 //UNUSED2008-05 return aCol[nCol].GetErrCode( nRow );
1109 //UNUSED2008-05 return 0;
1113 void ScTable::SetDirtyVar()
1115 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
1116 aCol
[i
].SetDirtyVar();
1120 void ScTable::SetDirty()
1122 BOOL bOldAutoCalc
= pDocument
->GetAutoCalc();
1123 pDocument
->SetAutoCalc( FALSE
); // Mehrfachberechnungen vermeiden
1124 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
1126 pDocument
->SetAutoCalc( bOldAutoCalc
);
1130 void ScTable::SetDirty( const ScRange
& rRange
)
1132 BOOL bOldAutoCalc
= pDocument
->GetAutoCalc();
1133 pDocument
->SetAutoCalc( FALSE
); // Mehrfachberechnungen vermeiden
1134 SCCOL nCol2
= rRange
.aEnd
.Col();
1135 for (SCCOL i
=rRange
.aStart
.Col(); i
<=nCol2
; i
++)
1136 aCol
[i
].SetDirty( rRange
);
1137 pDocument
->SetAutoCalc( bOldAutoCalc
);
1141 void ScTable::SetTableOpDirty( const ScRange
& rRange
)
1143 BOOL bOldAutoCalc
= pDocument
->GetAutoCalc();
1144 pDocument
->SetAutoCalc( FALSE
); // no multiple recalculation
1145 SCCOL nCol2
= rRange
.aEnd
.Col();
1146 for (SCCOL i
=rRange
.aStart
.Col(); i
<=nCol2
; i
++)
1147 aCol
[i
].SetTableOpDirty( rRange
);
1148 pDocument
->SetAutoCalc( bOldAutoCalc
);
1152 void ScTable::SetDirtyAfterLoad()
1154 BOOL bOldAutoCalc
= pDocument
->GetAutoCalc();
1155 pDocument
->SetAutoCalc( FALSE
); // Mehrfachberechnungen vermeiden
1156 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
1157 aCol
[i
].SetDirtyAfterLoad();
1158 pDocument
->SetAutoCalc( bOldAutoCalc
);
1162 void ScTable::SetRelNameDirty()
1164 BOOL bOldAutoCalc
= pDocument
->GetAutoCalc();
1165 pDocument
->SetAutoCalc( FALSE
); // Mehrfachberechnungen vermeiden
1166 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
1167 aCol
[i
].SetRelNameDirty();
1168 pDocument
->SetAutoCalc( bOldAutoCalc
);
1172 void ScTable::CalcAll()
1174 for (SCCOL i
=0; i
<=MAXCOL
; i
++) aCol
[i
].CalcAll();
1178 void ScTable::CompileAll()
1180 for (SCCOL i
=0; i
<= MAXCOL
; i
++) aCol
[i
].CompileAll();
1184 void ScTable::CompileXML( ScProgress
& rProgress
)
1186 for (SCCOL i
=0; i
<= MAXCOL
; i
++)
1188 aCol
[i
].CompileXML( rProgress
);
1192 void ScTable::CalcAfterLoad()
1194 for (SCCOL i
=0; i
<= MAXCOL
; i
++) aCol
[i
].CalcAfterLoad();
1198 bool ScTable::MarkUsedExternalReferences()
1200 bool bAllMarked
= false;
1201 for (SCCOL i
=0; i
<= MAXCOL
&& !bAllMarked
; ++i
)
1203 bAllMarked
= aCol
[i
].MarkUsedExternalReferences();
1209 void ScTable::ResetChanged( const ScRange
& rRange
)
1211 SCCOL nStartCol
= rRange
.aStart
.Col();
1212 SCROW nStartRow
= rRange
.aStart
.Row();
1213 SCCOL nEndCol
= rRange
.aEnd
.Col();
1214 SCROW nEndRow
= rRange
.aEnd
.Row();
1216 for (SCCOL nCol
=nStartCol
; nCol
<=nEndCol
; nCol
++)
1217 aCol
[nCol
].ResetChanged(nStartRow
, nEndRow
);
1222 const SfxPoolItem
* ScTable::GetAttr( SCCOL nCol
, SCROW nRow
, USHORT nWhich
) const
1224 if (ValidColRow(nCol
,nRow
))
1225 return aCol
[nCol
].GetAttr( nRow
, nWhich
);
1231 ULONG
ScTable::GetNumberFormat( SCCOL nCol
, SCROW nRow
) const
1233 if (ValidColRow(nCol
,nRow
))
1234 return aCol
[nCol
].GetNumberFormat( nRow
);
1239 sal_uInt32
ScTable::GetNumberFormat( SCCOL nCol
, SCROW nStartRow
, SCROW nEndRow
) const
1241 if (!ValidCol(nCol
) || !ValidRow(nStartRow
) || !ValidRow(nEndRow
))
1244 return aCol
[nCol
].GetNumberFormat(nStartRow
, nEndRow
);
1248 const ScPatternAttr
* ScTable::GetPattern( SCCOL nCol
, SCROW nRow
) const
1250 if (ValidColRow(nCol
,nRow
))
1251 return aCol
[nCol
].GetPattern( nRow
);
1254 DBG_ERROR("wrong column or row");
1255 return pDocument
->GetDefPattern(); // for safety
1260 const ScPatternAttr
* ScTable::GetMostUsedPattern( SCCOL nCol
, SCROW nStartRow
, SCROW nEndRow
) const
1262 if ( ValidColRow( nCol
, nStartRow
) && ValidRow( nEndRow
) && (nStartRow
<= nEndRow
) )
1263 return aCol
[nCol
].GetMostUsedPattern( nStartRow
, nEndRow
);
1269 BOOL
ScTable::HasAttrib( SCCOL nCol1
, SCROW nRow1
, SCCOL nCol2
, SCROW nRow2
, USHORT nMask
) const
1272 for (SCCOL i
=nCol1
; i
<=nCol2
&& !bFound
; i
++)
1273 bFound
|= aCol
[i
].HasAttrib( nRow1
, nRow2
, nMask
);
1278 //UNUSED2009-05 BOOL ScTable::HasLines( const ScRange& rRange, Rectangle& rSizes ) const
1280 //UNUSED2009-05 SCCOL nCol1 = rRange.aStart.Col();
1281 //UNUSED2009-05 SCROW nRow1 = rRange.aStart.Row();
1282 //UNUSED2009-05 SCCOL nCol2 = rRange.aEnd.Col();
1283 //UNUSED2009-05 SCROW nRow2 = rRange.aEnd.Row();
1284 //UNUSED2009-05 PutInOrder( nCol1, nCol2 );
1285 //UNUSED2009-05 PutInOrder( nRow1, nRow2 );
1287 //UNUSED2009-05 BOOL bFound = FALSE;
1288 //UNUSED2009-05 for (SCCOL i=nCol1; i<=nCol2; i++)
1289 //UNUSED2009-05 if (aCol[i].HasLines( nRow1, nRow2, rSizes, (i==nCol1), (i==nCol2) ))
1290 //UNUSED2009-05 bFound = TRUE;
1292 //UNUSED2009-05 return bFound;
1296 BOOL
ScTable::HasAttribSelection( const ScMarkData
& rMark
, USHORT nMask
) const
1299 for (SCCOL i
=0; i
<=MAXCOL
&& !bFound
; i
++)
1300 bFound
|= aCol
[i
].HasAttribSelection( rMark
, nMask
);
1305 BOOL
ScTable::ExtendMerge( SCCOL nStartCol
, SCROW nStartRow
,
1306 SCCOL
& rEndCol
, SCROW
& rEndRow
,
1307 BOOL bRefresh
, BOOL bAttrs
)
1309 if (!(ValidCol(nStartCol
) && ValidCol(rEndCol
)))
1311 DBG_ERRORFILE("ScTable::ExtendMerge: invalid column number");
1315 SCCOL nOldEndX
= rEndCol
;
1316 SCROW nOldEndY
= rEndRow
;
1317 for (SCCOL i
=nStartCol
; i
<=nOldEndX
; i
++)
1318 bFound
|= aCol
[i
].ExtendMerge( i
, nStartRow
, nOldEndY
, rEndCol
, rEndRow
, bRefresh
, bAttrs
);
1323 BOOL
ScTable::IsBlockEmpty( SCCOL nCol1
, SCROW nRow1
, SCCOL nCol2
, SCROW nRow2
, bool bIgnoreNotes
) const
1325 if (!(ValidCol(nCol1
) && ValidCol(nCol2
)))
1327 DBG_ERRORFILE("ScTable::IsBlockEmpty: invalid column number");
1331 for (SCCOL i
=nCol1
; i
<=nCol2
&& bEmpty
; i
++)
1332 bEmpty
= aCol
[i
].IsEmptyBlock( nRow1
, nRow2
, bIgnoreNotes
);
1336 SCSIZE
ScTable::FillMaxRot( RowInfo
* pRowInfo
, SCSIZE nArrCount
, SCCOL nX1
, SCCOL nX2
,
1337 SCCOL nCol
, SCROW nAttrRow1
, SCROW nAttrRow2
, SCSIZE nArrY
,
1338 const ScPatternAttr
* pPattern
, const SfxItemSet
* pCondSet
)
1340 // Rueckgabe = neues nArrY
1342 BYTE nRotDir
= pPattern
->GetRotateDir( pCondSet
);
1343 if ( nRotDir
!= SC_ROTDIR_NONE
)
1346 if ( nCol
+1 < nX1
) // column to the left
1347 bHit
= ( nRotDir
!= SC_ROTDIR_LEFT
);
1348 else if ( nCol
> nX2
+1 ) // column to the right
1349 bHit
= ( nRotDir
!= SC_ROTDIR_RIGHT
); // SC_ROTDIR_STANDARD may now also be extended to the left
1353 double nFactor
= 0.0;
1356 long nRotVal
= ((const SfxInt32Item
&) pPattern
->
1357 GetItem( ATTR_ROTATE_VALUE
, pCondSet
)).GetValue();
1358 double nRealOrient
= nRotVal
* F_PI18000
; // 1/100 Grad
1359 double nCos
= cos( nRealOrient
);
1360 double nSin
= sin( nRealOrient
);
1362 //! zusaetzlich Faktor fuer unterschiedliche PPT X/Y !!!
1364 // bei SC_ROTDIR_LEFT kommt immer ein negativer Wert heraus,
1365 // wenn der Modus beruecksichtigt wird
1366 nFactor
= -fabs( nCos
/ nSin
);
1369 for ( SCROW nRow
= nAttrRow1
; nRow
<= nAttrRow2
; nRow
++ )
1371 if (!RowHidden(nRow
))
1373 BOOL bHitOne
= TRUE
;
1376 // reicht die gedrehte Zelle bis in den sichtbaren Bereich?
1378 SCCOL nTouchedCol
= nCol
;
1379 long nWidth
= (long) ( pRowHeight
->GetValue(nRow
) * nFactor
);
1380 DBG_ASSERT(nWidth
<= 0, "Richtung falsch");
1381 while ( nWidth
< 0 && nTouchedCol
> 0 )
1384 nWidth
+= GetColWidth( nTouchedCol
);
1386 if ( nTouchedCol
> nX2
)
1392 while ( nArrY
<nArrCount
&& pRowInfo
[nArrY
].nRowNo
< nRow
)
1394 if ( nArrY
<nArrCount
&& pRowInfo
[nArrY
].nRowNo
== nRow
)
1395 pRowInfo
[nArrY
].nRotMaxCol
= nCol
;
1405 void ScTable::FindMaxRotCol( RowInfo
* pRowInfo
, SCSIZE nArrCount
, SCCOL nX1
, SCCOL nX2
)
1407 if ( !pColWidth
|| !pRowHeight
|| !pColFlags
|| !pRowFlags
)
1409 DBG_ERROR( "Spalten-/Zeileninfo fehlt" );
1413 // nRotMaxCol ist auf SC_ROTMAX_NONE initialisiert, nRowNo ist schon gesetzt
1415 SCROW nY1
= pRowInfo
[0].nRowNo
;
1416 SCROW nY2
= pRowInfo
[nArrCount
-1].nRowNo
;
1418 for (SCCOL nCol
=0; nCol
<=MAXCOL
; nCol
++)
1420 if (!ColHidden(nCol
))
1423 ScDocAttrIterator
aIter( pDocument
, nTab
, nCol
, nY1
, nCol
, nY2
);
1425 SCROW nAttrRow1
, nAttrRow2
;
1426 const ScPatternAttr
* pPattern
= aIter
.GetNext( nAttrCol
, nAttrRow1
, nAttrRow2
);
1429 const SfxPoolItem
* pCondItem
;
1430 if ( pPattern
->GetItemSet().GetItemState( ATTR_CONDITIONAL
, TRUE
, &pCondItem
)
1433 // alle Formate durchgehen, damit die Zellen nicht einzeln
1434 // angeschaut werden muessen
1436 ULONG nIndex
= ((const SfxUInt32Item
*)pCondItem
)->GetValue();
1437 ScConditionalFormatList
* pList
= pDocument
->GetCondFormList();
1438 ScStyleSheetPool
* pStylePool
= pDocument
->GetStyleSheetPool();
1439 if (pList
&& pStylePool
&& nIndex
)
1441 const ScConditionalFormat
* pFormat
= pList
->GetFormat(nIndex
);
1444 USHORT nEntryCount
= pFormat
->Count();
1445 for (USHORT nEntry
=0; nEntry
<nEntryCount
; nEntry
++)
1447 String aStyleName
= pFormat
->GetEntry(nEntry
)->GetStyle();
1448 if (aStyleName
.Len())
1450 SfxStyleSheetBase
* pStyleSheet
=
1451 pStylePool
->Find( aStyleName
, SFX_STYLE_FAMILY_PARA
);
1454 FillMaxRot( pRowInfo
, nArrCount
, nX1
, nX2
,
1455 nCol
, nAttrRow1
, nAttrRow2
,
1456 nArrY
, pPattern
, &pStyleSheet
->GetItemSet() );
1457 // nArrY nicht veraendern
1465 nArrY
= FillMaxRot( pRowInfo
, nArrCount
, nX1
, nX2
,
1466 nCol
, nAttrRow1
, nAttrRow2
,
1467 nArrY
, pPattern
, NULL
);
1469 pPattern
= aIter
.GetNext( nAttrCol
, nAttrRow1
, nAttrRow2
);
1475 BOOL
ScTable::HasBlockMatrixFragment( SCCOL nCol1
, SCROW nRow1
, SCCOL nCol2
, SCROW nRow2
) const
1477 // nix:0, mitte:1, unten:2, links:4, oben:8, rechts:16, offen:32
1480 if ( nCol1
== nCol2
)
1481 { // linke und rechte Spalte
1482 const USHORT n
= 4 | 16;
1483 nEdges
= aCol
[nCol1
].GetBlockMatrixEdges( nRow1
, nRow2
, n
);
1484 // nicht (4 und 16) oder 1 oder 32
1485 if ( nEdges
&& (((nEdges
& n
) != n
) || (nEdges
& 33)) )
1486 return TRUE
; // linke oder rechte Kante fehlt oder offen
1490 nEdges
= aCol
[nCol1
].GetBlockMatrixEdges( nRow1
, nRow2
, 4 );
1491 // nicht 4 oder 1 oder 32
1492 if ( nEdges
&& (((nEdges
& 4) != 4) || (nEdges
& 33)) )
1493 return TRUE
; // linke Kante fehlt oder offen
1495 nEdges
= aCol
[nCol2
].GetBlockMatrixEdges( nRow1
, nRow2
, 16 );
1496 // nicht 16 oder 1 oder 32
1497 if ( nEdges
&& (((nEdges
& 16) != 16) || (nEdges
& 33)) )
1498 return TRUE
; // rechte Kante fehlt oder offen
1501 if ( nRow1
== nRow2
)
1502 { // obere und untere Zeile
1504 const USHORT n
= 2 | 8;
1505 for ( SCCOL i
=nCol1
; i
<=nCol2
; i
++)
1507 nEdges
= aCol
[i
].GetBlockMatrixEdges( nRow1
, nRow1
, n
);
1510 if ( (nEdges
& n
) != n
)
1511 return TRUE
; // obere oder untere Kante fehlt
1513 bOpen
= TRUE
; // linke Kante oeffnet, weitersehen
1515 return TRUE
; // es gibt was, was nicht geoeffnet wurde
1517 bOpen
= FALSE
; // rechte Kante schliesst
1521 return TRUE
; // es geht noch weiter
1527 // erst obere Zeile, dann untere Zeile
1528 for ( j
=0, nR
=nRow1
, n
=8; j
<2; j
++, nR
=nRow2
, n
=2 )
1531 for ( SCCOL i
=nCol1
; i
<=nCol2
; i
++)
1533 nEdges
= aCol
[i
].GetBlockMatrixEdges( nR
, nR
, n
);
1536 // in oberere Zeile keine obere Kante bzw.
1537 // in unterer Zeile keine untere Kante
1538 if ( (nEdges
& n
) != n
)
1541 bOpen
= TRUE
; // linke Kante oeffnet, weitersehen
1543 return TRUE
; // es gibt was, was nicht geoeffnet wurde
1545 bOpen
= FALSE
; // rechte Kante schliesst
1549 return TRUE
; // es geht noch weiter
1556 BOOL
ScTable::HasSelectionMatrixFragment( const ScMarkData
& rMark
) const
1559 for (SCCOL i
=0; i
<=MAXCOL
&& !bFound
; i
++)
1560 bFound
|= aCol
[i
].HasSelectionMatrixFragment(rMark
);
1565 BOOL
ScTable::IsBlockEditable( SCCOL nCol1
, SCROW nRow1
, SCCOL nCol2
,
1566 SCROW nRow2
, BOOL
* pOnlyNotBecauseOfMatrix
/* = NULL */ ) const
1568 if ( !ValidColRow( nCol2
, nRow2
) )
1570 DBG_ERRORFILE("IsBlockEditable: invalid column or row");
1571 if (pOnlyNotBecauseOfMatrix
)
1572 *pOnlyNotBecauseOfMatrix
= FALSE
;
1576 BOOL bIsEditable
= TRUE
;
1578 bIsEditable
= FALSE
;
1579 else if ( IsProtected() && !pDocument
->IsScenario(nTab
) )
1581 if((bIsEditable
= !HasAttrib( nCol1
, nRow1
, nCol2
, nRow2
, HASATTR_PROTECTED
)) != FALSE
)
1583 // If Sheet is protected and cells are not protected then
1584 // check the active scenario protect flag if this range is
1585 // on the active scenario range. Note the 'copy back' must also
1586 // be set to apply protection.
1587 USHORT nScenTab
= nTab
+1;
1588 while(pDocument
->IsScenario(nScenTab
))
1590 ScRange
aEditRange(nCol1
, nRow1
, nScenTab
, nCol2
, nRow2
, nScenTab
);
1591 if(pDocument
->IsActiveScenario(nScenTab
) && pDocument
->HasScenarioRange(nScenTab
, aEditRange
))
1594 pDocument
->GetScenarioFlags(nScenTab
,nFlags
);
1595 bIsEditable
= !((nFlags
& SC_SCENARIO_PROTECT
) && (nFlags
& SC_SCENARIO_TWOWAY
));
1602 else if (pDocument
->IsScenario(nTab
))
1604 // Determine if the preceding sheet is protected
1605 SCTAB nActualTab
= nTab
;
1610 while(pDocument
->IsScenario(nActualTab
));
1612 if(pDocument
->IsTabProtected(nActualTab
))
1614 ScRange
aEditRange(nCol1
, nRow1
, nTab
, nCol2
, nRow2
, nTab
);
1615 if(pDocument
->HasScenarioRange(nTab
, aEditRange
))
1618 pDocument
->GetScenarioFlags(nTab
,nFlags
);
1619 bIsEditable
= !(nFlags
& SC_SCENARIO_PROTECT
);
1625 if ( HasBlockMatrixFragment( nCol1
, nRow1
, nCol2
, nRow2
) )
1627 bIsEditable
= FALSE
;
1628 if ( pOnlyNotBecauseOfMatrix
)
1629 *pOnlyNotBecauseOfMatrix
= TRUE
;
1631 else if ( pOnlyNotBecauseOfMatrix
)
1632 *pOnlyNotBecauseOfMatrix
= FALSE
;
1634 else if ( pOnlyNotBecauseOfMatrix
)
1635 *pOnlyNotBecauseOfMatrix
= FALSE
;
1640 BOOL
ScTable::IsSelectionEditable( const ScMarkData
& rMark
,
1641 BOOL
* pOnlyNotBecauseOfMatrix
/* = NULL */ ) const
1643 BOOL bIsEditable
= TRUE
;
1645 bIsEditable
= FALSE
;
1646 else if ( IsProtected() && !pDocument
->IsScenario(nTab
) )
1648 if((bIsEditable
= !HasAttribSelection( rMark
, HASATTR_PROTECTED
)) != FALSE
)
1650 // If Sheet is protected and cells are not protected then
1651 // check the active scenario protect flag if this area is
1652 // in the active scenario range.
1653 ScRangeList aRanges
;
1654 rMark
.FillRangeListWithMarks( &aRanges
, FALSE
);
1655 ULONG nRangeCount
= aRanges
.Count();
1656 SCTAB nScenTab
= nTab
+1;
1657 while(pDocument
->IsScenario(nScenTab
) && bIsEditable
)
1659 if(pDocument
->IsActiveScenario(nScenTab
))
1661 for (ULONG i
=0; i
<nRangeCount
&& bIsEditable
; i
++)
1663 ScRange aRange
= *aRanges
.GetObject(i
);
1664 if(pDocument
->HasScenarioRange(nScenTab
, aRange
))
1667 pDocument
->GetScenarioFlags(nScenTab
,nFlags
);
1668 bIsEditable
= !((nFlags
& SC_SCENARIO_PROTECT
) && (nFlags
& SC_SCENARIO_TWOWAY
));
1676 else if (pDocument
->IsScenario(nTab
))
1678 // Determine if the preceding sheet is protected
1679 SCTAB nActualTab
= nTab
;
1684 while(pDocument
->IsScenario(nActualTab
));
1686 if(pDocument
->IsTabProtected(nActualTab
))
1688 ScRangeList aRanges
;
1689 rMark
.FillRangeListWithMarks( &aRanges
, FALSE
);
1690 ULONG nRangeCount
= aRanges
.Count();
1691 for (ULONG i
=0; i
<nRangeCount
&& bIsEditable
; i
++)
1693 ScRange aRange
= *aRanges
.GetObject(i
);
1694 if(pDocument
->HasScenarioRange(nTab
, aRange
))
1697 pDocument
->GetScenarioFlags(nTab
,nFlags
);
1698 bIsEditable
= !(nFlags
& SC_SCENARIO_PROTECT
);
1705 if ( HasSelectionMatrixFragment( rMark
) )
1707 bIsEditable
= FALSE
;
1708 if ( pOnlyNotBecauseOfMatrix
)
1709 *pOnlyNotBecauseOfMatrix
= TRUE
;
1711 else if ( pOnlyNotBecauseOfMatrix
)
1712 *pOnlyNotBecauseOfMatrix
= FALSE
;
1714 else if ( pOnlyNotBecauseOfMatrix
)
1715 *pOnlyNotBecauseOfMatrix
= FALSE
;
1721 void ScTable::LockTable()
1727 void ScTable::UnlockTable()
1733 DBG_ERROR("UnlockTable ohne LockTable");
1738 void ScTable::MergeSelectionPattern( ScMergePatternState
& rState
, const ScMarkData
& rMark
, BOOL bDeep
) const
1740 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
1741 aCol
[i
].MergeSelectionPattern( rState
, rMark
, bDeep
);
1745 void ScTable::MergePatternArea( ScMergePatternState
& rState
, SCCOL nCol1
, SCROW nRow1
,
1746 SCCOL nCol2
, SCROW nRow2
, BOOL bDeep
) const
1748 for (SCCOL i
=nCol1
; i
<=nCol2
; i
++)
1749 aCol
[i
].MergePatternArea( rState
, nRow1
, nRow2
, bDeep
);
1753 void ScTable::MergeBlockFrame( SvxBoxItem
* pLineOuter
, SvxBoxInfoItem
* pLineInner
, ScLineFlags
& rFlags
,
1754 SCCOL nStartCol
, SCROW nStartRow
, SCCOL nEndCol
, SCROW nEndRow
) const
1756 if (ValidColRow(nStartCol
, nStartRow
) && ValidColRow(nEndCol
, nEndRow
))
1758 PutInOrder(nStartCol
, nEndCol
);
1759 PutInOrder(nStartRow
, nEndRow
);
1760 for (SCCOL i
=nStartCol
; i
<=nEndCol
; i
++)
1761 aCol
[i
].MergeBlockFrame( pLineOuter
, pLineInner
, rFlags
,
1762 nStartRow
, nEndRow
, (i
==nStartCol
), nEndCol
-i
);
1767 void ScTable::ApplyBlockFrame( const SvxBoxItem
* pLineOuter
, const SvxBoxInfoItem
* pLineInner
,
1768 SCCOL nStartCol
, SCROW nStartRow
, SCCOL nEndCol
, SCROW nEndRow
)
1770 if (ValidColRow(nStartCol
, nStartRow
) && ValidColRow(nEndCol
, nEndRow
))
1772 PutInOrder(nStartCol
, nEndCol
);
1773 PutInOrder(nStartRow
, nEndRow
);
1774 for (SCCOL i
=nStartCol
; i
<=nEndCol
; i
++)
1775 aCol
[i
].ApplyBlockFrame( pLineOuter
, pLineInner
,
1776 nStartRow
, nEndRow
, (i
==nStartCol
), nEndCol
-i
);
1781 void ScTable::ApplyPattern( SCCOL nCol
, SCROW nRow
, const ScPatternAttr
& rAttr
)
1783 if (ValidColRow(nCol
,nRow
))
1784 aCol
[nCol
].ApplyPattern( nRow
, rAttr
);
1788 void ScTable::ApplyPatternArea( SCCOL nStartCol
, SCROW nStartRow
, SCCOL nEndCol
, SCROW nEndRow
,
1789 const ScPatternAttr
& rAttr
, ScEditDataArray
* pDataArray
)
1791 if (ValidColRow(nStartCol
, nStartRow
) && ValidColRow(nEndCol
, nEndRow
))
1793 PutInOrder(nStartCol
, nEndCol
);
1794 PutInOrder(nStartRow
, nEndRow
);
1795 for (SCCOL i
= nStartCol
; i
<= nEndCol
; i
++)
1796 aCol
[i
].ApplyPatternArea(nStartRow
, nEndRow
, rAttr
, pDataArray
);
1800 void ScTable::ApplyPatternIfNumberformatIncompatible( const ScRange
& rRange
,
1801 const ScPatternAttr
& rPattern
, short nNewType
)
1803 SCCOL nEndCol
= rRange
.aEnd
.Col();
1804 for ( SCCOL nCol
= rRange
.aStart
.Col(); nCol
<= nEndCol
; nCol
++ )
1806 aCol
[nCol
].ApplyPatternIfNumberformatIncompatible( rRange
, rPattern
, nNewType
);
1812 void ScTable::ApplyStyle( SCCOL nCol
, SCROW nRow
, const ScStyleSheet
& rStyle
)
1814 if (ValidColRow(nCol
,nRow
))
1815 aCol
[nCol
].ApplyStyle( nRow
, rStyle
);
1819 void ScTable::ApplyStyleArea( SCCOL nStartCol
, SCROW nStartRow
, SCCOL nEndCol
, SCROW nEndRow
, const ScStyleSheet
& rStyle
)
1821 if (ValidColRow(nStartCol
, nStartRow
) && ValidColRow(nEndCol
, nEndRow
))
1823 PutInOrder(nStartCol
, nEndCol
);
1824 PutInOrder(nStartRow
, nEndRow
);
1825 for (SCCOL i
= nStartCol
; i
<= nEndCol
; i
++)
1826 aCol
[i
].ApplyStyleArea(nStartRow
, nEndRow
, rStyle
);
1831 void ScTable::ApplySelectionStyle(const ScStyleSheet
& rStyle
, const ScMarkData
& rMark
)
1833 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
1834 aCol
[i
].ApplySelectionStyle( rStyle
, rMark
);
1838 void ScTable::ApplySelectionLineStyle( const ScMarkData
& rMark
,
1839 const SvxBorderLine
* pLine
, BOOL bColorOnly
)
1841 if ( bColorOnly
&& !pLine
)
1844 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
1845 aCol
[i
].ApplySelectionLineStyle( rMark
, pLine
, bColorOnly
);
1849 const ScStyleSheet
* ScTable::GetStyle( SCCOL nCol
, SCROW nRow
) const
1851 if (ValidColRow(nCol
, nRow
))
1852 return aCol
[nCol
].GetStyle(nRow
);
1858 const ScStyleSheet
* ScTable::GetSelectionStyle( const ScMarkData
& rMark
, BOOL
& rFound
) const
1865 const ScStyleSheet
* pStyle
= NULL
;
1866 const ScStyleSheet
* pNewStyle
;
1868 for (SCCOL i
=0; i
<=MAXCOL
&& bEqual
; i
++)
1869 if (rMark
.HasMultiMarks(i
))
1871 pNewStyle
= aCol
[i
].GetSelectionStyle( rMark
, bColFound
);
1875 if ( !pNewStyle
|| ( pStyle
&& pNewStyle
!= pStyle
) )
1876 bEqual
= FALSE
; // unterschiedliche
1881 return bEqual
? pStyle
: NULL
;
1885 const ScStyleSheet
* ScTable::GetAreaStyle( BOOL
& rFound
, SCCOL nCol1
, SCROW nRow1
,
1886 SCCOL nCol2
, SCROW nRow2
) const
1893 const ScStyleSheet
* pStyle
= NULL
;
1894 const ScStyleSheet
* pNewStyle
;
1896 for (SCCOL i
=nCol1
; i
<=nCol2
&& bEqual
; i
++)
1898 pNewStyle
= aCol
[i
].GetAreaStyle(bColFound
, nRow1
, nRow2
);
1902 if ( !pNewStyle
|| ( pStyle
&& pNewStyle
!= pStyle
) )
1903 bEqual
= FALSE
; // unterschiedliche
1908 return bEqual
? pStyle
: NULL
;
1912 BOOL
ScTable::IsStyleSheetUsed( const ScStyleSheet
& rStyle
, BOOL bGatherAllStyles
) const
1914 BOOL bIsUsed
= FALSE
;
1916 for ( SCCOL i
=0; i
<=MAXCOL
; i
++ )
1918 if ( aCol
[i
].IsStyleSheetUsed( rStyle
, bGatherAllStyles
) )
1920 if ( !bGatherAllStyles
)
1930 void ScTable::StyleSheetChanged( const SfxStyleSheetBase
* pStyleSheet
, BOOL bRemoved
,
1932 double nPPTX
, double nPPTY
,
1933 const Fraction
& rZoomX
, const Fraction
& rZoomY
)
1935 ScFlatBoolRowSegments aUsedRows
;
1936 for (SCCOL i
= 0; i
<= MAXCOL
; ++i
)
1937 aCol
[i
].FindStyleSheet(pStyleSheet
, aUsedRows
, bRemoved
);
1940 while (nRow
<= MAXROW
)
1942 ScFlatBoolRowSegments::RangeData aData
;
1943 if (!aUsedRows
.getRangeData(nRow
, aData
))
1947 SCROW nEndRow
= aData
.mnRow2
;
1949 SetOptimalHeight(nRow
, nEndRow
, 0, pDev
, nPPTX
, nPPTY
, rZoomX
, rZoomY
, FALSE
);
1956 BOOL
ScTable::ApplyFlags( SCCOL nStartCol
, SCROW nStartRow
, SCCOL nEndCol
, SCROW nEndRow
,
1959 BOOL bChanged
= FALSE
;
1960 if (ValidColRow(nStartCol
, nStartRow
) && ValidColRow(nEndCol
, nEndRow
))
1961 for (SCCOL i
= nStartCol
; i
<= nEndCol
; i
++)
1962 bChanged
|= aCol
[i
].ApplyFlags(nStartRow
, nEndRow
, nFlags
);
1967 BOOL
ScTable::RemoveFlags( SCCOL nStartCol
, SCROW nStartRow
, SCCOL nEndCol
, SCROW nEndRow
,
1970 BOOL bChanged
= FALSE
;
1971 if (ValidColRow(nStartCol
, nStartRow
) && ValidColRow(nEndCol
, nEndRow
))
1972 for (SCCOL i
= nStartCol
; i
<= nEndCol
; i
++)
1973 bChanged
|= aCol
[i
].RemoveFlags(nStartRow
, nEndRow
, nFlags
);
1978 void ScTable::SetPattern( SCCOL nCol
, SCROW nRow
, const ScPatternAttr
& rAttr
, BOOL bPutToPool
)
1980 if (ValidColRow(nCol
,nRow
))
1981 aCol
[nCol
].SetPattern( nRow
, rAttr
, bPutToPool
);
1985 void ScTable::ApplyAttr( SCCOL nCol
, SCROW nRow
, const SfxPoolItem
& rAttr
)
1987 if (ValidColRow(nCol
,nRow
))
1988 aCol
[nCol
].ApplyAttr( nRow
, rAttr
);
1992 void ScTable::ApplySelectionCache( SfxItemPoolCache
* pCache
, const ScMarkData
& rMark
,
1993 ScEditDataArray
* pDataArray
)
1995 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
1996 aCol
[i
].ApplySelectionCache( pCache
, rMark
, pDataArray
);
2000 void ScTable::ChangeSelectionIndent( BOOL bIncrement
, const ScMarkData
& rMark
)
2002 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
2003 aCol
[i
].ChangeSelectionIndent( bIncrement
, rMark
);
2007 void ScTable::ClearSelectionItems( const USHORT
* pWhich
, const ScMarkData
& rMark
)
2009 for (SCCOL i
=0; i
<=MAXCOL
; i
++)
2010 aCol
[i
].ClearSelectionItems( pWhich
, rMark
);
2014 // Spaltenbreiten / Zeilenhoehen
2016 void ScTable::SetColWidth( SCCOL nCol
, USHORT nNewWidth
)
2018 if (VALIDCOL(nCol
) && pColWidth
)
2022 // DBG_ERROR("Spaltenbreite 0 in SetColWidth");
2023 nNewWidth
= STD_COL_WIDTH
;
2026 if ( nNewWidth
!= pColWidth
[nCol
] )
2029 InitializeNoteCaptions();
2030 ScDrawLayer
* pDrawLayer
= pDocument
->GetDrawLayer();
2032 pDrawLayer
->WidthChanged( nTab
, nCol
, ((long) nNewWidth
) - (long) pColWidth
[nCol
] );
2033 pColWidth
[nCol
] = nNewWidth
;
2037 InvalidatePageBreaks();
2042 DBG_ERROR("Falsche Spaltennummer oder keine Breiten");
2047 void ScTable::SetRowHeight( SCROW nRow
, USHORT nNewHeight
)
2049 if (VALIDROW(nRow
) && pRowHeight
)
2053 DBG_ERROR("Zeilenhoehe 0 in SetRowHeight");
2054 nNewHeight
= ScGlobal::nStdRowHeight
;
2057 USHORT nOldHeight
= pRowHeight
->GetValue(nRow
);
2058 if ( nNewHeight
!= nOldHeight
)
2061 InitializeNoteCaptions();
2062 ScDrawLayer
* pDrawLayer
= pDocument
->GetDrawLayer();
2064 pDrawLayer
->HeightChanged( nTab
, nRow
, ((long) nNewHeight
) - (long) nOldHeight
);
2065 pRowHeight
->SetValue( nRow
, nNewHeight
);
2069 InvalidatePageBreaks();
2074 DBG_ERROR("Falsche Zeilennummer oder keine Hoehen");
2079 BOOL
ScTable::SetRowHeightRange( SCROW nStartRow
, SCROW nEndRow
, USHORT nNewHeight
,
2080 double /* nPPTX */, double nPPTY
)
2082 BOOL bChanged
= FALSE
;
2083 if (VALIDROW(nStartRow
) && VALIDROW(nEndRow
) && pRowHeight
)
2086 InitializeNoteCaptions();
2089 DBG_ERROR("Zeilenhoehe 0 in SetRowHeight");
2090 nNewHeight
= ScGlobal::nStdRowHeight
;
2093 long nNewPix
= (long) ( nNewHeight
* nPPTY
);
2095 BOOL bSingle
= FALSE
; // TRUE = process every row for its own
2096 ScDrawLayer
* pDrawLayer
= pDocument
->GetDrawLayer();
2098 if (pDrawLayer
->HasObjectsInRows( nTab
, nStartRow
, nEndRow
))
2104 SCROW nRegionEndRow
;
2105 USHORT nOldHeight
= pRowHeight
->GetValue( nStartRow
, nIndex
, nRegionEndRow
);
2106 if (nNewHeight
== nOldHeight
&& nEndRow
<= nRegionEndRow
)
2107 bSingle
= FALSE
; // no difference in this range
2111 if (nEndRow
-nStartRow
< 20)
2113 // Whether new pixel size will differ from old pixel size in any row.
2114 ScCompressedArrayIterator
< SCROW
, USHORT
> aIter( *pRowHeight
,
2115 nStartRow
, nEndRow
);
2118 if (*aIter
!= nNewHeight
)
2119 bChanged
= (nNewPix
!= (long) (*aIter
* nPPTY
));
2120 } while (!bChanged
&& aIter
.NextRange());
2122 /* #i94028# #i94991# If drawing objects are involved, each row
2123 has to be changed for its own, because each call to
2124 ScDrawLayer::HeightChanged expects correct row heights
2125 above passed row in the document. Cannot use array iterator
2126 because array changes in every cycle. */
2129 for( SCROW nRow
= nStartRow
; nRow
<= nEndRow
; ++nRow
)
2131 pDrawLayer
->HeightChanged( nTab
, nRow
,
2132 ((long) nNewHeight
) - ((long) pRowHeight
->GetValue( nRow
)));
2133 pRowHeight
->SetValue( nRow
, nNewHeight
);
2137 pRowHeight
->SetValue( nStartRow
, nEndRow
, nNewHeight
);
2141 SCROW nMid
= (nStartRow
+nEndRow
) / 2;
2142 if (SetRowHeightRange( nStartRow
, nMid
, nNewHeight
, 1.0, 1.0 ))
2144 if (SetRowHeightRange( nMid
+1, nEndRow
, nNewHeight
, 1.0, 1.0 ))
2152 unsigned long nOldHeights
= pRowHeight
->SumValues( nStartRow
, nEndRow
);
2153 // FIXME: should we test for overflows?
2154 long nHeightDif
= (long) (unsigned long) nNewHeight
*
2155 (nEndRow
- nStartRow
+ 1) - nOldHeights
;
2156 pDrawLayer
->HeightChanged( nTab
, nEndRow
, nHeightDif
);
2158 // Whether new pixel size will differ from old pixel size in any row.
2159 ScCompressedArrayIterator
< SCROW
, USHORT
> aIter( *pRowHeight
,
2160 nStartRow
, nEndRow
);
2163 if (*aIter
!= nNewHeight
)
2164 bChanged
= (nNewPix
!= (long) (*aIter
* nPPTY
));
2165 } while (!bChanged
&& aIter
.NextRange());
2166 pRowHeight
->SetValue( nStartRow
, nEndRow
, nNewHeight
);
2172 InvalidatePageBreaks();
2176 DBG_ERROR("Falsche Zeilennummer oder keine Hoehen");
2183 void ScTable::SetManualHeight( SCROW nStartRow
, SCROW nEndRow
, BOOL bManual
)
2185 if (VALIDROW(nStartRow
) && VALIDROW(nEndRow
) && pRowFlags
)
2188 pRowFlags
->OrValue( nStartRow
, nEndRow
, CR_MANUALSIZE
);
2190 pRowFlags
->AndValue( nStartRow
, nEndRow
, sal::static_int_cast
<BYTE
>(~CR_MANUALSIZE
));
2194 DBG_ERROR("Falsche Zeilennummer oder keine Zeilenflags");
2199 USHORT
ScTable::GetColWidth( SCCOL nCol
)
2201 DBG_ASSERT(VALIDCOL(nCol
),"Falsche Spaltennummer");
2203 if (VALIDCOL(nCol
) && pColFlags
&& pColWidth
)
2205 if (ColHidden(nCol
))
2208 return pColWidth
[nCol
];
2211 return (USHORT
) STD_COL_WIDTH
;
2215 USHORT
ScTable::GetOriginalWidth( SCCOL nCol
) const // immer die eingestellte
2217 DBG_ASSERT(VALIDCOL(nCol
),"Falsche Spaltennummer");
2219 if (VALIDCOL(nCol
) && pColWidth
)
2220 return pColWidth
[nCol
];
2222 return (USHORT
) STD_COL_WIDTH
;
2226 USHORT
ScTable::GetCommonWidth( SCCOL nEndCol
)
2228 // get the width that is used in the largest continuous column range (up to nEndCol)
2230 if ( !ValidCol(nEndCol
) )
2232 DBG_ERROR("wrong column");
2236 USHORT nMaxWidth
= 0;
2237 USHORT nMaxCount
= 0;
2238 SCCOL nRangeStart
= 0;
2239 while ( nRangeStart
<= nEndCol
)
2241 // skip hidden columns
2242 while ( nRangeStart
<= nEndCol
&& ColHidden(nRangeStart
) )
2244 if ( nRangeStart
<= nEndCol
)
2246 USHORT nThisCount
= 0;
2247 USHORT nThisWidth
= pColWidth
[nRangeStart
];
2248 SCCOL nRangeEnd
= nRangeStart
;
2249 while ( nRangeEnd
<= nEndCol
&& pColWidth
[nRangeEnd
] == nThisWidth
)
2254 // skip hidden columns
2255 while ( nRangeEnd
<= nEndCol
&& ColHidden(nRangeEnd
) )
2259 if ( nThisCount
> nMaxCount
)
2261 nMaxCount
= nThisCount
;
2262 nMaxWidth
= nThisWidth
;
2265 nRangeStart
= nRangeEnd
; // next range
2273 USHORT
ScTable::GetRowHeight( SCROW nRow
)
2275 DBG_ASSERT(VALIDROW(nRow
),"Falsche Zeilennummer");
2277 if (VALIDROW(nRow
) && pRowHeight
)
2279 if (RowHidden(nRow
))
2282 return pRowHeight
->GetValue(nRow
);
2285 return (USHORT
) ScGlobal::nStdRowHeight
;
2289 ULONG
ScTable::GetRowHeight( SCROW nStartRow
, SCROW nEndRow
)
2291 DBG_ASSERT(VALIDROW(nStartRow
) && VALIDROW(nEndRow
),"Falsche Zeilennummer");
2293 if (VALIDROW(nStartRow
) && VALIDROW(nEndRow
) && pRowHeight
)
2296 SCROW nRow
= nStartRow
;
2297 while (nRow
<= nEndRow
)
2299 SCROW nLastRow
= -1;
2300 if (!RowHidden(nRow
, nLastRow
))
2302 if (nLastRow
> nEndRow
)
2304 nHeight
+= pRowFlags
->SumCoupledArrayForCondition(nRow
, nLastRow
, 0, 0, *pRowHeight
);
2306 nRow
= nLastRow
+ 1;
2311 return (ULONG
) ((nEndRow
- nStartRow
+ 1) * ScGlobal::nStdRowHeight
);
2315 ULONG
ScTable::GetScaledRowHeight( SCROW nStartRow
, SCROW nEndRow
, double fScale
)
2317 DBG_ASSERT(VALIDROW(nStartRow
) && VALIDROW(nEndRow
),"Falsche Zeilennummer");
2319 if (VALIDROW(nStartRow
) && VALIDROW(nEndRow
) && pRowHeight
)
2322 SCROW nRow
= nStartRow
;
2323 while (nRow
<= nEndRow
)
2325 SCROW nLastRow
= -1;
2326 if (!RowHidden(nRow
, nLastRow
))
2328 if (nLastRow
> nEndRow
)
2330 nHeight
+= pRowFlags
->SumScaledCoupledArrayForCondition(
2331 nRow
, nLastRow
, 0, 0, *pRowHeight
, fScale
);
2333 nRow
= nLastRow
+ 1;
2338 return (ULONG
) ((nEndRow
- nStartRow
+ 1) * ScGlobal::nStdRowHeight
* fScale
);
2342 USHORT
ScTable::GetOriginalHeight( SCROW nRow
) const // non-0 even if hidden
2344 DBG_ASSERT(VALIDROW(nRow
),"wrong row number");
2346 if (VALIDROW(nRow
) && pRowHeight
)
2347 return pRowHeight
->GetValue(nRow
);
2349 return (USHORT
) ScGlobal::nStdRowHeight
;
2353 // Spalten-/Zeilen-Flags
2356 SCROW
ScTable::GetHiddenRowCount( SCROW nRow
)
2358 if (!ValidRow(nRow
))
2361 SCROW nLastRow
= -1;
2362 if (!RowHidden(nRow
, nLastRow
) || !ValidRow(nLastRow
))
2365 return nLastRow
- nRow
+ 1;
2369 //! ShowRows / DBShowRows zusammenfassen
2371 void ScTable::ShowCol(SCCOL nCol
, BOOL bShow
)
2375 bool bWasVis
= !ColHidden(nCol
);
2376 if (bWasVis
!= bShow
)
2379 InitializeNoteCaptions();
2380 ScDrawLayer
* pDrawLayer
= pDocument
->GetDrawLayer();
2384 pDrawLayer
->WidthChanged( nTab
, nCol
, (long) pColWidth
[nCol
] );
2386 pDrawLayer
->WidthChanged( nTab
, nCol
, -(long) pColWidth
[nCol
] );
2389 SetColHidden(nCol
, nCol
, !bShow
);
2394 ScChartListenerCollection
* pCharts
= pDocument
->GetChartListenerCollection();
2396 pCharts
->SetRangeDirty(ScRange( nCol
, 0, nTab
, nCol
, MAXROW
, nTab
));
2401 DBG_ERROR("Falsche Spaltennummer oder keine Flags");
2406 void ScTable::ShowRow(SCROW nRow
, BOOL bShow
)
2408 if (VALIDROW(nRow
) && pRowFlags
)
2410 bool bWasVis
= !RowHidden(nRow
);
2411 if (bWasVis
!= bShow
)
2414 InitializeNoteCaptions();
2415 ScDrawLayer
* pDrawLayer
= pDocument
->GetDrawLayer();
2419 pDrawLayer
->HeightChanged( nTab
, nRow
, (long) pRowHeight
->GetValue(nRow
) );
2421 pDrawLayer
->HeightChanged( nTab
, nRow
, -(long) pRowHeight
->GetValue(nRow
) );
2424 SetRowHidden(nRow
, nRow
, !bShow
);
2426 SetRowFiltered(nRow
, nRow
, false);
2431 ScChartListenerCollection
* pCharts
= pDocument
->GetChartListenerCollection();
2433 pCharts
->SetRangeDirty(ScRange( 0, nRow
, nTab
, MAXCOL
, nRow
, nTab
));
2435 InvalidatePageBreaks();
2440 DBG_ERROR("Falsche Zeilennummer oder keine Flags");
2445 void ScTable::DBShowRow(SCROW nRow
, BOOL bShow
)
2447 if (VALIDROW(nRow
) && pRowFlags
)
2449 bool bWasVis
= !RowHidden(nRow
);
2451 InitializeNoteCaptions();
2452 if (bWasVis
!= bShow
)
2454 ScDrawLayer
* pDrawLayer
= pDocument
->GetDrawLayer();
2458 pDrawLayer
->HeightChanged( nTab
, nRow
, (long) pRowHeight
->GetValue(nRow
) );
2460 pDrawLayer
->HeightChanged( nTab
, nRow
, -(long) pRowHeight
->GetValue(nRow
) );
2464 // Filter-Flag immer setzen, auch wenn Hidden unveraendert
2466 SetRowHidden(nRow
, nRow
, !bShow
);
2467 SetRowFiltered(nRow
, nRow
, !bShow
);
2472 if (bWasVis
!= bShow
)
2474 ScChartListenerCollection
* pCharts
= pDocument
->GetChartListenerCollection();
2476 pCharts
->SetRangeDirty(ScRange( 0, nRow
, nTab
, MAXCOL
, nRow
, nTab
));
2479 UpdateOutlineRow( nRow
, nRow
, bShow
);
2481 InvalidatePageBreaks();
2486 DBG_ERROR("Falsche Zeilennummer oder keine Flags");
2491 void ScTable::DBShowRows(SCROW nRow1
, SCROW nRow2
, BOOL bShow
)
2493 SCROW nStartRow
= nRow1
;
2495 InitializeNoteCaptions();
2496 while (nStartRow
<= nRow2
)
2499 bool bWasVis
= !RowHidden(nStartRow
, nEndRow
);
2500 if (nEndRow
> nRow2
)
2503 BOOL bChanged
= ( bWasVis
!= bShow
);
2506 ScDrawLayer
* pDrawLayer
= pDocument
->GetDrawLayer();
2509 long nHeight
= (long) pRowHeight
->SumValues( nStartRow
, nEndRow
);
2511 pDrawLayer
->HeightChanged( nTab
, nStartRow
, nHeight
);
2513 pDrawLayer
->HeightChanged( nTab
, nStartRow
, -nHeight
);
2517 SetRowHidden(nStartRow
, nEndRow
, !bShow
);
2518 SetRowFiltered(nStartRow
, nEndRow
, !bShow
);
2522 ScChartListenerCollection
* pCharts
= pDocument
->GetChartListenerCollection();
2524 pCharts
->SetRangeDirty(ScRange( 0, nStartRow
, nTab
, MAXCOL
, nEndRow
, nTab
));
2527 nStartRow
= nEndRow
+ 1;
2530 // #i12341# For Show/Hide rows, the outlines are updated separately from the outside.
2531 // For filtering, the changes aren't visible to the caller, so UpdateOutlineRow has
2534 UpdateOutlineRow( nRow1
, nRow2
, bShow
);
2541 void ScTable::ShowRows(SCROW nRow1
, SCROW nRow2
, BOOL bShow
)
2543 SCROW nStartRow
= nRow1
;
2545 InitializeNoteCaptions();
2546 while (nStartRow
<= nRow2
)
2549 bool bWasVis
= !RowHidden(nStartRow
, nEndRow
);
2550 if (nEndRow
> nRow2
)
2553 BOOL bChanged
= ( bWasVis
!= bShow
);
2556 ScDrawLayer
* pDrawLayer
= pDocument
->GetDrawLayer();
2559 long nHeight
= (long) pRowHeight
->SumValues( nStartRow
, nEndRow
);
2561 pDrawLayer
->HeightChanged( nTab
, nStartRow
, nHeight
);
2563 pDrawLayer
->HeightChanged( nTab
, nStartRow
, -nHeight
);
2567 SetRowHidden(nStartRow
, nEndRow
, !bShow
);
2569 SetRowFiltered(nStartRow
, nEndRow
, false);
2573 ScChartListenerCollection
* pCharts
= pDocument
->GetChartListenerCollection();
2575 pCharts
->SetRangeDirty(ScRange( 0, nStartRow
, nTab
, MAXCOL
, nEndRow
, nTab
));
2577 InvalidatePageBreaks();
2580 nStartRow
= nEndRow
+ 1;
2587 void ScTable::SetColFlags( SCCOL nCol
, BYTE nNewFlags
)
2589 if (VALIDCOL(nCol
) && pColFlags
)
2590 pColFlags
[nCol
] = nNewFlags
;
2593 DBG_ERROR("Falsche Spaltennummer oder keine Flags");
2598 void ScTable::SetRowFlags( SCROW nRow
, BYTE nNewFlags
)
2600 if (VALIDROW(nRow
) && pRowFlags
)
2601 pRowFlags
->SetValue( nRow
, nNewFlags
);
2604 DBG_ERROR("Falsche Zeilennummer oder keine Flags");
2609 void ScTable::SetRowFlags( SCROW nStartRow
, SCROW nEndRow
, BYTE nNewFlags
)
2611 if (VALIDROW(nStartRow
) && VALIDROW(nEndRow
) && pRowFlags
)
2612 pRowFlags
->SetValue( nStartRow
, nEndRow
, nNewFlags
);
2615 DBG_ERROR("Falsche Zeilennummer(n) oder keine Flags");
2620 BYTE
ScTable::GetColFlags( SCCOL nCol
) const
2622 if (VALIDCOL(nCol
) && pColFlags
)
2623 return pColFlags
[nCol
];
2629 BYTE
ScTable::GetRowFlags( SCROW nRow
) const
2631 if (VALIDROW(nRow
) && pRowFlags
)
2632 return pRowFlags
->GetValue(nRow
);
2638 SCROW
ScTable::GetLastFlaggedRow() const
2643 SCROW nLastFound
= pRowFlags
->GetLastAnyBitAccess( 0, sal::static_int_cast
<BYTE
>(CR_ALL
) );
2644 return ValidRow(nLastFound
) ? nLastFound
: 0;
2648 SCCOL
ScTable::GetLastChangedCol() const
2653 SCCOL nLastFound
= 0;
2654 for (SCCOL nCol
= 1; nCol
<= MAXCOL
; nCol
++)
2655 if ((pColFlags
[nCol
] & CR_ALL
) || (pColWidth
[nCol
] != STD_COL_WIDTH
))
2662 SCROW
ScTable::GetLastChangedRow() const
2667 SCROW nLastFlags
= pRowFlags
->GetLastAnyBitAccess( 0, sal::static_int_cast
<BYTE
>(CR_ALL
) );
2668 if (!ValidRow(nLastFlags
))
2671 SCROW nLastHeight
= pRowHeight
->GetLastUnequalAccess( 0, ScGlobal::nStdRowHeight
);
2672 if (!ValidRow(nLastHeight
))
2675 return std::max( nLastFlags
, nLastHeight
);
2679 BOOL
ScTable::UpdateOutlineCol( SCCOL nStartCol
, SCCOL nEndCol
, BOOL bShow
)
2681 if (pOutlineTable
&& pColFlags
)
2683 ScBitMaskCompressedArray
< SCCOLROW
, BYTE
> aArray( MAXCOL
, pColFlags
, MAXCOLCOUNT
);
2684 return pOutlineTable
->GetColArray()->ManualAction( nStartCol
, nEndCol
, bShow
, *this, true );
2691 BOOL
ScTable::UpdateOutlineRow( SCROW nStartRow
, SCROW nEndRow
, BOOL bShow
)
2693 if (pOutlineTable
&& pRowFlags
)
2694 return pOutlineTable
->GetRowArray()->ManualAction( nStartRow
, nEndRow
, bShow
, *this, false );
2700 void ScTable::ExtendHidden( SCCOL
& rX1
, SCROW
& rY1
, SCCOL
& rX2
, SCROW
& rY2
)
2702 // Column-wise expansion
2704 while (rX1
> 0 && ColHidden(rX1
-1))
2707 while (rX2
< MAXCOL
&& ColHidden(rX2
+1))
2710 // Row-wise expansion
2714 ScFlatBoolRowSegments::RangeData aData
;
2715 if (mpHiddenRows
->getRangeData(rY1
-1, aData
) && aData
.mbValue
)
2717 SCROW nStartRow
= aData
.mnRow1
;
2718 if (ValidRow(nStartRow
))
2725 if (RowHidden(rY2
+1, nEndRow
) && ValidRow(nEndRow
))
2731 void ScTable::StripHidden( SCCOL
& rX1
, SCROW
& rY1
, SCCOL
& rX2
, SCROW
& rY2
)
2733 while ( rX2
>rX1
&& ColHidden(rX2
) )
2735 while ( rX2
>rX1
&& ColHidden(rX1
) )
2740 ScFlatBoolRowSegments::RangeData aData
;
2741 if (mpHiddenRows
->getRangeData(rY2
, aData
) && aData
.mbValue
)
2743 SCROW nStartRow
= aData
.mnRow1
;
2744 if (ValidRow(nStartRow
) && nStartRow
>= rY1
)
2752 if (RowHidden(rY1
, nEndRow
) && ValidRow(nEndRow
) && nEndRow
<= rY2
)
2760 template< typename T
>
2761 short DiffSign( T a
, T b
)
2768 void ScTable::DoAutoOutline( SCCOL nStartCol
, SCROW nStartRow
, SCCOL nEndCol
, SCROW nEndRow
)
2770 BOOL bSizeChanged
= FALSE
;
2771 BOOL bMissed
= FALSE
;
2777 ScOutlineArray
* pArray
;
2780 /* ScPatternAttr aBoldPattern( pDocument->GetPool() ); //! spezielle Format-Vorlage
2781 aBoldPattern.GetItemSet().Put( SvxWeightItem( WEIGHT_BOLD ) );
2784 StartOutlineTable();
2788 SCROW nCount
= nEndRow
-nStartRow
+1;
2789 BOOL
* pUsed
= new BOOL
[nCount
];
2790 for (i
=0; i
<nCount
; i
++)
2792 for (nCol
=nStartCol
; nCol
<=nEndCol
; nCol
++)
2793 if (!aCol
[nCol
].IsEmptyData())
2794 aCol
[nCol
].FindUsed( nStartRow
, nEndRow
, pUsed
);
2796 pArray
= pOutlineTable
->GetRowArray();
2797 for (nRow
=nStartRow
; nRow
<=nEndRow
; nRow
++)
2798 if (pUsed
[nRow
-nStartRow
])
2801 for (nCol
=nStartCol
; nCol
<=nEndCol
&& !bFound
; nCol
++)
2802 if (!aCol
[nCol
].IsEmptyData())
2804 pCell
= aCol
[nCol
].GetCell( nRow
);
2806 if ( pCell
->GetCellType() == CELLTYPE_FORMULA
)
2807 if (((ScFormulaCell
*)pCell
)->HasRefListExpressibleAsOneReference( aRef
))
2808 if ( aRef
.aStart
.Col() == nCol
&& aRef
.aEnd
.Col() == nCol
&&
2809 aRef
.aStart
.Tab() == nTab
&& aRef
.aEnd
.Tab() == nTab
&&
2810 DiffSign( aRef
.aStart
.Row(), nRow
) ==
2811 DiffSign( aRef
.aEnd
.Row(), nRow
) )
2813 if (pArray
->Insert( aRef
.aStart
.Row(), aRef
.aEnd
.Row(), bSizeChanged
))
2815 // ApplyPatternArea( nStartCol, nRow, nEndCol, nRow, aBoldPattern );
2828 pArray
= pOutlineTable
->GetColArray();
2829 for (nCol
=nStartCol
; nCol
<=nEndCol
; nCol
++)
2831 if (!aCol
[nCol
].IsEmptyData())
2834 ScColumnIterator
aIter( &aCol
[nCol
], nStartRow
, nEndRow
);
2835 while ( aIter
.Next( nRow
, pCell
) && !bFound
)
2837 if ( pCell
->GetCellType() == CELLTYPE_FORMULA
)
2838 if (((ScFormulaCell
*)pCell
)->HasRefListExpressibleAsOneReference( aRef
))
2839 if ( aRef
.aStart
.Row() == nRow
&& aRef
.aEnd
.Row() == nRow
&&
2840 aRef
.aStart
.Tab() == nTab
&& aRef
.aEnd
.Tab() == nTab
&&
2841 DiffSign( aRef
.aStart
.Col(), nCol
) ==
2842 DiffSign( aRef
.aEnd
.Col(), nCol
) )
2844 if (pArray
->Insert( aRef
.aStart
.Col(), aRef
.aEnd
.Col(), bSizeChanged
))
2846 // ApplyPatternArea( nCol, nStartRow, nCol, nEndRow, aBoldPattern );
2857 // CopyData - fuer Query in anderen Bereich
2859 void ScTable::CopyData( SCCOL nStartCol
, SCROW nStartRow
, SCCOL nEndCol
, SCROW nEndRow
,
2860 SCCOL nDestCol
, SCROW nDestRow
, SCTAB nDestTab
)
2862 //! wenn fuer mehrere Zeilen benutzt, nach Spalten optimieren!
2864 ScAddress
aSrc( nStartCol
, nStartRow
, nTab
);
2865 ScAddress
aDest( nDestCol
, nDestRow
, nDestTab
);
2866 ScRange
aRange( aSrc
, aDest
);
2867 BOOL bThisTab
= ( nDestTab
== nTab
);
2868 SCROW nDestY
= nDestRow
;
2869 for (SCROW nRow
=nStartRow
; nRow
<=nEndRow
; nRow
++)
2871 aSrc
.SetRow( nRow
);
2872 aDest
.SetRow( nDestY
);
2873 SCCOL nDestX
= nDestCol
;
2874 for (SCCOL nCol
=nStartCol
; nCol
<=nEndCol
; nCol
++)
2876 aSrc
.SetCol( nCol
);
2877 aDest
.SetCol( nDestX
);
2878 ScBaseCell
* pCell
= GetCell( nCol
, nRow
);
2881 pCell
= pCell
->CloneWithoutNote( *pDocument
);
2882 if (pCell
->GetCellType() == CELLTYPE_FORMULA
)
2884 ((ScFormulaCell
*)pCell
)->UpdateReference( URM_COPY
, aRange
,
2885 ((SCsCOL
) nDestCol
) - ((SCsCOL
) nStartCol
),
2886 ((SCsROW
) nDestRow
) - ((SCsROW
) nStartRow
),
2887 ((SCsTAB
) nDestTab
) - ((SCsTAB
) nTab
) );
2888 ((ScFormulaCell
*)pCell
)->aPos
= aDest
;
2893 PutCell( nDestX
, nDestY
, pCell
);
2894 SetPattern( nDestX
, nDestY
, *GetPattern( nCol
, nRow
), TRUE
);
2898 pDocument
->PutCell( aDest
, pCell
);
2899 pDocument
->SetPattern( aDest
, *GetPattern( nCol
, nRow
), TRUE
);
2909 BOOL
ScTable::RefVisible(ScFormulaCell
* pCell
)
2913 if (pCell
->HasOneReference(aRef
))
2915 if (aRef
.aStart
.Col()==aRef
.aEnd
.Col() && aRef
.aStart
.Tab()==aRef
.aEnd
.Tab())
2918 if (!RowFiltered(aRef
.aStart
.Row(), NULL
, &nEndRow
))
2919 // row not filtered.
2920 nEndRow
= ::std::numeric_limits
<SCROW
>::max();
2922 if (!ValidRow(nEndRow
) || nEndRow
< aRef
.aEnd
.Row())
2923 return TRUE
; // at least partly visible
2924 return FALSE
; // completely invisible
2928 return TRUE
; // irgendwie anders
2932 void ScTable::GetUpperCellString(SCCOL nCol
, SCROW nRow
, String
& rStr
)
2934 GetInputString(nCol
, nRow
, rStr
);
2935 rStr
.EraseTrailingChars();
2936 rStr
.EraseLeadingChars();
2937 ScGlobal::pCharClass
->toUpper(rStr
);
2941 // Berechnen der Groesse der Tabelle und setzen der Groesse an der DrawPage
2943 void ScTable::SetDrawPageSize(bool bResetStreamValid
)
2945 ScDrawLayer
* pDrawLayer
= pDocument
->GetDrawLayer();
2948 long x
= GetColOffset( MAXCOL
+ 1 );
2949 long y
= GetRowOffset( MAXROW
+ 1 );
2950 x
= (long) ((double) x
* HMM_PER_TWIPS
);
2951 y
= (long) ((double) y
* HMM_PER_TWIPS
);
2953 if ( IsLayoutRTL() ) // IsNegativePage
2956 pDrawLayer
->SetPageSize( static_cast<sal_uInt16
>(nTab
), Size( x
, y
) );
2959 // #i102616# actions that modify the draw page size count as sheet modification
2960 // (exception: InitDrawLayer)
2961 if (bResetStreamValid
&& IsStreamValid())
2962 SetStreamValid(FALSE
);
2966 ULONG
ScTable::GetRowOffset( SCROW nRow
)
2969 if ( pRowFlags
&& pRowHeight
)
2974 return GetRowHeight(0);
2976 n
= GetTotalRowHeight(0, nRow
-1);
2978 if (n
== ::std::numeric_limits
<unsigned long>::max())
2979 DBG_ERRORFILE("ScTable::GetRowOffset: row heights overflow");
2984 DBG_ERROR("GetRowOffset: Daten fehlen");
2989 SCROW
ScTable::GetRowForHeight(ULONG nHeight
)
2991 sal_uInt32 nSum
= 0;
2993 ScFlatBoolRowSegments::RangeData aData
;
2994 for (SCROW nRow
= 0; nRow
<= MAXROW
; ++nRow
)
2996 if (!mpHiddenRows
->getRangeData(nRow
, aData
))
3001 nRow
= aData
.mnRow2
;
3005 sal_uInt32 nNew
= pRowHeight
->GetValue(nRow
);
3009 return nRow
< MAXROW
? nRow
+ 1 : MAXROW
;
3016 ULONG
ScTable::GetColOffset( SCCOL nCol
)
3022 for( i
= 0; i
< nCol
; i
++ )
3028 DBG_ERROR("GetColumnOffset: Daten fehlen");