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 "refupdat.hxx"
21 : #include "document.hxx"
22 : #include "compiler.hxx"
23 : #include "bigrange.hxx"
24 : #include "chgtrack.hxx"
25 :
26 : #include <osl/diagnose.h>
27 :
28 : template< typename R, typename S, typename U >
29 2025 : static bool lcl_MoveStart( R& rRef, U nStart, S nDelta, U nMask )
30 : {
31 2025 : bool bCut = false;
32 2025 : if ( rRef >= nStart )
33 1874 : rRef = sal::static_int_cast<R>( rRef + nDelta );
34 151 : else if ( nDelta < 0 && rRef >= nStart + nDelta )
35 15 : rRef = nStart + nDelta; //TODO: limit ???
36 2025 : if ( rRef < 0 )
37 : {
38 80 : rRef = 0;
39 80 : bCut = true;
40 : }
41 1945 : else if ( rRef > nMask )
42 : {
43 7 : rRef = nMask;
44 7 : bCut = true;
45 : }
46 2025 : return bCut;
47 : }
48 :
49 : template< typename R, typename S, typename U >
50 2025 : static bool lcl_MoveEnd( R& rRef, U nStart, S nDelta, U nMask )
51 : {
52 2025 : bool bCut = false;
53 2025 : if ( rRef >= nStart )
54 1915 : rRef = sal::static_int_cast<R>( rRef + nDelta );
55 110 : else if ( nDelta < 0 && rRef >= nStart + nDelta )
56 17 : rRef = nStart + nDelta - 1; //TODO: limit ???
57 2025 : if ( rRef < 0 )
58 : {
59 81 : rRef = 0;
60 81 : bCut = true;
61 : }
62 1944 : else if ( rRef > nMask )
63 : {
64 13 : rRef = nMask;
65 13 : bCut = true;
66 : }
67 2025 : return bCut;
68 : }
69 :
70 : template< typename R, typename S, typename U >
71 8 : static bool lcl_MoveReorder( R& rRef, U nStart, U nEnd, S nDelta )
72 : {
73 8 : if ( rRef >= nStart && rRef <= nEnd )
74 : {
75 4 : rRef = sal::static_int_cast<R>( rRef + nDelta );
76 4 : return true;
77 : }
78 :
79 4 : if ( nDelta > 0 ) // nach hinten schieben
80 : {
81 0 : if ( rRef >= nStart && rRef <= nEnd + nDelta )
82 : {
83 0 : if ( rRef <= nEnd )
84 0 : rRef = sal::static_int_cast<R>( rRef + nDelta ); // in the moved range
85 : else
86 0 : rRef -= nEnd - nStart + 1; // nachruecken
87 0 : return true;
88 : }
89 : }
90 : else // nach vorne schieben
91 : {
92 4 : if ( rRef >= nStart + nDelta && rRef <= nEnd )
93 : {
94 4 : if ( rRef >= nStart )
95 0 : rRef = sal::static_int_cast<R>( rRef + nDelta ); // in the moved range
96 : else
97 4 : rRef += nEnd - nStart + 1; // nachruecken
98 4 : return true;
99 : }
100 : }
101 :
102 0 : return false;
103 : }
104 :
105 : template< typename R, typename S, typename U >
106 34 : static bool lcl_MoveItCut( R& rRef, S nDelta, U nMask )
107 : {
108 34 : bool bCut = false;
109 34 : rRef = sal::static_int_cast<R>( rRef + nDelta );
110 34 : if ( rRef < 0 )
111 : {
112 0 : rRef = 0;
113 0 : bCut = true;
114 : }
115 34 : else if ( rRef > nMask )
116 : {
117 0 : rRef = nMask;
118 0 : bCut = true;
119 : }
120 34 : return bCut;
121 : }
122 :
123 : template< typename R, typename S, typename U >
124 1444 : static void lcl_MoveItWrap( R& rRef, S nDelta, U nMask )
125 : {
126 1444 : rRef = sal::static_int_cast<R>( rRef + nDelta );
127 1444 : if ( rRef < 0 )
128 0 : rRef += nMask+1;
129 1444 : else if ( rRef > nMask )
130 0 : rRef -= nMask+1;
131 1444 : }
132 :
133 : template< typename R, typename S, typename U >
134 14 : bool IsExpand( R n1, R n2, U nStart, S nD )
135 : { // before normal Move...
136 : return
137 : nD > 0 // Insert
138 : && n1 < n2 // mindestens zwei Cols/Rows/Tabs in Ref
139 : && (
140 : (nStart <= n1 && n1 < nStart + nD) // n1 innerhalb des Insert
141 : || (n2 + 1 == nStart) // n2 direkt vor Insert
142 14 : ); // n1 < nStart <= n2 wird sowieso expanded!
143 : }
144 :
145 : template< typename R, typename S, typename U >
146 12 : void Expand( R& n1, R& n2, U nStart, S nD )
147 : { // after normal Move..., only if IsExpand was true before!
148 : // first the End
149 12 : if ( n2 + 1 == nStart )
150 : { // at End
151 6 : n2 = sal::static_int_cast<R>( n2 + nD );
152 18 : return;
153 : }
154 : // am Anfang
155 6 : n1 = sal::static_int_cast<R>( n1 - nD );
156 : }
157 :
158 0 : static bool lcl_IsWrapBig( sal_Int32 nRef, sal_Int32 nDelta )
159 : {
160 0 : if ( nRef > 0 && nDelta > 0 )
161 0 : return nRef + nDelta <= 0;
162 0 : else if ( nRef < 0 && nDelta < 0 )
163 0 : return nRef + nDelta >= 0;
164 0 : return false;
165 : }
166 :
167 288 : static bool lcl_MoveBig( sal_Int32& rRef, sal_Int32 nStart, sal_Int32 nDelta )
168 : {
169 288 : bool bCut = false;
170 288 : if ( rRef >= nStart )
171 : {
172 0 : if ( nDelta > 0 )
173 0 : bCut = lcl_IsWrapBig( rRef, nDelta );
174 0 : if ( bCut )
175 0 : rRef = nInt32Max;
176 : else
177 0 : rRef += nDelta;
178 : }
179 288 : return bCut;
180 : }
181 :
182 0 : static bool lcl_MoveItCutBig( sal_Int32& rRef, sal_Int32 nDelta )
183 : {
184 0 : bool bCut = lcl_IsWrapBig( rRef, nDelta );
185 0 : rRef += nDelta;
186 0 : return bCut;
187 : }
188 :
189 2240 : ScRefUpdateRes ScRefUpdate::Update( ScDocument* pDoc, UpdateRefMode eUpdateRefMode,
190 : SCCOL nCol1, SCROW nRow1, SCTAB nTab1,
191 : SCCOL nCol2, SCROW nRow2, SCTAB nTab2,
192 : SCsCOL nDx, SCsROW nDy, SCsTAB nDz,
193 : SCCOL& theCol1, SCROW& theRow1, SCTAB& theTab1,
194 : SCCOL& theCol2, SCROW& theRow2, SCTAB& theTab2 )
195 : {
196 2240 : ScRefUpdateRes eRet = UR_NOTHING;
197 :
198 2240 : SCCOL oldCol1 = theCol1;
199 2240 : SCROW oldRow1 = theRow1;
200 2240 : SCTAB oldTab1 = theTab1;
201 2240 : SCCOL oldCol2 = theCol2;
202 2240 : SCROW oldRow2 = theRow2;
203 2240 : SCTAB oldTab2 = theTab2;
204 :
205 : bool bCut1, bCut2;
206 :
207 2240 : if (eUpdateRefMode == URM_INSDEL)
208 : {
209 2186 : bool bExpand = pDoc->IsExpandRefs();
210 2564 : if ( nDx && (theRow1 >= nRow1) && (theRow2 <= nRow2) &&
211 756 : (theTab1 >= nTab1) && (theTab2 <= nTab2) )
212 : {
213 378 : bool bExp = (bExpand && IsExpand( theCol1, theCol2, nCol1, nDx ));
214 378 : bCut1 = lcl_MoveStart( theCol1, nCol1, nDx, MAXCOL );
215 378 : bCut2 = lcl_MoveEnd( theCol2, nCol1, nDx, MAXCOL );
216 378 : if ( theCol2 < theCol1 )
217 : {
218 0 : eRet = UR_INVALID;
219 0 : theCol2 = theCol1;
220 : }
221 378 : else if ( bCut1 || bCut2 )
222 10 : eRet = UR_UPDATED;
223 378 : if ( bExp )
224 : {
225 4 : Expand( theCol1, theCol2, nCol1, nDx );
226 4 : eRet = UR_UPDATED;
227 : }
228 : }
229 2321 : if ( nDy && (theCol1 >= nCol1) && (theCol2 <= nCol2) &&
230 270 : (theTab1 >= nTab1) && (theTab2 <= nTab2) )
231 : {
232 135 : bool bExp = (bExpand && IsExpand( theRow1, theRow2, nRow1, nDy ));
233 135 : bCut1 = lcl_MoveStart( theRow1, nRow1, nDy, MAXROW );
234 135 : bCut2 = lcl_MoveEnd( theRow2, nRow1, nDy, MAXROW );
235 135 : if ( theRow2 < theRow1 )
236 : {
237 0 : eRet = UR_INVALID;
238 0 : theRow2 = theRow1;
239 : }
240 135 : else if ( bCut1 || bCut2 )
241 3 : eRet = UR_UPDATED;
242 135 : if ( bExp )
243 : {
244 8 : Expand( theRow1, theRow2, nRow1, nDy );
245 8 : eRet = UR_UPDATED;
246 : }
247 : }
248 3698 : if ( nDz && (theCol1 >= nCol1) && (theCol2 <= nCol2) &&
249 3024 : (theRow1 >= nRow1) && (theRow2 <= nRow2) )
250 : {
251 1512 : SCsTAB nMaxTab = pDoc->GetTableCount() - 1;
252 1512 : nMaxTab = sal::static_int_cast<SCsTAB>(nMaxTab + nDz); // adjust to new count
253 1512 : bool bExp = (bExpand && IsExpand( theTab1, theTab2, nTab1, nDz ));
254 1512 : bCut1 = lcl_MoveStart( theTab1, nTab1, nDz, static_cast<SCTAB>(nMaxTab) );
255 1512 : bCut2 = lcl_MoveEnd( theTab2, nTab1, nDz, static_cast<SCTAB>(nMaxTab) );
256 1512 : if ( theTab2 < theTab1 )
257 : {
258 2 : eRet = UR_INVALID;
259 2 : theTab2 = theTab1;
260 : }
261 1510 : else if ( bCut1 || bCut2 )
262 81 : eRet = UR_UPDATED;
263 1512 : if ( bExp )
264 : {
265 0 : Expand( theTab1, theTab2, nTab1, nDz );
266 0 : eRet = UR_UPDATED;
267 : }
268 : }
269 : }
270 54 : else if (eUpdateRefMode == URM_MOVE)
271 : {
272 61 : if ((theCol1 >= nCol1-nDx) && (theRow1 >= nRow1-nDy) && (theTab1 >= nTab1-nDz) &&
273 28 : (theCol2 <= nCol2-nDx) && (theRow2 <= nRow2-nDy) && (theTab2 <= nTab2-nDz))
274 : {
275 13 : if ( nDx )
276 : {
277 8 : bCut1 = lcl_MoveItCut( theCol1, nDx, MAXCOL );
278 8 : bCut2 = lcl_MoveItCut( theCol2, nDx, MAXCOL );
279 8 : if ( bCut1 || bCut2 )
280 0 : eRet = UR_UPDATED;
281 : }
282 13 : if ( nDy )
283 : {
284 8 : bCut1 = lcl_MoveItCut( theRow1, nDy, MAXROW );
285 8 : bCut2 = lcl_MoveItCut( theRow2, nDy, MAXROW );
286 8 : if ( bCut1 || bCut2 )
287 0 : eRet = UR_UPDATED;
288 : }
289 13 : if ( nDz )
290 : {
291 1 : SCsTAB nMaxTab = (SCsTAB) pDoc->GetTableCount() - 1;
292 1 : bCut1 = lcl_MoveItCut( theTab1, nDz, static_cast<SCTAB>(nMaxTab) );
293 1 : bCut2 = lcl_MoveItCut( theTab2, nDz, static_cast<SCTAB>(nMaxTab) );
294 1 : if ( bCut1 || bCut2 )
295 0 : eRet = UR_UPDATED;
296 : }
297 : }
298 : }
299 8 : else if (eUpdateRefMode == URM_REORDER)
300 : {
301 : // bisher nur fuer nDz (MoveTab)
302 : OSL_ENSURE ( !nDx && !nDy, "URM_REORDER for x and y not yet implemented" );
303 :
304 8 : if ( nDz && (theCol1 >= nCol1) && (theCol2 <= nCol2) &&
305 8 : (theRow1 >= nRow1) && (theRow2 <= nRow2) )
306 : {
307 4 : bCut1 = lcl_MoveReorder( theTab1, nTab1, nTab2, nDz );
308 4 : bCut2 = lcl_MoveReorder( theTab2, nTab1, nTab2, nDz );
309 4 : if ( bCut1 || bCut2 )
310 4 : eRet = UR_UPDATED;
311 : }
312 : }
313 :
314 2240 : if ( eRet == UR_NOTHING )
315 : {
316 2128 : if (oldCol1 != theCol1
317 1810 : || oldRow1 != theRow1
318 1764 : || oldTab1 != theTab1
319 337 : || oldCol2 != theCol2
320 319 : || oldRow2 != theRow2
321 289 : || oldTab2 != theTab2
322 : )
323 1839 : eRet = UR_UPDATED;
324 : }
325 2240 : return eRet;
326 : }
327 :
328 : // simples UpdateReference fuer ScBigRange (ScChangeAction/ScChangeTrack)
329 : // Referenzen koennen auch ausserhalb des Dokuments liegen!
330 : // Ganze Spalten/Zeilen (nInt32Min..nInt32Max) bleiben immer solche!
331 144 : ScRefUpdateRes ScRefUpdate::Update( UpdateRefMode eUpdateRefMode,
332 : const ScBigRange& rWhere, sal_Int32 nDx, sal_Int32 nDy, sal_Int32 nDz,
333 : ScBigRange& rWhat )
334 : {
335 144 : ScRefUpdateRes eRet = UR_NOTHING;
336 144 : const ScBigRange aOldRange( rWhat );
337 :
338 : sal_Int32 nCol1, nRow1, nTab1, nCol2, nRow2, nTab2;
339 : sal_Int32 theCol1, theRow1, theTab1, theCol2, theRow2, theTab2;
340 144 : rWhere.GetVars( nCol1, nRow1, nTab1, nCol2, nRow2, nTab2 );
341 144 : rWhat.GetVars( theCol1, theRow1, theTab1, theCol2, theRow2, theTab2 );
342 :
343 : bool bCut1, bCut2;
344 :
345 144 : if (eUpdateRefMode == URM_INSDEL)
346 : {
347 144 : if ( nDx && (theRow1 >= nRow1) && (theRow2 <= nRow2) &&
348 0 : (theTab1 >= nTab1) && (theTab2 <= nTab2) &&
349 0 : !(theCol1 == nInt32Min && theCol2 == nInt32Max) )
350 : {
351 0 : bCut1 = lcl_MoveBig( theCol1, nCol1, nDx );
352 0 : bCut2 = lcl_MoveBig( theCol2, nCol1, nDx );
353 0 : if ( bCut1 || bCut2 )
354 0 : eRet = UR_UPDATED;
355 0 : rWhat.aStart.SetCol( theCol1 );
356 0 : rWhat.aEnd.SetCol( theCol2 );
357 : }
358 288 : if ( nDy && (theCol1 >= nCol1) && (theCol2 <= nCol2) &&
359 432 : (theTab1 >= nTab1) && (theTab2 <= nTab2) &&
360 144 : !(theRow1 == nInt32Min && theRow2 == nInt32Max) )
361 : {
362 144 : bCut1 = lcl_MoveBig( theRow1, nRow1, nDy );
363 144 : bCut2 = lcl_MoveBig( theRow2, nRow1, nDy );
364 144 : if ( bCut1 || bCut2 )
365 0 : eRet = UR_UPDATED;
366 144 : rWhat.aStart.SetRow( theRow1 );
367 144 : rWhat.aEnd.SetRow( theRow2 );
368 : }
369 144 : if ( nDz && (theCol1 >= nCol1) && (theCol2 <= nCol2) &&
370 0 : (theRow1 >= nRow1) && (theRow2 <= nRow2) &&
371 0 : !(theTab1 == nInt32Min && theTab2 == nInt32Max) )
372 : {
373 0 : bCut1 = lcl_MoveBig( theTab1, nTab1, nDz );
374 0 : bCut2 = lcl_MoveBig( theTab2, nTab1, nDz );
375 0 : if ( bCut1 || bCut2 )
376 0 : eRet = UR_UPDATED;
377 0 : rWhat.aStart.SetTab( theTab1 );
378 0 : rWhat.aEnd.SetTab( theTab2 );
379 : }
380 : }
381 0 : else if (eUpdateRefMode == URM_MOVE)
382 : {
383 0 : if ( rWhere.In( rWhat ) )
384 : {
385 0 : if ( nDx && !(theCol1 == nInt32Min && theCol2 == nInt32Max) )
386 : {
387 0 : bCut1 = lcl_MoveItCutBig( theCol1, nDx );
388 0 : bCut2 = lcl_MoveItCutBig( theCol2, nDx );
389 0 : if ( bCut1 || bCut2 )
390 0 : eRet = UR_UPDATED;
391 0 : rWhat.aStart.SetCol( theCol1 );
392 0 : rWhat.aEnd.SetCol( theCol2 );
393 : }
394 0 : if ( nDy && !(theRow1 == nInt32Min && theRow2 == nInt32Max) )
395 : {
396 0 : bCut1 = lcl_MoveItCutBig( theRow1, nDy );
397 0 : bCut2 = lcl_MoveItCutBig( theRow2, nDy );
398 0 : if ( bCut1 || bCut2 )
399 0 : eRet = UR_UPDATED;
400 0 : rWhat.aStart.SetRow( theRow1 );
401 0 : rWhat.aEnd.SetRow( theRow2 );
402 : }
403 0 : if ( nDz && !(theTab1 == nInt32Min && theTab2 == nInt32Max) )
404 : {
405 0 : bCut1 = lcl_MoveItCutBig( theTab1, nDz );
406 0 : bCut2 = lcl_MoveItCutBig( theTab2, nDz );
407 0 : if ( bCut1 || bCut2 )
408 0 : eRet = UR_UPDATED;
409 0 : rWhat.aStart.SetTab( theTab1 );
410 0 : rWhat.aEnd.SetTab( theTab2 );
411 : }
412 : }
413 : }
414 :
415 144 : if ( eRet == UR_NOTHING && rWhat != aOldRange )
416 0 : eRet = UR_UPDATED;
417 :
418 144 : return eRet;
419 : }
420 :
421 780 : void ScRefUpdate::MoveRelWrap( ScDocument* pDoc, const ScAddress& rPos,
422 : SCCOL nMaxCol, SCROW nMaxRow, ScComplexRefData& rRef )
423 : {
424 780 : ScRange aAbsRange = rRef.toAbs(rPos);
425 780 : if( rRef.Ref1.IsColRel() )
426 : {
427 180 : SCCOL nCol = aAbsRange.aStart.Col();
428 180 : lcl_MoveItWrap(nCol, static_cast<SCsCOL>(0), nMaxCol);
429 180 : aAbsRange.aStart.SetCol(nCol);
430 : }
431 780 : if( rRef.Ref2.IsColRel() )
432 : {
433 180 : SCCOL nCol = aAbsRange.aEnd.Col();
434 180 : lcl_MoveItWrap(nCol, static_cast<SCsCOL>(0), nMaxCol);
435 180 : aAbsRange.aEnd.SetCol(nCol);
436 : }
437 780 : if( rRef.Ref1.IsRowRel() )
438 : {
439 180 : SCROW nRow = aAbsRange.aStart.Row();
440 180 : lcl_MoveItWrap(nRow, static_cast<SCsROW>(0), nMaxRow);
441 180 : aAbsRange.aStart.SetRow(nRow);
442 : }
443 780 : if( rRef.Ref2.IsRowRel() )
444 : {
445 180 : SCROW nRow = aAbsRange.aEnd.Row();
446 180 : lcl_MoveItWrap(nRow, static_cast<SCsROW>(0), nMaxRow);
447 180 : aAbsRange.aEnd.SetRow(nRow);
448 : }
449 780 : SCsTAB nMaxTab = (SCsTAB) pDoc->GetTableCount() - 1;
450 780 : if( rRef.Ref1.IsTabRel() )
451 : {
452 362 : SCTAB nTab = aAbsRange.aStart.Tab();
453 362 : lcl_MoveItWrap(nTab, static_cast<SCsTAB>(0), static_cast<SCTAB>(nMaxTab));
454 362 : aAbsRange.aStart.SetTab(nTab);
455 : }
456 780 : if( rRef.Ref2.IsTabRel() )
457 : {
458 362 : SCTAB nTab = aAbsRange.aEnd.Tab();
459 362 : lcl_MoveItWrap(nTab, static_cast<SCsTAB>(0), static_cast<SCTAB>(nMaxTab));
460 362 : aAbsRange.aEnd.SetTab(nTab);
461 : }
462 :
463 780 : aAbsRange.PutInOrder();
464 780 : rRef.SetRange(aAbsRange, rPos);
465 780 : }
466 :
467 0 : void ScRefUpdate::DoTranspose( SCsCOL& rCol, SCsROW& rRow, SCsTAB& rTab,
468 : ScDocument* pDoc, const ScRange& rSource, const ScAddress& rDest )
469 : {
470 0 : SCsTAB nDz = ((SCsTAB)rDest.Tab())-(SCsTAB)rSource.aStart.Tab();
471 0 : if (nDz)
472 : {
473 0 : SCsTAB nNewTab = rTab+nDz;
474 0 : SCsTAB nCount = pDoc->GetTableCount();
475 0 : while (nNewTab<0) nNewTab = sal::static_int_cast<SCsTAB>( nNewTab + nCount );
476 0 : while (nNewTab>=nCount) nNewTab = sal::static_int_cast<SCsTAB>( nNewTab - nCount );
477 0 : rTab = nNewTab;
478 : }
479 : OSL_ENSURE( rCol>=rSource.aStart.Col() && rRow>=rSource.aStart.Row(),
480 : "UpdateTranspose: Pos. falsch" );
481 :
482 0 : SCsCOL nRelX = rCol - (SCsCOL)rSource.aStart.Col();
483 0 : SCsROW nRelY = rRow - (SCsROW)rSource.aStart.Row();
484 :
485 0 : rCol = static_cast<SCsCOL>(static_cast<SCsCOLROW>(rDest.Col()) +
486 0 : static_cast<SCsCOLROW>(nRelY));
487 0 : rRow = static_cast<SCsROW>(static_cast<SCsCOLROW>(rDest.Row()) +
488 0 : static_cast<SCsCOLROW>(nRelX));
489 0 : }
490 :
491 0 : ScRefUpdateRes ScRefUpdate::UpdateTranspose(
492 : ScDocument* pDoc, const ScRange& rSource, const ScAddress& rDest, ScRange& rRef )
493 : {
494 0 : ScRefUpdateRes eRet = UR_NOTHING;
495 0 : if (rRef.aStart.Col() >= rSource.aStart.Col() && rRef.aEnd.Col() <= rSource.aEnd.Col() &&
496 0 : rRef.aStart.Row() >= rSource.aStart.Row() && rRef.aEnd.Row() <= rSource.aEnd.Row() &&
497 0 : rRef.aStart.Tab() >= rSource.aStart.Tab() && rRef.aEnd.Tab() <= rSource.aEnd.Tab())
498 : {
499 : // Source range contains the reference range.
500 0 : SCCOL nCol1 = rRef.aStart.Col(), nCol2 = rRef.aEnd.Col();
501 0 : SCROW nRow1 = rRef.aStart.Row(), nRow2 = rRef.aEnd.Row();
502 0 : SCTAB nTab1 = rRef.aStart.Tab(), nTab2 = rRef.aEnd.Tab();
503 0 : DoTranspose(nCol1, nRow1, nTab1, pDoc, rSource, rDest);
504 0 : DoTranspose(nCol2, nRow2, nTab2, pDoc, rSource, rDest);
505 0 : rRef.aStart = ScAddress(nCol1, nRow1, nTab1);
506 0 : rRef.aEnd = ScAddress(nCol2, nRow2, nTab2);
507 0 : eRet = UR_UPDATED;
508 : }
509 0 : return eRet;
510 : }
511 :
512 : // UpdateGrow - erweitert Referenzen, die genau auf den Bereich zeigen
513 : // kommt ohne Dokument aus
514 :
515 0 : ScRefUpdateRes ScRefUpdate::UpdateGrow(
516 : const ScRange& rArea, SCCOL nGrowX, SCROW nGrowY, ScRange& rRef )
517 : {
518 0 : ScRefUpdateRes eRet = UR_NOTHING;
519 :
520 : // in Y-Richtung darf die Ref auch eine Zeile weiter unten anfangen,
521 : // falls ein Bereich Spaltenkoepfe enthaelt
522 :
523 0 : bool bUpdateX = ( nGrowX &&
524 0 : rRef.aStart.Col() == rArea.aStart.Col() && rRef.aEnd.Col() == rArea.aEnd.Col() &&
525 0 : rRef.aStart.Row() >= rArea.aStart.Row() && rRef.aEnd.Row() <= rArea.aEnd.Row() &&
526 0 : rRef.aStart.Tab() >= rArea.aStart.Tab() && rRef.aEnd.Tab() <= rArea.aEnd.Tab() );
527 0 : bool bUpdateY = ( nGrowY &&
528 0 : rRef.aStart.Col() >= rArea.aStart.Col() && rRef.aEnd.Col() <= rArea.aEnd.Col() &&
529 0 : (rRef.aStart.Row() == rArea.aStart.Row() || rRef.aStart.Row() == rArea.aStart.Row()+1) &&
530 0 : rRef.aEnd.Row() == rArea.aEnd.Row() &&
531 0 : rRef.aStart.Tab() >= rArea.aStart.Tab() && rRef.aEnd.Tab() <= rArea.aEnd.Tab() );
532 :
533 0 : if ( bUpdateX )
534 : {
535 0 : rRef.aEnd.SetCol(sal::static_int_cast<SCsCOL>(rRef.aEnd.Col() + nGrowX));
536 0 : eRet = UR_UPDATED;
537 : }
538 0 : if ( bUpdateY )
539 : {
540 0 : rRef.aEnd.SetRow(sal::static_int_cast<SCsROW>(rRef.aEnd.Row() + nGrowY));
541 0 : eRet = UR_UPDATED;
542 : }
543 :
544 0 : return eRet;
545 156 : }
546 :
547 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|