summaryrefslogtreecommitdiff
path: root/sc/source/core/data/table2.cxx
diff options
context:
space:
mode:
Diffstat (limited to 'sc/source/core/data/table2.cxx')
-rw-r--r--sc/source/core/data/table2.cxx77
1 files changed, 64 insertions, 13 deletions
diff --git a/sc/source/core/data/table2.cxx b/sc/source/core/data/table2.cxx
index e3f04f95e35c..86dd93da383b 100644
--- a/sc/source/core/data/table2.cxx
+++ b/sc/source/core/data/table2.cxx
@@ -774,6 +774,9 @@ void ScTable::CopyToTable(SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2,
pDestTab->pRowFlags->CopyFrom(*pRowFlags, nRow1, nRow2);
// Hidden flags.
+ // #i116164# Collect information first, then apply the changes,
+ // so RowHidden doesn't rebuild the tree for each row range.
+ std::vector<ScShowRowsEntry> aEntries;
for (SCROW i = nRow1; i <= nRow2; ++i)
{
SCROW nThisLastRow, nDestLastRow;
@@ -786,7 +789,8 @@ void ScTable::CopyToTable(SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2,
// the last row shouldn't exceed the upper bound the caller specified.
nLastRow = nRow2;
- pDestTab->SetRowHidden(i, nLastRow, bThisHidden);
+ //pDestTab->SetRowHidden(i, nLastRow, bThisHidden);
+ aEntries.push_back(ScShowRowsEntry(i, nLastRow, bThisHidden));
bool bThisHiddenChange = (bThisHidden != bDestHidden);
if (bThisHiddenChange && pCharts)
@@ -802,6 +806,19 @@ void ScTable::CopyToTable(SCCOL nCol1, SCROW nRow1, SCCOL nCol2, SCROW nRow2,
i = nLastRow;
}
+ std::vector<ScShowRowsEntry>::const_iterator aEnd = aEntries.end();
+ std::vector<ScShowRowsEntry>::const_iterator aIter = aEntries.begin();
+ if ( aIter != aEnd )
+ {
+ pDestTab->mpHiddenRows->setInsertFromBack(true); // important for undo document
+ while (aIter != aEnd)
+ {
+ pDestTab->SetRowHidden(aIter->mnRow1, aIter->mnRow2, !aIter->mbShow);
+ ++aIter;
+ }
+ pDestTab->mpHiddenRows->setInsertFromBack(false);
+ }
+
// Filtered flags.
for (SCROW i = nRow1; i <= nRow2; ++i)
{
@@ -2628,10 +2645,10 @@ void ScTable::DBShowRow(SCROW nRow, bool bShow)
}
-void ScTable::DBShowRows(SCROW nRow1, SCROW nRow2, bool bShow)
+void ScTable::DBShowRows(SCROW nRow1, SCROW nRow2, bool bShow, bool bSetFlags)
{
+ // #i116164# IncRecalcLevel/DecRecalcLevel is in ScTable::Query
SCROW nStartRow = nRow1;
- IncRecalcLevel();
InitializeNoteCaptions();
while (nStartRow <= nRow2)
{
@@ -2641,7 +2658,7 @@ void ScTable::DBShowRows(SCROW nRow1, SCROW nRow2, bool bShow)
nEndRow = nRow2;
BOOL bChanged = ( bWasVis != bShow );
- if ( bChanged )
+ if ( bChanged && bSetFlags )
{
ScDrawLayer* pDrawLayer = pDocument->GetDrawLayer();
if (pDrawLayer)
@@ -2654,8 +2671,13 @@ void ScTable::DBShowRows(SCROW nRow1, SCROW nRow2, bool bShow)
}
}
- SetRowHidden(nStartRow, nEndRow, !bShow);
- SetRowFiltered(nStartRow, nEndRow, !bShow);
+ // #i116164# Directly modify the flags only if there are drawing objects within the area.
+ // Otherwise, all modifications are made together in ScTable::Query, so the tree isn't constantly rebuilt.
+ if ( bSetFlags )
+ {
+ SetRowHidden(nStartRow, nEndRow, !bShow);
+ SetRowFiltered(nStartRow, nEndRow, !bShow);
+ }
if ( bChanged )
{
@@ -2672,8 +2694,6 @@ void ScTable::DBShowRows(SCROW nRow1, SCROW nRow2, bool bShow)
// to be done here.
if (pOutlineTable)
UpdateOutlineRow( nRow1, nRow2, bShow );
-
- DecRecalcLevel();
}
@@ -2682,6 +2702,14 @@ void ScTable::ShowRows(SCROW nRow1, SCROW nRow2, bool bShow)
SCROW nStartRow = nRow1;
IncRecalcLevel();
InitializeNoteCaptions();
+
+ // #i116164# if there are no drawing objects within the row range, a single HeightChanged call is enough
+ ScDrawLayer* pDrawLayer = pDocument->GetDrawLayer();
+ bool bHasObjects = pDrawLayer && pDrawLayer->HasObjectsInRows( nTab, nRow1, nRow2, false );
+ long nOldHeight = 0;
+ if ( pDrawLayer && !bHasObjects )
+ nOldHeight = static_cast<long>(GetRowHeight(nRow1, nRow2));
+
while (nStartRow <= nRow2)
{
SCROW nEndRow = -1;
@@ -2690,9 +2718,8 @@ void ScTable::ShowRows(SCROW nRow1, SCROW nRow2, bool bShow)
nEndRow = nRow2;
BOOL bChanged = ( bWasVis != bShow );
- if ( bChanged )
+ if ( bChanged && bHasObjects )
{
- ScDrawLayer* pDrawLayer = pDocument->GetDrawLayer();
if (pDrawLayer)
{
long nHeight = static_cast<long>(mpRowHeights->getSumValue(nStartRow, nEndRow));
@@ -2703,9 +2730,14 @@ void ScTable::ShowRows(SCROW nRow1, SCROW nRow2, bool bShow)
}
}
- SetRowHidden(nStartRow, nEndRow, !bShow);
- if (bShow)
- SetRowFiltered(nStartRow, nEndRow, false);
+ // #i116164# Directly modify the flags only if there are drawing objects within the area.
+ // Otherwise, all rows are modified together after the loop, so the tree isn't constantly rebuilt.
+ if ( bHasObjects )
+ {
+ SetRowHidden(nStartRow, nEndRow, !bShow);
+ if (bShow)
+ SetRowFiltered(nStartRow, nEndRow, false);
+ }
if ( bChanged )
{
@@ -2718,6 +2750,25 @@ void ScTable::ShowRows(SCROW nRow1, SCROW nRow2, bool bShow)
nStartRow = nEndRow + 1;
}
+
+ if ( !bHasObjects )
+ {
+ // #i116164# set the flags for the whole range at once
+ SetRowHidden(nRow1, nRow2, !bShow);
+ if (bShow)
+ SetRowFiltered(nRow1, nRow2, false);
+
+ if ( pDrawLayer )
+ {
+ // if there are no objects in the range, a single HeightChanged call is enough
+ long nNewHeight = 0;
+ if ( bShow )
+ nNewHeight = static_cast<long>(GetRowHeight(nRow1, nRow2));
+ if ( nNewHeight != nOldHeight )
+ pDrawLayer->HeightChanged( nTab, nRow1, nNewHeight - nOldHeight );
+ }
+ }
+
DecRecalcLevel();
}