Branch data Line data Source code
1 : : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : : /*************************************************************************
3 : : *
4 : : * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 : : *
6 : : * Copyright 2000, 2010 Oracle and/or its affiliates.
7 : : *
8 : : * OpenOffice.org - a multi-platform office productivity suite
9 : : *
10 : : * This file is part of OpenOffice.org.
11 : : *
12 : : * OpenOffice.org is free software: you can redistribute it and/or modify
13 : : * it under the terms of the GNU Lesser General Public License version 3
14 : : * only, as published by the Free Software Foundation.
15 : : *
16 : : * OpenOffice.org is distributed in the hope that it will be useful,
17 : : * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 : : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 : : * GNU Lesser General Public License version 3 for more details
20 : : * (a copy is included in the LICENSE file that accompanied this code).
21 : : *
22 : : * You should have received a copy of the GNU Lesser General Public License
23 : : * version 3 along with OpenOffice.org. If not, see
24 : : * <http://www.openoffice.org/license.html>
25 : : * for a copy of the LGPLv3 License.
26 : : *
27 : : ************************************************************************/
28 : :
29 : :
30 : : #include <ctype.h>
31 : : #include <float.h>
32 : : #include <hintids.hxx>
33 : : #include <hints.hxx> // for SwAttrSetChg
34 : : #include <editeng/lrspitem.hxx>
35 : : #include <editeng/shaditem.hxx>
36 : : #include <editeng/adjitem.hxx>
37 : : #include <editeng/colritem.hxx>
38 : : #include <sfx2/linkmgr.hxx>
39 : : #include <editeng/boxitem.hxx>
40 : : #include <fmtfsize.hxx>
41 : : #include <fmtornt.hxx>
42 : : #include <fmtpdsc.hxx>
43 : : #include <fldbas.hxx>
44 : : #include <fmtfld.hxx>
45 : : #include <frmatr.hxx>
46 : : #include <doc.hxx>
47 : : #include <docary.hxx> // for RedlineTbl()
48 : : #include <frame.hxx>
49 : : #include <swtable.hxx>
50 : : #include <ndtxt.hxx>
51 : : #include <tabcol.hxx>
52 : : #include <tabfrm.hxx>
53 : : #include <cellfrm.hxx>
54 : : #include <rowfrm.hxx>
55 : : #include <swserv.hxx>
56 : : #include <expfld.hxx>
57 : : #include <mdiexp.hxx>
58 : : #include <cellatr.hxx>
59 : : #include <txatbase.hxx>
60 : : #include <htmltbl.hxx>
61 : : #include <swtblfmt.hxx>
62 : : #include <ndindex.hxx>
63 : : #include <tblrwcl.hxx>
64 : : #include <shellres.hxx>
65 : : #include <viewsh.hxx>
66 : : #include <redline.hxx>
67 : : #include <list>
68 : : #include <switerator.hxx>
69 : :
70 : : #ifdef DBG_UTIL
71 : : #define CHECK_TABLE(t) (t).CheckConsistency();
72 : : #else
73 : : #define CHECK_TABLE(t)
74 : : #endif
75 : :
76 : : using namespace com::sun::star;
77 : :
78 [ + + ][ + + ]: 96234 : TYPEINIT1( SwTable, SwClient );
79 [ + + ][ + + ]: 136386 : TYPEINIT1( SwTableBox, SwClient );
80 [ + + ][ + + ]: 8262 : TYPEINIT1( SwTableLine, SwClient );
81 [ - + ][ + - ]: 332 : TYPEINIT1( SwTableFmt, SwFrmFmt );
82 [ - + ][ + - ]: 4062 : TYPEINIT1( SwTableBoxFmt, SwFrmFmt );
83 [ - + ][ + - ]: 2433 : TYPEINIT1( SwTableLineFmt, SwFrmFmt );
84 : :
85 [ # # ][ # # ]: 0 : SV_IMPL_REF( SwServerObject )
[ # # ][ # # ]
[ # # ]
86 : :
87 : : #define COLFUZZY 20
88 : :
89 : : void ChgTextToNum( SwTableBox& rBox, const String& rTxt, const Color* pCol,
90 : : sal_Bool bChgAlign,sal_uLong nNdPos );
91 : : //----------------------------------
92 : :
93 : : class SwTableBox_Impl
94 : : {
95 : : Color *mpUserColor, *mpNumFmtColor;
96 : : long mnRowSpan;
97 : : bool mbDummyFlag;
98 : :
99 : : void SetNewCol( Color** ppCol, const Color* pNewCol );
100 : : public:
101 : 46 : SwTableBox_Impl() : mpUserColor(0), mpNumFmtColor(0), mnRowSpan(1),
102 : 46 : mbDummyFlag( false ) {}
103 : 46 : ~SwTableBox_Impl() { delete mpUserColor; delete mpNumFmtColor; }
104 : :
105 : 0 : const Color* GetSaveUserColor() const { return mpUserColor; }
106 : 46 : const Color* GetSaveNumFmtColor() const { return mpNumFmtColor; }
107 : 80 : void SetSaveUserColor(const Color* p ) { SetNewCol( &mpUserColor, p ); }
108 : 80 : void SetSaveNumFmtColor( const Color* p ) { SetNewCol( &mpNumFmtColor, p ); }
109 : 936 : long getRowSpan() const { return mnRowSpan; }
110 : 14 : void setRowSpan( long nNewRowSpan ) { mnRowSpan = nNewRowSpan; }
111 : 0 : bool getDummyFlag() const { return mbDummyFlag; }
112 : 0 : void setDummyFlag( bool bDummy ) { mbDummyFlag = bDummy; }
113 : : };
114 : :
115 : : // ----------- Inlines -----------------------------
116 : :
117 : 0 : inline const Color* SwTableBox::GetSaveUserColor() const
118 : : {
119 [ # # ]: 0 : return pImpl ? pImpl->GetSaveUserColor() : 0;
120 : : }
121 : :
122 : 164 : inline const Color* SwTableBox::GetSaveNumFmtColor() const
123 : : {
124 [ + + ]: 164 : return pImpl ? pImpl->GetSaveNumFmtColor() : 0;
125 : : }
126 : :
127 : 80 : inline void SwTableBox::SetSaveUserColor(const Color* p )
128 : : {
129 [ + + ]: 80 : if( pImpl )
130 : 40 : pImpl->SetSaveUserColor( p );
131 [ + - ]: 40 : else if( p )
132 : 40 : ( pImpl = new SwTableBox_Impl ) ->SetSaveUserColor( p );
133 : 80 : }
134 : :
135 : 154 : inline void SwTableBox::SetSaveNumFmtColor( const Color* p )
136 : : {
137 [ + + ]: 154 : if( pImpl )
138 : 80 : pImpl->SetSaveNumFmtColor( p );
139 [ - + ]: 74 : else if( p )
140 : 0 : ( pImpl = new SwTableBox_Impl )->SetSaveNumFmtColor( p );
141 : 154 : }
142 : :
143 : 123727 : long SwTableBox::getRowSpan() const
144 : : {
145 [ + + ]: 123727 : return pImpl ? pImpl->getRowSpan() : 1;
146 : : }
147 : :
148 : 24 : void SwTableBox::setRowSpan( long nNewRowSpan )
149 : : {
150 [ + + ]: 24 : if( !pImpl )
151 : : {
152 [ + + ]: 16 : if( nNewRowSpan == 1 )
153 : 24 : return;
154 : 6 : pImpl = new SwTableBox_Impl();
155 : : }
156 : 14 : pImpl->setRowSpan( nNewRowSpan );
157 : : }
158 : :
159 : 0 : bool SwTableBox::getDummyFlag() const
160 : : {
161 [ # # ]: 0 : return pImpl ? pImpl->getDummyFlag() : false;
162 : : }
163 : :
164 : 0 : void SwTableBox::setDummyFlag( bool bDummy )
165 : : {
166 [ # # ]: 0 : if( !pImpl )
167 : : {
168 [ # # ]: 0 : if( !bDummy )
169 : 0 : return;
170 : 0 : pImpl = new SwTableBox_Impl();
171 : : }
172 : 0 : pImpl->setDummyFlag( bDummy );
173 : : }
174 : :
175 : : //JP 15.09.98: Bug 55741 - Keep tabs (front and rear)
176 : 0 : String& lcl_TabToBlankAtSttEnd( String& rTxt )
177 : : {
178 : : sal_Unicode c;
179 : : xub_StrLen n;
180 : :
181 [ # # ][ # # ]: 0 : for( n = 0; n < rTxt.Len() && ' ' >= ( c = rTxt.GetChar( n )); ++n )
[ # # ]
182 [ # # ]: 0 : if( '\x9' == c )
183 : 0 : rTxt.SetChar( n, ' ' );
184 [ # # ][ # # ]: 0 : for( n = rTxt.Len(); n && ' ' >= ( c = rTxt.GetChar( --n )); )
[ # # ]
185 [ # # ]: 0 : if( '\x9' == c )
186 : 0 : rTxt.SetChar( n, ' ' );
187 : 0 : return rTxt;
188 : : }
189 : :
190 : 0 : String& lcl_DelTabsAtSttEnd( String& rTxt )
191 : : {
192 : : sal_Unicode c;
193 : : xub_StrLen n;
194 : :
195 [ # # ][ # # ]: 0 : for( n = 0; n < rTxt.Len() && ' ' >= ( c = rTxt.GetChar( n )); ++n )
[ # # ]
196 [ # # ]: 0 : if( '\x9' == c )
197 : 0 : rTxt.Erase( n--, 1 );
198 [ # # ][ # # ]: 0 : for( n = rTxt.Len(); n && ' ' >= ( c = rTxt.GetChar( --n )); )
[ # # ]
199 [ # # ]: 0 : if( '\x9' == c )
200 : 0 : rTxt.Erase( n, 1 );
201 : 0 : return rTxt;
202 : : }
203 : :
204 : 10 : void _InsTblBox( SwDoc* pDoc, SwTableNode* pTblNd,
205 : : SwTableLine* pLine, SwTableBoxFmt* pBoxFrmFmt,
206 : : SwTableBox* pBox,
207 : : sal_uInt16 nInsPos, sal_uInt16 nCnt )
208 : : {
209 : : OSL_ENSURE( pBox->GetSttNd(), "Box with no start node" );
210 [ + - ]: 10 : SwNodeIndex aIdx( *pBox->GetSttNd(), +1 );
211 : 10 : SwCntntNode* pCNd = aIdx.GetNode().GetCntntNode();
212 [ - + ]: 10 : if( !pCNd )
213 [ # # ][ # # ]: 0 : pCNd = pDoc->GetNodes().GoNext( &aIdx );
214 : : OSL_ENSURE( pCNd, "Box with no content node" );
215 : :
216 [ + - ]: 10 : if( pCNd->IsTxtNode() )
217 : : {
218 [ - + ][ # # ]: 10 : if( pBox->GetSaveNumFmtColor() && pCNd->GetpSwAttrSet() )
[ # # ][ - + ]
219 : : {
220 [ # # ][ # # ]: 0 : SwAttrSet aAttrSet( *pCNd->GetpSwAttrSet() );
221 [ # # ]: 0 : if( pBox->GetSaveUserColor() )
222 [ # # ][ # # ]: 0 : aAttrSet.Put( SvxColorItem( *pBox->GetSaveUserColor(), RES_CHRATR_COLOR ));
[ # # ]
223 : : else
224 [ # # ]: 0 : aAttrSet.ClearItem( RES_CHRATR_COLOR );
225 [ # # ]: 0 : pDoc->GetNodes().InsBoxen( pTblNd, pLine, pBoxFrmFmt,
226 : : ((SwTxtNode*)pCNd)->GetTxtColl(),
227 [ # # ][ # # ]: 0 : &aAttrSet, nInsPos, nCnt );
228 : : }
229 : : else
230 [ + - ]: 10 : pDoc->GetNodes().InsBoxen( pTblNd, pLine, pBoxFrmFmt,
231 : : ((SwTxtNode*)pCNd)->GetTxtColl(),
232 [ + - ]: 10 : pCNd->GetpSwAttrSet(),
233 [ + - ]: 20 : nInsPos, nCnt );
234 : : }
235 : : else
236 [ # # ]: 0 : pDoc->GetNodes().InsBoxen( pTblNd, pLine, pBoxFrmFmt,
237 : 0 : (SwTxtFmtColl*)pDoc->GetDfltTxtFmtColl(), 0,
238 [ # # ]: 0 : nInsPos, nCnt );
239 : :
240 [ + - ]: 10 : long nRowSpan = pBox->getRowSpan();
241 [ - + ]: 10 : if( nRowSpan != 1 )
242 : : {
243 : 0 : SwTableBoxes& rTblBoxes = pLine->GetTabBoxes();
244 [ # # ]: 0 : for( sal_uInt16 i = 0; i < nCnt; ++i )
245 : : {
246 : 0 : pBox = rTblBoxes[ i + nInsPos ];
247 [ # # ]: 0 : pBox->setRowSpan( nRowSpan );
248 : : }
249 [ + - ]: 10 : }
250 : 10 : }
251 : :
252 : : /*************************************************************************
253 : : |*
254 : : |* SwTable::SwTable()
255 : : |*
256 : : |*************************************************************************/
257 : 232 : SwTable::SwTable( SwTableFmt* pFmt )
258 : : : SwClient( pFmt ),
259 : : pHTMLLayout( 0 ),
260 : : pTableNode( 0 ),
261 : : nGrfsThatResize( 0 ),
262 : : nRowsToRepeat( 1 ),
263 : : bModifyLocked( sal_False ),
264 [ + - ][ + - ]: 232 : bNewModel( sal_True )
265 : : {
266 : : // default value set in the options
267 [ + - ]: 232 : eTblChgMode = (TblChgMode)GetTblChgDefaultMode();
268 : 232 : }
269 : :
270 : 0 : SwTable::SwTable( const SwTable& rTable )
271 : 0 : : SwClient( rTable.GetFrmFmt() ),
272 : : pHTMLLayout( 0 ),
273 : : pTableNode( 0 ),
274 : : eTblChgMode( rTable.eTblChgMode ),
275 : : nGrfsThatResize( 0 ),
276 [ # # ]: 0 : nRowsToRepeat( rTable.GetRowsToRepeat() ),
277 : : bModifyLocked( sal_False ),
278 [ # # ][ # # ]: 0 : bNewModel( rTable.bNewModel )
279 : : {
280 : 0 : }
281 : :
282 : 232 : void DelBoxNode( SwTableSortBoxes& rSortCntBoxes )
283 : : {
284 [ + + ]: 2534 : for( sal_uInt16 n = 0; n < rSortCntBoxes.size(); ++n )
285 : 2302 : rSortCntBoxes[ n ]->pSttNd = 0;
286 : 232 : }
287 : :
288 [ + - ][ + - ]: 232 : SwTable::~SwTable()
289 : : {
290 [ - + ]: 232 : if( refObj.Is() )
291 : : {
292 : 0 : SwDoc* pDoc = GetFrmFmt()->GetDoc();
293 [ # # ]: 0 : if( !pDoc->IsInDtor() ) // then remove from the list
294 [ # # ][ # # ]: 0 : pDoc->GetLinkManager().RemoveServer( &refObj );
295 : :
296 [ # # ]: 0 : refObj->Closed();
297 : : }
298 : :
299 : : // the table can be deleted if it's the last client of the FrameFormat
300 : 232 : SwTableFmt* pFmt = (SwTableFmt*)GetFrmFmt();
301 [ + - ]: 232 : pFmt->Remove( this ); // remove
302 : :
303 [ + - ]: 232 : if( !pFmt->GetDepends() )
304 [ + - ]: 232 : pFmt->GetDoc()->DelTblFrmFmt( pFmt ); // and delete
305 : :
306 : : // Delete the pointers from the SortArray of the boxes. The objects
307 : : // are preserved and are deleted by the lines/boxes arrays dtor.
308 : : // Note: unfortunately not enough, pointers to the StartNode of the
309 : : // section need deletion.
310 [ + - ]: 232 : DelBoxNode( aSortCntBoxes );
311 : 232 : aSortCntBoxes.clear();
312 [ # # ][ - + ]: 232 : delete pHTMLLayout;
313 [ - + ]: 464 : }
314 : :
315 : : /*************************************************************************
316 : : |*
317 : : |* SwTable::Modify()
318 : : |*
319 : : |*************************************************************************/
320 : 598 : static void FmtInArr( std::vector<SwFmt*>& rFmtArr, SwFmt* pBoxFmt )
321 : : {
322 [ + - ][ + - ]: 598 : std::vector<SwFmt*>::const_iterator it = std::find( rFmtArr.begin(), rFmtArr.end(), pBoxFmt );
323 [ + - ][ + + ]: 598 : if ( it == rFmtArr.end() )
324 [ + - ]: 339 : rFmtArr.push_back( pBoxFmt );
325 : 598 : }
326 : :
327 : : static void lcl_ModifyBoxes( SwTableBoxes &rBoxes, const long nOld,
328 : : const long nNew, std::vector<SwFmt*>& rFmtArr );
329 : :
330 : 171 : static void lcl_ModifyLines( SwTableLines &rLines, const long nOld,
331 : : const long nNew, std::vector<SwFmt*>& rFmtArr, const bool bCheckSum )
332 : : {
333 [ + + ]: 412 : for ( sal_uInt16 i = 0; i < rLines.size(); ++i )
334 : 241 : ::lcl_ModifyBoxes( rLines[i]->GetTabBoxes(), nOld, nNew, rFmtArr );
335 [ + - ]: 171 : if( bCheckSum )
336 : : {
337 [ + + ]: 510 : for( sal_uInt16 i = 0; i < rFmtArr.size(); ++i )
338 : : {
339 [ + - ]: 339 : SwFmt* pFmt = rFmtArr[i];
340 [ + - ]: 339 : sal_uInt64 nBox = pFmt->GetFrmSize().GetWidth();
341 : 339 : nBox *= nNew;
342 : 339 : nBox /= nOld;
343 [ + - ]: 339 : SwFmtFrmSize aNewBox( ATT_VAR_SIZE, SwTwips(nBox), 0 );
344 : 339 : pFmt->LockModify();
345 [ + - ]: 339 : pFmt->SetFmtAttr( aNewBox );
346 : 339 : pFmt->UnlockModify();
347 [ + - ]: 339 : }
348 : : }
349 : 171 : }
350 : :
351 : 241 : static void lcl_ModifyBoxes( SwTableBoxes &rBoxes, const long nOld,
352 : : const long nNew, std::vector<SwFmt*>& rFmtArr )
353 : : {
354 : 241 : sal_uInt64 nSum = 0; // To avoid rounding errors we summarize all box widths
355 : 241 : sal_uInt64 nOriginalSum = 0; // Sum of original widths
356 [ + + ]: 1214 : for ( sal_uInt16 i = 0; i < rBoxes.size(); ++i )
357 : : {
358 : 973 : SwTableBox &rBox = *rBoxes[i];
359 [ - + ]: 973 : if ( !rBox.GetTabLines().empty() )
360 : : {
361 : : // For SubTables the rounding problem will not be solved :-(
362 : 0 : ::lcl_ModifyLines( rBox.GetTabLines(), nOld, nNew, rFmtArr, false );
363 : : }
364 : : // Adjust the box
365 : 973 : SwFrmFmt *pFmt = rBox.GetFrmFmt();
366 : 973 : sal_uInt64 nBox = pFmt->GetFrmSize().GetWidth();
367 : 973 : nOriginalSum += nBox;
368 : 973 : nBox *= nNew;
369 : 973 : nBox /= nOld;
370 : 973 : sal_uInt64 nWishedSum = nOriginalSum;
371 : 973 : nWishedSum *= nNew;
372 : 973 : nWishedSum /= nOld;
373 : 973 : nWishedSum -= nSum;
374 [ + - ]: 973 : if( nWishedSum > 0 )
375 : : {
376 [ + + ]: 973 : if( nBox == nWishedSum )
377 : 598 : FmtInArr( rFmtArr, pFmt );
378 : : else
379 : : {
380 : 375 : nBox = nWishedSum;
381 [ + - ]: 375 : pFmt = rBox.ClaimFrmFmt();
382 [ + - ]: 375 : SwFmtFrmSize aNewBox( ATT_VAR_SIZE, static_cast< SwTwips >(nBox), 0 );
383 : 375 : pFmt->LockModify();
384 [ + - ]: 375 : pFmt->SetFmtAttr( aNewBox );
385 [ + - ]: 375 : pFmt->UnlockModify();
386 : : }
387 : : }
388 : : else {
389 : : OSL_FAIL( "Rounding error" );
390 : : }
391 : 973 : nSum += nBox;
392 : : }
393 : 241 : }
394 : :
395 : 868 : void SwTable::Modify( const SfxPoolItem* pOld, const SfxPoolItem *pNew )
396 : : {
397 : : // catch SSize changes, to adjust the lines/boxes
398 [ + - ][ # # ]: 868 : sal_uInt16 nWhich = pOld ? pOld->Which() : pNew ? pNew->Which() : 0 ;
399 : 868 : const SwFmtFrmSize* pNewSize = 0, *pOldSize = 0;
400 : :
401 [ + + ]: 868 : if( RES_ATTRSET_CHG == nWhich )
402 : : {
403 [ + + ]: 1104 : if( SFX_ITEM_SET == ((SwAttrSetChg*)pNew)->GetChgSet()->GetItemState(
404 [ + - ]: 552 : RES_FRM_SIZE, sal_False, (const SfxPoolItem**)&pNewSize ))
405 [ + - ]: 171 : pOldSize = &((SwAttrSetChg*)pOld)->GetChgSet()->GetFrmSize();
406 : : }
407 [ - + ]: 316 : else if( RES_FRM_SIZE == nWhich )
408 : : {
409 : 0 : pOldSize = (const SwFmtFrmSize*)pOld;
410 : 0 : pNewSize = (const SwFmtFrmSize*)pNew;
411 : : }
412 : : else
413 [ + - ]: 316 : CheckRegistration( pOld, pNew );
414 : :
415 [ + + ][ - + ]: 868 : if( pOldSize || pNewSize )
416 : : {
417 [ + - ]: 171 : if ( !IsModifyLocked() )
418 : : {
419 : : OSL_ENSURE( pOldSize && pOldSize->Which() == RES_FRM_SIZE &&
420 : : pNewSize && pNewSize->Which() == RES_FRM_SIZE,
421 : : "No Old or New for FmtFrmSize-Modify of the SwTable." );
422 [ + - ]: 171 : AdjustWidths( pOldSize->GetWidth(), pNewSize->GetWidth() );
423 : : }
424 : : }
425 : 868 : }
426 : :
427 : 171 : void SwTable::AdjustWidths( const long nOld, const long nNew )
428 : : {
429 [ + - ]: 171 : std::vector<SwFmt*> aFmtArr;
430 [ + - ]: 171 : aFmtArr.reserve( aLines[0]->GetTabBoxes().size() );
431 [ + - ]: 171 : ::lcl_ModifyLines( aLines, nOld, nNew, aFmtArr, true );
432 : 171 : }
433 : :
434 : : /*************************************************************************
435 : : |*
436 : : |* SwTable::GetTabCols()
437 : : |*
438 : : |*************************************************************************/
439 : 0 : void lcl_RefreshHidden( SwTabCols &rToFill, sal_uInt16 nPos )
440 : : {
441 [ # # ]: 0 : for ( sal_uInt16 i = 0; i < rToFill.Count(); ++i )
442 : : {
443 [ # # ]: 0 : if ( Abs((long)(nPos - rToFill[i])) <= COLFUZZY )
444 : : {
445 : 0 : rToFill.SetHidden( i, sal_False );
446 : 0 : break;
447 : : }
448 : : }
449 : 0 : }
450 : :
451 : 562 : void lcl_SortedTabColInsert( SwTabCols &rToFill, const SwTableBox *pBox,
452 : : const SwFrmFmt *pTabFmt, const sal_Bool bHidden,
453 : : const bool bRefreshHidden )
454 : : {
455 : 562 : const long nWish = pTabFmt->GetFrmSize().GetWidth();
456 : : OSL_ENSURE(nWish, "weird <= 0 width frmfrm");
457 : 562 : const long nAct = rToFill.GetRight() - rToFill.GetLeft(); // +1 why?
458 : :
459 : : // The value for the left edge of the box is calculated from the
460 : : // widths of the previous boxes.
461 : 562 : sal_uInt16 nPos = 0;
462 : 562 : sal_uInt16 nSum = 0;
463 : 562 : sal_uInt16 nLeftMin = 0;
464 : 562 : sal_uInt16 nRightMax = 0;
465 : 562 : const SwTableBox *pCur = pBox;
466 : 562 : const SwTableLine *pLine = pBox->GetUpper();
467 [ + + ]: 1124 : while ( pLine )
468 : : {
469 : 562 : const SwTableBoxes &rBoxes = pLine->GetTabBoxes();
470 [ + - ]: 1947 : for ( sal_uInt16 i = 0; i < rBoxes.size(); ++i )
471 : : {
472 : 1947 : SwTwips nWidth = rBoxes[i]->GetFrmFmt()->GetFrmSize().GetWidth();
473 : 1947 : nSum = (sal_uInt16)(nSum + nWidth);
474 : 1947 : sal_uInt64 nTmp = nSum;
475 : 1947 : nTmp *= nAct;
476 : :
477 [ - + ]: 1947 : if (nWish == 0) //fdo#33012 0 width frmfmt
478 : 0 : continue;
479 : :
480 : 1947 : nTmp /= nWish;
481 [ + + ]: 1947 : if (rBoxes[i] != pCur)
482 : : {
483 [ - + ][ # # ]: 1385 : if ( pLine == pBox->GetUpper() || 0 == nLeftMin )
[ + - ]
484 : 1385 : nLeftMin = (sal_uInt16)(nTmp - nPos);
485 : 1385 : nPos = (sal_uInt16)nTmp;
486 : : }
487 : : else
488 : : {
489 : 562 : nSum = (sal_uInt16)(nSum - nWidth);
490 [ + - ]: 562 : if ( 0 == nRightMax )
491 : 562 : nRightMax = (sal_uInt16)(nTmp - nPos);
492 : 562 : break;
493 : : }
494 : : }
495 : 562 : pCur = pLine->GetUpper();
496 [ - + ]: 562 : pLine = pCur ? pCur->GetUpper() : 0;
497 : : }
498 : :
499 : 562 : sal_Bool bInsert = !bRefreshHidden;
500 [ + + ][ + + ]: 2027 : for ( sal_uInt16 j = 0; bInsert && (j < rToFill.Count()); ++j )
[ + + ]
501 : : {
502 : 1465 : long nCmp = rToFill[j];
503 [ + - ][ + + ]: 1465 : if ( (nPos >= ((nCmp >= COLFUZZY) ? nCmp - COLFUZZY : nCmp)) &&
[ + + ]
504 : : (nPos <= (nCmp + COLFUZZY)) )
505 : : {
506 : 80 : bInsert = sal_False; // Already has it.
507 : : }
508 [ - + ]: 1385 : else if ( nPos < nCmp )
509 : : {
510 : 0 : bInsert = sal_False;
511 : 0 : rToFill.Insert( nPos, bHidden, j );
512 : : }
513 : : }
514 [ + + ]: 562 : if ( bInsert )
515 : 482 : rToFill.Insert( nPos, bHidden, rToFill.Count() );
516 [ - + ]: 80 : else if ( bRefreshHidden )
517 : 0 : ::lcl_RefreshHidden( rToFill, nPos );
518 : :
519 [ + + ][ + - ]: 562 : if ( bHidden && !bRefreshHidden )
520 : : {
521 : : // calculate minimum/maximum values for the existing entries:
522 : 80 : nLeftMin = nPos - nLeftMin;
523 : 80 : nRightMax = nPos + nRightMax;
524 : :
525 : : // check if nPos is entry:
526 : 80 : bool bFoundPos = false;
527 : 80 : bool bFoundMax = false;
528 [ + + ][ + + ]: 240 : for ( sal_uInt16 j = 0; !(bFoundPos && bFoundMax ) && j < rToFill.Count(); ++j )
[ + + ][ + + ]
529 : : {
530 : 160 : SwTabColsEntry& rEntry = rToFill.GetEntry( j );
531 : 160 : long nCmp = rToFill[j];
532 : :
533 [ + + ][ + + ]: 160 : if ( (nPos >= ((nCmp >= COLFUZZY) ? nCmp - COLFUZZY : nCmp)) &&
[ + + ]
534 : : (nPos <= (nCmp + COLFUZZY)) )
535 : : {
536 : : // check if nLeftMin is > old minimum for entry nPos:
537 : 80 : const long nOldMin = rEntry.nMin;
538 [ - + ]: 80 : if ( nLeftMin > nOldMin )
539 : 0 : rEntry.nMin = nLeftMin;
540 : : // check if nRightMin is < old maximum for entry nPos:
541 : 80 : const long nOldMax = rEntry.nMax;
542 [ + + ]: 80 : if ( nRightMax < nOldMax )
543 : 16 : rEntry.nMax = nRightMax;
544 : :
545 : 80 : bFoundPos = true;
546 : : }
547 [ + + ][ + - ]: 80 : else if ( (nRightMax >= ((nCmp >= COLFUZZY) ? nCmp - COLFUZZY : nCmp)) &&
[ + + ]
548 : : (nRightMax <= (nCmp + COLFUZZY)) )
549 : : {
550 : : // check if nPos is > old minimum for entry nRightMax:
551 : 76 : const long nOldMin = rEntry.nMin;
552 [ + + ]: 76 : if ( nPos > nOldMin )
553 : 6 : rEntry.nMin = nPos;
554 : :
555 : 76 : bFoundMax = true;
556 : : }
557 : : }
558 : : }
559 : 562 : }
560 : :
561 : 482 : void lcl_ProcessBoxGet( const SwTableBox *pBox, SwTabCols &rToFill,
562 : : const SwFrmFmt *pTabFmt, bool bRefreshHidden )
563 : : {
564 [ - + ]: 482 : if ( !pBox->GetTabLines().empty() )
565 : : {
566 : 0 : const SwTableLines &rLines = pBox->GetTabLines();
567 [ # # ]: 0 : for ( sal_uInt16 i = 0; i < rLines.size(); ++i )
568 : 0 : { const SwTableBoxes &rBoxes = rLines[i]->GetTabBoxes();
569 [ # # ]: 0 : for ( sal_uInt16 j = 0; j < rBoxes.size(); ++j )
570 : 0 : ::lcl_ProcessBoxGet( rBoxes[j], rToFill, pTabFmt, bRefreshHidden);
571 : : }
572 : : }
573 : : else
574 : 482 : ::lcl_SortedTabColInsert( rToFill, pBox, pTabFmt, sal_False, bRefreshHidden );
575 : 482 : }
576 : :
577 : 40 : void lcl_ProcessLineGet( const SwTableLine *pLine, SwTabCols &rToFill,
578 : : const SwFrmFmt *pTabFmt )
579 : : {
580 [ + + ]: 120 : for ( sal_uInt16 i = 0; i < pLine->GetTabBoxes().size(); ++i )
581 : : {
582 : 80 : const SwTableBox *pBox = pLine->GetTabBoxes()[i];
583 [ + - ]: 80 : if ( pBox->GetSttNd() )
584 : 80 : ::lcl_SortedTabColInsert( rToFill, pBox, pTabFmt, sal_True, sal_False );
585 : : else
586 [ # # ]: 0 : for ( sal_uInt16 j = 0; j < pBox->GetTabLines().size(); ++j )
587 : 0 : ::lcl_ProcessLineGet( pBox->GetTabLines()[j], rToFill, pTabFmt );
588 : : }
589 : 40 : }
590 : :
591 : 93 : void SwTable::GetTabCols( SwTabCols &rToFill, const SwTableBox *pStart,
592 : : sal_Bool bRefreshHidden, sal_Bool bCurRowOnly ) const
593 : : {
594 : : // Optimization: if bHidden is set, we only update the Hidden Array.
595 [ - + ]: 93 : if ( bRefreshHidden )
596 : : {
597 : : // remove corrections
598 : : sal_uInt16 i;
599 [ # # ]: 0 : for ( i = 0; i < rToFill.Count(); ++i )
600 : : {
601 : 0 : SwTabColsEntry& rEntry = rToFill.GetEntry( i );
602 : 0 : rEntry.nPos -= rToFill.GetLeft();
603 : 0 : rEntry.nMin -= rToFill.GetLeft();
604 : 0 : rEntry.nMax -= rToFill.GetLeft();
605 : : }
606 : :
607 : : // All are hidden, so add the visible ones.
608 [ # # ]: 0 : for ( i = 0; i < rToFill.Count(); ++i )
609 : 0 : rToFill.SetHidden( i, sal_True );
610 : : }
611 : : else
612 : : {
613 : 93 : rToFill.Remove( 0, rToFill.Count() );
614 : : }
615 : :
616 : : // Insertion cases:
617 : : // 1. All boxes which are inferior to Line which is superior to the Start,
618 : : // as well as their inferior boxes if present.
619 : : // 2. Starting from the Line, the superior box plus its neighbours; but no inferiors.
620 : : // 3. Apply 2. to the Line superior to the chain of boxes,
621 : : // until the Line's superior is not a box but the table.
622 : : // Only those boxes are inserted that don't contain further rows. The insertion
623 : : // function takes care to avoid duplicates. In order to achieve this, we work
624 : : // with some degree of fuzzyness (to avoid rounding errors).
625 : : // Only the left edge of the boxes are inserted.
626 : : // Finally, the first entry is removed again, because it's already
627 : : // covered by the border.
628 : : // 4. Scan the table again and insert _all_ boxes, this time as hidden.
629 : :
630 : 93 : const SwFrmFmt *pTabFmt = GetFrmFmt();
631 : :
632 : : // 1.
633 : 93 : const SwTableBoxes &rBoxes = pStart->GetUpper()->GetTabBoxes();
634 : :
635 : : sal_uInt16 i;
636 [ + + ]: 575 : for ( i = 0; i < rBoxes.size(); ++i )
637 : 482 : ::lcl_ProcessBoxGet( rBoxes[i], rToFill, pTabFmt, bRefreshHidden );
638 : :
639 : : // 2. and 3.
640 : 93 : const SwTableLine *pLine = pStart->GetUpper()->GetUpper() ?
641 [ - + ]: 93 : pStart->GetUpper()->GetUpper()->GetUpper() : 0;
642 [ - + ]: 93 : while ( pLine )
643 : : {
644 : 0 : const SwTableBoxes &rBoxes2 = pLine->GetTabBoxes();
645 [ # # ]: 0 : for ( sal_uInt16 k = 0; k < rBoxes2.size(); ++k )
646 : 0 : ::lcl_SortedTabColInsert( rToFill, rBoxes2[k],
647 : 0 : pTabFmt, sal_False, bRefreshHidden );
648 [ # # ]: 0 : pLine = pLine->GetUpper() ? pLine->GetUpper()->GetUpper() : 0;
649 : : }
650 : :
651 [ + - ]: 93 : if ( !bRefreshHidden )
652 : : {
653 : : // 4.
654 [ + + ]: 93 : if ( !bCurRowOnly )
655 : : {
656 [ + + ]: 48 : for ( i = 0; i < aLines.size(); ++i )
657 : 40 : ::lcl_ProcessLineGet( aLines[i], rToFill, pTabFmt );
658 : : }
659 : :
660 : 93 : rToFill.Remove( 0, 1 );
661 : : }
662 : :
663 : : // Now the coordinates are relative to the left table border - i.e.
664 : : // relative to SwTabCols.nLeft. However, they are expected
665 : : // relative to the left document border, i.e. SwTabCols.nLeftMin.
666 : : // So all values need to be extended by nLeft.
667 [ + + ]: 482 : for ( i = 0; i < rToFill.Count(); ++i )
668 : : {
669 : 389 : SwTabColsEntry& rEntry = rToFill.GetEntry( i );
670 : 389 : rEntry.nPos += rToFill.GetLeft();
671 : 389 : rEntry.nMin += rToFill.GetLeft();
672 : 389 : rEntry.nMax += rToFill.GetLeft();
673 : : }
674 : 93 : }
675 : :
676 : : /*************************************************************************
677 : : |*
678 : : |* SwTable::SetTabCols()
679 : : |*
680 : : |*************************************************************************/
681 : : // Structure for parameter passing
682 [ + - ]: 79 : struct Parm
683 : : {
684 : : const SwTabCols &rNew;
685 : : const SwTabCols &rOld;
686 : : long nNewWish,
687 : : nOldWish;
688 : : std::deque<SwTableBox*> aBoxArr;
689 : : SwShareBoxFmts aShareFmts;
690 : :
691 : 79 : Parm( const SwTabCols &rN, const SwTabCols &rO )
692 [ + - ]: 79 : : rNew( rN ), rOld( rO ), nNewWish(0), nOldWish(0)
693 : 79 : {}
694 : : };
695 : :
696 : : void lcl_ProcessBoxSet( SwTableBox *pBox, Parm &rParm );
697 : :
698 : 0 : void lcl_ProcessLine( SwTableLine *pLine, Parm &rParm )
699 : : {
700 : 0 : SwTableBoxes &rBoxes = pLine->GetTabBoxes();
701 [ # # ]: 0 : for ( int i = rBoxes.size()-1; i >= 0; --i )
702 : 0 : ::lcl_ProcessBoxSet( rBoxes[ static_cast< sal_uInt16 >(i) ], rParm );
703 : 0 : }
704 : :
705 : 0 : void lcl_ProcessBoxSet( SwTableBox *pBox, Parm &rParm )
706 : : {
707 [ # # ]: 0 : if ( !pBox->GetTabLines().empty() )
708 : 0 : { SwTableLines &rLines = pBox->GetTabLines();
709 [ # # ]: 0 : for ( int i = rLines.size()-1; i >= 0; --i )
710 : 0 : lcl_ProcessLine( rLines[ static_cast< sal_uInt16 >(i) ], rParm );
711 : : }
712 : : else
713 : : {
714 : : // Search the old TabCols for the current position (calculate from
715 : : // left and right edge). Adjust the box if the values differ from
716 : : // the new TabCols. If the adjusted edge has no neighbour we also
717 : : // adjust all superior boxes.
718 : :
719 : 0 : const long nOldAct = rParm.rOld.GetRight() -
720 : 0 : rParm.rOld.GetLeft(); // +1 why?
721 : :
722 : : // The value for the left edge of the box is calculated from the
723 : : // widths of the previous boxes plus the left edge.
724 : 0 : long nLeft = rParm.rOld.GetLeft();
725 : 0 : const SwTableBox *pCur = pBox;
726 : 0 : const SwTableLine *pLine = pBox->GetUpper();
727 : :
728 [ # # ]: 0 : while ( pLine )
729 : 0 : { const SwTableBoxes &rBoxes = pLine->GetTabBoxes();
730 [ # # ][ # # ]: 0 : for ( sal_uInt16 i = 0; (i < rBoxes.size()) && (rBoxes[i] != pCur); ++i)
[ # # ]
731 : : {
732 : 0 : sal_uInt64 nWidth = rBoxes[i]->GetFrmFmt()->
733 : 0 : GetFrmSize().GetWidth();
734 : 0 : nWidth *= nOldAct;
735 : 0 : nWidth /= rParm.nOldWish;
736 : 0 : nLeft += (sal_uInt16)nWidth;
737 : : }
738 : 0 : pCur = pLine->GetUpper();
739 [ # # ]: 0 : pLine = pCur ? pCur->GetUpper() : 0;
740 : : }
741 : : long nLeftDiff;
742 : 0 : long nRightDiff = 0;
743 [ # # ]: 0 : if ( nLeft != rParm.rOld.GetLeft() ) // There are still boxes before this.
744 : : {
745 : : // Right edge is left edge plus width.
746 : 0 : sal_uInt64 nWidth = pBox->GetFrmFmt()->GetFrmSize().GetWidth();
747 : 0 : nWidth *= nOldAct;
748 : 0 : nWidth /= rParm.nOldWish;
749 : 0 : long nRight = nLeft + (long)nWidth;
750 : 0 : sal_uInt16 nLeftPos = USHRT_MAX,
751 : 0 : nRightPos = USHRT_MAX;
752 [ # # ]: 0 : for ( sal_uInt16 i = 0; i < rParm.rOld.Count(); ++i )
753 : : {
754 [ # # # # ]: 0 : if ( nLeft >= (rParm.rOld[i] - COLFUZZY) &&
[ # # ]
755 : 0 : nLeft <= (rParm.rOld[i] + COLFUZZY) )
756 : 0 : nLeftPos = i;
757 [ # # # # ]: 0 : else if ( nRight >= (rParm.rOld[i] - COLFUZZY) &&
[ # # ]
758 : 0 : nRight <= (rParm.rOld[i] + COLFUZZY) )
759 : 0 : nRightPos = i;
760 : : }
761 : : nLeftDiff = nLeftPos != USHRT_MAX ?
762 [ # # ]: 0 : (int)rParm.rOld[nLeftPos] - (int)rParm.rNew[nLeftPos] : 0;
763 : : nRightDiff= nRightPos!= USHRT_MAX ?
764 [ # # ]: 0 : (int)rParm.rNew[nRightPos] - (int)rParm.rOld[nRightPos] : 0;
765 : : }
766 : : else // The first box.
767 : : {
768 : 0 : nLeftDiff = (long)rParm.rOld.GetLeft() - (long)rParm.rNew.GetLeft();
769 [ # # ]: 0 : if ( rParm.rOld.Count() )
770 : : {
771 : : // Calculate the difference to the edge touching the first box.
772 : 0 : sal_uInt64 nWidth = pBox->GetFrmFmt()->GetFrmSize().GetWidth();
773 : 0 : nWidth *= nOldAct;
774 : 0 : nWidth /= rParm.nOldWish;
775 : 0 : long nTmp = (long)nWidth;
776 : 0 : nTmp += rParm.rOld.GetLeft();
777 : 0 : sal_uInt16 nLeftPos = USHRT_MAX;
778 [ # # ][ # # ]: 0 : for ( sal_uInt16 i = 0; i < rParm.rOld.Count() &&
[ # # ]
779 : : nLeftPos == USHRT_MAX; ++i )
780 : : {
781 [ # # # # ]: 0 : if ( nTmp >= (rParm.rOld[i] - COLFUZZY) &&
[ # # ]
782 : 0 : nTmp <= (rParm.rOld[i] + COLFUZZY) )
783 : 0 : nLeftPos = i;
784 : : }
785 [ # # ]: 0 : if ( nLeftPos != USHRT_MAX )
786 : 0 : nRightDiff = (long)rParm.rNew[nLeftPos] -
787 : 0 : (long)rParm.rOld[nLeftPos];
788 : : }
789 : : }
790 : :
791 [ # # ]: 0 : if( pBox->getRowSpan() == 1 )
792 : : {
793 : 0 : SwTableBoxes& rTblBoxes = pBox->GetUpper()->GetTabBoxes();
794 : 0 : sal_uInt16 nPos = rTblBoxes.GetPos( pBox );
795 [ # # ][ # # ]: 0 : if( nPos && rTblBoxes[ nPos - 1 ]->getRowSpan() != 1 )
[ # # ]
796 : 0 : nLeftDiff = 0;
797 [ # # # # ]: 0 : if( nPos + 1 < (sal_uInt16)rTblBoxes.size() &&
[ # # ]
798 : 0 : rTblBoxes[ nPos + 1 ]->getRowSpan() != 1 )
799 : 0 : nRightDiff = 0;
800 : : }
801 : : else
802 : 0 : nLeftDiff = nRightDiff = 0;
803 : :
804 [ # # ][ # # ]: 0 : if ( nLeftDiff || nRightDiff )
805 : : {
806 : : // The difference is the actual difference amount. For stretched
807 : : // tables, it does not make sense to adjust the attributes of the
808 : : // boxes by this amount. The difference amount needs to be converted
809 : : // accordingly.
810 : 0 : long nTmp = rParm.rNew.GetRight() - rParm.rNew.GetLeft(); // +1 why?
811 : 0 : nLeftDiff *= rParm.nNewWish;
812 : 0 : nLeftDiff /= nTmp;
813 : 0 : nRightDiff *= rParm.nNewWish;
814 : 0 : nRightDiff /= nTmp;
815 : 0 : long nDiff = nLeftDiff + nRightDiff;
816 : :
817 : : // Adjust the box and all superiors by the difference amount.
818 [ # # ]: 0 : while ( pBox )
819 : : {
820 [ # # ][ # # ]: 0 : SwFmtFrmSize aFmtFrmSize( pBox->GetFrmFmt()->GetFrmSize() );
821 : 0 : aFmtFrmSize.SetWidth( aFmtFrmSize.GetWidth() + nDiff );
822 [ # # ]: 0 : if ( aFmtFrmSize.GetWidth() < 0 )
823 : 0 : aFmtFrmSize.SetWidth( -aFmtFrmSize.GetWidth() );
824 [ # # ]: 0 : rParm.aShareFmts.SetSize( *pBox, aFmtFrmSize );
825 : :
826 : : // The outer cells of the last row are responsible to adjust a surrounding cell.
827 : : // Last line check:
828 [ # # ][ # # ]: 0 : if ( pBox->GetUpper()->GetUpper() &&
[ # # ]
829 [ # # ]: 0 : pBox->GetUpper() != pBox->GetUpper()->GetUpper()->GetTabLines().back())
830 : : {
831 : 0 : pBox = 0;
832 : : }
833 : : else
834 : : {
835 : : // Middle cell check:
836 [ # # ][ # # ]: 0 : if ( pBox != pBox->GetUpper()->GetTabBoxes().front() )
837 : 0 : nDiff = nRightDiff;
838 : :
839 [ # # ][ # # ]: 0 : if ( pBox != pBox->GetUpper()->GetTabBoxes().back() )
840 : 0 : nDiff -= nRightDiff;
841 : :
842 [ # # ]: 0 : pBox = nDiff ? pBox->GetUpper()->GetUpper() : 0;
843 : : }
844 [ # # ]: 0 : }
845 : : }
846 : : }
847 : 0 : }
848 : :
849 : 0 : void lcl_ProcessBoxPtr( SwTableBox *pBox, std::deque<SwTableBox*> &rBoxArr,
850 : : sal_Bool bBefore )
851 : : {
852 [ # # ]: 0 : if ( !pBox->GetTabLines().empty() )
853 : : {
854 : 0 : const SwTableLines &rLines = pBox->GetTabLines();
855 [ # # ]: 0 : for ( sal_uInt16 i = 0; i < rLines.size(); ++i )
856 : : {
857 : 0 : const SwTableBoxes &rBoxes = rLines[i]->GetTabBoxes();
858 [ # # ]: 0 : for ( sal_uInt16 j = 0; j < rBoxes.size(); ++j )
859 : 0 : ::lcl_ProcessBoxPtr( rBoxes[j], rBoxArr, bBefore );
860 : : }
861 : : }
862 [ # # ]: 0 : else if ( bBefore )
863 : 0 : rBoxArr.push_front( pBox );
864 : : else
865 : 0 : rBoxArr.push_back( pBox );
866 : 0 : }
867 : :
868 : : void lcl_AdjustBox( SwTableBox *pBox, const long nDiff, Parm &rParm );
869 : :
870 : 0 : void lcl_AdjustLines( SwTableLines &rLines, const long nDiff, Parm &rParm )
871 : : {
872 [ # # ]: 0 : for ( sal_uInt16 i = 0; i < rLines.size(); ++i )
873 : : {
874 : 0 : SwTableBox *pBox = rLines[i]->GetTabBoxes()
875 : 0 : [rLines[i]->GetTabBoxes().size()-1];
876 : 0 : lcl_AdjustBox( pBox, nDiff, rParm );
877 : : }
878 : 0 : }
879 : :
880 : 0 : void lcl_AdjustBox( SwTableBox *pBox, const long nDiff, Parm &rParm )
881 : : {
882 [ # # ]: 0 : if ( !pBox->GetTabLines().empty() )
883 [ # # ]: 0 : ::lcl_AdjustLines( pBox->GetTabLines(), nDiff, rParm );
884 : :
885 : : // Adjust the size of the box.
886 [ # # ][ # # ]: 0 : SwFmtFrmSize aFmtFrmSize( pBox->GetFrmFmt()->GetFrmSize() );
887 : 0 : aFmtFrmSize.SetWidth( aFmtFrmSize.GetWidth() + nDiff );
888 : :
889 [ # # ][ # # ]: 0 : rParm.aShareFmts.SetSize( *pBox, aFmtFrmSize );
890 : 0 : }
891 : :
892 : 79 : void SwTable::SetTabCols( const SwTabCols &rNew, const SwTabCols &rOld,
893 : : const SwTableBox *pStart, sal_Bool bCurRowOnly )
894 : : {
895 : : CHECK_TABLE( *this )
896 : :
897 [ + - ]: 79 : SetHTMLTableLayout( 0 ); // delete HTML-Layout
898 : :
899 : : // FME: Made rOld const. The caller is responsible for passing correct
900 : : // values of rOld. Therefore we do not have to call GetTabCols anymore:
901 : : //GetTabCols( rOld, pStart );
902 : :
903 [ + - ]: 79 : Parm aParm( rNew, rOld );
904 : :
905 : : OSL_ENSURE( rOld.Count() == rNew.Count(), "Columnanzahl veraendert.");
906 : :
907 : : // Convert the edges. We need to adjust the size of the table and some boxes.
908 : : // For the size adjustment, we must not make use of the Modify, since that'd
909 : : // adjust all boxes, which we really don't want.
910 : 79 : SwFrmFmt *pFmt = GetFrmFmt();
911 [ + - ]: 79 : aParm.nOldWish = aParm.nNewWish = pFmt->GetFrmSize().GetWidth();
912 [ - + ]: 158 : if ( (rOld.GetLeft() != rNew.GetLeft()) ||
[ + - - + ]
913 : 79 : (rOld.GetRight()!= rNew.GetRight()) )
914 : : {
915 : 0 : LockModify();
916 : : {
917 [ # # ][ # # ]: 0 : SvxLRSpaceItem aLR( pFmt->GetLRSpace() );
918 [ # # ][ # # ]: 0 : SvxShadowItem aSh( pFmt->GetShadow() );
919 : :
920 [ # # ]: 0 : SwTwips nShRight = aSh.CalcShadowSpace( SHADOW_RIGHT );
921 [ # # ]: 0 : SwTwips nShLeft = aSh.CalcShadowSpace( SHADOW_LEFT );
922 : :
923 : 0 : aLR.SetLeft ( rNew.GetLeft() - nShLeft );
924 : 0 : aLR.SetRight( rNew.GetRightMax() - rNew.GetRight() - nShRight );
925 [ # # ]: 0 : pFmt->SetFmtAttr( aLR );
926 : :
927 : : // The alignment of the table needs to be adjusted accordingly.
928 : : // This is done by preserving the exact positions that have been
929 : : // set by the user.
930 [ # # ][ # # ]: 0 : SwFmtHoriOrient aOri( pFmt->GetHoriOrient() );
931 [ # # ]: 0 : if(text::HoriOrientation::NONE != aOri.GetHoriOrient())
932 : : {
933 : 0 : const sal_Bool bLeftDist = rNew.GetLeft() != nShLeft;
934 : 0 : const sal_Bool bRightDist = rNew.GetRight() + nShRight != rNew.GetRightMax();
935 [ # # ][ # # ]: 0 : if(!bLeftDist && !bRightDist)
936 : 0 : aOri.SetHoriOrient( text::HoriOrientation::FULL );
937 [ # # ][ # # ]: 0 : else if(!bRightDist && rNew.GetLeft() > nShLeft )
[ # # ]
938 : 0 : aOri.SetHoriOrient( text::HoriOrientation::RIGHT );
939 [ # # ][ # # ]: 0 : else if(!bLeftDist && rNew.GetRight() + nShRight < rNew.GetRightMax())
[ # # ]
940 : 0 : aOri.SetHoriOrient( text::HoriOrientation::LEFT );
941 : : else
942 : 0 : aOri.SetHoriOrient( text::HoriOrientation::LEFT_AND_WIDTH );
943 : : }
944 [ # # ][ # # ]: 0 : pFmt->SetFmtAttr( aOri );
[ # # ][ # # ]
945 : : }
946 : 0 : const long nAct = rOld.GetRight() - rOld.GetLeft(); // +1 why?
947 : 0 : long nTabDiff = 0;
948 : :
949 [ # # ]: 0 : if ( rOld.GetLeft() != rNew.GetLeft() )
950 : : {
951 : 0 : nTabDiff = rOld.GetLeft() - rNew.GetLeft();
952 : 0 : nTabDiff *= aParm.nOldWish;
953 : 0 : nTabDiff /= nAct;
954 : : }
955 [ # # ]: 0 : if ( rOld.GetRight() != rNew.GetRight() )
956 : : {
957 : 0 : long nDiff = rNew.GetRight() - rOld.GetRight();
958 : 0 : nDiff *= aParm.nOldWish;
959 : 0 : nDiff /= nAct;
960 : 0 : nTabDiff += nDiff;
961 [ # # ]: 0 : if( !IsNewModel() )
962 [ # # ]: 0 : ::lcl_AdjustLines( GetTabLines(), nDiff, aParm );
963 : : }
964 : :
965 : : // Adjust the size of the table, watch out for stretched tables.
966 [ # # ]: 0 : if ( nTabDiff )
967 : : {
968 : 0 : aParm.nNewWish += nTabDiff;
969 [ # # ]: 0 : if ( aParm.nNewWish < 0 )
970 : 0 : aParm.nNewWish = USHRT_MAX; // Oops! Have to roll back.
971 [ # # ][ # # ]: 0 : SwFmtFrmSize aSz( pFmt->GetFrmSize() );
972 [ # # ]: 0 : if ( aSz.GetWidth() != aParm.nNewWish )
973 : : {
974 : 0 : aSz.SetWidth( aParm.nNewWish );
975 : 0 : aSz.SetWidthPercent( 0 );
976 [ # # ]: 0 : pFmt->SetFmtAttr( aSz );
977 [ # # ]: 0 : }
978 : : }
979 : 0 : UnlockModify();
980 : : }
981 : :
982 [ + - ]: 79 : if( IsNewModel() )
983 [ + - ]: 79 : NewSetTabCols( aParm, rNew, rOld, pStart, bCurRowOnly );
984 : : else
985 : : {
986 [ # # ]: 0 : if ( bCurRowOnly )
987 : : {
988 : : // To adjust the current row, we need to process all its boxes,
989 : : // similar to the filling of the TabCols (see GetTabCols()).
990 : : // Unfortunately we again have to take care to adjust the boxes
991 : : // from back to front, respectively from outer to inner.
992 : : // The best way to achieve this is probably to track the boxes
993 : : // in a PtrArray.
994 : 0 : const SwTableBoxes &rBoxes = pStart->GetUpper()->GetTabBoxes();
995 [ # # ]: 0 : for ( sal_uInt16 i = 0; i < rBoxes.size(); ++i )
996 [ # # ]: 0 : ::lcl_ProcessBoxPtr( rBoxes[i], aParm.aBoxArr, sal_False );
997 : :
998 : 0 : const SwTableLine *pLine = pStart->GetUpper()->GetUpper() ?
999 [ # # ]: 0 : pStart->GetUpper()->GetUpper()->GetUpper() : 0;
1000 : 0 : const SwTableBox *pExcl = pStart->GetUpper()->GetUpper();
1001 [ # # ]: 0 : while ( pLine )
1002 : : {
1003 : 0 : const SwTableBoxes &rBoxes2 = pLine->GetTabBoxes();
1004 : 0 : sal_Bool bBefore = sal_True;
1005 [ # # ]: 0 : for ( sal_uInt16 i = 0; i < rBoxes2.size(); ++i )
1006 : : {
1007 [ # # ]: 0 : if ( rBoxes2[i] != pExcl )
1008 [ # # ]: 0 : ::lcl_ProcessBoxPtr( rBoxes2[i], aParm.aBoxArr, bBefore );
1009 : : else
1010 : 0 : bBefore = sal_False;
1011 : : }
1012 : 0 : pExcl = pLine->GetUpper();
1013 [ # # ]: 0 : pLine = pLine->GetUpper() ? pLine->GetUpper()->GetUpper() : 0;
1014 : : }
1015 : : // After we've inserted a bunch of boxes (hopefully all and in
1016 : : // correct order), we just need to process them in reverse order.
1017 [ # # ]: 0 : for ( int j = aParm.aBoxArr.size()-1; j >= 0; --j )
1018 : : {
1019 [ # # ]: 0 : SwTableBox *pBox = aParm.aBoxArr[j];
1020 [ # # ]: 0 : ::lcl_ProcessBoxSet( pBox, aParm );
1021 : : }
1022 : : }
1023 : : else
1024 : : {
1025 : : // Adjusting the entire table is 'easy'. All boxes without lines are
1026 : : // adjusted, as are their superiors. Of course we need to process
1027 : : // in reverse order to prevent fooling ourselves!
1028 : 0 : SwTableLines &rLines = GetTabLines();
1029 [ # # ]: 0 : for ( int i = rLines.size()-1; i >= 0; --i )
1030 [ # # ]: 0 : ::lcl_ProcessLine( rLines[ static_cast< sal_uInt16 >(i) ], aParm );
1031 : : }
1032 [ + - ]: 79 : }
1033 : :
1034 : : #ifdef DBG_UTIL
1035 : : {
1036 : : // to be found in tblrwcl.cxx
1037 : : extern void _CheckBoxWidth( const SwTableLine&, SwTwips );
1038 : : // do some checking for correct table widths
1039 : : SwTwips nSize = GetFrmFmt()->GetFrmSize().GetWidth();
1040 : : for (size_t n = 0; n < aLines.size(); ++n)
1041 : : {
1042 : : _CheckBoxWidth( *aLines[ n ], nSize );
1043 : : }
1044 : : }
1045 : : #endif
1046 : 79 : }
1047 : :
1048 : : typedef std::pair<sal_uInt16, sal_uInt16> ColChange;
1049 : : typedef std::list< ColChange > ChangeList;
1050 : :
1051 : 79 : static void lcl_AdjustWidthsInLine( SwTableLine* pLine, ChangeList& rOldNew,
1052 : : Parm& rParm, sal_uInt16 nColFuzzy )
1053 : : {
1054 : 79 : ChangeList::iterator pCurr = rOldNew.begin();
1055 [ + - ][ + - ]: 79 : if( pCurr == rOldNew.end() )
1056 : 79 : return;
1057 : 79 : sal_uInt16 nCount = pLine->GetTabBoxes().size();
1058 : 79 : sal_uInt16 i = 0;
1059 : 79 : SwTwips nBorder = 0;
1060 : 79 : SwTwips nRest = 0;
1061 [ + + ]: 515 : while( i < nCount )
1062 : : {
1063 : 436 : SwTableBox* pBox = pLine->GetTabBoxes()[i++];
1064 [ + - ]: 436 : SwTwips nWidth = pBox->GetFrmFmt()->GetFrmSize().GetWidth();
1065 : 436 : SwTwips nNewWidth = nWidth - nRest;
1066 : 436 : nRest = 0;
1067 : 436 : nBorder += nWidth;
1068 [ + + ][ + - ]: 436 : if( pCurr != rOldNew.end() && nBorder + nColFuzzy >= pCurr->first )
[ + + ][ + - ]
[ + + # # ]
[ + - ]
1069 : : {
1070 : 346 : nBorder -= nColFuzzy;
1071 [ + - ][ + - ]: 425 : while( pCurr != rOldNew.end() && nBorder > pCurr->first )
[ + - ][ + + ]
[ + - ]
[ + + # # ]
1072 [ + - ]: 79 : ++pCurr;
1073 [ + - ][ + - ]: 346 : if( pCurr != rOldNew.end() )
1074 : : {
1075 : 346 : nBorder += nColFuzzy;
1076 [ + - ][ + + ]: 346 : if( nBorder + nColFuzzy >= pCurr->first )
1077 : : {
1078 [ + - ][ + - ]: 338 : if( pCurr->second == pCurr->first )
[ - + ]
1079 : 0 : nRest = 0;
1080 : : else
1081 [ + - ]: 338 : nRest = pCurr->second - nBorder;
1082 : 338 : nNewWidth += nRest;
1083 [ + - ]: 338 : ++pCurr;
1084 : : }
1085 : : }
1086 : : }
1087 [ + + ]: 436 : if( nNewWidth != nWidth )
1088 : : {
1089 [ - + ]: 365 : if( nNewWidth < 0 )
1090 : : {
1091 : 0 : nRest += 1 - nNewWidth;
1092 : 0 : nNewWidth = 1;
1093 : : }
1094 [ + - ][ + - ]: 365 : SwFmtFrmSize aFmtFrmSize( pBox->GetFrmFmt()->GetFrmSize() );
1095 : 365 : aFmtFrmSize.SetWidth( nNewWidth );
1096 [ + - ][ + - ]: 365 : rParm.aShareFmts.SetSize( *pBox, aFmtFrmSize );
1097 : : }
1098 : : }
1099 : : }
1100 : :
1101 : 14 : static void lcl_CalcNewWidths( std::list<sal_uInt16> &rSpanPos, ChangeList& rChanges,
1102 : : SwTableLine* pLine, long nWish, long nWidth, bool bTop )
1103 : : {
1104 [ - + ]: 14 : if( rChanges.empty() )
1105 : : {
1106 : 0 : rSpanPos.clear();
1107 : : return;
1108 : : }
1109 [ - + ]: 14 : if( rSpanPos.empty() )
1110 : : {
1111 : 0 : rChanges.clear();
1112 : : return;
1113 : : }
1114 [ + - ]: 14 : std::list<sal_uInt16> aNewSpanPos;
1115 [ + - ]: 14 : ChangeList aNewChanges;
1116 : 14 : ChangeList::iterator pCurr = rChanges.begin();
1117 [ + - ][ + - ]: 14 : aNewChanges.push_back( *pCurr ); // Nullposition
1118 : 14 : std::list<sal_uInt16>::iterator pSpan = rSpanPos.begin();
1119 : 14 : sal_uInt16 nCurr = 0;
1120 : 14 : sal_uInt16 nOrgSum = 0;
1121 : 14 : bool bRowSpan = false;
1122 : 14 : sal_uInt16 nRowSpanCount = 0;
1123 : 14 : sal_uInt16 nCount = pLine->GetTabBoxes().size();
1124 [ + + ]: 58 : for( sal_uInt16 nCurrBox = 0; nCurrBox < nCount; ++nCurrBox )
1125 : : {
1126 : 44 : SwTableBox* pBox = pLine->GetTabBoxes()[nCurrBox];
1127 [ + - ]: 44 : SwTwips nCurrWidth = pBox->GetFrmFmt()->GetFrmSize().GetWidth();
1128 [ + - ]: 44 : const long nRowSpan = pBox->getRowSpan();
1129 : : const bool bCurrRowSpan = bTop ? nRowSpan < 0 :
1130 [ + + ][ + - ]: 44 : ( nRowSpan > 1 || nRowSpan < -1 );
[ - + ]
1131 [ + - ][ - + ]: 44 : if( bRowSpan || bCurrRowSpan )
1132 [ # # ]: 0 : aNewSpanPos.push_back( nRowSpanCount );
1133 : 44 : bRowSpan = bCurrRowSpan;
1134 : 44 : nOrgSum = (sal_uInt16)(nOrgSum + nCurrWidth);
1135 : 44 : sal_uInt64 nSum = nOrgSum;
1136 : 44 : nSum *= nWidth;
1137 : 44 : nSum /= nWish;
1138 : 44 : nSum *= nWish;
1139 : 44 : nSum /= nWidth;
1140 : 44 : sal_uInt16 nPos = (sal_uInt16)nSum;
1141 [ + - ][ + + ]: 88 : while( pCurr != rChanges.end() && pCurr->first < nPos )
[ + - ][ + + ]
[ + - ]
[ + + # # ]
1142 : : {
1143 : 44 : ++nCurr;
1144 [ + - ]: 44 : ++pCurr;
1145 : : }
1146 : 44 : bool bNew = true;
1147 [ + - ][ + + ]: 74 : if( pCurr != rChanges.end() && pCurr->first <= nPos &&
[ + - ][ + - ]
[ + - ][ + - ]
[ + + # # ]
1148 [ + - ][ + - ]: 30 : pCurr->first != pCurr->second )
1149 : : {
1150 [ + - ][ + - ]: 60 : while( pSpan != rSpanPos.end() && *pSpan < nCurr )
[ + - ][ + + ]
[ + - ]
[ + + # # ]
1151 [ + - ]: 30 : ++pSpan;
1152 [ + - ][ + - ]: 30 : if( pSpan != rSpanPos.end() && *pSpan == nCurr )
[ + - ][ + - ]
[ + - ]
[ + - # # ]
1153 : : {
1154 [ + - ][ + - ]: 30 : aNewChanges.push_back( *pCurr );
1155 : 30 : ++nRowSpanCount;
1156 : 30 : bNew = false;
1157 : : }
1158 : : }
1159 [ + + ]: 44 : if( bNew )
1160 : : {
1161 [ + - ]: 14 : ColChange aTmp( nPos, nPos );
1162 [ + - ]: 14 : aNewChanges.push_back( aTmp );
1163 : 14 : ++nRowSpanCount;
1164 : : }
1165 : : }
1166 : :
1167 : 14 : pCurr = aNewChanges.begin();
1168 : 14 : ChangeList::iterator pLast = pCurr;
1169 : 14 : ChangeList::iterator pLeftMove = pCurr;
1170 [ + - ][ + + ]: 72 : while( pCurr != aNewChanges.end() )
1171 : : {
1172 [ + - ][ + + ]: 58 : if( pLeftMove == pCurr )
1173 : : {
1174 [ + - ][ + - ]: 58 : while( ++pLeftMove != aNewChanges.end() && pLeftMove->first <= pLeftMove->second )
[ + + ][ + - ]
[ + - ][ + + ]
[ + - ]
[ + + # # ]
1175 : : ;
1176 : : }
1177 [ + - ][ + - ]: 58 : if( pCurr->second == pCurr->first )
[ + + ]
1178 : : {
1179 [ + - ][ + + ]: 28 : if( pLeftMove != aNewChanges.end() && pCurr->second > pLeftMove->second )
[ + - ][ + - ]
[ - + ][ + - ]
[ - + # # ]
1180 : : {
1181 [ # # ][ # # ]: 0 : if( pLeftMove->first == pLast->first )
[ # # ]
1182 [ # # ][ # # ]: 0 : pCurr->second = pLeftMove->second;
1183 : : else
1184 : : {
1185 [ # # ][ # # ]: 0 : sal_uInt64 nTmp = pCurr->first - pLast->first;
1186 [ # # ][ # # ]: 0 : nTmp *= pLeftMove->second - pLast->second;
1187 [ # # ][ # # ]: 0 : nTmp /= pLeftMove->first - pLast->first;
1188 [ # # ]: 0 : nTmp += pLast->second;
1189 [ # # ]: 0 : pCurr->second = (sal_uInt16)nTmp;
1190 : : }
1191 : : }
1192 : 28 : pLast = pCurr;
1193 [ + - ]: 28 : ++pCurr;
1194 : : }
1195 [ + - ][ + - ]: 30 : else if( pCurr->second > pCurr->first )
[ + + ]
1196 : : {
1197 : 24 : pLast = pCurr;
1198 [ + - ]: 24 : ++pCurr;
1199 : 24 : ChangeList::iterator pNext = pCurr;
1200 [ + - ][ + - ]: 32 : while( pNext != pLeftMove && pNext->second == pNext->first &&
[ + - ][ + - ]
[ + + ][ - + ]
[ - + ]
1201 [ + - ][ + - ]: 8 : pNext->second < pLast->second )
1202 [ # # ]: 0 : ++pNext;
1203 [ + - ][ - + ]: 24 : while( pCurr != pNext )
1204 : : {
1205 [ # # ][ # # ]: 0 : if( pNext == aNewChanges.end() || pNext->first == pLast->first )
[ # # ][ # # ]
[ # # ][ # # ]
[ # # # # ]
1206 [ # # ][ # # ]: 0 : pCurr->second = pLast->second;
1207 : : else
1208 : : {
1209 [ # # ][ # # ]: 0 : sal_uInt64 nTmp = pCurr->first - pLast->first;
1210 [ # # ][ # # ]: 0 : nTmp *= pNext->second - pLast->second;
1211 [ # # ][ # # ]: 0 : nTmp /= pNext->first - pLast->first;
1212 [ # # ]: 0 : nTmp += pLast->second;
1213 [ # # ]: 0 : pCurr->second = (sal_uInt16)nTmp;
1214 : : }
1215 [ # # ]: 0 : ++pCurr;
1216 : : }
1217 : 24 : pLast = pCurr;
1218 : : }
1219 : : else
1220 : : {
1221 : 6 : pLast = pCurr;
1222 [ + - ]: 6 : ++pCurr;
1223 : : }
1224 : : }
1225 : :
1226 : 14 : rChanges.clear();
1227 : 14 : ChangeList::iterator pCopy = aNewChanges.begin();
1228 [ + - ][ + + ]: 72 : while( pCopy != aNewChanges.end() )
1229 [ + - ][ + - ]: 58 : rChanges.push_back( *pCopy++ );
[ + - ]
1230 : 14 : rSpanPos.clear();
1231 : 14 : std::list<sal_uInt16>::iterator pSpCopy = aNewSpanPos.begin();
1232 [ + - ][ - + ]: 14 : while( pSpCopy != aNewSpanPos.end() )
1233 [ # # ][ # # ]: 14 : rSpanPos.push_back( *pSpCopy++ );
[ # # ]
1234 : : }
1235 : :
1236 : 79 : void SwTable::NewSetTabCols( Parm &rParm, const SwTabCols &rNew,
1237 : : const SwTabCols &rOld, const SwTableBox *pStart, sal_Bool bCurRowOnly )
1238 : : {
1239 : : #if OSL_DEBUG_LEVEL > 1
1240 : : static int nCallCount = 0;
1241 : : ++nCallCount;
1242 : : #endif
1243 : : // First step: evaluate which lines have been moved/which widths changed
1244 [ + - ]: 79 : ChangeList aOldNew;
1245 : 79 : const long nNewWidth = rParm.rNew.GetRight() - rParm.rNew.GetLeft();
1246 : 79 : const long nOldWidth = rParm.rOld.GetRight() - rParm.rOld.GetLeft();
1247 [ - + ][ + - ]: 79 : if( nNewWidth < 1 || nOldWidth < 1 )
1248 : : return;
1249 [ + - ][ + + ]: 515 : for( sal_uInt16 i = 0; i <= rOld.Count(); ++i )
1250 : : {
1251 : : sal_uInt64 nNewPos;
1252 : : sal_uInt64 nOldPos;
1253 [ + - ][ + + ]: 436 : if( i == rOld.Count() )
1254 : : {
1255 : 79 : nOldPos = rParm.rOld.GetRight() - rParm.rOld.GetLeft();
1256 : 79 : nNewPos = rParm.rNew.GetRight() - rParm.rNew.GetLeft();
1257 : : }
1258 : : else
1259 : : {
1260 [ + - ]: 357 : nOldPos = rOld[i] - rParm.rOld.GetLeft();
1261 [ + - ]: 357 : nNewPos = rNew[i] - rParm.rNew.GetLeft();
1262 : : }
1263 : 436 : nNewPos *= rParm.nNewWish;
1264 : 436 : nNewPos /= nNewWidth;
1265 : 436 : nOldPos *= rParm.nOldWish;
1266 : 436 : nOldPos /= nOldWidth;
1267 [ + + ][ + - ]: 436 : if( nOldPos != nNewPos && nNewPos > 0 && nOldPos > 0 )
[ + - ]
1268 : : {
1269 [ + - ]: 338 : ColChange aChg( (sal_uInt16)nOldPos, (sal_uInt16)nNewPos );
1270 [ + - ]: 338 : aOldNew.push_back( aChg );
1271 : : }
1272 : : }
1273 : : // Finished first step
1274 : 79 : int nCount = aOldNew.size();
1275 [ - + ]: 79 : if( !nCount )
1276 : : return; // no change, nothing to do
1277 : 79 : SwTableLines &rLines = GetTabLines();
1278 [ + - ]: 79 : if( bCurRowOnly )
1279 : : {
1280 : 79 : const SwTableLine* pCurrLine = pStart->GetUpper();
1281 [ + - ]: 79 : sal_uInt16 nCurr = rLines.GetPos( pCurrLine );
1282 [ + - ]: 79 : if( nCurr >= USHRT_MAX )
1283 : : return;
1284 : :
1285 : 79 : ColChange aChg( 0, 0 );
1286 [ + - ]: 79 : aOldNew.push_front( aChg );
1287 [ + - ]: 79 : std::list<sal_uInt16> aRowSpanPos;
1288 [ + + ]: 79 : if( nCurr )
1289 : : {
1290 [ + - ]: 7 : ChangeList aCopy;
1291 : 7 : ChangeList::iterator pCop = aOldNew.begin();
1292 : 7 : sal_uInt16 nPos = 0;
1293 [ + - ][ + + ]: 29 : while( pCop != aOldNew.end() )
1294 : : {
1295 [ + - ][ + - ]: 22 : aCopy.push_back( *pCop );
1296 [ + - ]: 22 : ++pCop;
1297 [ + - ]: 22 : aRowSpanPos.push_back( nPos++ );
1298 : : }
1299 : 7 : lcl_CalcNewWidths( aRowSpanPos, aCopy, rLines[nCurr],
1300 [ + - ]: 7 : rParm.nOldWish, nOldWidth, true );
1301 : 7 : bool bGoOn = !aRowSpanPos.empty();
1302 : 7 : sal_uInt16 j = nCurr;
1303 [ - + ]: 7 : while( bGoOn )
1304 : : {
1305 : 0 : lcl_CalcNewWidths( aRowSpanPos, aCopy, rLines[--j],
1306 [ # # ]: 0 : rParm.nOldWish, nOldWidth, true );
1307 [ # # ]: 0 : lcl_AdjustWidthsInLine( rLines[j], aCopy, rParm, 0 );
1308 [ # # ][ # # ]: 0 : bGoOn = !aRowSpanPos.empty() && j > 0;
1309 : : };
1310 : 7 : aRowSpanPos.clear();
1311 : : }
1312 [ + + ]: 79 : if( nCurr+1 < (sal_uInt16)rLines.size() )
1313 : : {
1314 [ + - ]: 7 : ChangeList aCopy;
1315 : 7 : ChangeList::iterator pCop = aOldNew.begin();
1316 : 7 : sal_uInt16 nPos = 0;
1317 [ + - ][ + + ]: 29 : while( pCop != aOldNew.end() )
1318 : : {
1319 [ + - ][ + - ]: 22 : aCopy.push_back( *pCop );
1320 [ + - ]: 22 : ++pCop;
1321 [ + - ]: 22 : aRowSpanPos.push_back( nPos++ );
1322 : : }
1323 : 7 : lcl_CalcNewWidths( aRowSpanPos, aCopy, rLines[nCurr],
1324 [ + - ]: 7 : rParm.nOldWish, nOldWidth, false );
1325 : 7 : bool bGoOn = !aRowSpanPos.empty();
1326 : 7 : sal_uInt16 j = nCurr;
1327 [ - + ]: 7 : while( bGoOn )
1328 : : {
1329 : 0 : lcl_CalcNewWidths( aRowSpanPos, aCopy, rLines[++j],
1330 [ # # ]: 0 : rParm.nOldWish, nOldWidth, false );
1331 [ # # ]: 0 : lcl_AdjustWidthsInLine( rLines[j], aCopy, rParm, 0 );
1332 [ # # ][ # # ]: 0 : bGoOn = !aRowSpanPos.empty() && j+1 < (sal_uInt16)rLines.size();
1333 : 7 : };
1334 : : }
1335 [ + - ]: 79 : ::lcl_AdjustWidthsInLine( rLines[nCurr], aOldNew, rParm, COLFUZZY );
1336 : : }
1337 [ # # ]: 79 : else for( sal_uInt16 i = 0; i < rLines.size(); ++i )
1338 [ # # ][ + - ]: 79 : ::lcl_AdjustWidthsInLine( rLines[i], aOldNew, rParm, COLFUZZY );
1339 : : CHECK_TABLE( *this )
1340 : : }
1341 : :
1342 : :
1343 : : /*************************************************************************
1344 : : |*
1345 : : |* const SwTableBox* SwTable::GetTblBox( const Strn?ng& rName ) const
1346 : : |* return the pointer of the box specified.
1347 : : |*
1348 : : |*************************************************************************/
1349 : :
1350 : 0 : sal_Bool IsValidRowName( const String& rStr )
1351 : : {
1352 : 0 : sal_Bool bIsValid = sal_True;
1353 : 0 : xub_StrLen nLen = rStr.Len();
1354 [ # # ][ # # ]: 0 : for (xub_StrLen i = 0; i < nLen && bIsValid; ++i)
[ # # ]
1355 : : {
1356 : 0 : const sal_Unicode cChar = rStr.GetChar(i);
1357 [ # # ][ # # ]: 0 : if (cChar < '0' || cChar > '9')
1358 : 0 : bIsValid = sal_False;
1359 : : }
1360 : 0 : return bIsValid;
1361 : : }
1362 : :
1363 : : // #i80314#
1364 : : // add 3rd parameter and its handling
1365 : 3292 : sal_uInt16 SwTable::_GetBoxNum( String& rStr, sal_Bool bFirstPart,
1366 : : const bool bPerformValidCheck )
1367 : : {
1368 : 3292 : sal_uInt16 nRet = 0;
1369 : 3292 : xub_StrLen nPos = 0;
1370 [ + + ]: 3292 : if( bFirstPart ) // sal_True == column; sal_False == row
1371 : : {
1372 : : // the first one uses letters for addressing!
1373 : : sal_Unicode cChar;
1374 : 1646 : sal_Bool bFirst = sal_True;
1375 [ + - ][ + + ]: 3292 : while( 0 != ( cChar = rStr.GetChar( nPos )) &&
[ - + ][ - + ]
[ # # ][ + + ]
1376 : : ( (cChar >= 'A' && cChar <= 'Z') ||
1377 : : (cChar >= 'a' && cChar <= 'z') ) )
1378 : : {
1379 [ - + ]: 1646 : if( (cChar -= 'A') >= 26 )
1380 : 0 : cChar -= 'a' - '[';
1381 [ + - ]: 1646 : if( bFirst )
1382 : 1646 : bFirst = sal_False;
1383 : : else
1384 : 0 : ++nRet;
1385 : 1646 : nRet = nRet * 52 + cChar;
1386 : 1646 : ++nPos;
1387 : : }
1388 : 1646 : rStr.Erase( 0, nPos ); // Remove char from String
1389 : : }
1390 [ + - ][ + - ]: 1646 : else if( STRING_NOTFOUND == ( nPos = rStr.Search( aDotStr ) ))
1391 : : {
1392 : 1646 : nRet = 0;
1393 [ - + ][ # # ]: 1646 : if ( !bPerformValidCheck || IsValidRowName( rStr ) )
[ + - ]
1394 : : {
1395 : 1646 : nRet = static_cast<sal_uInt16>(rStr.ToInt32());
1396 : : }
1397 : 1646 : rStr.Erase();
1398 : : }
1399 : : else
1400 : : {
1401 : 0 : nRet = 0;
1402 [ # # ]: 0 : String aTxt( rStr.Copy( 0, nPos ) );
1403 [ # # ][ # # ]: 0 : if ( !bPerformValidCheck || IsValidRowName( aTxt ) )
[ # # ]
1404 : : {
1405 [ # # ]: 0 : nRet = static_cast<sal_uInt16>(aTxt.ToInt32());
1406 : : }
1407 [ # # ][ # # ]: 0 : rStr.Erase( 0, nPos+1 );
1408 : : }
1409 : 3292 : return nRet;
1410 : : }
1411 : :
1412 : : // #i80314#
1413 : : // add 2nd parameter and its handling
1414 : 1646 : const SwTableBox* SwTable::GetTblBox( const String& rName,
1415 : : const bool bPerformValidCheck ) const
1416 : : {
1417 : 1646 : const SwTableBox* pBox = 0;
1418 : : const SwTableLine* pLine;
1419 : : const SwTableLines* pLines;
1420 : : const SwTableBoxes* pBoxes;
1421 : :
1422 : : sal_uInt16 nLine, nBox;
1423 [ + - ]: 1646 : String aNm( rName );
1424 [ + + ]: 3292 : while( aNm.Len() )
1425 : : {
1426 [ + - ]: 1646 : nBox = SwTable::_GetBoxNum( aNm, 0 == pBox, bPerformValidCheck );
1427 : : // first box ?
1428 [ + - ]: 1646 : if( !pBox )
1429 : 1646 : pLines = &GetTabLines();
1430 : : else
1431 : : {
1432 : 0 : pLines = &pBox->GetTabLines();
1433 [ # # ]: 0 : if( nBox )
1434 : 0 : --nBox;
1435 : : }
1436 : :
1437 [ + - ]: 1646 : nLine = SwTable::_GetBoxNum( aNm, sal_False, bPerformValidCheck );
1438 : :
1439 : : // determine line
1440 [ + - ][ - + ]: 1646 : if( !nLine || nLine > pLines->size() )
[ - + ]
1441 : 0 : return 0;
1442 : 1646 : pLine = (*pLines)[ nLine-1 ];
1443 : :
1444 : : // determine box
1445 : 1646 : pBoxes = &pLine->GetTabBoxes();
1446 [ - + ]: 1646 : if( nBox >= pBoxes->size() )
1447 : 0 : return 0;
1448 : 1646 : pBox = (*pBoxes)[ nBox ];
1449 : : }
1450 : :
1451 : : // check if the box found has any contents
1452 [ + - ][ - + ]: 1646 : if( pBox && !pBox->GetSttNd() )
[ - + ]
1453 : : {
1454 : : OSL_FAIL( "Box without content, looking for the next one!" );
1455 : : // "drop this" until the first box
1456 [ # # ]: 0 : while( !pBox->GetTabLines().empty() )
1457 [ # # ][ # # ]: 0 : pBox = pBox->GetTabLines().front()->GetTabBoxes().front();
1458 : : }
1459 [ + - ]: 1646 : return pBox;
1460 : : }
1461 : :
1462 : 1138 : SwTableBox* SwTable::GetTblBox( sal_uLong nSttIdx )
1463 : : {
1464 : : // For optimizations, don't always process the entire SortArray.
1465 : : // Converting text to table, tries certain conditions
1466 : : // to ask for a table box of a table that is not yet having a format
1467 [ - + ]: 1138 : if(!GetFrmFmt())
1468 : 0 : return 0;
1469 : 1138 : SwTableBox* pRet = 0;
1470 : 1138 : SwNodes& rNds = GetFrmFmt()->GetDoc()->GetNodes();
1471 : 1138 : sal_uLong nIndex = nSttIdx + 1;
1472 : 1138 : SwCntntNode* pCNd = 0;
1473 : 1138 : SwTableNode* pTblNd = 0;
1474 : :
1475 [ + - ]: 1138 : while ( nIndex < rNds.Count() )
1476 : : {
1477 : 1138 : pTblNd = rNds[ nIndex ]->GetTableNode();
1478 [ - + ]: 1138 : if ( pTblNd )
1479 : 0 : break;
1480 : :
1481 : 1138 : pCNd = rNds[ nIndex ]->GetCntntNode();
1482 [ + - ]: 1138 : if ( pCNd )
1483 : 1138 : break;
1484 : :
1485 : 0 : ++nIndex;
1486 : : }
1487 : :
1488 [ - + ][ # # ]: 1138 : if ( pCNd || pTblNd )
1489 : : {
1490 : 1138 : SwModify* pModify = pCNd;
1491 : : // #144862# Better handling of table in table
1492 [ - + ][ # # ]: 1138 : if ( pTblNd && pTblNd->GetTable().GetFrmFmt() )
[ - + ]
1493 : 0 : pModify = pTblNd->GetTable().GetFrmFmt();
1494 : :
1495 : 1138 : SwFrm* pFrm = SwIterator<SwFrm,SwModify>::FirstElement( *pModify );
1496 [ + + ][ + + ]: 1547 : while ( pFrm && !pFrm->IsCellFrm() )
[ + + ]
1497 : 409 : pFrm = pFrm->GetUpper();
1498 [ + + ]: 1138 : if ( pFrm )
1499 : 409 : pRet = (SwTableBox*)((SwCellFrm*)pFrm)->GetTabBox();
1500 : : }
1501 : :
1502 : : // In case the layout doesn't exist yet or anything else goes wrong.
1503 [ + + ]: 1138 : if ( !pRet )
1504 : : {
1505 [ + - ]: 789 : for( sal_uInt16 n = aSortCntBoxes.size(); n; )
1506 [ + + ]: 789 : if( aSortCntBoxes[ --n ]->GetSttIdx() == nSttIdx )
1507 : 729 : return aSortCntBoxes[ n ];
1508 : : }
1509 : 1138 : return pRet;
1510 : : }
1511 : :
1512 : 96 : sal_Bool SwTable::IsTblComplex() const
1513 : : {
1514 : : // Returns sal_True for complex tables, i.e. tables that contain nestings,
1515 : : // like containing boxes not part of the first line, e.g. results of
1516 : : // splits/merges which lead to more complex structures.
1517 [ + + ]: 1246 : for( sal_uInt16 n = 0; n < aSortCntBoxes.size(); ++n )
1518 [ - + ]: 1150 : if( aSortCntBoxes[ n ]->GetUpper()->GetUpper() )
1519 : 0 : return sal_True;
1520 : 96 : return sal_False;
1521 : : }
1522 : :
1523 : :
1524 : :
1525 : : /*************************************************************************
1526 : : |*
1527 : : |* SwTableLine::SwTableLine()
1528 : : |*
1529 : : |*************************************************************************/
1530 : 548 : SwTableLine::SwTableLine( SwTableLineFmt *pFmt, sal_uInt16 nBoxes,
1531 : : SwTableBox *pUp )
1532 : : : SwClient( pFmt ),
1533 : : aBoxes(),
1534 [ + - ]: 548 : pUpper( pUp )
1535 : : {
1536 [ + - ]: 548 : aBoxes.reserve( (sal_uInt8)nBoxes );
1537 : 548 : }
1538 : :
1539 : 548 : SwTableLine::~SwTableLine()
1540 : : {
1541 [ + + ]: 2850 : for (size_t i = 0; i < aBoxes.size(); ++i)
1542 : : {
1543 [ + - ][ + - ]: 2302 : delete aBoxes[i];
1544 : : }
1545 : : // the TabelleLine can be deleted if it's the last client of the FrameFormat
1546 : 548 : SwModify* pMod = GetFrmFmt();
1547 [ + - ]: 548 : pMod->Remove( this ); // remove,
1548 [ + + ]: 548 : if( !pMod->GetDepends() )
1549 [ + - ][ + - ]: 313 : delete pMod; // and delete
1550 [ - + ]: 1096 : }
1551 : :
1552 : : /*************************************************************************
1553 : : |*
1554 : : |* SwTableLine::ClaimFrmFmt(), ChgFrmFmt()
1555 : : |*
1556 : : |*************************************************************************/
1557 : 236 : SwFrmFmt* SwTableLine::ClaimFrmFmt()
1558 : : {
1559 : : // This method makes sure that this object is an exclusive SwTableLine client
1560 : : // of an SwTableLineFmt object
1561 : : // If other SwTableLine objects currently listen to the same SwTableLineFmt as
1562 : : // this one, something needs to be done
1563 : 236 : SwTableLineFmt *pRet = (SwTableLineFmt*)GetFrmFmt();
1564 [ + - ]: 236 : SwIterator<SwTableLine,SwFmt> aIter( *pRet );
1565 [ + - ][ + - ]: 402 : for( SwTableLine* pLast = aIter.First(); pLast; pLast = aIter.Next() )
[ + + ]
1566 : : {
1567 [ + + ]: 247 : if ( pLast != this )
1568 : : {
1569 : : // found another SwTableLine that is a client of the current Fmt
1570 : : // create a new Fmt as a copy and use it for this object
1571 [ + - ]: 81 : SwTableLineFmt *pNewFmt = pRet->GetDoc()->MakeTableLineFmt();
1572 [ + - ]: 81 : *pNewFmt = *pRet;
1573 : :
1574 : : // register SwRowFrms that know me as clients at the new Fmt
1575 [ + - ]: 81 : SwIterator<SwRowFrm,SwFmt> aFrmIter( *pRet );
1576 [ + - ][ + - ]: 91 : for( SwRowFrm* pFrm = aFrmIter.First(); pFrm; pFrm = aFrmIter.Next() )
[ + + ]
1577 [ + + ]: 10 : if( pFrm->GetTabLine() == this )
1578 [ + - ]: 2 : pFrm->RegisterToFormat( *pNewFmt );
1579 : :
1580 : : // register myself
1581 [ + - ]: 81 : pNewFmt->Add( this );
1582 : 81 : pRet = pNewFmt;
1583 [ + - ]: 81 : break;
1584 : : }
1585 : : }
1586 : :
1587 [ + - ]: 236 : return pRet;
1588 : : }
1589 : :
1590 : 0 : void SwTableLine::ChgFrmFmt( SwTableLineFmt *pNewFmt )
1591 : : {
1592 : 0 : SwFrmFmt *pOld = GetFrmFmt();
1593 [ # # ]: 0 : SwIterator<SwRowFrm,SwFmt> aIter( *pOld );
1594 : :
1595 : : // First, re-register the Frms.
1596 [ # # ][ # # ]: 0 : for( SwRowFrm* pRow = aIter.First(); pRow; pRow = aIter.Next() )
[ # # ]
1597 : : {
1598 [ # # ]: 0 : if( pRow->GetTabLine() == this )
1599 : : {
1600 [ # # ]: 0 : pRow->RegisterToFormat( *pNewFmt );
1601 : :
1602 [ # # ]: 0 : pRow->InvalidateSize();
1603 [ # # ]: 0 : pRow->_InvalidatePrt();
1604 : 0 : pRow->SetCompletePaint();
1605 [ # # ]: 0 : pRow->ReinitializeFrmSizeAttrFlags();
1606 : :
1607 : : // #i35063#
1608 : : // consider 'split row allowed' attribute
1609 [ # # ]: 0 : SwTabFrm* pTab = pRow->FindTabFrm();
1610 : 0 : bool bInFollowFlowRow = false;
1611 : 0 : const bool bInFirstNonHeadlineRow = pTab->IsFollow() &&
1612 [ # # ][ # # ]: 0 : pRow == pTab->GetFirstNonHeadlineRow();
[ # # ]
1613 [ # # # # ]: 0 : if ( bInFirstNonHeadlineRow ||
[ # # ][ # # ]
[ # # ]
1614 : 0 : !pRow->GetNext() ||
1615 [ # # ]: 0 : 0 != ( bInFollowFlowRow = pRow->IsInFollowFlowRow() ) ||
1616 [ # # ]: 0 : 0 != pRow->IsInSplitTableRow() )
1617 : : {
1618 [ # # ][ # # ]: 0 : if ( bInFirstNonHeadlineRow || bInFollowFlowRow )
1619 [ # # ]: 0 : pTab = pTab->FindMaster();
1620 : :
1621 : 0 : pTab->SetRemoveFollowFlowLinePending( sal_True );
1622 [ # # ]: 0 : pTab->InvalidatePos();
1623 : : }
1624 : : }
1625 : : }
1626 : :
1627 : : // Now, re-register self.
1628 [ # # ]: 0 : pNewFmt->Add( this );
1629 : :
1630 [ # # ]: 0 : if ( !pOld->GetDepends() )
1631 [ # # ][ # # ]: 0 : delete pOld;
[ # # ]
1632 : 0 : }
1633 : :
1634 : 0 : SwTwips SwTableLine::GetTableLineHeight( bool& bLayoutAvailable ) const
1635 : : {
1636 : 0 : SwTwips nRet = 0;
1637 : 0 : bLayoutAvailable = false;
1638 [ # # ]: 0 : SwIterator<SwRowFrm,SwFmt> aIter( *GetFrmFmt() );
1639 : : // A row could appear several times in headers/footers so only one chain of master/follow tables
1640 : : // will be accepted...
1641 : 0 : const SwTabFrm* pChain = NULL; // My chain
1642 [ # # ][ # # ]: 0 : for( SwRowFrm* pLast = aIter.First(); pLast; pLast = aIter.Next() )
[ # # ]
1643 : : {
1644 [ # # ]: 0 : if( pLast->GetTabLine() == this )
1645 : : {
1646 [ # # ]: 0 : const SwTabFrm* pTab = pLast->FindTabFrm();
1647 [ # # ]: 0 : bLayoutAvailable = ( pTab && pTab->IsVertical() ) ?
1648 : 0 : ( 0 < pTab->Frm().Height() ) :
1649 [ # # ][ # # ]: 0 : ( 0 < pTab->Frm().Width() );
1650 : :
1651 : : // The first one defines the chain, if a chain is defined, only members of the chain
1652 : : // will be added.
1653 [ # # ][ # # ]: 0 : if( !pChain || pChain->IsAnFollow( pTab ) || pTab->IsAnFollow( pChain ) )
[ # # ][ # # ]
[ # # ][ # # ]
[ # # ][ # # ]
1654 : : {
1655 : 0 : pChain = pTab; // defines my chain (even it is already)
1656 [ # # ][ # # ]: 0 : if( pTab->IsVertical() )
1657 : 0 : nRet += pLast->Frm().Width();
1658 : : else
1659 : 0 : nRet += pLast->Frm().Height();
1660 : : // Optimization, if there are no master/follows in my chain, nothing more to add
1661 [ # # ][ # # ]: 0 : if( !pTab->HasFollow() && !pTab->IsFollow() )
[ # # ]
1662 : 0 : break;
1663 : : // This is not an optimization, this is necessary to avoid double additions of
1664 : : // repeating rows
1665 [ # # ][ # # ]: 0 : if( pTab->IsInHeadline(*pLast) )
1666 : 0 : break;
1667 : : }
1668 : : }
1669 : : }
1670 [ # # ]: 0 : return nRet;
1671 : : }
1672 : :
1673 : : /*************************************************************************
1674 : : |*
1675 : : |* SwTableBox::SwTableBox()
1676 : : |*
1677 : : |*************************************************************************/
1678 : 0 : SwTableBox::SwTableBox( SwTableBoxFmt* pFmt, sal_uInt16 nLines, SwTableLine *pUp )
1679 : : : SwClient( 0 ),
1680 : : aLines(),
1681 : : pSttNd( 0 ),
1682 : : pUpper( pUp ),
1683 [ # # ]: 0 : pImpl( 0 )
1684 : : {
1685 [ # # ]: 0 : aLines.reserve( (sal_uInt8)nLines );
1686 [ # # ][ # # ]: 0 : CheckBoxFmt( pFmt )->Add( this );
1687 : 0 : }
1688 : :
1689 : 1347 : SwTableBox::SwTableBox( SwTableBoxFmt* pFmt, const SwNodeIndex &rIdx,
1690 : : SwTableLine *pUp )
1691 : : : SwClient( 0 ),
1692 : : aLines(),
1693 : : pUpper( pUp ),
1694 [ + - ]: 1347 : pImpl( 0 )
1695 : : {
1696 [ + - ][ + - ]: 1347 : CheckBoxFmt( pFmt )->Add( this );
1697 : :
1698 : 1347 : pSttNd = rIdx.GetNode().GetStartNode();
1699 : :
1700 : : // insert into the table
1701 [ + - ]: 1347 : const SwTableNode* pTblNd = pSttNd->FindTableNode();
1702 : : OSL_ENSURE( pTblNd, "In which table is that box?" );
1703 : 1347 : SwTableSortBoxes& rSrtArr = (SwTableSortBoxes&)pTblNd->GetTable().
1704 : 1347 : GetTabSortBoxes();
1705 : 1347 : SwTableBox* p = this; // error: &this
1706 [ + - ]: 1347 : rSrtArr.insert( p ); // insert
1707 : 1347 : }
1708 : :
1709 : 965 : SwTableBox::SwTableBox( SwTableBoxFmt* pFmt, const SwStartNode& rSttNd, SwTableLine *pUp ) :
1710 : : SwClient( 0 ),
1711 : : aLines(),
1712 : : pSttNd( &rSttNd ),
1713 : : pUpper( pUp ),
1714 [ + - ]: 965 : pImpl( 0 )
1715 : : {
1716 [ + - ][ + - ]: 965 : CheckBoxFmt( pFmt )->Add( this );
1717 : :
1718 : : // insert into the table
1719 [ + - ]: 965 : const SwTableNode* pTblNd = pSttNd->FindTableNode();
1720 : : OSL_ENSURE( pTblNd, "In which table is the box?" );
1721 : 965 : SwTableSortBoxes& rSrtArr = (SwTableSortBoxes&)pTblNd->GetTable().
1722 : 965 : GetTabSortBoxes();
1723 : 965 : SwTableBox* p = this; // error: &this
1724 [ + - ]: 965 : rSrtArr.insert( p ); // insert
1725 : 965 : }
1726 : :
1727 [ + - ]: 2312 : SwTableBox::~SwTableBox()
1728 : : {
1729 : : // box containing contents?
1730 [ + + ][ + + ]: 2312 : if( !GetFrmFmt()->GetDoc()->IsInDtor() && pSttNd )
[ + + ]
1731 : : {
1732 : : // remove from table
1733 [ + - ]: 10 : const SwTableNode* pTblNd = pSttNd->FindTableNode();
1734 : : OSL_ENSURE( pTblNd, "In which table is that box?" );
1735 : 10 : SwTableSortBoxes& rSrtArr = (SwTableSortBoxes&)pTblNd->GetTable().
1736 : 10 : GetTabSortBoxes();
1737 : 10 : SwTableBox *p = this; // error: &this
1738 [ + - ]: 10 : rSrtArr.erase( p ); // remove
1739 : : }
1740 : :
1741 : : // the TabelleBox can be deleted if it's the last client of the FrameFormat
1742 : 2312 : SwModify* pMod = GetFrmFmt();
1743 [ + - ]: 2312 : pMod->Remove( this ); // remove,
1744 [ + + ]: 2312 : if( !pMod->GetDepends() )
1745 [ + - ][ + - ]: 1489 : delete pMod; // and delete
1746 : :
1747 [ + + ]: 2312 : delete pImpl;
1748 [ - + ]: 4624 : }
1749 : :
1750 : 2312 : SwTableBoxFmt* SwTableBox::CheckBoxFmt( SwTableBoxFmt* pFmt )
1751 : : {
1752 : : // We might need to create a new format here, because the box must be
1753 : : // added to the format solely if pFmt has a value or formular.
1754 [ + + - + ]: 4622 : if( SFX_ITEM_SET == pFmt->GetItemState( RES_BOXATR_VALUE, sal_False ) ||
[ + + ]
1755 : 2310 : SFX_ITEM_SET == pFmt->GetItemState( RES_BOXATR_FORMULA, sal_False ) )
1756 : : {
1757 : 2 : SwTableBox* pOther = SwIterator<SwTableBox,SwFmt>::FirstElement( *pFmt );
1758 [ + - ]: 2 : if( pOther )
1759 : : {
1760 : 2 : SwTableBoxFmt* pNewFmt = pFmt->GetDoc()->MakeTableBoxFmt();
1761 : 2 : pNewFmt->LockModify();
1762 : 2 : *pNewFmt = *pFmt;
1763 : :
1764 : : // Remove values and formulars
1765 : 2 : pNewFmt->ResetFmtAttr( RES_BOXATR_FORMULA, RES_BOXATR_VALUE );
1766 : 2 : pNewFmt->UnlockModify();
1767 : :
1768 : 2 : pFmt = pNewFmt;
1769 : : }
1770 : : }
1771 : 2312 : return pFmt;
1772 : : }
1773 : :
1774 : : /*************************************************************************
1775 : : |*
1776 : : |* SwTableBox::ClaimFrmFmt(), ChgFrmFmt()
1777 : : |*
1778 : : |*************************************************************************/
1779 : 5886 : SwFrmFmt* SwTableBox::ClaimFrmFmt()
1780 : : {
1781 : : // This method makes sure that this object is an exclusive SwTableBox client
1782 : : // of an SwTableBoxFmt object
1783 : : // If other SwTableBox objects currently listen to the same SwTableBoxFmt as
1784 : : // this one, something needs to be done
1785 : 5886 : SwTableBoxFmt *pRet = (SwTableBoxFmt*)GetFrmFmt();
1786 [ + - ]: 5886 : SwIterator<SwTableBox,SwFmt> aIter( *pRet );
1787 [ + - ][ + - ]: 10870 : for( SwTableBox* pLast = aIter.First(); pLast; pLast = aIter.Next() )
[ + + ]
1788 : : {
1789 [ + + ]: 6046 : if ( pLast != this )
1790 : : {
1791 : : // Found another SwTableBox object
1792 : : // create a new Fmt as a copy and assign me to it
1793 : : // don't copy values and formulas
1794 [ + - ]: 1062 : SwTableBoxFmt* pNewFmt = pRet->GetDoc()->MakeTableBoxFmt();
1795 : 1062 : pNewFmt->LockModify();
1796 [ + - ]: 1062 : *pNewFmt = *pRet;
1797 [ + - ]: 1062 : pNewFmt->ResetFmtAttr( RES_BOXATR_FORMULA, RES_BOXATR_VALUE );
1798 : 1062 : pNewFmt->UnlockModify();
1799 : :
1800 : : // re-register SwCellFrm objects that know me
1801 [ + - ]: 1062 : SwIterator<SwCellFrm,SwFmt> aFrmIter( *pRet );
1802 [ + - ][ + - ]: 1524 : for( SwCellFrm* pCell = aFrmIter.First(); pCell; pCell = aFrmIter.Next() )
[ + + ]
1803 [ + + ]: 462 : if( pCell->GetTabBox() == this )
1804 [ + - ]: 88 : pCell->RegisterToFormat( *pNewFmt );
1805 : :
1806 : : // re-register myself
1807 [ + - ]: 1062 : pNewFmt->Add( this );
1808 : 1062 : pRet = pNewFmt;
1809 [ + - ]: 1062 : break;
1810 : : }
1811 : : }
1812 [ + - ]: 5886 : return pRet;
1813 : : }
1814 : :
1815 : 295 : void SwTableBox::ChgFrmFmt( SwTableBoxFmt* pNewFmt )
1816 : : {
1817 : 295 : SwFrmFmt *pOld = GetFrmFmt();
1818 [ + - ]: 295 : SwIterator<SwCellFrm,SwFmt> aIter( *pOld );
1819 : :
1820 : : // First, re-register the Frms.
1821 [ + - ][ + - ]: 299 : for( SwCellFrm* pCell = aIter.First(); pCell; pCell = aIter.Next() )
[ + + ]
1822 : : {
1823 [ + - ]: 4 : if( pCell->GetTabBox() == this )
1824 : : {
1825 [ + - ]: 4 : pCell->RegisterToFormat( *pNewFmt );
1826 [ + - ]: 4 : pCell->InvalidateSize();
1827 [ + - ]: 4 : pCell->_InvalidatePrt();
1828 : 4 : pCell->SetCompletePaint();
1829 : 4 : pCell->SetDerivedVert( sal_False );
1830 [ + - ]: 4 : pCell->CheckDirChange();
1831 : :
1832 : : // #i47489#
1833 : : // make sure that the row will be formatted, in order
1834 : : // to have the correct Get(Top|Bottom)MarginForLowers values
1835 : : // set at the row.
1836 [ + - ]: 4 : const SwTabFrm* pTab = pCell->FindTabFrm();
1837 [ + - ][ + - ]: 4 : if ( pTab && pTab->IsCollapsingBorders() )
[ + - ][ + - ]
1838 : : {
1839 : 4 : SwFrm* pRow = pCell->GetUpper();
1840 [ + - ]: 4 : pRow->_InvalidateSize();
1841 [ + - ]: 4 : pRow->_InvalidatePrt();
1842 : : }
1843 : : }
1844 : : }
1845 : :
1846 : : // Now, re-register self.
1847 [ + - ]: 295 : pNewFmt->Add( this );
1848 : :
1849 [ + + ]: 295 : if( !pOld->GetDepends() )
1850 [ + - ][ + - ]: 295 : delete pOld;
[ + - ]
1851 : 295 : }
1852 : :
1853 : : /*************************************************************************
1854 : : |*
1855 : : |* String SwTableBox::GetName() const
1856 : : |* Return the name of this box. This is determined dynamically
1857 : : |* resulting from the position in the lines/boxes/tables.
1858 : : |*
1859 : : |*************************************************************************/
1860 : 3020 : void lcl_GetTblBoxColStr( sal_uInt16 nCol, String& rNm )
1861 : : {
1862 : 3020 : const sal_uInt16 coDiff = 52; // 'A'-'Z' 'a' - 'z'
1863 : : sal_uInt16 nCalc;
1864 : :
1865 : 0 : do {
1866 : 3020 : nCalc = nCol % coDiff;
1867 [ - + ]: 3020 : if( nCalc >= 26 )
1868 : 0 : rNm.Insert( sal_Unicode('a' - 26 + nCalc ), 0 );
1869 : : else
1870 : 3020 : rNm.Insert( sal_Unicode('A' + nCalc ), 0 );
1871 : :
1872 [ + - ]: 3020 : if( 0 == (nCol = nCol - nCalc) )
1873 : 3020 : break;
1874 : 0 : nCol /= coDiff;
1875 : 0 : --nCol;
1876 : : } while( 1 );
1877 : 3020 : }
1878 : :
1879 : 2039 : String SwTableBox::GetName() const
1880 : : {
1881 [ - + ]: 2039 : if( !pSttNd ) // box without content?
1882 : : {
1883 : : // search for the next first box?
1884 [ # # ]: 0 : return aEmptyStr;
1885 : : }
1886 : :
1887 [ + - ]: 2039 : const SwTable& rTbl = pSttNd->FindTableNode()->GetTable();
1888 : : sal_uInt16 nPos;
1889 [ + - ][ + - ]: 2039 : String sNm, sTmp;
1890 : 2039 : const SwTableBox* pBox = this;
1891 [ - + ]: 2039 : do {
1892 : 2039 : const SwTableBoxes* pBoxes = &pBox->GetUpper()->GetTabBoxes();
1893 : 2039 : const SwTableLine* pLine = pBox->GetUpper();
1894 : : // at the first level?
1895 : 2039 : const SwTableLines* pLines = pLine->GetUpper()
1896 [ - + ]: 2039 : ? &pLine->GetUpper()->GetTabLines() : &rTbl.GetTabLines();
1897 : :
1898 [ + - ][ + - ]: 2039 : sTmp = String::CreateFromInt32( nPos = pLines->GetPos( pLine ) + 1 );
[ + - ][ + - ]
1899 [ - + ]: 2039 : if( sNm.Len() )
1900 [ # # ][ # # ]: 0 : sNm.Insert( aDotStr, 0 ).Insert( sTmp, 0 );
[ # # ][ # # ]
1901 : : else
1902 [ + - ]: 2039 : sNm = sTmp;
1903 : :
1904 [ + - ][ + - ]: 2039 : sTmp = String::CreateFromInt32(( nPos = pBoxes->GetPos( pBox )) + 1 );
[ + - ][ + - ]
1905 [ - + ]: 2039 : if( 0 != ( pBox = pLine->GetUpper()) )
1906 [ # # ][ # # ]: 0 : sNm.Insert( aDotStr, 0 ).Insert( sTmp, 0 );
[ # # ][ # # ]
1907 : : else
1908 [ + - ]: 2039 : ::lcl_GetTblBoxColStr( nPos, sNm );
1909 : :
1910 : : } while( pBox );
1911 [ + - ][ + - ]: 2039 : return sNm;
[ + - ]
1912 : : }
1913 : :
1914 : 6 : sal_Bool SwTableBox::IsInHeadline( const SwTable* pTbl ) const
1915 : : {
1916 [ - + ]: 6 : if( !GetUpper() ) // should only happen upon merge.
1917 : 0 : return sal_False;
1918 : :
1919 [ - + ]: 6 : if( !pTbl )
1920 : 0 : pTbl = &pSttNd->FindTableNode()->GetTable();
1921 : :
1922 : 6 : const SwTableLine* pLine = GetUpper();
1923 [ - + ]: 6 : while( pLine->GetUpper() )
1924 : 0 : pLine = pLine->GetUpper()->GetUpper();
1925 : :
1926 : : // Headerline?
1927 : 6 : return pTbl->GetTabLines()[ 0 ] == pLine;
1928 : : }
1929 : :
1930 : 41795 : sal_uLong SwTableBox::GetSttIdx() const
1931 : : {
1932 [ + - ]: 41795 : return pSttNd ? pSttNd->GetIndex() : 0;
1933 : : }
1934 : :
1935 : : // retrieve informations from the client
1936 : 463 : sal_Bool SwTable::GetInfo( SfxPoolItem& rInfo ) const
1937 : : {
1938 [ + - - - ]: 463 : switch( rInfo.Which() )
1939 : : {
1940 : : case RES_AUTOFMT_DOCNODE:
1941 : : {
1942 : 463 : const SwTableNode* pTblNode = GetTableNode();
1943 [ + + ][ + + ]: 463 : if( pTblNode && &pTblNode->GetNodes() == ((SwAutoFmtGetDocNode&)rInfo).pNodes )
[ + - ]
1944 : : {
1945 [ + - ]: 457 : if ( !aSortCntBoxes.empty() )
1946 : : {
1947 [ + - ]: 457 : SwNodeIndex aIdx( *aSortCntBoxes[ 0 ]->GetSttNd() );
1948 : : ((SwAutoFmtGetDocNode&)rInfo).pCntntNode =
1949 [ + - ][ + - ]: 457 : GetFrmFmt()->GetDoc()->GetNodes().GoNext( &aIdx );
[ + - ]
1950 : : }
1951 : 457 : return sal_False;
1952 : : }
1953 : 6 : break;
1954 : : }
1955 : : case RES_FINDNEARESTNODE:
1956 [ # # ][ # # : 0 : if( GetFrmFmt() && ((SwFmtPageDesc&)GetFrmFmt()->GetFmtAttr(
# # # # ]
[ # # ]
1957 : 0 : RES_PAGEDESC )).GetPageDesc() &&
1958 : 0 : !aSortCntBoxes.empty() &&
1959 : 0 : aSortCntBoxes[ 0 ]->GetSttNd()->GetNodes().IsDocNodes() )
1960 : : ((SwFindNearestNode&)rInfo).CheckNode( *
1961 : 0 : aSortCntBoxes[ 0 ]->GetSttNd()->FindTableNode() );
1962 : 0 : break;
1963 : :
1964 : : case RES_CONTENT_VISIBLE:
1965 : : {
1966 : 0 : ((SwPtrMsgPoolItem&)rInfo).pObject = SwIterator<SwFrm,SwFmt>::FirstElement( *GetFrmFmt() );
1967 : : }
1968 : 0 : return sal_False;
1969 : : }
1970 : 463 : return sal_True;
1971 : : }
1972 : :
1973 : 10448 : SwTable * SwTable::FindTable( SwFrmFmt const*const pFmt )
1974 : : {
1975 : : return (pFmt)
1976 : 10448 : ? SwIterator<SwTable,SwFmt>::FirstElement(*pFmt)
1977 [ + - ]: 10448 : : 0;
1978 : : }
1979 : :
1980 : 869 : SwTableNode* SwTable::GetTableNode() const
1981 : : {
1982 : 869 : return !GetTabSortBoxes().empty() ?
1983 : 869 : (SwTableNode*)GetTabSortBoxes()[ 0 ]->GetSttNd()->FindTableNode() :
1984 [ + - ]: 1738 : pTableNode;
1985 : : }
1986 : :
1987 : 0 : void SwTable::SetRefObject( SwServerObject* pObj )
1988 : : {
1989 [ # # ]: 0 : if( refObj.Is() )
1990 : 0 : refObj->Closed();
1991 : :
1992 : 0 : refObj = pObj;
1993 : 0 : }
1994 : :
1995 : :
1996 : 97 : void SwTable::SetHTMLTableLayout( SwHTMLTableLayout *p )
1997 : : {
1998 [ - + ]: 97 : delete pHTMLLayout;
1999 : 97 : pHTMLLayout = p;
2000 : 97 : }
2001 : :
2002 : 144 : void ChgTextToNum( SwTableBox& rBox, const String& rTxt, const Color* pCol,
2003 : : sal_Bool bChgAlign )
2004 : : {
2005 : 144 : sal_uLong nNdPos = rBox.IsValidNumTxtNd( sal_True );
2006 : 144 : ChgTextToNum( rBox,rTxt,pCol,bChgAlign,nNdPos);
2007 : 144 : }
2008 : 144 : void ChgTextToNum( SwTableBox& rBox, const String& rTxt, const Color* pCol,
2009 : : sal_Bool bChgAlign,sal_uLong nNdPos )
2010 : : {
2011 : :
2012 [ + - ]: 144 : if( ULONG_MAX != nNdPos )
2013 : : {
2014 : 144 : SwDoc* pDoc = rBox.GetFrmFmt()->GetDoc();
2015 [ + - ][ + - ]: 144 : SwTxtNode* pTNd = pDoc->GetNodes()[ nNdPos ]->GetTxtNode();
2016 : : const SfxPoolItem* pItem;
2017 : :
2018 : : // assign adjustment
2019 [ - + ]: 144 : if( bChgAlign )
2020 : : {
2021 [ # # ]: 0 : pItem = &pTNd->SwCntntNode::GetAttr( RES_PARATR_ADJUST );
2022 : 0 : SvxAdjust eAdjust = ((SvxAdjustItem*)pItem)->GetAdjust();
2023 [ # # ][ # # ]: 0 : if( SVX_ADJUST_LEFT == eAdjust || SVX_ADJUST_BLOCK == eAdjust )
2024 : : {
2025 [ # # ]: 0 : SvxAdjustItem aAdjust( *(SvxAdjustItem*)pItem );
2026 : 0 : aAdjust.SetAdjust( SVX_ADJUST_RIGHT );
2027 [ # # ][ # # ]: 0 : pTNd->SetAttr( aAdjust );
2028 : : }
2029 : : }
2030 : :
2031 : : // assign color or save "user color"
2032 [ + - ][ + + ]: 224 : if( !pTNd->GetpSwAttrSet() || SFX_ITEM_SET != pTNd->GetpSwAttrSet()->
[ + - ][ - + ]
[ + + ]
2033 [ + - ]: 80 : GetItemState( RES_CHRATR_COLOR, sal_False, &pItem ))
2034 : 64 : pItem = 0;
2035 : :
2036 : 144 : const Color* pOldNumFmtColor = rBox.GetSaveNumFmtColor();
2037 [ + + ]: 144 : const Color* pNewUserColor = pItem ? &((SvxColorItem*)pItem)->GetValue() : 0;
2038 : :
2039 [ + + ]: 144 : if( ( pNewUserColor && pOldNumFmtColor &&
[ - + # # ]
[ + + ][ + - ]
[ + + ]
2040 : 0 : *pNewUserColor == *pOldNumFmtColor ) ||
2041 : : ( !pNewUserColor && !pOldNumFmtColor ))
2042 : : {
2043 : : // Keep the user color, set updated values, delete old NumFmtColor if needed
2044 [ - + ]: 64 : if( pCol )
2045 : : // if needed, set the color
2046 [ # # ][ # # ]: 0 : pTNd->SetAttr( SvxColorItem( *pCol, RES_CHRATR_COLOR ));
[ # # ]
2047 [ - + ]: 64 : else if( pItem )
2048 : : {
2049 : 0 : pNewUserColor = rBox.GetSaveUserColor();
2050 [ # # ]: 0 : if( pNewUserColor )
2051 [ # # ][ # # ]: 0 : pTNd->SetAttr( SvxColorItem( *pNewUserColor, RES_CHRATR_COLOR ));
[ # # ]
2052 : : else
2053 [ # # ]: 0 : pTNd->ResetAttr( RES_CHRATR_COLOR );
2054 : : }
2055 : : }
2056 : : else
2057 : : {
2058 : : // Save user color, set NumFormat color if needed, but never reset the color
2059 [ + - ]: 80 : rBox.SetSaveUserColor( pNewUserColor );
2060 : :
2061 [ - + ]: 80 : if( pCol )
2062 : : // if needed, set the color
2063 [ # # ][ # # ]: 0 : pTNd->SetAttr( SvxColorItem( *pCol, RES_CHRATR_COLOR ));
[ # # ]
2064 : :
2065 : : }
2066 [ + - ]: 144 : rBox.SetSaveNumFmtColor( pCol );
2067 : :
2068 [ + - ][ + - ]: 144 : if( pTNd->GetTxt() != rTxt )
2069 : : {
2070 : : // Exchange text. Bugfix to keep Tabs (front and back!)
2071 : 144 : const String& rOrig = pTNd->GetTxt();
2072 : : xub_StrLen n;
2073 : :
2074 [ - + ][ # # ]: 144 : for( n = 0; n < rOrig.Len() && '\x9' == rOrig.GetChar( n ); ++n )
[ - + ]
2075 : : ;
2076 [ - + ][ # # ]: 144 : for( ; n < rOrig.Len() && '\x01' == rOrig.GetChar( n ); ++n )
[ - + ]
2077 : : ;
2078 [ + - ][ + - ]: 144 : SwIndex aIdx( pTNd, n );
2079 [ - + ][ # # ]: 144 : for( n = rOrig.Len(); n && '\x9' == rOrig.GetChar( --n ); )
[ - + ]
2080 : : ;
2081 : 144 : n -= aIdx.GetIndex() - 1;
2082 : :
2083 : : // Reset DontExpand-Flags before exchange, to retrigger expansion
2084 : : {
2085 [ + - ]: 144 : SwIndex aResetIdx( aIdx, n );
2086 [ + - ][ + - ]: 144 : pTNd->DontExpandFmt( aResetIdx, sal_False, sal_False );
2087 : : }
2088 : :
2089 [ + - ][ + - ]: 144 : if( !pDoc->IsIgnoreRedline() && !pDoc->GetRedlineTbl().empty() )
[ + - ][ - + ]
[ - + ]
2090 : : {
2091 [ # # ]: 0 : SwPaM aTemp(*pTNd, 0, *pTNd, rOrig.Len());
2092 [ # # ][ # # ]: 0 : pDoc->DeleteRedline(aTemp, true, USHRT_MAX);
2093 : : }
2094 : :
2095 : : pTNd->EraseText( aIdx, n,
2096 [ + - ]: 144 : IDocumentContentOperations::INS_EMPTYEXPAND );
2097 : : pTNd->InsertText( rTxt, aIdx,
2098 [ + - ]: 144 : IDocumentContentOperations::INS_EMPTYEXPAND );
2099 : :
2100 [ + - ][ - + ]: 144 : if( pDoc->IsRedlineOn() )
2101 : : {
2102 [ # # ]: 0 : SwPaM aTemp(*pTNd, 0, *pTNd, rTxt.Len());
2103 [ # # ][ # # ]: 0 : pDoc->AppendRedline(new SwRedline(nsRedlineType_t::REDLINE_INSERT, aTemp), true);
[ # # ][ # # ]
2104 [ + - ]: 144 : }
2105 : : }
2106 : :
2107 : : // assign vertical orientation
2108 [ - + ]: 144 : if( bChgAlign &&
[ # # # # ]
[ - + ]
2109 : 0 : ( SFX_ITEM_SET != rBox.GetFrmFmt()->GetItemState(
2110 [ # # ]: 0 : RES_VERT_ORIENT, sal_True, &pItem ) ||
2111 : 0 : text::VertOrientation::TOP == ((SwFmtVertOrient*)pItem)->GetVertOrient() ))
2112 : : {
2113 [ # # ][ # # ]: 144 : rBox.GetFrmFmt()->SetFmtAttr( SwFmtVertOrient( 0, text::VertOrientation::BOTTOM ));
[ # # ]
2114 : : }
2115 : : }
2116 : 144 : }
2117 : :
2118 : 10 : void ChgNumToText( SwTableBox& rBox, sal_uLong nFmt )
2119 : : {
2120 : 10 : sal_uLong nNdPos = rBox.IsValidNumTxtNd( sal_False );
2121 [ + - ]: 10 : if( ULONG_MAX != nNdPos )
2122 : : {
2123 : 10 : SwDoc* pDoc = rBox.GetFrmFmt()->GetDoc();
2124 [ + - ][ + - ]: 10 : SwTxtNode* pTNd = pDoc->GetNodes()[ nNdPos ]->GetTxtNode();
2125 [ + - ]: 10 : sal_Bool bChgAlign = pDoc->IsInsTblAlignNum();
2126 : : const SfxPoolItem* pItem;
2127 : :
2128 : 10 : Color* pCol = 0;
2129 [ - + ]: 10 : if( NUMBERFORMAT_TEXT != nFmt )
2130 : : {
2131 : : // special text format:
2132 [ # # ][ # # ]: 0 : String sTmp, sTxt( pTNd->GetTxt() );
2133 [ # # ][ # # ]: 0 : pDoc->GetNumberFormatter()->GetOutputString( sTxt, nFmt, sTmp, &pCol );
2134 [ # # ][ # # ]: 0 : if( sTxt != sTmp )
2135 : : {
2136 : : // exchange text
2137 [ # # ][ # # ]: 0 : SwIndex aIdx( pTNd, sTxt.Len() );
2138 : : // Reset DontExpand-Flags before exchange, to retrigger expansion
2139 [ # # ]: 0 : pTNd->DontExpandFmt( aIdx, sal_False, sal_False );
2140 [ # # ]: 0 : aIdx = 0;
2141 : : pTNd->EraseText( aIdx, STRING_LEN,
2142 [ # # ]: 0 : IDocumentContentOperations::INS_EMPTYEXPAND );
2143 : : pTNd->InsertText( sTmp, aIdx,
2144 [ # # ][ # # ]: 0 : IDocumentContentOperations::INS_EMPTYEXPAND );
2145 [ # # ][ # # ]: 0 : }
2146 : : }
2147 : :
2148 [ + - ]: 10 : const SfxItemSet* pAttrSet = pTNd->GetpSwAttrSet();
2149 : :
2150 : : // assign adjustment
2151 [ - + ][ # # ]: 10 : if( bChgAlign && pAttrSet && SFX_ITEM_SET == pAttrSet->GetItemState(
[ # # # # ]
[ - + ]
2152 [ # # ]: 0 : RES_PARATR_ADJUST, sal_False, &pItem ) &&
2153 : 0 : SVX_ADJUST_RIGHT == ((SvxAdjustItem*)pItem)->GetAdjust() )
2154 : : {
2155 [ # # ][ # # ]: 0 : pTNd->SetAttr( SvxAdjustItem( SVX_ADJUST_LEFT, RES_PARATR_ADJUST ) );
[ # # ]
2156 : : }
2157 : :
2158 : : // assign color or save "user color"
2159 [ - + ][ # # ]: 10 : if( !pAttrSet || SFX_ITEM_SET != pAttrSet->
[ + - ]
2160 [ # # ]: 0 : GetItemState( RES_CHRATR_COLOR, sal_False, &pItem ))
2161 : 10 : pItem = 0;
2162 : :
2163 : 10 : const Color* pOldNumFmtColor = rBox.GetSaveNumFmtColor();
2164 [ - + ]: 10 : const Color* pNewUserColor = pItem ? &((SvxColorItem*)pItem)->GetValue() : 0;
2165 : :
2166 [ - + ]: 10 : if( ( pNewUserColor && pOldNumFmtColor &&
[ # # # # ]
[ + - ][ + - ]
[ + - ]
2167 : 0 : *pNewUserColor == *pOldNumFmtColor ) ||
2168 : : ( !pNewUserColor && !pOldNumFmtColor ))
2169 : : {
2170 : : // Keep the user color, set updated values, delete old NumFmtColor if needed
2171 [ - + ]: 10 : if( pCol )
2172 : : // if needed, set the color
2173 [ # # ][ # # ]: 0 : pTNd->SetAttr( SvxColorItem( *pCol, RES_CHRATR_COLOR ));
[ # # ]
2174 [ - + ]: 10 : else if( pItem )
2175 : : {
2176 : 0 : pNewUserColor = rBox.GetSaveUserColor();
2177 [ # # ]: 0 : if( pNewUserColor )
2178 [ # # ][ # # ]: 0 : pTNd->SetAttr( SvxColorItem( *pNewUserColor, RES_CHRATR_COLOR ));
[ # # ]
2179 : : else
2180 [ # # ]: 0 : pTNd->ResetAttr( RES_CHRATR_COLOR );
2181 : : }
2182 : : }
2183 : : else
2184 : : {
2185 : : // Save user color, set NumFormat color if needed, but never reset the color
2186 [ # # ]: 0 : rBox.SetSaveUserColor( pNewUserColor );
2187 : :
2188 [ # # ]: 0 : if( pCol )
2189 : : // if needed, set the color
2190 [ # # ][ # # ]: 0 : pTNd->SetAttr( SvxColorItem( *pCol, RES_CHRATR_COLOR ));
[ # # ]
2191 : :
2192 : : }
2193 [ + - ]: 10 : rBox.SetSaveNumFmtColor( pCol );
2194 : :
2195 : :
2196 : : // assign vertical orientation
2197 [ - + ]: 10 : if( bChgAlign &&
[ # # # # ]
[ - + ]
2198 : 0 : SFX_ITEM_SET == rBox.GetFrmFmt()->GetItemState(
2199 [ # # ]: 0 : RES_VERT_ORIENT, sal_False, &pItem ) &&
2200 : 0 : text::VertOrientation::BOTTOM == ((SwFmtVertOrient*)pItem)->GetVertOrient() )
2201 : : {
2202 [ # # ][ # # ]: 10 : rBox.GetFrmFmt()->SetFmtAttr( SwFmtVertOrient( 0, text::VertOrientation::TOP ));
[ # # ]
2203 : : }
2204 : : }
2205 : 10 : }
2206 : :
2207 : : // for detection of modifications (mainly TableBoxAttribute)
2208 : 6952 : void SwTableBoxFmt::Modify( const SfxPoolItem* pOld, const SfxPoolItem* pNew )
2209 : : {
2210 [ + + ][ + - ]: 6952 : if( !IsModifyLocked() && !IsInDocDTOR() )
[ + + ]
2211 : : {
2212 : 5888 : const SwTblBoxNumFormat *pNewFmt = 0;
2213 : 5888 : const SwTblBoxFormula *pNewFml = 0;
2214 : 5888 : const SwTblBoxValue *pNewVal = 0;
2215 : 5888 : sal_uLong nOldFmt = NUMBERFORMAT_TEXT;
2216 : :
2217 [ + - ][ + - : 5888 : switch( pNew ? pNew->Which() : 0 )
- - - ]
2218 : : {
2219 : : case RES_ATTRSET_CHG:
2220 : : {
2221 : 5888 : const SfxItemSet& rSet = *((SwAttrSetChg*)pNew)->GetChgSet();
2222 [ + + ]: 5888 : if( SFX_ITEM_SET == rSet.GetItemState( RES_BOXATR_FORMAT,
2223 [ + - ]: 5888 : sal_False, (const SfxPoolItem**)&pNewFmt ) )
2224 : : nOldFmt = ((SwTblBoxNumFormat&)((SwAttrSetChg*)pOld)->
2225 [ + - ]: 136 : GetChgSet()->Get( RES_BOXATR_FORMAT )).GetValue();
2226 : : rSet.GetItemState( RES_BOXATR_FORMULA, sal_False,
2227 [ + - ]: 5888 : (const SfxPoolItem**)&pNewFml );
2228 : : rSet.GetItemState( RES_BOXATR_VALUE, sal_False,
2229 [ + - ]: 5888 : (const SfxPoolItem**)&pNewVal );
2230 : : }
2231 : 5888 : break;
2232 : :
2233 : : case RES_BOXATR_FORMAT:
2234 : 0 : pNewFmt = (SwTblBoxNumFormat*)pNew;
2235 : 0 : nOldFmt = ((SwTblBoxNumFormat*)pOld)->GetValue();
2236 : 0 : break;
2237 : : case RES_BOXATR_FORMULA:
2238 : 0 : pNewFml = (SwTblBoxFormula*)pNew;
2239 : 0 : break;
2240 : : case RES_BOXATR_VALUE:
2241 : 0 : pNewVal = (SwTblBoxValue*)pNew;
2242 : 0 : break;
2243 : : }
2244 : :
2245 : : // something changed and some BoxAttribut remained in the set!
2246 [ + + ][ + - ]: 5888 : if( pNewFmt || pNewFml || pNewVal )
[ + + ]
2247 : : {
2248 [ + - ]: 156 : GetDoc()->SetFieldsDirty(true, NULL, 0);
2249 : :
2250 [ + - ][ + + ]: 170 : if( SFX_ITEM_SET == GetItemState( RES_BOXATR_FORMAT, sal_False ) ||
[ + + ][ - + ]
[ + + ]
2251 [ + - ]: 12 : SFX_ITEM_SET == GetItemState( RES_BOXATR_VALUE, sal_False ) ||
2252 [ + - ]: 2 : SFX_ITEM_SET == GetItemState( RES_BOXATR_FORMULA, sal_False ) )
2253 : : {
2254 : : // fetch the box
2255 [ + - ]: 154 : SwIterator<SwTableBox,SwFmt> aIter( *this );
2256 [ + - ]: 154 : SwTableBox* pBox = aIter.First();
2257 [ + - ]: 154 : if( pBox )
2258 : : {
2259 : : OSL_ENSURE( !aIter.Next(), "zeor or more than one box at format" );
2260 : :
2261 : : sal_uLong nNewFmt;
2262 [ + + ]: 154 : if( pNewFmt )
2263 : : {
2264 : 134 : nNewFmt = pNewFmt->GetValue();
2265 : : // new formatting
2266 : : // is it newer or has the current been removed?
2267 [ - + ][ + - ]: 134 : if( SFX_ITEM_SET != GetItemState( RES_BOXATR_VALUE, sal_False ))
2268 : 0 : pNewFmt = 0;
2269 : : }
2270 : : else
2271 : : {
2272 : : // fetch the current Item
2273 : : GetItemState( RES_BOXATR_FORMAT, sal_False,
2274 [ + - ]: 20 : (const SfxPoolItem**)&pNewFmt );
2275 [ + - ]: 20 : nOldFmt = GetTblBoxNumFmt().GetValue();
2276 [ + + ]: 20 : nNewFmt = pNewFmt ? pNewFmt->GetValue() : nOldFmt;
2277 : : }
2278 : :
2279 : : // is it newer or has the current been removed?
2280 [ + - ]: 154 : if( pNewVal )
2281 : : {
2282 [ + + ]: 154 : if( NUMBERFORMAT_TEXT != nNewFmt )
2283 : : {
2284 [ + - ]: 144 : if( SFX_ITEM_SET == GetItemState(
2285 [ + - ]: 144 : RES_BOXATR_VALUE, sal_False ))
2286 : 144 : nOldFmt = NUMBERFORMAT_TEXT;
2287 : : else
2288 : 0 : nNewFmt = NUMBERFORMAT_TEXT;
2289 : : }
2290 [ + - ]: 10 : else if( NUMBERFORMAT_TEXT == nNewFmt )
2291 : 10 : nOldFmt = 0;
2292 : : }
2293 : :
2294 : : // Logic:
2295 : : // Value change: -> "simulate" a format change!
2296 : : // Format change:
2297 : : // Text -> !Text or format change:
2298 : : // - align right for horizontal alignment, if LEFT or JUSTIFIED
2299 : : // - align bottom for vertical alignment, if TOP is set, or default
2300 : : // - replace text (color? negative numbers RED?)
2301 : : // !Text -> Text:
2302 : : // - align left for horizontal alignment, if RIGHT
2303 : : // - align top for vertical alignment, if BOTTOM is set
2304 [ + - ]: 154 : SvNumberFormatter* pNumFmtr = GetDoc()->GetNumberFormatter();
2305 [ + - ]: 154 : sal_Bool bNewIsTxtFmt = pNumFmtr->IsTextFormat( nNewFmt ) ||
2306 [ + - ][ + + ]: 154 : NUMBERFORMAT_TEXT == nNewFmt;
2307 : :
2308 [ + + ][ - + ]: 154 : if( (!bNewIsTxtFmt && nOldFmt != nNewFmt) || pNewFml )
[ - + ]
2309 : : {
2310 : 144 : sal_Bool bChgTxt = sal_True;
2311 : 144 : double fVal = 0;
2312 [ - + ][ # # ]: 144 : if( !pNewVal && SFX_ITEM_SET != GetItemState(
[ - + ]
2313 [ # # ]: 0 : RES_BOXATR_VALUE, sal_False, (const SfxPoolItem**)&pNewVal ))
2314 : : {
2315 : : // so far, no value has been set, so try to evaluate the content
2316 [ # # ]: 0 : sal_uLong nNdPos = pBox->IsValidNumTxtNd( sal_True );
2317 [ # # ]: 0 : if( ULONG_MAX != nNdPos )
2318 : : {
2319 : 0 : sal_uInt32 nTmpFmtIdx = nNewFmt;
2320 [ # # ]: 0 : String aTxt( GetDoc()->GetNodes()[ nNdPos ]
2321 [ # # ][ # # ]: 0 : ->GetTxtNode()->GetRedlineTxt());
2322 [ # # ]: 0 : if( !aTxt.Len() )
2323 : 0 : bChgTxt = sal_False;
2324 : : else
2325 : : {
2326 : : // Keep Tabs
2327 [ # # ]: 0 : lcl_TabToBlankAtSttEnd( aTxt );
2328 : :
2329 : : // JP 22.04.98: Bug 49659 -
2330 : : // Special casing for percent
2331 : 0 : sal_Bool bIsNumFmt = sal_False;
2332 [ # # ]: 0 : if( NUMBERFORMAT_PERCENT ==
2333 [ # # ]: 0 : pNumFmtr->GetType( nNewFmt ))
2334 : : {
2335 : 0 : sal_uInt32 nTmpFmt = 0;
2336 [ # # ][ # # ]: 0 : if( pNumFmtr->IsNumberFormat(
2337 : : aTxt, nTmpFmt, fVal ))
2338 : : {
2339 [ # # ]: 0 : if( NUMBERFORMAT_NUMBER ==
2340 [ # # ]: 0 : pNumFmtr->GetType( nTmpFmt ))
2341 [ # # ]: 0 : aTxt += '%';
2342 : :
2343 : : bIsNumFmt = pNumFmtr->IsNumberFormat(
2344 [ # # ]: 0 : aTxt, nTmpFmtIdx, fVal );
2345 : : }
2346 : : }
2347 : : else
2348 : : bIsNumFmt = pNumFmtr->IsNumberFormat(
2349 [ # # ]: 0 : aTxt, nTmpFmtIdx, fVal );
2350 : :
2351 [ # # ]: 0 : if( bIsNumFmt )
2352 : : {
2353 : : // directly assign value - without Modify
2354 : 0 : int bIsLockMod = IsModifyLocked();
2355 : 0 : LockModify();
2356 [ # # ][ # # ]: 0 : SetFmtAttr( SwTblBoxValue( fVal ));
[ # # ]
2357 [ # # ]: 0 : if( !bIsLockMod )
2358 : 0 : UnlockModify();
2359 : : }
2360 [ # # ]: 0 : }
2361 : : }
2362 : : }
2363 : : else
2364 : 144 : fVal = pNewVal->GetValue();
2365 : :
2366 : : // format contents with the new value assigned and write to paragraph
2367 : 144 : Color* pCol = 0;
2368 [ + - ]: 144 : String sNewTxt;
2369 [ - + ]: 144 : if( DBL_MAX == fVal )
2370 [ # # ][ # # ]: 0 : sNewTxt = ViewShell::GetShellRes()->aCalc_Error;
2371 : : else
2372 : : {
2373 [ + - ]: 144 : pNumFmtr->GetOutputString( fVal, nNewFmt, sNewTxt, &pCol );
2374 : :
2375 [ - + ]: 144 : if( !bChgTxt )
2376 [ # # ]: 0 : sNewTxt.Erase();
2377 : : }
2378 : :
2379 : : // across all boxes
2380 : : ChgTextToNum( *pBox, sNewTxt, pCol,
2381 [ + - ][ + - ]: 144 : GetDoc()->IsInsTblAlignNum() );
[ + - ]
2382 : :
2383 : : }
2384 [ + - ][ + - ]: 10 : else if( bNewIsTxtFmt && nOldFmt != nNewFmt )
2385 : : {
2386 [ + - ]: 154 : ChgNumToText( *pBox, nNewFmt );
2387 : : }
2388 [ + - ]: 5888 : }
2389 : : }
2390 : : }
2391 : : }
2392 : : // call base class
2393 : 6952 : SwFrmFmt::Modify( pOld, pNew );
2394 : 6952 : }
2395 : :
2396 : 0 : sal_Bool SwTableBox::HasNumCntnt( double& rNum, sal_uInt32& rFmtIndex,
2397 : : sal_Bool& rIsEmptyTxtNd ) const
2398 : : {
2399 : 0 : sal_Bool bRet = sal_False;
2400 : 0 : sal_uLong nNdPos = IsValidNumTxtNd( sal_True );
2401 [ # # ]: 0 : if( ULONG_MAX != nNdPos )
2402 : : {
2403 : 0 : String aTxt( pSttNd->GetNodes()[ nNdPos ]->GetTxtNode()->
2404 [ # # ][ # # ]: 0 : GetRedlineTxt() );
2405 : : // Keep Tabs
2406 [ # # ]: 0 : lcl_TabToBlankAtSttEnd( aTxt );
2407 : 0 : rIsEmptyTxtNd = 0 == aTxt.Len();
2408 [ # # ]: 0 : SvNumberFormatter* pNumFmtr = GetFrmFmt()->GetDoc()->GetNumberFormatter();
2409 : :
2410 : : const SfxPoolItem* pItem;
2411 [ # # ]: 0 : if( SFX_ITEM_SET == GetFrmFmt()->GetItemState( RES_BOXATR_FORMAT,
2412 [ # # ]: 0 : sal_False, &pItem ))
2413 : : {
2414 : 0 : rFmtIndex = ((SwTblBoxNumFormat*)pItem)->GetValue();
2415 : : // Special casing for percent
2416 [ # # ][ # # ]: 0 : if( !rIsEmptyTxtNd &&
[ # # ]
2417 [ # # ]: 0 : NUMBERFORMAT_PERCENT == pNumFmtr->GetType( rFmtIndex ))
2418 : : {
2419 : 0 : sal_uInt32 nTmpFmt = 0;
2420 [ # # ][ # # ]: 0 : if( pNumFmtr->IsNumberFormat( aTxt, nTmpFmt, rNum ) &&
[ # # ][ # # ]
2421 [ # # ]: 0 : NUMBERFORMAT_NUMBER == pNumFmtr->GetType( nTmpFmt ))
2422 [ # # ]: 0 : aTxt += '%';
2423 : : }
2424 : : }
2425 : : else
2426 : 0 : rFmtIndex = 0;
2427 : :
2428 [ # # ][ # # ]: 0 : bRet = pNumFmtr->IsNumberFormat( aTxt, rFmtIndex, rNum );
2429 : : }
2430 : : else
2431 : 0 : rIsEmptyTxtNd = sal_False;
2432 : 0 : return bRet;
2433 : : }
2434 : :
2435 : 0 : sal_Bool SwTableBox::IsNumberChanged() const
2436 : : {
2437 : 0 : sal_Bool bRet = sal_True;
2438 : :
2439 [ # # ]: 0 : if( SFX_ITEM_SET == GetFrmFmt()->GetItemState( RES_BOXATR_FORMULA, sal_False ))
2440 : : {
2441 : : const SwTblBoxNumFormat *pNumFmt;
2442 : : const SwTblBoxValue *pValue;
2443 : :
2444 [ # # ]: 0 : if( SFX_ITEM_SET != GetFrmFmt()->GetItemState( RES_BOXATR_VALUE, sal_False,
2445 [ # # ]: 0 : (const SfxPoolItem**)&pValue ))
2446 : 0 : pValue = 0;
2447 [ # # ]: 0 : if( SFX_ITEM_SET != GetFrmFmt()->GetItemState( RES_BOXATR_FORMAT, sal_False,
2448 [ # # ]: 0 : (const SfxPoolItem**)&pNumFmt ))
2449 : 0 : pNumFmt = 0;
2450 : :
2451 : : sal_uLong nNdPos;
2452 [ # # ][ # # ]: 0 : if( pNumFmt && pValue &&
[ # # ][ # # ]
[ # # ]
2453 : : ULONG_MAX != ( nNdPos = IsValidNumTxtNd( sal_True ) ) )
2454 : : {
2455 [ # # ]: 0 : String sNewTxt, sOldTxt( pSttNd->GetNodes()[ nNdPos ]->
2456 [ # # ][ # # ]: 0 : GetTxtNode()->GetRedlineTxt() );
2457 [ # # ]: 0 : lcl_DelTabsAtSttEnd( sOldTxt );
2458 : :
2459 : 0 : Color* pCol = 0;
2460 : 0 : GetFrmFmt()->GetDoc()->GetNumberFormatter()->GetOutputString(
2461 [ # # ][ # # ]: 0 : pValue->GetValue(), pNumFmt->GetValue(), sNewTxt, &pCol );
2462 : :
2463 [ # # ]: 0 : bRet = sNewTxt != sOldTxt ||
2464 : 0 : !( ( !pCol && !GetSaveNumFmtColor() ) ||
2465 : 0 : ( pCol && GetSaveNumFmtColor() &&
2466 [ # # ]: 0 : *pCol == *GetSaveNumFmtColor() ));
[ # # # # ]
[ # # # # ]
[ # # ][ # # ]
[ # # ]
2467 : : }
2468 : : }
2469 : 0 : return bRet;
2470 : : }
2471 : :
2472 : 444 : sal_uLong SwTableBox::IsValidNumTxtNd( sal_Bool bCheckAttr ) const
2473 : : {
2474 : 444 : sal_uLong nPos = ULONG_MAX;
2475 [ + - ]: 444 : if( pSttNd )
2476 : : {
2477 [ + - ]: 444 : SwNodeIndex aIdx( *pSttNd );
2478 : 444 : sal_uLong nIndex = aIdx.GetIndex();
2479 [ + - ]: 444 : const sal_uLong nIndexEnd = pSttNd->GetNodes()[ nIndex ]->EndOfSectionIndex();
2480 : 444 : const SwTxtNode *pTextNode = 0;
2481 [ + + ]: 888 : while( ++nIndex < nIndexEnd )
2482 : : {
2483 [ + - ]: 444 : const SwNode* pNode = pSttNd->GetNodes()[nIndex];
2484 [ - + ]: 444 : if( pNode->IsTableNode() )
2485 : : {
2486 : 0 : pTextNode = 0;
2487 : 0 : break;
2488 : : }
2489 [ + - ]: 444 : if( pNode->IsTxtNode() )
2490 : : {
2491 [ - + ]: 444 : if( pTextNode )
2492 : : {
2493 : 0 : pTextNode = 0;
2494 : 0 : break;
2495 : : }
2496 : : else
2497 : : {
2498 : 444 : pTextNode = pNode->GetTxtNode();
2499 : 444 : nPos = nIndex;
2500 : : }
2501 : : }
2502 : : }
2503 [ + - ]: 444 : if( pTextNode )
2504 : : {
2505 [ + + ]: 444 : if( bCheckAttr )
2506 : : {
2507 : 290 : const SwpHints* pHts = pTextNode->GetpSwpHints();
2508 : 290 : const String& rTxt = pTextNode->GetTxt();
2509 : : // do some tests if there's only text in the node!
2510 : : // Flys/fields/...
2511 [ + + ]: 290 : if( pHts )
2512 : : {
2513 : 80 : xub_StrLen nNextSetField = 0;
2514 [ + + ]: 240 : for( sal_uInt16 n = 0; n < pHts->Count(); ++n )
2515 : : {
2516 [ + - ]: 160 : const SwTxtAttr* pAttr = (*pHts)[ n ];
2517 [ + - ][ + - : 480 : if( RES_TXTATR_NOEND_BEGIN <= pAttr->Which() ||
+ - - + ]
[ - + ]
2518 : 160 : *pAttr->GetStart() ||
2519 [ + - ]: 160 : *pAttr->GetAnyEnd() < rTxt.Len() )
2520 : : {
2521 [ # # ][ # # ]: 0 : if ((*pAttr->GetStart() == nNextSetField) &&
[ # # ]
2522 [ # # ]: 0 : (pAttr->Which() == RES_TXTATR_FIELD))
2523 : : {
2524 : : // #i104949# hideous hack for report builder:
2525 : : // it inserts hidden variable-set fields at
2526 : : // the beginning of para in cell, but they
2527 : : // should not turn cell into text cell
2528 : 0 : const SwField* pField = pAttr->GetFld().GetFld();
2529 [ # # ][ # # ]: 0 : if (pField &&
[ # # ][ # # ]
2530 [ # # ]: 0 : (pField->GetTypeId() == TYP_SETFLD) &&
2531 : : (0 != (static_cast<SwSetExpField const*>
2532 [ # # ]: 0 : (pField)->GetSubType() &
2533 : : nsSwExtendedSubType::SUB_INVISIBLE)))
2534 : : {
2535 : 0 : nNextSetField = *pAttr->GetStart() + 1;
2536 : 0 : continue;
2537 : : }
2538 : : }
2539 : 0 : nPos = ULONG_MAX;
2540 : 0 : break;
2541 : : }
2542 : : }
2543 : : }
2544 : : }
2545 : : }
2546 : : else
2547 [ + - ]: 444 : nPos = ULONG_MAX;
2548 : : }
2549 : 444 : return nPos;
2550 : : }
2551 : :
2552 : : // is this a Formula box or one with numeric content (AutoSum)
2553 : 0 : sal_uInt16 SwTableBox::IsFormulaOrValueBox() const
2554 : : {
2555 : 0 : sal_uInt16 nWhich = 0;
2556 : : const SwTxtNode* pTNd;
2557 : 0 : SwFrmFmt* pFmt = GetFrmFmt();
2558 [ # # ]: 0 : if( SFX_ITEM_SET == pFmt->GetItemState( RES_BOXATR_FORMULA, sal_False ))
2559 : 0 : nWhich = RES_BOXATR_FORMULA;
2560 [ # # # # ]: 0 : else if( SFX_ITEM_SET == pFmt->GetItemState( RES_BOXATR_VALUE, sal_False ) &&
[ # # ]
2561 : : !pFmt->GetDoc()->GetNumberFormatter()->IsTextFormat(
2562 : 0 : pFmt->GetTblBoxNumFmt().GetValue() ))
2563 : 0 : nWhich = RES_BOXATR_VALUE;
2564 [ # # ][ # # : 0 : else if( pSttNd && pSttNd->GetIndex() + 2 == pSttNd->EndOfSectionIndex()
# # # # ]
[ # # ]
2565 : 0 : && 0 != ( pTNd = pSttNd->GetNodes()[ pSttNd->GetIndex() + 1 ]
2566 : 0 : ->GetTxtNode() ) && !pTNd->GetTxt().Len() )
2567 : 0 : nWhich = USHRT_MAX;
2568 : :
2569 : 0 : return nWhich;
2570 : : }
2571 : :
2572 : 345 : void SwTableBox::ActualiseValueBox()
2573 : : {
2574 : : const SfxPoolItem *pFmtItem, *pValItem;
2575 : 345 : SwFrmFmt* pFmt = GetFrmFmt();
2576 [ - + ][ # # ]: 345 : if( SFX_ITEM_SET == pFmt->GetItemState( RES_BOXATR_FORMAT, sal_True, &pFmtItem )
[ - + ][ + - ]
2577 [ # # ]: 0 : && SFX_ITEM_SET == pFmt->GetItemState( RES_BOXATR_VALUE, sal_True, &pValItem ))
2578 : : {
2579 : 0 : const sal_uLong nFmtId = ((SwTblBoxNumFormat*)pFmtItem)->GetValue();
2580 : 0 : sal_uLong nNdPos = ULONG_MAX;
2581 [ # # ]: 0 : SvNumberFormatter* pNumFmtr = pFmt->GetDoc()->GetNumberFormatter();
2582 : :
2583 [ # # ][ # # ]: 0 : if( !pNumFmtr->IsTextFormat( nFmtId ) &&
[ # # ][ # # ]
[ # # ]
2584 : : ULONG_MAX != (nNdPos = IsValidNumTxtNd( sal_True )) )
2585 : : {
2586 : 0 : double fVal = ((SwTblBoxValue*)pValItem)->GetValue();
2587 : 0 : Color* pCol = 0;
2588 [ # # ]: 0 : String sNewTxt;
2589 [ # # ]: 0 : pNumFmtr->GetOutputString( fVal, nFmtId, sNewTxt, &pCol );
2590 : :
2591 [ # # ]: 0 : const String& rTxt = pSttNd->GetNodes()[ nNdPos ]->GetTxtNode()->GetTxt();
2592 [ # # ][ # # ]: 0 : if( rTxt != sNewTxt )
2593 [ # # ][ # # ]: 0 : ChgTextToNum( *this, sNewTxt, pCol, sal_False ,nNdPos);
2594 : : }
2595 : : }
2596 : 345 : }
2597 : :
2598 : 160 : void SwTableBox_Impl::SetNewCol( Color** ppCol, const Color* pNewCol )
2599 : : {
2600 [ + + ]: 160 : if( *ppCol != pNewCol )
2601 : : {
2602 : 80 : delete *ppCol;
2603 [ + - ]: 80 : if( pNewCol )
2604 : 80 : *ppCol = new Color( *pNewCol );
2605 : : else
2606 : 0 : *ppCol = 0;
2607 : : }
2608 : 160 : }
2609 : :
2610 : : struct SwTableCellInfo::Impl
2611 : : {
2612 : : const SwTable * m_pTable;
2613 : : const SwCellFrm * m_pCellFrm;
2614 : : const SwTabFrm * m_pTabFrm;
2615 : : typedef ::std::set<const SwTableBox *> TableBoxes_t;
2616 : : TableBoxes_t m_HandledTableBoxes;
2617 : :
2618 : : public:
2619 : 0 : Impl()
2620 : 0 : : m_pTable(NULL), m_pCellFrm(NULL), m_pTabFrm(NULL)
2621 : : {
2622 : 0 : }
2623 : :
2624 : 0 : ~Impl() {}
2625 : :
2626 : 0 : void setTable(const SwTable * pTable) {
2627 : 0 : m_pTable = pTable;
2628 : 0 : SwFrmFmt * pFrmFmt = m_pTable->GetFrmFmt();
2629 : 0 : m_pTabFrm = SwIterator<SwTabFrm,SwFmt>::FirstElement(*pFrmFmt);
2630 [ # # ]: 0 : if (m_pTabFrm->IsFollow())
2631 : 0 : m_pTabFrm = m_pTabFrm->FindMaster(true);
2632 : 0 : }
2633 : : const SwTable * getTable() const { return m_pTable; }
2634 : :
2635 : 0 : const SwCellFrm * getCellFrm() const { return m_pCellFrm; }
2636 : :
2637 : : const SwFrm * getNextFrmInTable(const SwFrm * pFrm);
2638 : : const SwCellFrm * getNextCellFrm(const SwFrm * pFrm);
2639 : : const SwCellFrm * getNextTableBoxsCellFrm(const SwFrm * pFrm);
2640 : : bool getNext();
2641 : : };
2642 : :
2643 : 0 : const SwFrm * SwTableCellInfo::Impl::getNextFrmInTable(const SwFrm * pFrm)
2644 : : {
2645 : 0 : const SwFrm * pResult = NULL;
2646 : :
2647 [ # # ][ # # ]: 0 : if (((! pFrm->IsTabFrm()) || pFrm == m_pTabFrm) && pFrm->GetLower())
[ # # ][ # # ]
2648 : 0 : pResult = pFrm->GetLower();
2649 [ # # ]: 0 : else if (pFrm->GetNext())
2650 : 0 : pResult = pFrm->GetNext();
2651 : : else
2652 : : {
2653 [ # # ]: 0 : while (pFrm->GetUpper() != NULL)
2654 : : {
2655 : 0 : pFrm = pFrm->GetUpper();
2656 : :
2657 [ # # ]: 0 : if (pFrm->IsTabFrm())
2658 : : {
2659 : 0 : m_pTabFrm = static_cast<const SwTabFrm *>(pFrm)->GetFollow();
2660 : 0 : pResult = m_pTabFrm;
2661 : 0 : break;
2662 : : }
2663 [ # # ]: 0 : else if (pFrm->GetNext())
2664 : : {
2665 : 0 : pResult = pFrm->GetNext();
2666 : 0 : break;
2667 : : }
2668 : : }
2669 : : }
2670 : :
2671 : 0 : return pResult;
2672 : : }
2673 : :
2674 : 0 : const SwCellFrm * SwTableCellInfo::Impl::getNextCellFrm(const SwFrm * pFrm)
2675 : : {
2676 : 0 : const SwCellFrm * pResult = NULL;
2677 : :
2678 [ # # ]: 0 : while ((pFrm = getNextFrmInTable(pFrm)) != NULL)
2679 : : {
2680 [ # # ]: 0 : if (pFrm->IsCellFrm())
2681 : : {
2682 : 0 : pResult = static_cast<const SwCellFrm *>(pFrm);
2683 : 0 : break;
2684 : : }
2685 : : }
2686 : :
2687 : 0 : return pResult;
2688 : : }
2689 : :
2690 : 0 : const SwCellFrm * SwTableCellInfo::Impl::getNextTableBoxsCellFrm(const SwFrm * pFrm)
2691 : : {
2692 : 0 : const SwCellFrm * pResult = NULL;
2693 : :
2694 [ # # ]: 0 : while ((pFrm = getNextCellFrm(pFrm)) != NULL)
2695 : : {
2696 : 0 : const SwCellFrm * pCellFrm = static_cast<const SwCellFrm *>(pFrm);
2697 : 0 : const SwTableBox * pTabBox = pCellFrm->GetTabBox();
2698 [ # # ]: 0 : TableBoxes_t::const_iterator aIt = m_HandledTableBoxes.find(pTabBox);
2699 : :
2700 [ # # ][ # # ]: 0 : if (aIt == m_HandledTableBoxes.end())
2701 : : {
2702 : 0 : pResult = pCellFrm;
2703 [ # # ]: 0 : m_HandledTableBoxes.insert(pTabBox);
2704 : : break;
2705 : : }
2706 : : }
2707 : :
2708 : 0 : return pResult;
2709 : : }
2710 : :
2711 : 0 : const SwCellFrm * SwTableCellInfo::getCellFrm() const
2712 : : {
2713 : 0 : return m_pImpl->getCellFrm();
2714 : : }
2715 : :
2716 : 0 : bool SwTableCellInfo::Impl::getNext()
2717 : : {
2718 [ # # ]: 0 : if (m_pCellFrm == NULL)
2719 : : {
2720 [ # # ]: 0 : if (m_pTabFrm != NULL)
2721 : 0 : m_pCellFrm = Impl::getNextTableBoxsCellFrm(m_pTabFrm);
2722 : : }
2723 : : else
2724 : 0 : m_pCellFrm = Impl::getNextTableBoxsCellFrm(m_pCellFrm);
2725 : :
2726 : 0 : return m_pCellFrm != NULL;
2727 : : }
2728 : :
2729 : 0 : SwTableCellInfo::SwTableCellInfo(const SwTable * pTable)
2730 : : {
2731 [ # # ][ # # ]: 0 : m_pImpl.reset(new Impl());
2732 [ # # ]: 0 : m_pImpl->setTable(pTable);
2733 : 0 : }
2734 : :
2735 [ # # ]: 0 : SwTableCellInfo::~SwTableCellInfo()
2736 : : {
2737 : 0 : }
2738 : :
2739 : 0 : bool SwTableCellInfo::getNext()
2740 : : {
2741 : 0 : return m_pImpl->getNext();
2742 : : }
2743 : :
2744 : 0 : SwRect SwTableCellInfo::getRect() const
2745 : : {
2746 : 0 : SwRect aRet;
2747 : :
2748 [ # # ]: 0 : if (getCellFrm() != NULL)
2749 : 0 : aRet = getCellFrm()->Frm();
2750 : :
2751 : 0 : return aRet;
2752 : : }
2753 : :
2754 : 0 : const SwTableBox * SwTableCellInfo::getTableBox() const
2755 : : {
2756 : 0 : const SwTableBox * pRet = NULL;
2757 : :
2758 [ # # ]: 0 : if (getCellFrm() != NULL)
2759 : 0 : pRet = getCellFrm()->GetTabBox();
2760 : :
2761 : 0 : return pRet;
2762 : : }
2763 : :
2764 : 232 : void SwTable::RegisterToFormat( SwFmt& rFmt )
2765 : : {
2766 : 232 : rFmt.Add( this );
2767 : 232 : }
2768 : :
2769 : 0 : bool SwTable::HasLayout() const
2770 : : {
2771 : 0 : const SwFrmFmt* pFrmFmt = GetFrmFmt();
2772 : : //a table in a clipboard document doesn't have any layout information
2773 [ # # ][ # # ]: 0 : return pFrmFmt && SwIterator<SwTabFrm,SwFmt>::FirstElement(*pFrmFmt);
2774 : : }
2775 : :
2776 : 0 : void SwTableLine::RegisterToFormat( SwFmt& rFmt )
2777 : : {
2778 : 0 : rFmt.Add( this );
2779 : 0 : }
2780 : :
2781 : 0 : void SwTableBox::RegisterToFormat( SwFmt& rFmt )
2782 : : {
2783 : 0 : rFmt.Add( this );
2784 : 0 : }
2785 : :
2786 : 0 : void SwTableBox::ForgetFrmFmt()
2787 : : {
2788 [ # # ]: 0 : if ( GetRegisteredIn() )
2789 : 0 : GetRegisteredInNonConst()->Remove(this);
2790 : 0 : }
2791 : :
2792 : : // free's any remaining child objects
2793 : 2544 : SwTableLines::~SwTableLines()
2794 : : {
2795 [ + - ][ + - ]: 3088 : for ( const_iterator it = begin(); it != end(); ++it )
[ + + ]
2796 [ + - ][ + - ]: 544 : delete *it;
2797 : 2544 : }
2798 : :
2799 : : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|