diff options
Diffstat (limited to 'sc/source/core/data/table3.cxx')
-rw-r--r-- | sc/source/core/data/table3.cxx | 69 |
1 files changed, 67 insertions, 2 deletions
diff --git a/sc/source/core/data/table3.cxx b/sc/source/core/data/table3.cxx index bd6a2c92c442..8828d8ab2449 100644 --- a/sc/source/core/data/table3.cxx +++ b/sc/source/core/data/table3.cxx @@ -59,6 +59,8 @@ #include "cellform.hxx" #include "postit.hxx" #include "queryparam.hxx" +#include "segmenttree.hxx" +#include "drwlayer.hxx" #include <vector> @@ -1489,6 +1491,14 @@ SCSIZE ScTable::Query(ScQueryParam& rParamOrg, BOOL bKeepSub) aParam.nDestCol, aParam.nDestRow, aParam.nDestTab ); } + if (aParam.bInplace) + IncRecalcLevel(); // #i116164# once for all entries + + // #i116164# If there are no drawing objects within the area, call SetRowHidden/SetRowFiltered for all rows at the end + std::vector<ScShowRowsEntry> aEntries; + ScDrawLayer* pDrawLayer = pDocument->GetDrawLayer(); + bool bHasObjects = pDrawLayer && pDrawLayer->HasObjectsInRows( nTab, aParam.nRow1 + nHeader, aParam.nRow2, false ); + for (SCROW j=aParam.nRow1 + nHeader; j<=aParam.nRow2; j++) { BOOL bResult; // Filterergebnis @@ -1544,7 +1554,11 @@ SCSIZE ScTable::Query(ScQueryParam& rParamOrg, BOOL bKeepSub) else { if (bStarted) - DBShowRows(nOldStart,nOldEnd, bOldResult); + { + DBShowRows(nOldStart,nOldEnd, bOldResult, bHasObjects); + if (!bHasObjects) + aEntries.push_back(ScShowRowsEntry(nOldStart, nOldEnd, bOldResult)); + } nOldStart = nOldEnd = j; bOldResult = bResult; } @@ -1563,7 +1577,58 @@ SCSIZE ScTable::Query(ScQueryParam& rParamOrg, BOOL bKeepSub) } if (aParam.bInplace && bStarted) - DBShowRows(nOldStart,nOldEnd, bOldResult); + { + DBShowRows(nOldStart,nOldEnd, bOldResult, bHasObjects); + if (!bHasObjects) + aEntries.push_back(ScShowRowsEntry(nOldStart, nOldEnd, bOldResult)); + } + + // #i116164# execute the collected SetRowHidden/SetRowFiltered calls + if (!bHasObjects) + { + std::vector<ScShowRowsEntry>::const_iterator aEnd = aEntries.end(); + std::vector<ScShowRowsEntry>::const_iterator aIter = aEntries.begin(); + if ( aIter != aEnd ) + { + // do only one HeightChanged call with the final difference in heights + long nOldHeight = 0; + if ( pDrawLayer ) + nOldHeight = static_cast<long>(GetRowHeight(aParam.nRow1 + nHeader, aParam.nRow2)); + + // clear the range first instead of many changes in the middle of the filled array + SetRowHidden(aParam.nRow1 + nHeader, aParam.nRow2, false); + SetRowFiltered(aParam.nRow1 + nHeader, aParam.nRow2, false); + + // insert from back, in case the filter range is large + mpHiddenRows->setInsertFromBack(true); + mpFilteredRows->setInsertFromBack(true); + + while (aIter != aEnd) + { + if (!aIter->mbShow) + { + SCROW nStartRow = aIter->mnRow1; + SCROW nEndRow = aIter->mnRow2; + SetRowHidden(nStartRow, nEndRow, true); + SetRowFiltered(nStartRow, nEndRow, true); + } + ++aIter; + } + + mpHiddenRows->setInsertFromBack(false); + mpFilteredRows->setInsertFromBack(false); + + if ( pDrawLayer ) + { + // if there are no objects in the filtered range, a single HeightChanged call is enough + long nNewHeight = static_cast<long>(GetRowHeight(aParam.nRow1 + nHeader, aParam.nRow2)); + pDrawLayer->HeightChanged( nTab, aParam.nRow1 + nHeader, nNewHeight - nOldHeight ); + } + } + } + + if (aParam.bInplace) + DecRecalcLevel(); delete[] pSpecial; |