summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEike Rathke <erack@redhat.com>2018-07-04 20:43:34 +0200
committerEike Rathke <erack@redhat.com>2018-07-05 01:51:41 +0200
commit7d0426a26f59ecf19a5e58b1554af884ddc56948 (patch)
tree7770a0a9ece643ff0dfd7c873fa731daaf515aaa
parent07c5fdacc8e760809f0f6bfca37a7ce66d3b3d03 (diff)
Limit GetNextPos() loops to range, if available, tdf#68290 follow-up
It's unnecessary to check all columns if there was a range marked anyway. Also use GetPrintArea() only for bUnprotected and enlarge the result a bit to cover the case where a protected form may be empty but not have vidsual indications either. Also adding nMoveY to nCol was nonsense all the time already, what was actually meant is to add the direction of movement. Worked by chance because nMoveY was always +1/-1. Change-Id: Ic1175a607a1169f3ef0e28d0f3a91f8c526314f4 Reviewed-on: https://gerrit.libreoffice.org/56966 Reviewed-by: Eike Rathke <erack@redhat.com> Tested-by: Jenkins (cherry picked from commit 7903fa04d2d2233fe193eef7dfd3c203430edcc6) Reviewed-on: https://gerrit.libreoffice.org/56977
-rw-r--r--sc/source/core/data/table1.cxx75
1 files changed, 58 insertions, 17 deletions
diff --git a/sc/source/core/data/table1.cxx b/sc/source/core/data/table1.cxx
index 65b1b288fce7..9b672f67b054 100644
--- a/sc/source/core/data/table1.cxx
+++ b/sc/source/core/data/table1.cxx
@@ -1384,45 +1384,86 @@ void ScTable::GetNextPos( SCCOL& rCol, SCROW& rRow, SCCOL nMovX, SCROW nMovY,
if ( nMovY && (bMarked || bUnprotected))
{
bool bUp = ( nMovY < 0 );
- SCROW nUsedY = nRow;
- SCCOL nUsedX = nCol;
+ const SCCOL nColAdd = (bUp ? -1 : 1);
+ SCCOL nStartCol, nEndCol;
+ SCROW nStartRow, nEndRow;
+ if (bMarked && rMark.IsMarked())
+ {
+ ScRange aRange( ScAddress::UNINITIALIZED);
+ rMark.GetMarkArea( aRange);
+ nStartCol = aRange.aStart.Col();
+ nStartRow = aRange.aStart.Row();
+ nEndCol = aRange.aEnd.Col();
+ nEndRow = aRange.aEnd.Row();
+ }
+ else if (bMarked && rMark.IsMultiMarked())
+ {
+ ScRange aRange( ScAddress::UNINITIALIZED);
+ rMark.GetMultiMarkArea( aRange);
+ nStartCol = aRange.aStart.Col();
+ nStartRow = aRange.aStart.Row();
+ nEndCol = aRange.aEnd.Col();
+ nEndRow = aRange.aEnd.Row();
+ }
+ else if (bUnprotected)
+ {
+ nStartCol = 0;
+ nStartRow = 0;
+ nEndCol = nCol;
+ nEndRow = nRow;
+ pDocument->GetPrintArea( nTab, nEndCol, nEndRow, true );
+ // Add some cols/rows to the print area (which is "content or
+ // visually different from empty") to enable travelling through
+ // protected forms with empty cells and no visual indicator.
+ // 42 might be good enough and not too much..
+ nEndCol = std::min<SCCOL>( nEndCol+42, MAXCOL);
+ nEndRow = std::min<SCROW>( nEndRow+42, MAXROW);
+ }
+ else
+ {
+ SAL_WARN("sc.core","ScTable::GetNextPos - bMarked but not marked");
+ nStartCol = 0;
+ nStartRow = 0;
+ nEndCol = MAXCOL;
+ nEndRow = MAXROW;
+ }
if (bMarked)
nRow = rMark.GetNextMarked( nCol, nRow, bUp );
- pDocument->GetPrintArea( nTab, nUsedX, nUsedY );
- while ( SkipRow( nCol, nRow, nMovY, rMark, bUp, nUsedY, bMarked, bSheetProtected ))
+ while ( SkipRow( nCol, nRow, nMovY, rMark, bUp, nEndRow, bMarked, bSheetProtected ))
;
- while ( nRow < 0 || nRow > MAXROW )
+ while ( nRow < nStartRow || nRow > nEndRow )
{
- nCol = sal::static_int_cast<SCCOL>( nCol + static_cast<SCCOL>(nMovY) );
+ nCol += nColAdd;
- while ( ValidCol(nCol) && ColHidden(nCol) )
- nCol = sal::static_int_cast<SCCOL>( nCol + static_cast<SCCOL>(nMovY) ); // skip hidden rows (see above)
- if (nCol < 0)
+ while (nStartCol <= nCol && nCol <= nEndCol && ValidCol(nCol) && ColHidden(nCol))
+ nCol += nColAdd; // skip hidden cols
+
+ if (nCol < nStartCol)
{
- nCol = (bSheetProtected ? nUsedX : MAXCOL);
+ nCol = nEndCol;
if (++nWrap >= 2)
return;
}
- else if (nCol > MAXCOL || ( nCol > nUsedX && bSheetProtected ))
+ else if (nCol > nEndCol)
{
- nCol = 0;
+ nCol = nStartCol;
if (++nWrap >= 2)
return;
}
- if (nRow < 0)
- nRow = MAXROW;
- else if (nRow > MAXROW)
- nRow = 0;
+ if (nRow < nStartRow)
+ nRow = nEndRow;
+ else if (nRow > nEndRow)
+ nRow = nStartRow;
if (bMarked)
nRow = rMark.GetNextMarked( nCol, nRow, bUp );
- while ( SkipRow( nCol, nRow, nMovY, rMark, bUp, nUsedY, bMarked, bSheetProtected ))
+ while ( SkipRow( nCol, nRow, nMovY, rMark, bUp, nEndRow, bMarked, bSheetProtected ))
;
}
}