xref: /aoo4110/main/sw/source/core/doc/docfmt.cxx (revision b1cdbd2c)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_sw.hxx"
26 
27 
28 #define _ZFORLIST_DECLARE_TABLE
29 #define _SVSTDARR_USHORTSSORT
30 #define _SVSTDARR_USHORTS
31 #include <hintids.hxx>
32 #include <rtl/logfile.hxx>
33 #include <svl/itemiter.hxx>
34 #include <sfx2/app.hxx>
35 #include <editeng/tstpitem.hxx>
36 #include <editeng/eeitem.hxx>
37 #include <editeng/langitem.hxx>
38 #include <editeng/lrspitem.hxx>
39 #include <editeng/brkitem.hxx>
40 #include <svl/whiter.hxx>
41 #ifndef _ZFORLIST_HXX //autogen
42 #define _ZFORLIST_DECLARE_TABLE
43 #include <svl/zforlist.hxx>
44 #endif
45 #include <comphelper/processfactory.hxx>
46 #include <unotools/misccfg.hxx>
47 #include <com/sun/star/i18n/WordType.hdl>
48 #include <fmtpdsc.hxx>
49 #include <fmthdft.hxx>
50 #include <fmtcntnt.hxx>
51 #include <frmatr.hxx>
52 #include <doc.hxx>
53 #include <IDocumentUndoRedo.hxx>
54 #include <rootfrm.hxx>
55 #include <pagefrm.hxx>
56 #include <hints.hxx>			// fuer SwHyphenBug (in SetDefault)
57 #include <ndtxt.hxx>
58 #include <pam.hxx>
59 #include <UndoCore.hxx>
60 #include <UndoAttribute.hxx>
61 #include <ndgrf.hxx>
62 #include <pagedesc.hxx>			// Fuer Sonderbehandlung in InsFrmFmt
63 #include <rolbck.hxx>			// Undo-Attr
64 #include <mvsave.hxx>			// servieren: Veraenderungen erkennen
65 #include <txatbase.hxx>
66 #include <swtable.hxx>
67 #include <swtblfmt.hxx>
68 #include <charfmt.hxx>
69 #include <docary.hxx>
70 #include <paratr.hxx>
71 #include <redline.hxx>
72 #include <reffld.hxx>
73 #include <txtinet.hxx>
74 #include <fmtinfmt.hxx>
75 #include <breakit.hxx>
76 #include <SwStyleNameMapper.hxx>
77 #include <fmtautofmt.hxx>
78 #include <istyleaccess.hxx>
79 #include <SwUndoFmt.hxx>
80 #include <docsh.hxx>
81 
82 using namespace ::com::sun::star::i18n;
83 using namespace ::com::sun::star::lang;
84 using namespace ::com::sun::star::uno;
85 
SV_IMPL_PTRARR(SwFrmFmts,SwFrmFmtPtr)86 SV_IMPL_PTRARR(SwFrmFmts,SwFrmFmtPtr)
87 SV_IMPL_PTRARR(SwCharFmts,SwCharFmtPtr)
88 
89 //Spezifische Frameformate (Rahmen)
90 SV_IMPL_PTRARR(SwSpzFrmFmts,SwFrmFmtPtr)
91 
92 /*
93  * interne Funktionen
94  */
95 
96 sal_Bool SetTxtFmtCollNext( const SwTxtFmtCollPtr& rpTxtColl, void* pArgs )
97 {
98 	SwTxtFmtColl *pDel = (SwTxtFmtColl*) pArgs;
99 	if ( &rpTxtColl->GetNextTxtFmtColl() == pDel )
100 	{
101 		rpTxtColl->SetNextTxtFmtColl( *rpTxtColl );
102 	}
103 	return sal_True;
104 }
105 
106 /*
107  * Zuruecksetzen der harten Formatierung fuer Text
108  */
109 
110 // Uebergabeparameter fuer _Rst und lcl_SetTxtFmtColl
111 struct ParaRstFmt
112 {
113 	SwFmtColl* pFmtColl;
114 	SwHistory* pHistory;
115 	const SwPosition *pSttNd, *pEndNd;
116 	const SfxItemSet* pDelSet;
117 	sal_uInt16 nWhich;
118     bool bReset;
119     bool bResetListAttrs;
120     bool bResetAll;
121     bool bInclRefToxMark;
122 
ParaRstFmtParaRstFmt123 	ParaRstFmt( const SwPosition* pStt, const SwPosition* pEnd,
124                 SwHistory* pHst, sal_uInt16 nWhch = 0, const SfxItemSet* pSet = 0 )
125         : pFmtColl(0),
126           pHistory(pHst),
127           pSttNd(pStt),
128           pEndNd(pEnd),
129           pDelSet(pSet),
130           nWhich(nWhch),
131           bReset( false ),
132           bResetListAttrs( false ),
133           bResetAll( true ),
134           bInclRefToxMark( false )
135     {
136     }
137 
ParaRstFmtParaRstFmt138 	ParaRstFmt( SwHistory* pHst )
139         : pFmtColl(0),
140           pHistory(pHst),
141           pSttNd(0),
142           pEndNd(0),
143           pDelSet(0),
144           nWhich(0),
145           bReset( false ),
146           bResetListAttrs( false ),
147           bResetAll( true ),
148           bInclRefToxMark( false )
149     {
150     }
151 };
152 
153 /* in pArgs steht die ChrFmtTablle vom Dokument
154  * (wird bei Selectionen am Start/Ende und bei keiner SSelection benoetigt)
155  */
156 
lcl_RstTxtAttr(const SwNodePtr & rpNd,void * pArgs)157 sal_Bool lcl_RstTxtAttr( const SwNodePtr& rpNd, void* pArgs )
158 {
159     ParaRstFmt* pPara = (ParaRstFmt*)pArgs;
160     SwTxtNode * pTxtNode = (SwTxtNode*)rpNd->GetTxtNode();
161     if( pTxtNode && pTxtNode->GetpSwpHints() )
162     {
163         SwIndex aSt( pTxtNode, 0 );
164         sal_uInt16 nEnd = pTxtNode->Len();
165 
166         if( &pPara->pSttNd->nNode.GetNode() == pTxtNode &&
167             pPara->pSttNd->nContent.GetIndex() )
168             aSt = pPara->pSttNd->nContent.GetIndex();
169 
170         if( &pPara->pEndNd->nNode.GetNode() == rpNd )
171             nEnd = pPara->pEndNd->nContent.GetIndex();
172 
173         if( pPara->pHistory )
174         {
175             // fuers Undo alle Attribute sichern
176             SwRegHistory aRHst( *pTxtNode, pPara->pHistory );
177             pTxtNode->GetpSwpHints()->Register( &aRHst );
178             pTxtNode->RstTxtAttr( aSt, nEnd - aSt.GetIndex(), pPara->nWhich,
179                                   pPara->pDelSet, pPara->bInclRefToxMark );
180             if( pTxtNode->GetpSwpHints() )
181                 pTxtNode->GetpSwpHints()->DeRegister();
182         }
183         else
184             pTxtNode->RstTxtAttr( aSt, nEnd - aSt.GetIndex(), pPara->nWhich,
185                                   pPara->pDelSet, pPara->bInclRefToxMark );
186     }
187     return sal_True;
188 }
189 
lcl_RstAttr(const SwNodePtr & rpNd,void * pArgs)190 sal_Bool lcl_RstAttr( const SwNodePtr& rpNd, void* pArgs )
191 {
192     const ParaRstFmt* pPara = (ParaRstFmt*) pArgs;
193     SwCntntNode* pNode = (SwCntntNode*) rpNd->GetCntntNode();
194     if( pNode && pNode->HasSwAttrSet() )
195 	{
196         const sal_Bool bLocked = pNode->IsModifyLocked();
197         pNode->LockModify();
198 
199         SwDoc* pDoc = pNode->GetDoc();
200 
201         SfxItemSet aSavedAttrsSet(
202             pDoc->GetAttrPool(),
203             RES_PAGEDESC, RES_BREAK,
204             RES_PARATR_NUMRULE, RES_PARATR_NUMRULE,
205             RES_PARATR_LIST_BEGIN, RES_PARATR_LIST_END - 1,
206             0 );
207         const SfxItemSet* pAttrSetOfNode = pNode->GetpSwAttrSet();
208 
209         SvUShorts aClearWhichIds;
210         // restoring all paragraph list attributes
211         {
212             SfxItemSet aListAttrSet( pDoc->GetAttrPool(),
213                                      RES_PARATR_LIST_BEGIN, RES_PARATR_LIST_END - 1,
214                                      0 );
215             aListAttrSet.Set( *pAttrSetOfNode );
216             if ( aListAttrSet.Count() )
217             {
218                 aSavedAttrsSet.Put( aListAttrSet );
219                 SfxItemIter aIter( aListAttrSet );
220                 const SfxPoolItem* pItem = aIter.GetCurItem();
221                 while( pItem )
222                 {
223                     aClearWhichIds.Insert( pItem->Which(), aClearWhichIds.Count() );
224                     pItem = aIter.NextItem();
225                 }
226             }
227         }
228 
229         const SfxPoolItem* pItem;
230         sal_uInt16 __READONLY_DATA aSavIds[3] =
231                 { RES_PAGEDESC, RES_BREAK, RES_PARATR_NUMRULE };
232         for ( sal_uInt16 n = 0; n < 3; ++n )
233         {
234             if ( SFX_ITEM_SET == pAttrSetOfNode->GetItemState( aSavIds[n], sal_False, &pItem ) )
235             {
236                 bool bSave = false;
237                 switch (aSavIds[n])
238                 {
239                 case RES_PAGEDESC:
240                     bSave = 0 != ( (SwFmtPageDesc*) pItem )->GetPageDesc();
241                     break;
242                 case RES_BREAK:
243                     bSave = SVX_BREAK_NONE != ( (SvxFmtBreakItem*) pItem )->GetBreak();
244                     break;
245                 case RES_PARATR_NUMRULE:
246                     bSave = 0 != ( (SwNumRuleItem*) pItem )->GetValue().Len();
247                     break;
248                 }
249                 if ( bSave )
250                 {
251                     aSavedAttrsSet.Put( *pItem );
252                     aClearWhichIds.Insert( aSavIds[n], aClearWhichIds.Count() );
253                 }
254             }
255         }
256 
257         // do not clear items directly from item set and only clear to be kept
258         // attributes, if no deletion item set is found.
259         const bool bKeepAttributes =
260                     !pPara || !pPara->pDelSet || pPara->pDelSet->Count() == 0;
261         if ( bKeepAttributes )
262         {
263             pNode->ResetAttr( aClearWhichIds );
264         }
265 
266         if( !bLocked )
267             pNode->UnlockModify();
268 
269         if ( pPara )
270         {
271             SwRegHistory aRegH( pNode, *pNode, pPara->pHistory );
272 
273             if ( pPara->pDelSet && pPara->pDelSet->Count() )
274             {
275                 ASSERT( !bKeepAttributes,
276                         "<lcl_RstAttr(..)> - certain attributes are kept, but not needed. -> please inform OD" );
277                 SfxItemIter aIter( *pPara->pDelSet );
278                 pItem = aIter.FirstItem();
279                 while ( sal_True )
280                 {
281                     if ( ( pItem->Which() != RES_PAGEDESC &&
282                            pItem->Which() != RES_BREAK &&
283                            pItem->Which() != RES_PARATR_NUMRULE ) ||
284                          ( aSavedAttrsSet.GetItemState( pItem->Which(), sal_False ) != SFX_ITEM_SET ) )
285                     {
286                         pNode->ResetAttr( pItem->Which() );
287                     }
288                     if ( aIter.IsAtEnd() )
289                         break;
290                     pItem = aIter.NextItem();
291                 }
292             }
293             else if ( pPara->bResetAll )
294                 pNode->ResetAllAttr();
295             else
296                 pNode->ResetAttr( RES_PARATR_BEGIN, POOLATTR_END - 1 );
297         }
298         else
299             pNode->ResetAllAttr();
300 
301         // only restore saved attributes, if needed
302         if ( bKeepAttributes && aSavedAttrsSet.Count() )
303         {
304             pNode->LockModify();
305 
306             pNode->SetAttr( aSavedAttrsSet );
307 
308             if ( !bLocked )
309                 pNode->UnlockModify();
310         }
311     }
312     return sal_True;
313 }
314 
315 
RstTxtAttrs(const SwPaM & rRg,sal_Bool bInclRefToxMark)316 void SwDoc::RstTxtAttrs(const SwPaM &rRg, sal_Bool bInclRefToxMark )
317 {
318 	SwHistory* pHst = 0;
319 	SwDataChanged aTmp( rRg, 0 );
320     if (GetIDocumentUndoRedo().DoesUndo())
321     {
322         SwUndoResetAttr* pUndo = new SwUndoResetAttr( rRg, RES_CHRFMT );
323         pHst = &pUndo->GetHistory();
324         GetIDocumentUndoRedo().AppendUndo(pUndo);
325     }
326 	const SwPosition *pStt = rRg.Start(), *pEnd = rRg.End();
327 	ParaRstFmt aPara( pStt, pEnd, pHst );
328     aPara.bInclRefToxMark = ( bInclRefToxMark == sal_True );
329 	GetNodes().ForEach( pStt->nNode.GetIndex(), pEnd->nNode.GetIndex()+1,
330 						lcl_RstTxtAttr, &aPara );
331 	SetModified();
332 }
333 
ResetAttrs(const SwPaM & rRg,sal_Bool bTxtAttr,const SvUShortsSort * pAttrs,const bool bSendDataChangedEvents)334 void SwDoc::ResetAttrs( const SwPaM &rRg,
335                         sal_Bool bTxtAttr,
336                         const SvUShortsSort* pAttrs,
337                         // --> OD 2008-11-28 #b96644#
338                         const bool bSendDataChangedEvents )
339                         // <--
340 {
341 	SwPaM* pPam = (SwPaM*)&rRg;
342 	if( !bTxtAttr && pAttrs && pAttrs->Count() &&
343 		RES_TXTATR_END > (*pAttrs)[ 0 ] )
344 		bTxtAttr = sal_True;
345 
346 	if( !rRg.HasMark() )
347 	{
348 		SwTxtNode* pTxtNd = rRg.GetPoint()->nNode.GetNode().GetTxtNode();
349 		if( !pTxtNd )
350 			return ;
351 
352 		pPam = new SwPaM( *rRg.GetPoint() );
353 
354 		SwIndex& rSt = pPam->GetPoint()->nContent;
355 		sal_uInt16 nMkPos, nPtPos = rSt.GetIndex();
356 
357 		// JP 22.08.96: Sonderfall: steht der Crsr in einem URL-Attribut
358 		//				dann wird dessen Bereich genommen
359         SwTxtAttr const*const pURLAttr(
360             pTxtNd->GetTxtAttrAt(rSt.GetIndex(), RES_TXTATR_INETFMT));
361         if (pURLAttr && pURLAttr->GetINetFmt().GetValue().Len())
362 		{
363 			nMkPos = *pURLAttr->GetStart();
364 			nPtPos = *pURLAttr->End();
365 		}
366 		else
367 		{
368 			Boundary aBndry;
369 			if( pBreakIt->GetBreakIter().is() )
370 				aBndry = pBreakIt->GetBreakIter()->getWordBoundary(
371 							pTxtNd->GetTxt(), nPtPos,
372 							pBreakIt->GetLocale( pTxtNd->GetLang( nPtPos ) ),
373 							WordType::ANY_WORD /*ANYWORD_IGNOREWHITESPACES*/,
374 							sal_True );
375 
376 			if( aBndry.startPos < nPtPos && nPtPos < aBndry.endPos )
377 			{
378 				nMkPos = (xub_StrLen)aBndry.startPos;
379 				nPtPos = (xub_StrLen)aBndry.endPos;
380 			}
381 			else
382 			{
383 				nPtPos = nMkPos = rSt.GetIndex();
384 				if( bTxtAttr )
385 					pTxtNd->DontExpandFmt( rSt, sal_True );
386 			}
387 		}
388 
389 		rSt = nMkPos;
390 		pPam->SetMark();
391 		pPam->GetPoint()->nContent = nPtPos;
392 	}
393 
394     // --> OD 2008-11-28 #i96644#
395 //    SwDataChanged aTmp( *pPam, 0 );
396     std::auto_ptr< SwDataChanged > pDataChanged;
397     if ( bSendDataChangedEvents )
398     {
399         pDataChanged.reset( new SwDataChanged( *pPam, 0 ) );
400     }
401     // <--
402 	SwHistory* pHst = 0;
403     if (GetIDocumentUndoRedo().DoesUndo())
404     {
405         SwUndoResetAttr* pUndo = new SwUndoResetAttr( rRg,
406             static_cast<sal_uInt16>(bTxtAttr ? RES_CONDTXTFMTCOLL : RES_TXTFMTCOLL ));
407 		if( pAttrs && pAttrs->Count() )
408         {
409             pUndo->SetAttrs( *pAttrs );
410         }
411         pHst = &pUndo->GetHistory();
412         GetIDocumentUndoRedo().AppendUndo(pUndo);
413     }
414 
415 	const SwPosition *pStt = pPam->Start(), *pEnd = pPam->End();
416 	ParaRstFmt aPara( pStt, pEnd, pHst );
417 
418     // mst: not including META here; it seems attrs with CH_TXTATR are omitted
419     sal_uInt16 __FAR_DATA aResetableSetRange[] = {
420         RES_FRMATR_BEGIN, RES_FRMATR_END-1,
421         RES_CHRATR_BEGIN, RES_CHRATR_END-1,
422         RES_PARATR_BEGIN, RES_PARATR_END-1,
423         // --> OD 2008-02-25 #refactorlists#
424         RES_PARATR_LIST_BEGIN, RES_PARATR_LIST_END-1,
425         // <--
426         RES_TXTATR_INETFMT, RES_TXTATR_INETFMT,
427         RES_TXTATR_CHARFMT, RES_TXTATR_CHARFMT,
428         RES_TXTATR_CJK_RUBY, RES_TXTATR_CJK_RUBY,
429         RES_TXTATR_UNKNOWN_CONTAINER, RES_TXTATR_UNKNOWN_CONTAINER,
430         RES_UNKNOWNATR_BEGIN, RES_UNKNOWNATR_END-1,
431         0
432     };
433 
434 	SfxItemSet aDelSet( GetAttrPool(), aResetableSetRange );
435 	if( pAttrs && pAttrs->Count() )
436 	{
437 		for( sal_uInt16 n = pAttrs->Count(); n; )
438 			if( POOLATTR_END > (*pAttrs)[ --n ] )
439 				aDelSet.Put( *GetDfltAttr( (*pAttrs)[ n ] ));
440 
441 		if( aDelSet.Count() )
442 			aPara.pDelSet = &aDelSet;
443 	}
444 
445 	sal_Bool bAdd = sal_True;
446 	SwNodeIndex aTmpStt( pStt->nNode );
447 	SwNodeIndex aTmpEnd( pEnd->nNode );
448 	if( pStt->nContent.GetIndex() )		// nur ein Teil
449 	{
450 		// dann spaeter aufsetzen und alle CharFmtAttr -> TxtFmtAttr
451 		SwTxtNode* pTNd = aTmpStt.GetNode().GetTxtNode();
452         if( pTNd && pTNd->HasSwAttrSet() && pTNd->GetpSwAttrSet()->Count() )
453 		{
454             if (pHst)
455             {
456                 SwRegHistory history(pTNd, *pTNd, pHst);
457                 pTNd->FmtToTxtAttr(pTNd);
458             }
459             else
460             {
461                 pTNd->FmtToTxtAttr(pTNd);
462             }
463 		}
464 
465 		aTmpStt++;
466 	}
467 	if( pEnd->nContent.GetIndex() == pEnd->nNode.GetNode().GetCntntNode()->Len() )
468 		// dann spaeter aufsetzen und alle CharFmtAttr -> TxtFmtAttr
469 		aTmpEnd++, bAdd = sal_False;
470 	else if( pStt->nNode != pEnd->nNode || !pStt->nContent.GetIndex() )
471 	{
472 		SwTxtNode* pTNd = aTmpEnd.GetNode().GetTxtNode();
473         if( pTNd && pTNd->HasSwAttrSet() && pTNd->GetpSwAttrSet()->Count() )
474 		{
475             if (pHst)
476             {
477                 SwRegHistory history(pTNd, *pTNd, pHst);
478                 pTNd->FmtToTxtAttr(pTNd);
479             }
480             else
481             {
482                 pTNd->FmtToTxtAttr(pTNd);
483             }
484 		}
485 	}
486 
487 	if( aTmpStt < aTmpEnd )
488 		GetNodes().ForEach( pStt->nNode, aTmpEnd, lcl_RstAttr, &aPara );
489 	else if( !rRg.HasMark() )
490 	{
491         aPara.bResetAll = false ;
492 		::lcl_RstAttr( &pStt->nNode.GetNode(), &aPara );
493         aPara.bResetAll = true ;
494 	}
495 
496 	if( bTxtAttr )
497 	{
498 		if( bAdd )
499 			aTmpEnd++;
500 		GetNodes().ForEach( pStt->nNode, aTmpEnd, lcl_RstTxtAttr, &aPara );
501 	}
502 
503 	if( pPam != &rRg )
504 		delete pPam;
505 
506 	SetModified();
507 }
508 
509 #define DELETECHARSETS if ( bDelete ) { delete pCharSet; delete pOtherSet; }
510 
511 // Einfuegen der Hints nach Inhaltsformen;
512 // wird in SwDoc::Insert(..., SwFmtHint &rHt) benutzt
513 
lcl_InsAttr(SwDoc * const pDoc,const SwPaM & rRg,const SfxItemSet & rChgSet,const SetAttrMode nFlags,SwUndoAttr * const pUndo,const bool bExpandCharToPara=false)514 static bool lcl_InsAttr(
515     SwDoc *const pDoc,
516     const SwPaM &rRg,
517     const SfxItemSet& rChgSet,
518     const SetAttrMode nFlags,
519     SwUndoAttr *const pUndo,
520     //Modify here for #119405, by easyfan, 2012-05-24
521     const bool bExpandCharToPara=false)
522     //End of modification, by easyfan
523 {
524     // teil die Sets auf (fuer Selektion in Nodes)
525     const SfxItemSet* pCharSet = 0;
526     const SfxItemSet* pOtherSet = 0;
527     bool bDelete = false;
528     bool bCharAttr = false;
529     bool bOtherAttr = false;
530 
531     // Check, if we can work with rChgSet or if we have to create additional SfxItemSets
532     if ( 1 == rChgSet.Count() )
533     {
534         SfxItemIter aIter( rChgSet );
535         const SfxPoolItem* pItem = aIter.FirstItem();
536 
537         if (!IsInvalidItem(pItem))
538         {
539             const sal_uInt16 nWhich = pItem->Which();
540 
541             if ( isCHRATR(nWhich) ||
542                  (RES_TXTATR_CHARFMT == nWhich) ||
543                  (RES_TXTATR_INETFMT == nWhich) ||
544                  (RES_TXTATR_AUTOFMT == nWhich) ||
545                  (RES_TXTATR_UNKNOWN_CONTAINER == nWhich) )
546             {
547                 pCharSet  = &rChgSet;
548                 bCharAttr = true;
549             }
550 
551             if (    isPARATR(nWhich)
552                     || isPARATR_LIST(nWhich)
553                     || isFRMATR(nWhich)
554                     || isGRFATR(nWhich)
555                     || isUNKNOWNATR(nWhich) )
556             {
557                 pOtherSet = &rChgSet;
558                 bOtherAttr = true;
559             }
560         }
561     }
562 
563     // Build new itemset if either
564     // - rChgSet.Count() > 1 or
565     // - The attribute in rChgSet does not belong to one of the above categories
566     if ( !bCharAttr && !bOtherAttr )
567     {
568         SfxItemSet* pTmpCharItemSet = new SfxItemSet( pDoc->GetAttrPool(),
569                                    RES_CHRATR_BEGIN, RES_CHRATR_END-1,
570                                    RES_TXTATR_AUTOFMT, RES_TXTATR_AUTOFMT,
571                                    RES_TXTATR_INETFMT, RES_TXTATR_INETFMT,
572                                    RES_TXTATR_CHARFMT, RES_TXTATR_CHARFMT,
573                RES_TXTATR_UNKNOWN_CONTAINER, RES_TXTATR_UNKNOWN_CONTAINER,
574                                    0 );
575 
576         SfxItemSet* pTmpOtherItemSet = new SfxItemSet( pDoc->GetAttrPool(),
577                                     RES_PARATR_BEGIN, RES_PARATR_END-1,
578                                     RES_PARATR_LIST_BEGIN, RES_PARATR_LIST_END-1,
579                                     RES_FRMATR_BEGIN, RES_FRMATR_END-1,
580                                     RES_GRFATR_BEGIN, RES_GRFATR_END-1,
581                                     RES_UNKNOWNATR_BEGIN, RES_UNKNOWNATR_END-1,
582                                     0 );
583 
584         pTmpCharItemSet->Put( rChgSet );
585         pTmpOtherItemSet->Put( rChgSet );
586 
587         pCharSet = pTmpCharItemSet;
588         pOtherSet = pTmpOtherItemSet;
589 
590         bDelete = true;
591     }
592 
593     SwHistory* pHistory = pUndo ? &pUndo->GetHistory() : 0;
594     bool bRet = false;
595     const SwPosition *pStt = rRg.Start(), *pEnd = rRg.End();
596     SwCntntNode* pNode = pStt->nNode.GetNode().GetCntntNode();
597 
598     if( pNode && pNode->IsTxtNode() )
599     {
600         // -> #i27615#
601         if (rRg.IsInFrontOfLabel())
602         {
603             SwTxtNode * pTxtNd = pNode->GetTxtNode();
604             SwNumRule * pNumRule = pTxtNd->GetNumRule();
605 
606             if ( !pNumRule )
607             {
608                 ASSERT( false,
609                         "<InsAttr(..)> - PaM in front of label, but text node has no numbering rule set. This is a serious defect, please inform OD." );
610                 DELETECHARSETS
611                 return false;
612             }
613 
614             SwNumFmt aNumFmt = pNumRule->Get(static_cast<sal_uInt16>(pTxtNd->GetActualListLevel()));
615             SwCharFmt * pCharFmt =
616                 pDoc->FindCharFmtByName(aNumFmt.GetCharFmtName());
617 
618             if (pCharFmt)
619             {
620                 if (pHistory)
621                     pHistory->Add(pCharFmt->GetAttrSet(), *pCharFmt);
622 
623                 if ( pCharSet )
624                     pCharFmt->SetFmtAttr(*pCharSet);
625             }
626 
627             DELETECHARSETS
628             return true;
629         }
630 
631         const SwIndex& rSt = pStt->nContent;
632 
633         // Attribute ohne Ende haben keinen Bereich
634         if ( !bCharAttr && !bOtherAttr )
635         {
636             SfxItemSet aTxtSet( pDoc->GetAttrPool(),
637                         RES_TXTATR_NOEND_BEGIN, RES_TXTATR_NOEND_END-1 );
638             aTxtSet.Put( rChgSet );
639             if( aTxtSet.Count() )
640             {
641                 SwRegHistory history( pNode, *pNode, pHistory );
642                 bRet = history.InsertItems(
643                     aTxtSet, rSt.GetIndex(), rSt.GetIndex(), nFlags ) || bRet;
644 
645                 if (bRet && (pDoc->IsRedlineOn() || (!pDoc->IsIgnoreRedline()
646                                 && pDoc->GetRedlineTbl().Count())))
647                 {
648                     SwPaM aPam( pStt->nNode, pStt->nContent.GetIndex()-1,
649                                 pStt->nNode, pStt->nContent.GetIndex() );
650 
651                     if( pUndo )
652                         pUndo->SaveRedlineData( aPam, sal_True );
653 
654                     if( pDoc->IsRedlineOn() )
655                         pDoc->AppendRedline( new SwRedline( nsRedlineType_t::REDLINE_INSERT, aPam ), true);
656                     else
657                         pDoc->SplitRedline( aPam );
658                 }
659             }
660         }
661 
662         // TextAttribute mit Ende expandieren nie ihren Bereich
663         if ( !bCharAttr && !bOtherAttr )
664         {
665             // CharFmt wird gesondert behandelt !!!
666             // JP 22.08.96: URL-Attribute auch!!
667             // TEST_TEMP ToDo: AutoFmt!
668             SfxItemSet aTxtSet( pDoc->GetAttrPool(),
669                                 RES_TXTATR_REFMARK, RES_TXTATR_TOXMARK,
670                                 RES_TXTATR_META, RES_TXTATR_METAFIELD,
671                                 RES_TXTATR_CJK_RUBY, RES_TXTATR_CJK_RUBY,
672                                 RES_TXTATR_INPUTFIELD, RES_TXTATR_INPUTFIELD,
673                                 0 );
674 
675             aTxtSet.Put( rChgSet );
676             if( aTxtSet.Count() )
677             {
678                 sal_uInt16 nInsCnt = rSt.GetIndex();
679                 sal_uInt16 nEnd = pStt->nNode == pEnd->nNode
680                                 ? pEnd->nContent.GetIndex()
681                                 : pNode->Len();
682                 SwRegHistory history( pNode, *pNode, pHistory );
683                 bRet = history.InsertItems( aTxtSet, nInsCnt, nEnd, nFlags )
684                        || bRet;
685 
686                 if (bRet && (pDoc->IsRedlineOn() || (!pDoc->IsIgnoreRedline()
687                                 && pDoc->GetRedlineTbl().Count())))
688                 {
689                     // wurde Text-Inhalt eingefuegt? (RefMark/TOXMarks ohne Ende)
690                     sal_Bool bTxtIns = nInsCnt != rSt.GetIndex();
691                     // wurde Inhalt eingefuegt oder ueber die Selektion gesetzt?
692                     SwPaM aPam( pStt->nNode, bTxtIns ? nInsCnt + 1 : nEnd,
693                                 pStt->nNode, nInsCnt );
694                     if( pUndo )
695                         pUndo->SaveRedlineData( aPam, bTxtIns );
696 
697                     if( pDoc->IsRedlineOn() )
698                         pDoc->AppendRedline(
699                             new SwRedline(
700                                 bTxtIns ? nsRedlineType_t::REDLINE_INSERT : nsRedlineType_t::REDLINE_FORMAT, aPam ),
701                                 true);
702                     else if( bTxtIns )
703                         pDoc->SplitRedline( aPam );
704                 }
705             }
706         }
707     }
708 
709     // bei PageDesc's, die am Node gesetzt werden, muss immer das
710     // Auto-Flag gesetzt werden!!
711     if( pOtherSet && pOtherSet->Count() )
712     {
713         SwTableNode* pTblNd;
714         const SwFmtPageDesc* pDesc;
715         if( SFX_ITEM_SET == pOtherSet->GetItemState( RES_PAGEDESC,
716                         sal_False, (const SfxPoolItem**)&pDesc ))
717         {
718             if( pNode )
719             {
720                 // Auto-Flag setzen, nur in Vorlagen ist ohne Auto !
721                 SwFmtPageDesc aNew( *pDesc );
722                 // Bug 38479: AutoFlag wird jetzt in der WrtShell gesetzt
723                 // aNew.SetAuto();
724 
725                 // Tabellen kennen jetzt auch Umbrueche
726                 if( 0 == (nFlags & nsSetAttrMode::SETATTR_APICALL) &&
727                     0 != ( pTblNd = pNode->FindTableNode() ) )
728                 {
729                     SwTableNode* pCurTblNd = pTblNd;
730                     while ( 0 != ( pCurTblNd = pCurTblNd->StartOfSectionNode()->FindTableNode() ) )
731                         pTblNd = pCurTblNd;
732 
733                     // dann am Tabellen Format setzen
734                     SwFrmFmt* pFmt = pTblNd->GetTable().GetFrmFmt();
735                     SwRegHistory aRegH( pFmt, *pTblNd, pHistory );
736                     pFmt->SetFmtAttr( aNew );
737                     bRet = true;
738                 }
739                 else
740                 {
741                     SwRegHistory aRegH( pNode, *pNode, pHistory );
742                     bRet = pNode->SetAttr( aNew ) || bRet;
743                 }
744             }
745 
746             // bOtherAttr = true means that pOtherSet == rChgSet. In this case
747             // we know, that there is only one attribute in pOtherSet. We cannot
748             // perform the following operations, instead we return:
749             if ( bOtherAttr )
750                 return bRet;
751 
752             const_cast<SfxItemSet*>(pOtherSet)->ClearItem( RES_PAGEDESC );
753             if( !pOtherSet->Count() )
754             {
755                 DELETECHARSETS
756                 return bRet;
757             }
758         }
759 
760         // Tabellen kennen jetzt auch Umbrueche
761         const SvxFmtBreakItem* pBreak;
762         if( pNode && 0 == (nFlags & nsSetAttrMode::SETATTR_APICALL) &&
763             0 != (pTblNd = pNode->FindTableNode() ) &&
764             SFX_ITEM_SET == pOtherSet->GetItemState( RES_BREAK,
765                         sal_False, (const SfxPoolItem**)&pBreak ) )
766         {
767             SwTableNode* pCurTblNd = pTblNd;
768             while ( 0 != ( pCurTblNd = pCurTblNd->StartOfSectionNode()->FindTableNode() ) )
769                 pTblNd = pCurTblNd;
770 
771             // dann am Tabellen Format setzen
772             SwFrmFmt* pFmt = pTblNd->GetTable().GetFrmFmt();
773             SwRegHistory aRegH( pFmt, *pTblNd, pHistory );
774             pFmt->SetFmtAttr( *pBreak );
775             bRet = true;
776 
777             // bOtherAttr = true means that pOtherSet == rChgSet. In this case
778             // we know, that there is only one attribute in pOtherSet. We cannot
779             // perform the following operations, instead we return:
780             if ( bOtherAttr )
781                 return bRet;
782 
783             const_cast<SfxItemSet*>(pOtherSet)->ClearItem( RES_BREAK );
784             if( !pOtherSet->Count() )
785             {
786                 DELETECHARSETS
787                 return bRet;
788             }
789         }
790 
791         {
792             // wenns eine PoolNumRule ist, diese ggfs. anlegen
793             const SwNumRuleItem* pRule;
794             sal_uInt16 nPoolId;
795             if( SFX_ITEM_SET == pOtherSet->GetItemState( RES_PARATR_NUMRULE,
796                                 sal_False, (const SfxPoolItem**)&pRule ) &&
797                 !pDoc->FindNumRulePtr( pRule->GetValue() ) &&
798                 USHRT_MAX != (nPoolId = SwStyleNameMapper::GetPoolIdFromUIName ( pRule->GetValue(),
799                                 nsSwGetPoolIdFromName::GET_POOLID_NUMRULE )) )
800                 pDoc->GetNumRuleFromPool( nPoolId );
801         }
802 
803     }
804 
805     if( !rRg.HasMark() )		// kein Bereich
806     {
807         if( !pNode )
808         {
809             DELETECHARSETS
810             return bRet;
811         }
812 
813         if( pNode->IsTxtNode() && pCharSet && pCharSet->Count() )
814         {
815             SwTxtNode* pTxtNd = static_cast<SwTxtNode*>(pNode);
816             const SwIndex& rSt = pStt->nContent;
817             sal_uInt16 nMkPos, nPtPos = rSt.GetIndex();
818             const String& rStr = pTxtNd->GetTxt();
819 
820             // JP 22.08.96: Sonderfall: steht der Crsr in einem URL-Attribut
821             //				dann wird dessen Bereich genommen
822             SwTxtAttr const*const pURLAttr(
823                 pTxtNd->GetTxtAttrAt(rSt.GetIndex(), RES_TXTATR_INETFMT));
824             if (pURLAttr && pURLAttr->GetINetFmt().GetValue().Len())
825             {
826                 nMkPos = *pURLAttr->GetStart();
827                 nPtPos = *pURLAttr->End();
828             }
829             else
830             {
831                 Boundary aBndry;
832                 if( pBreakIt->GetBreakIter().is() )
833                     aBndry = pBreakIt->GetBreakIter()->getWordBoundary(
834                                 pTxtNd->GetTxt(), nPtPos,
835                                 pBreakIt->GetLocale( pTxtNd->GetLang( nPtPos ) ),
836                                 WordType::ANY_WORD /*ANYWORD_IGNOREWHITESPACES*/,
837                                 sal_True );
838 
839                 if( aBndry.startPos < nPtPos && nPtPos < aBndry.endPos )
840                 {
841                     nMkPos = (xub_StrLen)aBndry.startPos;
842                     nPtPos = (xub_StrLen)aBndry.endPos;
843                 }
844                 else
845                     nPtPos = nMkPos = rSt.GetIndex();
846             }
847 
848             // erstmal die zu ueberschreibenden Attribute aus dem
849             // SwpHintsArray entfernen, wenn die Selektion den gesamten
850             // Absatz umspannt. (Diese Attribute werden als FormatAttr.
851             // eingefuegt und verdraengen nie die TextAttr.!)
852             if( !(nFlags & nsSetAttrMode::SETATTR_DONTREPLACE ) &&
853                 pTxtNd->HasHints() && !nMkPos && nPtPos == rStr.Len() )
854             {
855                 SwIndex aSt( pTxtNd );
856                 if( pHistory )
857                 {
858                     // fuers Undo alle Attribute sichern
859                     SwRegHistory aRHst( *pTxtNd, pHistory );
860                     pTxtNd->GetpSwpHints()->Register( &aRHst );
861                     pTxtNd->RstTxtAttr( aSt, nPtPos, 0, pCharSet );
862                     if( pTxtNd->GetpSwpHints() )
863                         pTxtNd->GetpSwpHints()->DeRegister();
864                 }
865                 else
866                     pTxtNd->RstTxtAttr( aSt, nPtPos, 0, pCharSet );
867             }
868 
869             // the SwRegHistory inserts the attribute into the TxtNode!
870             SwRegHistory history( pNode, *pNode, pHistory );
871             bRet = history.InsertItems( *pCharSet, nMkPos, nPtPos, nFlags )
872                 || bRet;
873 
874             if( pDoc->IsRedlineOn() )
875             {
876                 SwPaM aPam( *pNode, nMkPos, *pNode, nPtPos );
877 
878                 if( pUndo )
879                     pUndo->SaveRedlineData( aPam, sal_False );
880                 pDoc->AppendRedline( new SwRedline( nsRedlineType_t::REDLINE_FORMAT, aPam ), true);
881             }
882         }
883         if( pOtherSet && pOtherSet->Count() )
884         {
885             SwRegHistory aRegH( pNode, *pNode, pHistory );
886             bRet = pNode->SetAttr( *pOtherSet ) || bRet;
887         }
888 
889         DELETECHARSETS
890         return bRet;
891     }
892 
893     if( pDoc->IsRedlineOn() && pCharSet && pCharSet->Count() )
894     {
895         if( pUndo )
896             pUndo->SaveRedlineData( rRg, sal_False );
897         pDoc->AppendRedline( new SwRedline( nsRedlineType_t::REDLINE_FORMAT, rRg ), true);
898     }
899 
900     /* jetzt wenn Bereich */
901     sal_uLong nNodes = 0;
902 
903     SwNodeIndex aSt( pDoc->GetNodes() );
904     SwNodeIndex aEnd( pDoc->GetNodes() );
905     SwIndex aCntEnd( pEnd->nContent );
906 
907     if( pNode )
908     {
909         sal_uInt16 nLen = pNode->Len();
910         if( pStt->nNode != pEnd->nNode )
911             aCntEnd.Assign( pNode, nLen );
912 
913         if( pStt->nContent.GetIndex() != 0 || aCntEnd.GetIndex() != nLen )
914         {
915             // the SwRegHistory inserts the attribute into the TxtNode!
916             if( pNode->IsTxtNode() && pCharSet && pCharSet->Count() )
917             {
918                 SwRegHistory history( pNode, *pNode, pHistory );
919                 bRet = history.InsertItems(*pCharSet,
920                         pStt->nContent.GetIndex(), aCntEnd.GetIndex(), nFlags)
921                     || bRet;
922             }
923 
924             if( pOtherSet && pOtherSet->Count() )
925             {
926                 SwRegHistory aRegH( pNode, *pNode, pHistory );
927                 bRet = pNode->SetAttr( *pOtherSet ) || bRet;
928             }
929 
930             // lediglich Selektion in einem Node.
931             if( pStt->nNode == pEnd->nNode )
932             {
933             //Modify here for #119405, by easyfan, 2012-05-24
934             //The data parameter flag: bExpandCharToPara, comes from the data member of SwDoc,
935             //Which is set in SW MS word Binary filter WW8ImplRreader. With this flag on, means that
936             //current setting attribute set is a character range properties set and comes from a MS word
937             //binary file, And the setting range include a paragraph end position (0X0D);
938             //More specifications, as such property inside the character range properties set recorded in
939             //MS word binary file are dealed and inserted into data model (SwDoc) one by one, so we
940             //only dealing the scenario that the char properties set with 1 item inside;
941 
942                     if (bExpandCharToPara && pCharSet && pCharSet->Count() ==1 )
943             {
944                 SwTxtNode* pCurrentNd = pStt->nNode.GetNode().GetTxtNode();
945 
946                 if (pCurrentNd)
947                 {
948                     pCurrentNd->TryCharSetExpandToNum(*pCharSet);
949 
950                 }
951             }
952             //End of modification, by easyfan
953                 DELETECHARSETS
954                 return bRet;
955             }
956             ++nNodes;
957             aSt.Assign( pStt->nNode.GetNode(), +1 );
958         }
959         else
960             aSt = pStt->nNode;
961         aCntEnd = pEnd->nContent; // aEnd wurde veraendert !!
962     }
963     else
964         aSt.Assign( pStt->nNode.GetNode(), +1 );
965 
966     // aSt zeigt jetzt auf den ersten vollen Node
967 
968     /*
969      * die Selektion umfasst mehr als einen Node
970      */
971     if( pStt->nNode < pEnd->nNode )
972     {
973         pNode = pEnd->nNode.GetNode().GetCntntNode();
974         if(pNode)
975         {
976             sal_uInt16 nLen = pNode->Len();
977             if( aCntEnd.GetIndex() != nLen )
978             {
979                 // the SwRegHistory inserts the attribute into the TxtNode!
980                 if( pNode->IsTxtNode() && pCharSet && pCharSet->Count() )
981                 {
982                     SwRegHistory history( pNode, *pNode, pHistory );
983                     history.InsertItems(*pCharSet,
984                             0, aCntEnd.GetIndex(), nFlags);
985                 }
986 
987                 if( pOtherSet && pOtherSet->Count() )
988                 {
989                     SwRegHistory aRegH( pNode, *pNode, pHistory );
990                     pNode->SetAttr( *pOtherSet );
991                 }
992 
993                 ++nNodes;
994                 aEnd = pEnd->nNode;
995             }
996             else
997                 aEnd.Assign( pEnd->nNode.GetNode(), +1 );
998         }
999         else
1000             aEnd = pEnd->nNode;
1001     }
1002     else
1003         aEnd.Assign( pEnd->nNode.GetNode(), +1 );
1004 
1005     // aEnd zeigt jetzt HINTER den letzten voll Node
1006 
1007     /* Bearbeitung der vollstaendig selektierten Nodes. */
1008 // alle Attribute aus dem Set zuruecksetzen !!
1009     if( pCharSet && pCharSet->Count() && !( nsSetAttrMode::SETATTR_DONTREPLACE & nFlags ) )
1010     {
1011 
1012         ParaRstFmt aPara( pStt, pEnd, pHistory, 0, pCharSet );
1013         pDoc->GetNodes().ForEach( aSt, aEnd, lcl_RstTxtAttr, &aPara );
1014     }
1015 
1016     sal_Bool bCreateSwpHints = pCharSet && (
1017         SFX_ITEM_SET == pCharSet->GetItemState( RES_TXTATR_CHARFMT, sal_False ) ||
1018         SFX_ITEM_SET == pCharSet->GetItemState( RES_TXTATR_INETFMT, sal_False ) );
1019 
1020     for(; aSt < aEnd; aSt++ )
1021     {
1022         pNode = aSt.GetNode().GetCntntNode();
1023         if( !pNode )
1024             continue;
1025 
1026         SwTxtNode* pTNd = pNode->GetTxtNode();
1027         if( pHistory )
1028         {
1029             SwRegHistory aRegH( pNode, *pNode, pHistory );
1030             SwpHints *pSwpHints;
1031 
1032             if( pTNd && pCharSet && pCharSet->Count() )
1033             {
1034                 pSwpHints = bCreateSwpHints ? &pTNd->GetOrCreateSwpHints()
1035                                             : pTNd->GetpSwpHints();
1036                 if( pSwpHints )
1037                     pSwpHints->Register( &aRegH );
1038 
1039                 pTNd->SetAttr( *pCharSet, 0, pTNd->GetTxt().Len(), nFlags );
1040                 if( pSwpHints )
1041                     pSwpHints->DeRegister();
1042             }
1043             if( pOtherSet && pOtherSet->Count() )
1044                 pNode->SetAttr( *pOtherSet );
1045         }
1046         else
1047         {
1048             if( pTNd && pCharSet && pCharSet->Count() )
1049                 pTNd->SetAttr( *pCharSet, 0, pTNd->GetTxt().Len(), nFlags );
1050             if( pOtherSet && pOtherSet->Count() )
1051                 pNode->SetAttr( *pOtherSet );
1052         }
1053         ++nNodes;
1054     }
1055 
1056     //The data parameter flag: bExpandCharToPara, comes from the data member of SwDoc,
1057     //Which is set in SW MS word Binary filter WW8ImplRreader. With this flag on, means that
1058     //current setting attribute set is a character range properties set and comes from a MS word
1059     //binary file, And the setting range include a paragraph end position (0X0D);
1060     //More specifications, as such property inside the character range properties set recorded in
1061     //MS word binary file are dealed and inserted into data model (SwDoc) one by one, so we
1062     //only dealing the scenario that the char properties set with 1 item inside;
1063     if (bExpandCharToPara && pCharSet && pCharSet->Count() ==1)
1064     {
1065         SwPosition aStartPos (*rRg.Start());
1066         SwPosition aEndPos (*rRg.End());
1067 
1068         if (aEndPos.nNode.GetNode().GetTxtNode() && aEndPos.nContent != aEndPos.nNode.GetNode().GetTxtNode()->Len())
1069             aEndPos.nNode--;
1070 
1071         for (;aStartPos<=aEndPos;aStartPos.nNode++)
1072         {
1073             SwTxtNode* pCurrentNd = aStartPos.nNode.GetNode().GetTxtNode();
1074 
1075             if (pCurrentNd)
1076             {
1077                 pCurrentNd->TryCharSetExpandToNum(*pCharSet);
1078 
1079             }
1080 
1081         }
1082     }
1083 
1084     DELETECHARSETS
1085     return (nNodes != 0) || bRet;
1086 }
1087 
InsertPoolItem(const SwPaM & rRg,const SfxPoolItem & rHt,const SetAttrMode nFlags,const bool bExpandCharToPara)1088 bool SwDoc::InsertPoolItem(
1089     const SwPaM &rRg,
1090     const SfxPoolItem &rHt,
1091     const SetAttrMode nFlags,
1092     const bool bExpandCharToPara)
1093 {
1094     SwDataChanged aTmp( rRg, 0 );
1095     SwUndoAttr* pUndoAttr = 0;
1096     if (GetIDocumentUndoRedo().DoesUndo())
1097     {
1098         GetIDocumentUndoRedo().ClearRedo();
1099         pUndoAttr = new SwUndoAttr( rRg, rHt, nFlags );
1100     }
1101 
1102     SfxItemSet aSet( GetAttrPool(), rHt.Which(), rHt.Which() );
1103     aSet.Put( rHt );
1104     const bool bRet = lcl_InsAttr( this, rRg, aSet, nFlags, pUndoAttr,bExpandCharToPara );
1105 
1106     if (GetIDocumentUndoRedo().DoesUndo())
1107     {
1108         GetIDocumentUndoRedo().AppendUndo( pUndoAttr );
1109     }
1110 
1111     if( bRet )
1112     {
1113         SetModified();
1114     }
1115     return bRet;
1116 }
1117 
InsertItemSet(const SwPaM & rRg,const SfxItemSet & rSet,const SetAttrMode nFlags)1118 bool SwDoc::InsertItemSet ( const SwPaM &rRg, const SfxItemSet &rSet,
1119                             const SetAttrMode nFlags )
1120 {
1121 	SwDataChanged aTmp( rRg, 0 );
1122 	SwUndoAttr* pUndoAttr = 0;
1123     if (GetIDocumentUndoRedo().DoesUndo())
1124     {
1125         GetIDocumentUndoRedo().ClearRedo();
1126         pUndoAttr = new SwUndoAttr( rRg, rSet, nFlags );
1127 	}
1128 
1129     bool bRet = lcl_InsAttr( this, rRg, rSet, nFlags, pUndoAttr );
1130 
1131     if (GetIDocumentUndoRedo().DoesUndo())
1132     {
1133         GetIDocumentUndoRedo().AppendUndo( pUndoAttr );
1134     }
1135 
1136 	if( bRet )
1137 		SetModified();
1138 	return bRet;
1139 }
1140 
1141 
1142 	// Setze das Attribut im angegebenen Format. Ist Undo aktiv, wird
1143 	// das alte in die Undo-History aufgenommen
SetAttr(const SfxPoolItem & rAttr,SwFmt & rFmt)1144 void SwDoc::SetAttr( const SfxPoolItem& rAttr, SwFmt& rFmt )
1145 {
1146 	SfxItemSet aSet( GetAttrPool(), rAttr.Which(), rAttr.Which() );
1147 	aSet.Put( rAttr );
1148 	SetAttr( aSet, rFmt );
1149 }
1150 
1151 
1152 	// Setze das Attribut im angegebenen Format. Ist Undo aktiv, wird
1153 	// das alte in die Undo-History aufgenommen
SetAttr(const SfxItemSet & rSet,SwFmt & rFmt)1154 void SwDoc::SetAttr( const SfxItemSet& rSet, SwFmt& rFmt )
1155 {
1156     if (GetIDocumentUndoRedo().DoesUndo())
1157     {
1158         SwUndoFmtAttrHelper aTmp( rFmt );
1159         rFmt.SetFmtAttr( rSet );
1160         if ( aTmp.GetUndo() )
1161         {
1162             GetIDocumentUndoRedo().AppendUndo( aTmp.ReleaseUndo() );
1163         }
1164         else
1165         {
1166             GetIDocumentUndoRedo().ClearRedo();
1167         }
1168     }
1169     else
1170     {
1171         rFmt.SetFmtAttr( rSet );
1172     }
1173 	SetModified();
1174 }
1175 
1176 // --> OD 2008-02-12 #newlistlevelattrs#
ResetAttrAtFormat(const sal_uInt16 nWhichId,SwFmt & rChangedFormat)1177 void SwDoc::ResetAttrAtFormat( const sal_uInt16 nWhichId,
1178                                SwFmt& rChangedFormat )
1179 {
1180     SwUndo *const pUndo = (GetIDocumentUndoRedo().DoesUndo())
1181         ?   new SwUndoFmtResetAttr( rChangedFormat, nWhichId )
1182         :   0;
1183 
1184     const sal_Bool bAttrReset = rChangedFormat.ResetFmtAttr( nWhichId );
1185 
1186     if ( bAttrReset )
1187     {
1188         if ( pUndo )
1189         {
1190             GetIDocumentUndoRedo().AppendUndo( pUndo );
1191         }
1192 
1193         SetModified();
1194     }
1195     else if ( pUndo )
1196         delete pUndo;
1197 }
1198 // <--
1199 
lcl_SetNewDefTabStops(SwTwips nOldWidth,SwTwips nNewWidth,SvxTabStopItem & rChgTabStop)1200 int lcl_SetNewDefTabStops( SwTwips nOldWidth, SwTwips nNewWidth,
1201 								SvxTabStopItem& rChgTabStop )
1202 {
1203 	// dann aender bei allen TabStop die default's auf den neuen Wert
1204 	// !!! Achtung: hier wird immer auf dem PoolAttribut gearbeitet,
1205 	// 				damit nicht in allen Sets die gleiche Berechnung
1206 	//				auf dem gleichen TabStop (gepoolt!) vorgenommen
1207 	//				wird. Als Modify wird ein FmtChg verschickt.
1208 
1209 	sal_uInt16 nOldCnt = rChgTabStop.Count();
1210 	if( !nOldCnt || nOldWidth == nNewWidth )
1211 		return sal_False;
1212 
1213 	// suche den Anfang der Defaults
1214 	SvxTabStop* pTabs = ((SvxTabStop*)rChgTabStop.GetStart())
1215 						+ (nOldCnt-1);
1216 	sal_uInt16 n;
1217 
1218 	for( n = nOldCnt; n ; --n, --pTabs )
1219 		if( SVX_TAB_ADJUST_DEFAULT != pTabs->GetAdjustment() )
1220 			break;
1221 	++n;
1222 	if( n < nOldCnt )	// die DefTabStops loeschen
1223 		rChgTabStop.Remove( n, nOldCnt - n );
1224 	return sal_True;
1225 }
1226 
1227 // Setze das Attribut als neues default Attribut in diesem Dokument.
1228 // Ist Undo aktiv, wird das alte in die Undo-History aufgenommen
SetDefault(const SfxPoolItem & rAttr)1229 void SwDoc::SetDefault( const SfxPoolItem& rAttr )
1230 {
1231 	SfxItemSet aSet( GetAttrPool(), rAttr.Which(), rAttr.Which() );
1232 	aSet.Put( rAttr );
1233 	SetDefault( aSet );
1234 }
1235 
SetDefault(const SfxItemSet & rSet)1236 void SwDoc::SetDefault( const SfxItemSet& rSet )
1237 {
1238 	if( !rSet.Count() )
1239 		return;
1240 
1241 	SwModify aCallMod( 0 );
1242 	SwAttrSet aOld( GetAttrPool(), rSet.GetRanges() ),
1243 			aNew( GetAttrPool(), rSet.GetRanges() );
1244 	SfxItemIter aIter( rSet );
1245 	sal_uInt16 nWhich;
1246 	const SfxPoolItem* pItem = aIter.GetCurItem();
1247 	SfxItemPool* pSdrPool = GetAttrPool().GetSecondaryPool();
1248 	while( sal_True )
1249 	{
1250 		sal_Bool bCheckSdrDflt = sal_False;
1251 		nWhich = pItem->Which();
1252 		aOld.Put( GetAttrPool().GetDefaultItem( nWhich ) );
1253 		GetAttrPool().SetPoolDefaultItem( *pItem );
1254 		aNew.Put( GetAttrPool().GetDefaultItem( nWhich ) );
1255 
1256         if (isCHRATR(nWhich) || isTXTATR(nWhich))
1257         {
1258 			aCallMod.Add( pDfltTxtFmtColl );
1259 			aCallMod.Add( pDfltCharFmt );
1260 			bCheckSdrDflt = 0 != pSdrPool;
1261         }
1262         else if ( isPARATR(nWhich) ||
1263                   // --> OD 2008-02-25 #refactorlists#
1264                   isPARATR_LIST(nWhich) )
1265                   // <--
1266         {
1267 			aCallMod.Add( pDfltTxtFmtColl );
1268 			bCheckSdrDflt = 0 != pSdrPool;
1269         }
1270         else if (isGRFATR(nWhich))
1271         {
1272             aCallMod.Add( pDfltGrfFmtColl );
1273         }
1274         else if (isFRMATR(nWhich))
1275         {
1276 			aCallMod.Add( pDfltGrfFmtColl );
1277 			aCallMod.Add( pDfltTxtFmtColl );
1278 			aCallMod.Add( pDfltFrmFmt );
1279         }
1280         else if (isBOXATR(nWhich))
1281         {
1282             aCallMod.Add( pDfltFrmFmt );
1283         }
1284 
1285 		// copy also the defaults
1286 		if( bCheckSdrDflt )
1287 		{
1288 			sal_uInt16 nEdtWhich, nSlotId;
1289 			if( 0 != (nSlotId = GetAttrPool().GetSlotId( nWhich ) ) &&
1290 				nSlotId != nWhich &&
1291 				0 != (nEdtWhich = pSdrPool->GetWhich( nSlotId )) &&
1292 				nSlotId != nEdtWhich )
1293 			{
1294 				SfxPoolItem* pCpy = pItem->Clone();
1295 				pCpy->SetWhich( nEdtWhich );
1296 				pSdrPool->SetPoolDefaultItem( *pCpy );
1297 				delete pCpy;
1298 			}
1299 		}
1300 
1301 		if( aIter.IsAtEnd() )
1302 			break;
1303 		pItem = aIter.NextItem();
1304 	}
1305 
1306 	if( aNew.Count() && aCallMod.GetDepends() )
1307     {
1308         if (GetIDocumentUndoRedo().DoesUndo())
1309         {
1310             GetIDocumentUndoRedo().AppendUndo( new SwUndoDefaultAttr( aOld ) );
1311         }
1312 
1313 		const SfxPoolItem* pTmpItem;
1314 		if( ( SFX_ITEM_SET ==
1315                 aNew.GetItemState( RES_PARATR_TABSTOP, sal_False, &pTmpItem ) ) &&
1316 			((SvxTabStopItem*)pTmpItem)->Count() )
1317 		{
1318 			// TabStop-Aenderungen behandeln wir erstmal anders:
1319 			// dann aender bei allen TabStop die dafault's auf den neuen Wert
1320 			// !!! Achtung: hier wird immer auf dem PoolAttribut gearbeitet,
1321 			// 				damit nicht in allen Sets die gleiche Berechnung
1322 			//				auf dem gleichen TabStop (gepoolt!) vorgenommen
1323 			//				wird. Als Modify wird ein FmtChg verschickt.
1324 			SwTwips nNewWidth = (*(SvxTabStopItem*)pTmpItem)[ 0 ].GetTabPos(),
1325 					nOldWidth = ((SvxTabStopItem&)aOld.Get(RES_PARATR_TABSTOP))[ 0 ].GetTabPos();
1326 
1327 			int bChg = sal_False;
1328 			sal_uInt32 nMaxItems = GetAttrPool().GetItemCount2( RES_PARATR_TABSTOP );
1329 			for( sal_uInt32 n = 0; n < nMaxItems; ++n )
1330 				if( 0 != (pTmpItem = GetAttrPool().GetItem2( RES_PARATR_TABSTOP, n ) ))
1331 					bChg |= lcl_SetNewDefTabStops( nOldWidth, nNewWidth,
1332 												*(SvxTabStopItem*)pTmpItem );
1333 
1334 			aNew.ClearItem( RES_PARATR_TABSTOP );
1335 			aOld.ClearItem( RES_PARATR_TABSTOP );
1336 			if( bChg )
1337 			{
1338 				SwFmtChg aChgFmt( pDfltCharFmt );
1339 				// dann sage mal den Frames bescheid
1340 				aCallMod.ModifyNotification( &aChgFmt, &aChgFmt );
1341 			}
1342 		}
1343 	}
1344 
1345 	if( aNew.Count() && aCallMod.GetDepends() )
1346 	{
1347 		SwAttrSetChg aChgOld( aOld, aOld );
1348 		SwAttrSetChg aChgNew( aNew, aNew );
1349 		aCallMod.ModifyNotification( &aChgOld, &aChgNew );		// alle veraenderten werden verschickt
1350 	}
1351 
1352 	// und die default-Formate wieder beim Object austragen
1353 	SwClient* pDep;
1354 	while( 0 != ( pDep = (SwClient*)aCallMod.GetDepends()) )
1355 		aCallMod.Remove( pDep );
1356 
1357 	SetModified();
1358 }
1359 
1360 	// Erfrage das Default Attribut in diesem Dokument.
GetDefault(sal_uInt16 nFmtHint) const1361 const SfxPoolItem& SwDoc::GetDefault( sal_uInt16 nFmtHint ) const
1362 {
1363 	return GetAttrPool().GetDefaultItem( nFmtHint );
1364 }
1365 
1366 /*
1367  * Loeschen der Formate
1368  */
DelCharFmt(sal_uInt16 nFmt,sal_Bool bBroadcast)1369 void SwDoc::DelCharFmt(sal_uInt16 nFmt, sal_Bool bBroadcast)
1370 {
1371     SwCharFmt * pDel = (*pCharFmtTbl)[nFmt];
1372 
1373     if (bBroadcast)
1374         BroadcastStyleOperation(pDel->GetName(), SFX_STYLE_FAMILY_CHAR,
1375                                 SFX_STYLESHEET_ERASED);
1376 
1377     if (GetIDocumentUndoRedo().DoesUndo())
1378     {
1379         SwUndo * pUndo =
1380             new SwUndoCharFmtDelete(pDel, this);
1381 
1382         GetIDocumentUndoRedo().AppendUndo(pUndo);
1383     }
1384 
1385 	pCharFmtTbl->DeleteAndDestroy(nFmt);
1386 
1387 	SetModified();
1388 }
1389 
DelCharFmt(SwCharFmt * pFmt,sal_Bool bBroadcast)1390 void SwDoc::DelCharFmt( SwCharFmt *pFmt, sal_Bool bBroadcast )
1391 {
1392 	sal_uInt16 nFmt = pCharFmtTbl->GetPos( pFmt );
1393 	ASSERT( USHRT_MAX != nFmt, "Fmt not found," );
1394 
1395 	DelCharFmt( nFmt, bBroadcast );
1396 }
1397 
DelFrmFmt(SwFrmFmt * pFmt,sal_Bool bBroadcast)1398 void SwDoc::DelFrmFmt( SwFrmFmt *pFmt, sal_Bool bBroadcast )
1399 {
1400 	if( pFmt->ISA( SwTableBoxFmt ) || pFmt->ISA( SwTableLineFmt ))
1401 	{
1402 		ASSERT( !this, "Format steht nicht mehr im DocArray, "
1403 					   "kann per delete geloescht werden" );
1404 		delete pFmt;
1405 	}
1406 	else
1407 	{
1408 
1409 		//Das Format muss in einem der beiden Arrays stehen, in welchem
1410 		//werden wir schon merken.
1411 		sal_uInt16 nPos;
1412 		if ( USHRT_MAX != ( nPos = pFrmFmtTbl->GetPos( pFmt )) )
1413         {
1414             if (bBroadcast)
1415                 BroadcastStyleOperation(pFmt->GetName(),
1416                                         SFX_STYLE_FAMILY_FRAME,
1417                                         SFX_STYLESHEET_ERASED);
1418 
1419             if (GetIDocumentUndoRedo().DoesUndo())
1420             {
1421                 SwUndo * pUndo = new SwUndoFrmFmtDelete(pFmt, this);
1422 
1423                 GetIDocumentUndoRedo().AppendUndo(pUndo);
1424             }
1425 
1426 			pFrmFmtTbl->DeleteAndDestroy( nPos );
1427         }
1428 		else
1429 		{
1430 			nPos = GetSpzFrmFmts()->GetPos( pFmt );
1431 			ASSERT( nPos != USHRT_MAX, "FrmFmt not found." );
1432 			if( USHRT_MAX != nPos )
1433 				GetSpzFrmFmts()->DeleteAndDestroy( nPos );
1434 		}
1435 	}
1436 }
1437 
DelTblFrmFmt(SwTableFmt * pFmt)1438 void SwDoc::DelTblFrmFmt( SwTableFmt *pFmt )
1439 {
1440 	sal_uInt16 nPos = pTblFrmFmtTbl->GetPos( pFmt );
1441 	ASSERT( USHRT_MAX != nPos, "Fmt not found," );
1442 	pTblFrmFmtTbl->DeleteAndDestroy( nPos );
1443 }
1444 
1445 /*
1446  * Erzeugen der Formate
1447  */
MakeFlyFrmFmt(const String & rFmtName,SwFrmFmt * pDerivedFrom)1448 SwFlyFrmFmt *SwDoc::MakeFlyFrmFmt( const String &rFmtName,
1449 									SwFrmFmt *pDerivedFrom )
1450 {
1451 	SwFlyFrmFmt *pFmt = new SwFlyFrmFmt( GetAttrPool(), rFmtName, pDerivedFrom );
1452 	GetSpzFrmFmts()->Insert(pFmt, GetSpzFrmFmts()->Count());
1453 	SetModified();
1454 	return pFmt;
1455 }
1456 
MakeDrawFrmFmt(const String & rFmtName,SwFrmFmt * pDerivedFrom)1457 SwDrawFrmFmt *SwDoc::MakeDrawFrmFmt( const String &rFmtName,
1458 									 SwFrmFmt *pDerivedFrom )
1459 {
1460 	SwDrawFrmFmt *pFmt = new SwDrawFrmFmt( GetAttrPool(), rFmtName, pDerivedFrom);
1461 	GetSpzFrmFmts()->Insert(pFmt,GetSpzFrmFmts()->Count());
1462 	SetModified();
1463 	return pFmt;
1464 }
1465 
1466 
GetTblFrmFmtCount(sal_Bool bUsed) const1467 sal_uInt16 SwDoc::GetTblFrmFmtCount(sal_Bool bUsed) const
1468 {
1469 	sal_uInt16 nCount = pTblFrmFmtTbl->Count();
1470 	if(bUsed)
1471 	{
1472         SwAutoFmtGetDocNode aGetHt( &GetNodes() );
1473 		for ( sal_uInt16 i = nCount; i; )
1474 		{
1475 			if((*pTblFrmFmtTbl)[--i]->GetInfo( aGetHt ))
1476 
1477 				--nCount;
1478 		}
1479 	}
1480 
1481 	return nCount;
1482 }
1483 
1484 
GetTblFrmFmt(sal_uInt16 nFmt,sal_Bool bUsed) const1485 SwFrmFmt& SwDoc::GetTblFrmFmt(sal_uInt16 nFmt, sal_Bool bUsed ) const
1486 {
1487 	sal_uInt16 nRemoved = 0;
1488 	if(bUsed)
1489 	{
1490         SwAutoFmtGetDocNode aGetHt( &GetNodes() );
1491 		for ( sal_uInt16 i = 0; i <= nFmt; i++ )
1492 		{
1493 			while ( (*pTblFrmFmtTbl)[ i + nRemoved]->GetInfo( aGetHt ))
1494 			{
1495 				nRemoved++;
1496 			}
1497 		}
1498 	}
1499 	return *((*pTblFrmFmtTbl)[nRemoved + nFmt]);
1500 }
1501 
MakeTblFrmFmt(const String & rFmtName,SwFrmFmt * pDerivedFrom)1502 SwTableFmt* SwDoc::MakeTblFrmFmt( const String &rFmtName,
1503 									SwFrmFmt *pDerivedFrom )
1504 {
1505 	SwTableFmt* pFmt = new SwTableFmt( GetAttrPool(), rFmtName, pDerivedFrom );
1506 	pTblFrmFmtTbl->Insert( pFmt, pTblFrmFmtTbl->Count() );
1507 	SetModified();
1508 
1509 	return pFmt;
1510 }
1511 
MakeFrmFmt(const String & rFmtName,SwFrmFmt * pDerivedFrom,sal_Bool bBroadcast,sal_Bool bAuto)1512 SwFrmFmt *SwDoc::MakeFrmFmt(const String &rFmtName,
1513 							SwFrmFmt *pDerivedFrom,
1514                             sal_Bool bBroadcast, sal_Bool bAuto)
1515 {
1516 
1517 	SwFrmFmt *pFmt = new SwFrmFmt( GetAttrPool(), rFmtName, pDerivedFrom );
1518 
1519     pFmt->SetAuto(bAuto);
1520 	pFrmFmtTbl->Insert( pFmt, pFrmFmtTbl->Count());
1521 	SetModified();
1522 
1523     if (bBroadcast)
1524     {
1525         BroadcastStyleOperation(rFmtName, SFX_STYLE_FAMILY_PARA,
1526                                 SFX_STYLESHEET_CREATED);
1527 
1528         if (GetIDocumentUndoRedo().DoesUndo())
1529         {
1530             SwUndo * pUndo = new SwUndoFrmFmtCreate(pFmt, pDerivedFrom, this);
1531 
1532             GetIDocumentUndoRedo().AppendUndo(pUndo);
1533         }
1534     }
1535 
1536 	return pFmt;
1537 }
1538 
_MakeFrmFmt(const String & rFmtName,SwFmt * pDerivedFrom,sal_Bool bBroadcast,sal_Bool bAuto)1539 SwFmt *SwDoc::_MakeFrmFmt(const String &rFmtName,
1540 							SwFmt *pDerivedFrom,
1541                             sal_Bool bBroadcast, sal_Bool bAuto)
1542 {
1543     SwFrmFmt *pFrmFmt = dynamic_cast<SwFrmFmt*>(pDerivedFrom);
1544     pFrmFmt = MakeFrmFmt( rFmtName, pFrmFmt, bBroadcast, bAuto );
1545     return dynamic_cast<SwFmt*>(pFrmFmt);
1546 }
1547 
1548 
1549 // --> OD 2005-01-13 #i40550# - add parameter <bAuto> - not relevant
MakeCharFmt(const String & rFmtName,SwCharFmt * pDerivedFrom,sal_Bool bBroadcast,sal_Bool)1550 SwCharFmt *SwDoc::MakeCharFmt( const String &rFmtName,
1551                                SwCharFmt *pDerivedFrom,
1552                                sal_Bool bBroadcast,
1553                                sal_Bool )
1554 // <--
1555 {
1556 	SwCharFmt *pFmt = new SwCharFmt( GetAttrPool(), rFmtName, pDerivedFrom );
1557     pCharFmtTbl->Insert( pFmt, pCharFmtTbl->Count() );
1558     pFmt->SetAuto( sal_False );
1559     SetModified();
1560 
1561     if (GetIDocumentUndoRedo().DoesUndo())
1562     {
1563         SwUndo * pUndo = new SwUndoCharFmtCreate(pFmt, pDerivedFrom, this);
1564 
1565         GetIDocumentUndoRedo().AppendUndo(pUndo);
1566     }
1567 
1568     if (bBroadcast)
1569     {
1570         BroadcastStyleOperation(rFmtName, SFX_STYLE_FAMILY_CHAR,
1571                                 SFX_STYLESHEET_CREATED);
1572     }
1573 
1574 	return pFmt;
1575 }
1576 
_MakeCharFmt(const String & rFmtName,SwFmt * pDerivedFrom,sal_Bool bBroadcast,sal_Bool bAuto)1577 SwFmt *SwDoc::_MakeCharFmt(const String &rFmtName,
1578 							SwFmt *pDerivedFrom,
1579                             sal_Bool bBroadcast, sal_Bool bAuto)
1580 {
1581     SwCharFmt *pCharFmt = dynamic_cast<SwCharFmt*>(pDerivedFrom);
1582     pCharFmt = MakeCharFmt( rFmtName, pCharFmt, bBroadcast, bAuto );
1583     return dynamic_cast<SwFmt*>(pCharFmt);
1584 }
1585 
1586 
1587 /*
1588  * Erzeugen der FormatCollections
1589  */
1590 // TXT
1591 // --> OD 2005-01-13 #i40550# - add parameter <bAuto> - not relevant
MakeTxtFmtColl(const String & rFmtName,SwTxtFmtColl * pDerivedFrom,sal_Bool bBroadcast,sal_Bool)1592 SwTxtFmtColl* SwDoc::MakeTxtFmtColl( const String &rFmtName,
1593 									 SwTxtFmtColl *pDerivedFrom,
1594                                      sal_Bool bBroadcast,
1595                                      sal_Bool )
1596 // <--
1597 {
1598 	SwTxtFmtColl *pFmtColl = new SwTxtFmtColl( GetAttrPool(), rFmtName,
1599 												pDerivedFrom );
1600 	pTxtFmtCollTbl->Insert(pFmtColl, pTxtFmtCollTbl->Count());
1601 	pFmtColl->SetAuto( sal_False );
1602 	SetModified();
1603 
1604     if (GetIDocumentUndoRedo().DoesUndo())
1605     {
1606         SwUndo * pUndo = new SwUndoTxtFmtCollCreate(pFmtColl, pDerivedFrom,
1607                                                     this);
1608         GetIDocumentUndoRedo().AppendUndo(pUndo);
1609     }
1610 
1611     if (bBroadcast)
1612         BroadcastStyleOperation(rFmtName, SFX_STYLE_FAMILY_PARA,
1613                                 SFX_STYLESHEET_CREATED);
1614 
1615 	return pFmtColl;
1616 }
1617 
_MakeTxtFmtColl(const String & rFmtName,SwFmt * pDerivedFrom,sal_Bool bBroadcast,sal_Bool bAuto)1618 SwFmt *SwDoc::_MakeTxtFmtColl(const String &rFmtName,
1619 							SwFmt *pDerivedFrom,
1620                             sal_Bool bBroadcast, sal_Bool bAuto)
1621 {
1622     SwTxtFmtColl *pTxtFmtColl = dynamic_cast<SwTxtFmtColl*>(pDerivedFrom);
1623     pTxtFmtColl = MakeTxtFmtColl( rFmtName, pTxtFmtColl, bBroadcast, bAuto );
1624     return dynamic_cast<SwFmt*>(pTxtFmtColl);
1625 }
1626 
1627 
1628 //FEATURE::CONDCOLL
MakeCondTxtFmtColl(const String & rFmtName,SwTxtFmtColl * pDerivedFrom,sal_Bool bBroadcast)1629 SwConditionTxtFmtColl* SwDoc::MakeCondTxtFmtColl( const String &rFmtName,
1630                                                   SwTxtFmtColl *pDerivedFrom,
1631                                                   sal_Bool bBroadcast)
1632 {
1633 	SwConditionTxtFmtColl*pFmtColl = new SwConditionTxtFmtColl( GetAttrPool(),
1634 													rFmtName, pDerivedFrom );
1635 	pTxtFmtCollTbl->Insert(pFmtColl, pTxtFmtCollTbl->Count());
1636 	pFmtColl->SetAuto( sal_False );
1637 	SetModified();
1638 
1639     if (bBroadcast)
1640         BroadcastStyleOperation(rFmtName, SFX_STYLE_FAMILY_PARA,
1641                                 SFX_STYLESHEET_CREATED);
1642 
1643 	return pFmtColl;
1644 }
1645 //FEATURE::CONDCOLL
1646 
1647 // GRF
1648 
MakeGrfFmtColl(const String & rFmtName,SwGrfFmtColl * pDerivedFrom)1649 SwGrfFmtColl* SwDoc::MakeGrfFmtColl( const String &rFmtName,
1650 									 SwGrfFmtColl *pDerivedFrom )
1651 {
1652 	SwGrfFmtColl *pFmtColl = new SwGrfFmtColl( GetAttrPool(), rFmtName,
1653 												pDerivedFrom );
1654 	pGrfFmtCollTbl->Insert( pFmtColl, pGrfFmtCollTbl->Count() );
1655 	pFmtColl->SetAuto( sal_False );
1656 	SetModified();
1657 	return pFmtColl;
1658 }
1659 
DelTxtFmtColl(sal_uInt16 nFmtColl,sal_Bool bBroadcast)1660 void SwDoc::DelTxtFmtColl(sal_uInt16 nFmtColl, sal_Bool bBroadcast)
1661 {
1662 	ASSERT( nFmtColl, "Remove fuer Coll 0." );
1663 
1664 	// Wer hat die zu loeschende als Next
1665 	SwTxtFmtColl *pDel = (*pTxtFmtCollTbl)[nFmtColl];
1666 	if( pDfltTxtFmtColl == pDel )
1667 		return;		// default nie loeschen !!
1668 
1669     if (bBroadcast)
1670         BroadcastStyleOperation(pDel->GetName(), SFX_STYLE_FAMILY_PARA,
1671                                 SFX_STYLESHEET_ERASED);
1672 
1673     if (GetIDocumentUndoRedo().DoesUndo())
1674     {
1675         SwUndoTxtFmtCollDelete * pUndo =
1676             new SwUndoTxtFmtCollDelete(pDel, this);
1677 
1678         GetIDocumentUndoRedo().AppendUndo(pUndo);
1679     }
1680 
1681 	// Die FmtColl austragen
1682 	pTxtFmtCollTbl->Remove(nFmtColl);
1683 	// Next korrigieren
1684 	pTxtFmtCollTbl->ForEach( 1, pTxtFmtCollTbl->Count(),
1685 							&SetTxtFmtCollNext, pDel );
1686 	delete pDel;
1687 	SetModified();
1688 }
1689 
DelTxtFmtColl(SwTxtFmtColl * pColl,sal_Bool bBroadcast)1690 void SwDoc::DelTxtFmtColl( SwTxtFmtColl *pColl, sal_Bool bBroadcast )
1691 {
1692 	sal_uInt16 nFmt = pTxtFmtCollTbl->GetPos( pColl );
1693 	ASSERT( USHRT_MAX != nFmt, "Collection not found," );
1694 	DelTxtFmtColl( nFmt, bBroadcast );
1695 }
1696 
lcl_SetTxtFmtColl(const SwNodePtr & rpNode,void * pArgs)1697 sal_Bool lcl_SetTxtFmtColl( const SwNodePtr& rpNode, void* pArgs )
1698 {
1699     SwCntntNode* pCNd = (SwCntntNode*) rpNode->GetTxtNode();
1700     if ( pCNd )
1701     {
1702         ParaRstFmt* pPara = (ParaRstFmt*) pArgs;
1703 
1704         SwTxtFmtColl* pFmt = static_cast< SwTxtFmtColl* >( pPara->pFmtColl );
1705         if ( pPara->bReset )
1706         {
1707 
1708             lcl_RstAttr( pCNd, pPara );
1709 
1710             // check, if paragraph style has changed
1711             if ( pPara->bResetListAttrs &&
1712                  pFmt != pCNd->GetFmtColl() &&
1713                  pFmt->GetItemState( RES_PARATR_NUMRULE ) == SFX_ITEM_SET )
1714             {
1715                 // --> OD 2009-09-07 #b6876367#
1716                 // Check, if the list style of the paragraph will change.
1717                 bool bChangeOfListStyleAtParagraph( true );
1718                 SwTxtNode* pTNd( dynamic_cast<SwTxtNode*>(pCNd) );
1719                 ASSERT( pTNd,
1720                         "<lcl_SetTxtFmtColl(..)> - text node expected -> crash" );
1721                 {
1722                     SwNumRule* pNumRuleAtParagraph( pTNd->GetNumRule() );
1723                     if ( pNumRuleAtParagraph )
1724                     {
1725                         const SwNumRuleItem& rNumRuleItemAtParagraphStyle =
1726                                                             pFmt->GetNumRule();
1727                         if ( rNumRuleItemAtParagraphStyle.GetValue() ==
1728                                                 pNumRuleAtParagraph->GetName() )
1729                         {
1730                             bChangeOfListStyleAtParagraph = false;
1731                         }
1732                     }
1733                 }
1734 
1735                 if ( bChangeOfListStyleAtParagraph )
1736                 {
1737                     std::auto_ptr< SwRegHistory > pRegH;
1738                     if ( pPara->pHistory )
1739                     {
1740                         pRegH.reset( new SwRegHistory( pTNd, *pTNd, pPara->pHistory ) );
1741                     }
1742 
1743                     pCNd->ResetAttr( RES_PARATR_NUMRULE );
1744 
1745                     // reset all list attributes
1746                     pCNd->ResetAttr( RES_PARATR_LIST_LEVEL );
1747                     pCNd->ResetAttr( RES_PARATR_LIST_ISRESTART );
1748                     pCNd->ResetAttr( RES_PARATR_LIST_RESTARTVALUE );
1749                     pCNd->ResetAttr( RES_PARATR_LIST_ISCOUNTED );
1750                     pCNd->ResetAttr( RES_PARATR_LIST_ID );
1751                 }
1752             }
1753         }
1754 
1755         // erst in die History aufnehmen, damit ggfs. alte Daten
1756 		// gesichert werden koennen
1757 		if( pPara->pHistory )
1758 			pPara->pHistory->Add( pCNd->GetFmtColl(), pCNd->GetIndex(),
1759 									ND_TEXTNODE );
1760 
1761         pCNd->ChgFmtColl( pFmt );
1762 
1763 		pPara->nWhich++;
1764 	}
1765 	return sal_True;
1766 }
1767 
1768 
SetTxtFmtColl(const SwPaM & rRg,SwTxtFmtColl * pFmt,const bool bReset,const bool bResetListAttrs)1769 sal_Bool SwDoc::SetTxtFmtColl(
1770     const SwPaM &rRg,
1771     SwTxtFmtColl *pFmt,
1772     const bool bReset,
1773     const bool bResetListAttrs )
1774 {
1775 	SwDataChanged aTmp( rRg, 0 );
1776 	const SwPosition *pStt = rRg.Start(), *pEnd = rRg.End();
1777 	SwHistory* pHst = 0;
1778 	sal_Bool bRet = sal_True;
1779 
1780     if (GetIDocumentUndoRedo().DoesUndo())
1781     {
1782         SwUndoFmtColl* pUndo = new SwUndoFmtColl( rRg, pFmt,
1783                                                   bReset,
1784                                                   bResetListAttrs );
1785         pHst = pUndo->GetHistory();
1786         GetIDocumentUndoRedo().AppendUndo(pUndo);
1787     }
1788 
1789     ParaRstFmt aPara( pStt, pEnd, pHst );
1790     aPara.pFmtColl = pFmt;
1791     aPara.bReset = bReset;
1792     aPara.bResetListAttrs = bResetListAttrs;
1793 
1794     GetNodes().ForEach( pStt->nNode.GetIndex(), pEnd->nNode.GetIndex()+1,
1795                         lcl_SetTxtFmtColl, &aPara );
1796     if ( !aPara.nWhich )
1797         bRet = sal_False;           // keinen gueltigen Node gefunden
1798 
1799     if ( bRet )
1800     {
1801         SetModified();
1802     }
1803 
1804     return bRet;
1805 }
1806 
1807 
1808 // ---- Kopiere die Formate in sich selbst (SwDoc) ----------------------
1809 
CopyFmt(const SwFmt & rFmt,const SvPtrarr & rFmtArr,FNCopyFmt fnCopyFmt,const SwFmt & rDfltFmt)1810 SwFmt* SwDoc::CopyFmt( const SwFmt& rFmt,
1811 						const SvPtrarr& rFmtArr,
1812 						FNCopyFmt fnCopyFmt, const SwFmt& rDfltFmt )
1813 {
1814 	//  kein-Autoformat || default Format || Collection-Format
1815 	// dann suche danach.
1816 	if( !rFmt.IsAuto() || !rFmt.GetRegisteredIn() )
1817 		for( sal_uInt16 n = 0; n < rFmtArr.Count(); n++ )
1818 		{
1819 			// ist die Vorlage schon im Doc vorhanden ??
1820 			if( ((SwFmt*)rFmtArr[n])->GetName().Equals( rFmt.GetName() ))
1821 				return (SwFmt*)rFmtArr[n];
1822 		}
1823 
1824 	// suche erstmal nach dem "Parent"
1825 	SwFmt* pParent = (SwFmt*)&rDfltFmt;
1826 	if( rFmt.DerivedFrom() && pParent != rFmt.DerivedFrom() )
1827 		pParent = CopyFmt( *rFmt.DerivedFrom(), rFmtArr,
1828 								fnCopyFmt, rDfltFmt );
1829 
1830 	// erzeuge das Format und kopiere die Attribute
1831     // --> OD 2005-01-13 #i40550#
1832     SwFmt* pNewFmt = (this->*fnCopyFmt)( rFmt.GetName(), pParent, sal_False, sal_True );
1833     // <--
1834     pNewFmt->SetAuto( rFmt.IsAuto() );
1835 	pNewFmt->CopyAttrs( rFmt, sal_True );			// kopiere Attribute
1836 
1837 	pNewFmt->SetPoolFmtId( rFmt.GetPoolFmtId() );
1838 	pNewFmt->SetPoolHelpId( rFmt.GetPoolHelpId() );
1839 
1840 	// HelpFile-Id immer auf dflt setzen !!
1841 	pNewFmt->SetPoolHlpFileId( UCHAR_MAX );
1842 
1843 	return pNewFmt;
1844 }
1845 
1846 
1847 // ---- kopiere das Frame-Format --------
CopyFrmFmt(const SwFrmFmt & rFmt)1848 SwFrmFmt* SwDoc::CopyFrmFmt( const SwFrmFmt& rFmt )
1849 {
1850 
1851     return (SwFrmFmt*)CopyFmt( rFmt, *GetFrmFmts(), &SwDoc::_MakeFrmFmt,
1852                                 *GetDfltFrmFmt() );
1853 }
1854 
1855 // ---- kopiere das Char-Format --------
CopyCharFmt(const SwCharFmt & rFmt)1856 SwCharFmt* SwDoc::CopyCharFmt( const SwCharFmt& rFmt )
1857 {
1858 	return (SwCharFmt*)CopyFmt( rFmt, *GetCharFmts(),
1859 								&SwDoc::_MakeCharFmt,
1860 								*GetDfltCharFmt() );
1861 }
1862 
1863 
1864 // --- Kopiere TextNodes ----
1865 
CopyTxtColl(const SwTxtFmtColl & rColl)1866 SwTxtFmtColl* SwDoc::CopyTxtColl( const SwTxtFmtColl& rColl )
1867 {
1868 	SwTxtFmtColl* pNewColl = FindTxtFmtCollByName( rColl.GetName() );
1869 	if( pNewColl )
1870 		return pNewColl;
1871 
1872 	// suche erstmal nach dem "Parent"
1873 	SwTxtFmtColl* pParent = pDfltTxtFmtColl;
1874 	if( pParent != rColl.DerivedFrom() )
1875 		pParent = CopyTxtColl( *(SwTxtFmtColl*)rColl.DerivedFrom() );
1876 
1877 
1878 //FEATURE::CONDCOLL
1879 	if( RES_CONDTXTFMTCOLL == rColl.Which() )
1880 	{
1881 		pNewColl = new SwConditionTxtFmtColl( GetAttrPool(), rColl.GetName(),
1882 												pParent);
1883 		pTxtFmtCollTbl->Insert( pNewColl, pTxtFmtCollTbl->Count() );
1884 		pNewColl->SetAuto( sal_False );
1885 		SetModified();
1886 
1887 		// Kopiere noch die Bedingungen
1888 		((SwConditionTxtFmtColl*)pNewColl)->SetConditions(
1889 							((SwConditionTxtFmtColl&)rColl).GetCondColls() );
1890 	}
1891 	else
1892 //FEATURE::CONDCOLL
1893 		pNewColl = MakeTxtFmtColl( rColl.GetName(), pParent );
1894 
1895 	// kopiere jetzt noch die Auto-Formate oder kopiere die Attribute
1896 	pNewColl->CopyAttrs( rColl, sal_True );
1897 
1898     // setze noch den Outline-Level
1899     if ( rColl.IsAssignedToListLevelOfOutlineStyle() )
1900         pNewColl->AssignToListLevelOfOutlineStyle( rColl.GetAssignedOutlineStyleLevel() );
1901 
1902     pNewColl->SetPoolFmtId( rColl.GetPoolFmtId() );
1903     pNewColl->SetPoolHelpId( rColl.GetPoolHelpId() );
1904 
1905 	// HelpFile-Id immer auf dflt setzen !!
1906 	pNewColl->SetPoolHlpFileId( UCHAR_MAX );
1907 
1908 	if( &rColl.GetNextTxtFmtColl() != &rColl )
1909 		pNewColl->SetNextTxtFmtColl( *CopyTxtColl( rColl.GetNextTxtFmtColl() ));
1910 
1911 	// ggfs. die NumRule erzeugen
1912 	if( this != rColl.GetDoc() )
1913 	{
1914 		const SfxPoolItem* pItem;
1915 		if( SFX_ITEM_SET == pNewColl->GetItemState( RES_PARATR_NUMRULE,
1916 			sal_False, &pItem ))
1917 		{
1918 			const SwNumRule* pRule;
1919 			const String& rName = ((SwNumRuleItem*)pItem)->GetValue();
1920 			if( rName.Len() &&
1921 				0 != ( pRule = rColl.GetDoc()->FindNumRulePtr( rName )) &&
1922 				!pRule->IsAutoRule() )
1923 			{
1924 				SwNumRule* pDestRule = FindNumRulePtr( rName );
1925 				if( pDestRule )
1926 					pDestRule->SetInvalidRule( sal_True );
1927 				else
1928 					MakeNumRule( rName, pRule );
1929 			}
1930 		}
1931 	}
1932 	return pNewColl;
1933 }
1934 
1935 // --- Kopiere GrafikNodes ----
1936 
CopyGrfColl(const SwGrfFmtColl & rColl)1937 SwGrfFmtColl* SwDoc::CopyGrfColl( const SwGrfFmtColl& rColl )
1938 {
1939 	SwGrfFmtColl* pNewColl = FindGrfFmtCollByName( rColl.GetName() );
1940 	if( pNewColl )
1941 		return pNewColl;
1942 
1943 	// suche erstmal nach dem "Parent"
1944 	SwGrfFmtColl* pParent = pDfltGrfFmtColl;
1945 	if( pParent != rColl.DerivedFrom() )
1946 		pParent = CopyGrfColl( *(SwGrfFmtColl*)rColl.DerivedFrom() );
1947 
1948 	// falls nicht, so kopiere sie
1949 	pNewColl = MakeGrfFmtColl( rColl.GetName(), pParent );
1950 
1951 	// noch die Attribute kopieren
1952 	pNewColl->CopyAttrs( rColl );
1953 
1954 	pNewColl->SetPoolFmtId( rColl.GetPoolFmtId() );
1955 	pNewColl->SetPoolHelpId( rColl.GetPoolHelpId() );
1956 
1957 	// HelpFile-Id immer auf dflt setzen !!
1958 	pNewColl->SetPoolHlpFileId( UCHAR_MAX );
1959 
1960 	return pNewColl;
1961 }
1962 
lcl_FindPageDesc(const SwPageDescs & rArr,const String & rName)1963 SwPageDesc* lcl_FindPageDesc( const SwPageDescs& rArr, const String& rName )
1964 {
1965 	for( sal_uInt16 n = rArr.Count(); n; )
1966 	{
1967 		SwPageDesc* pDesc = rArr[ --n ];
1968 		if( pDesc->GetName() == rName )
1969 			return pDesc;
1970 	}
1971 	return 0;
1972 }
1973 
CopyFmtArr(const SvPtrarr & rSourceArr,SvPtrarr & rDestArr,FNCopyFmt fnCopyFmt,SwFmt & rDfltFmt)1974 void SwDoc::CopyFmtArr( const SvPtrarr& rSourceArr,
1975 						SvPtrarr& rDestArr,
1976 						FNCopyFmt fnCopyFmt,
1977 						SwFmt& rDfltFmt )
1978 {
1979 	sal_uInt16 nSrc;
1980 	SwFmt* pSrc, *pDest;
1981 
1982 	// 1. Schritt alle Formate anlegen (das 0. ueberspringen - Default!)
1983 	for( nSrc = rSourceArr.Count(); nSrc > 1; )
1984 	{
1985 		pSrc = (SwFmt*)rSourceArr[ --nSrc ];
1986 		if( pSrc->IsDefault() || pSrc->IsAuto() )
1987 			continue;
1988 
1989 		if( 0 == FindFmtByName( rDestArr, pSrc->GetName() ) )
1990 		{
1991 			if( RES_CONDTXTFMTCOLL == pSrc->Which() )
1992                 MakeCondTxtFmtColl( pSrc->GetName(), (SwTxtFmtColl*)&rDfltFmt );
1993 			else
1994                 // --> OD 2005-01-13 #i40550#
1995                 (this->*fnCopyFmt)( pSrc->GetName(), &rDfltFmt, sal_False, sal_True );
1996                 // <--
1997 		}
1998 	}
1999 
2000 	// 2. Schritt alle Attribute kopieren, richtige Parents setzen
2001 	for( nSrc = rSourceArr.Count(); nSrc > 1; )
2002 	{
2003 		pSrc = (SwFmt*)rSourceArr[ --nSrc ];
2004 		if( pSrc->IsDefault() || pSrc->IsAuto() )
2005 			continue;
2006 
2007 		pDest = FindFmtByName( rDestArr, pSrc->GetName() );
2008 		pDest->SetAuto( sal_False );
2009 		pDest->DelDiffs( *pSrc );
2010 
2011         // #i94285#: existing <SwFmtPageDesc> instance, before copying attributes
2012         const SfxPoolItem* pItem;
2013         if( &GetAttrPool() != pSrc->GetAttrSet().GetPool() &&
2014             SFX_ITEM_SET == pSrc->GetAttrSet().GetItemState(
2015             RES_PAGEDESC, sal_False, &pItem ) &&
2016             ((SwFmtPageDesc*)pItem)->GetPageDesc() )
2017         {
2018             SwFmtPageDesc aPageDesc( *(SwFmtPageDesc*)pItem );
2019             const String& rNm = aPageDesc.GetPageDesc()->GetName();
2020             SwPageDesc* pPageDesc = ::lcl_FindPageDesc( aPageDescs, rNm );
2021             if( !pPageDesc )
2022             {
2023                 pPageDesc = aPageDescs[ MakePageDesc( rNm ) ];
2024             }
2025             aPageDesc.RegisterToPageDesc( *pPageDesc );
2026             SwAttrSet aTmpAttrSet( pSrc->GetAttrSet() );
2027             aTmpAttrSet.Put( aPageDesc );
2028             pDest->SetFmtAttr( aTmpAttrSet );
2029         }
2030         else
2031         {
2032             pDest->SetFmtAttr( pSrc->GetAttrSet() );
2033         }
2034 
2035 		pDest->SetPoolFmtId( pSrc->GetPoolFmtId() );
2036 		pDest->SetPoolHelpId( pSrc->GetPoolHelpId() );
2037 
2038 		// HelpFile-Id immer auf dflt setzen !!
2039 		pDest->SetPoolHlpFileId( UCHAR_MAX );
2040 
2041 		if( pSrc->DerivedFrom() )
2042 			pDest->SetDerivedFrom( FindFmtByName( rDestArr,
2043 										pSrc->DerivedFrom()->GetName() ) );
2044 		if( RES_TXTFMTCOLL == pSrc->Which() ||
2045 			RES_CONDTXTFMTCOLL == pSrc->Which() )
2046 		{
2047 			SwTxtFmtColl* pSrcColl = (SwTxtFmtColl*)pSrc,
2048 						* pDstColl = (SwTxtFmtColl*)pDest;
2049 			if( &pSrcColl->GetNextTxtFmtColl() != pSrcColl )
2050 				pDstColl->SetNextTxtFmtColl( *(SwTxtFmtColl*)FindFmtByName(
2051 					rDestArr, pSrcColl->GetNextTxtFmtColl().GetName() ) );
2052 
2053 			// setze noch den Outline-Level
2054 			if(pSrcColl->IsAssignedToListLevelOfOutlineStyle())
2055 				pDstColl->AssignToListLevelOfOutlineStyle(pSrcColl->GetAssignedOutlineStyleLevel());
2056 
2057 //FEATURE::CONDCOLL
2058 			if( RES_CONDTXTFMTCOLL == pSrc->Which() )
2059 				// Kopiere noch die Bedingungen
2060 				// aber erst die alten loeschen!
2061 				((SwConditionTxtFmtColl*)pDstColl)->SetConditions(
2062 							((SwConditionTxtFmtColl*)pSrc)->GetCondColls() );
2063 //FEATURE::CONDCOLL
2064 		}
2065 	}
2066 }
2067 
CopyPageDescHeaderFooterImpl(bool bCpyHeader,const SwFrmFmt & rSrcFmt,SwFrmFmt & rDestFmt)2068 void SwDoc::CopyPageDescHeaderFooterImpl( bool bCpyHeader,
2069 								const SwFrmFmt& rSrcFmt, SwFrmFmt& rDestFmt )
2070 {
2071 	// jetzt noch Header-/Footer-Attribute richtig behandeln
2072 	// Contenten Nodes Dokumentuebergreifend kopieren!
2073 	sal_uInt16 nAttr = static_cast<sal_uInt16>( bCpyHeader ? RES_HEADER : RES_FOOTER );
2074 	const SfxPoolItem* pItem;
2075 	if( SFX_ITEM_SET != rSrcFmt.GetAttrSet().GetItemState( nAttr, sal_False, &pItem ))
2076 		return ;
2077 
2078 	// Im Header steht noch der Verweis auf das Format aus dem
2079 	// anderen Document!!
2080 	SfxPoolItem* pNewItem = pItem->Clone();
2081 
2082 	SwFrmFmt* pOldFmt;
2083 	if( bCpyHeader )
2084 		 pOldFmt = ((SwFmtHeader*)pNewItem)->GetHeaderFmt();
2085 	else
2086 		 pOldFmt = ((SwFmtFooter*)pNewItem)->GetFooterFmt();
2087 
2088 	if( pOldFmt )
2089 	{
2090 		SwFrmFmt* pNewFmt = new SwFrmFmt( GetAttrPool(), "CpyDesc",
2091 											GetDfltFrmFmt() );
2092 		pNewFmt->CopyAttrs( *pOldFmt, sal_True );
2093 
2094 		if( SFX_ITEM_SET == pNewFmt->GetAttrSet().GetItemState(
2095 			RES_CNTNT, sal_False, &pItem ))
2096 		{
2097 			SwFmtCntnt* pCntnt = (SwFmtCntnt*)pItem;
2098 			if( pCntnt->GetCntntIdx() )
2099 			{
2100 				SwNodeIndex aTmpIdx( GetNodes().GetEndOfAutotext() );
2101 				const SwNodes& rSrcNds = rSrcFmt.GetDoc()->GetNodes();
2102 				SwStartNode* pSttNd = GetNodes().MakeEmptySection( aTmpIdx,
2103 												bCpyHeader
2104 													? SwHeaderStartNode
2105 													: SwFooterStartNode );
2106 				const SwNode& rCSttNd = pCntnt->GetCntntIdx()->GetNode();
2107 				SwNodeRange aRg( rCSttNd, 0, *rCSttNd.EndOfSectionNode() );
2108 				aTmpIdx = *pSttNd->EndOfSectionNode();
2109 				rSrcNds._Copy( aRg, aTmpIdx );
2110 				aTmpIdx = *pSttNd;
2111                 rSrcFmt.GetDoc()->CopyFlyInFlyImpl( aRg, 0, aTmpIdx );
2112                 pNewFmt->SetFmtAttr( SwFmtCntnt( pSttNd ));
2113 			}
2114 			else
2115                 pNewFmt->ResetFmtAttr( RES_CNTNT );
2116 		}
2117 		if( bCpyHeader )
2118             ((SwFmtHeader*)pNewItem)->RegisterToFormat(*pNewFmt);
2119 		else
2120             ((SwFmtFooter*)pNewItem)->RegisterToFormat(*pNewFmt);
2121         rDestFmt.SetFmtAttr( *pNewItem );
2122 	}
2123 	delete pNewItem;
2124 }
2125 
CopyPageDesc(const SwPageDesc & rSrcDesc,SwPageDesc & rDstDesc,sal_Bool bCopyPoolIds)2126 void SwDoc::CopyPageDesc( const SwPageDesc& rSrcDesc, SwPageDesc& rDstDesc,
2127 							sal_Bool bCopyPoolIds )
2128 {
2129 	sal_Bool bNotifyLayout = sal_False;
2130 	SwRootFrm* pTmpRoot = GetCurrentLayout();//swmod 080219
2131 
2132 	rDstDesc.SetLandscape( rSrcDesc.GetLandscape() );
2133 	rDstDesc.SetNumType( rSrcDesc.GetNumType() );
2134 	if( rDstDesc.ReadUseOn() != rSrcDesc.ReadUseOn() )
2135 	{
2136 		rDstDesc.WriteUseOn( rSrcDesc.ReadUseOn() );
2137 		bNotifyLayout = sal_True;
2138 	}
2139 
2140 	if( bCopyPoolIds )
2141 	{
2142 		rDstDesc.SetPoolFmtId( rSrcDesc.GetPoolFmtId() );
2143 		rDstDesc.SetPoolHelpId( rSrcDesc.GetPoolHelpId() );
2144 		// HelpFile-Id immer auf dflt setzen !!
2145 		rDstDesc.SetPoolHlpFileId( UCHAR_MAX );
2146 	}
2147 
2148 	if( rSrcDesc.GetFollow() != &rSrcDesc )
2149 	{
2150 		SwPageDesc* pFollow = ::lcl_FindPageDesc( aPageDescs,
2151 									rSrcDesc.GetFollow()->GetName() );
2152 		if( !pFollow )
2153 		{
2154 			// dann mal kopieren
2155 			sal_uInt16 nPos = MakePageDesc( rSrcDesc.GetFollow()->GetName() );
2156 			pFollow = aPageDescs[ nPos ];
2157 			CopyPageDesc( *rSrcDesc.GetFollow(), *pFollow );
2158 		}
2159 		rDstDesc.SetFollow( pFollow );
2160 		bNotifyLayout = sal_True;
2161 	}
2162 
2163 	// die Header/Footer-Attribute werden gesondert kopiert, die Content-
2164 	// Sections muessen vollstaendig mitgenommen werden!
2165 	{
2166 		SfxItemSet aAttrSet( rSrcDesc.GetMaster().GetAttrSet() );
2167 		aAttrSet.ClearItem( RES_HEADER );
2168 		aAttrSet.ClearItem( RES_FOOTER );
2169 
2170 		rDstDesc.GetMaster().DelDiffs( aAttrSet );
2171         rDstDesc.GetMaster().SetFmtAttr( aAttrSet );
2172 
2173 		aAttrSet.ClearItem();
2174 		aAttrSet.Put( rSrcDesc.GetLeft().GetAttrSet() );
2175 		aAttrSet.ClearItem( RES_HEADER );
2176 		aAttrSet.ClearItem( RES_FOOTER );
2177 
2178 		rDstDesc.GetLeft().DelDiffs( aAttrSet );
2179         rDstDesc.GetLeft().SetFmtAttr( aAttrSet );
2180 	}
2181 
2182 	CopyHeader( rSrcDesc.GetMaster(), rDstDesc.GetMaster() );
2183 	CopyFooter( rSrcDesc.GetMaster(), rDstDesc.GetMaster() );
2184 	if( !rDstDesc.IsHeaderShared() )
2185 		CopyHeader( rSrcDesc.GetLeft(), rDstDesc.GetLeft() );
2186 	else
2187         rDstDesc.GetLeft().SetFmtAttr( rDstDesc.GetMaster().GetHeader() );
2188 
2189 	if( !rDstDesc.IsFooterShared() )
2190 		CopyFooter( rSrcDesc.GetLeft(), rDstDesc.GetLeft() );
2191 	else
2192         rDstDesc.GetLeft().SetFmtAttr( rDstDesc.GetMaster().GetFooter() );
2193 
2194 	if( bNotifyLayout && pTmpRoot )
2195 	{
2196 		std::set<SwRootFrm*> aAllLayouts = GetAllLayouts();//swmod 080225
2197 		std::for_each( aAllLayouts.begin(), aAllLayouts.end(),std::mem_fun(&SwRootFrm::AllCheckPageDescs));//swmod 080226
2198 	}
2199 
2200 	//Wenn sich FussnotenInfo veraendert, so werden die Seiten
2201 	//angetriggert.
2202 	if( !(rDstDesc.GetFtnInfo() == rSrcDesc.GetFtnInfo()) )
2203 	{
2204 		rDstDesc.SetFtnInfo( rSrcDesc.GetFtnInfo() );
2205 		SwMsgPoolItem  aInfo( RES_PAGEDESC_FTNINFO );
2206 		{
2207             rDstDesc.GetMaster().ModifyBroadcast( &aInfo, 0, TYPE(SwFrm) );
2208 		}
2209 		{
2210             rDstDesc.GetLeft().ModifyBroadcast( &aInfo, 0, TYPE(SwFrm) );
2211 		}
2212 	}
2213 }
2214 
ReplaceStyles(SwDoc & rSource)2215 void SwDoc::ReplaceStyles( SwDoc& rSource )
2216 {
2217     ::sw::UndoGuard const undoGuard(GetIDocumentUndoRedo());
2218 
2219 	CopyFmtArr( *rSource.pCharFmtTbl, *pCharFmtTbl,
2220 				&SwDoc::_MakeCharFmt, *pDfltCharFmt );
2221 	CopyFmtArr( *rSource.pFrmFmtTbl, *pFrmFmtTbl,
2222 				&SwDoc::_MakeFrmFmt, *pDfltFrmFmt );
2223 	CopyFmtArr( *rSource.pTxtFmtCollTbl, *pTxtFmtCollTbl,
2224 				&SwDoc::_MakeTxtFmtColl, *pDfltTxtFmtColl );
2225 
2226 	// und jetzt noch die Seiten-Vorlagen
2227 	sal_uInt16 nCnt = rSource.aPageDescs.Count();
2228 	if( nCnt )
2229 	{
2230 		// ein anderes Doc -> Numberformatter muessen gemergt werden
2231 		SwTblNumFmtMerge aTNFM( rSource, *this );
2232 
2233 		// 1. Schritt alle Formate anlegen (das 0. ueberspringen - Default!)
2234 		while( nCnt )
2235 		{
2236 			SwPageDesc *pSrc = rSource.aPageDescs[ --nCnt ];
2237 			if( 0 == ::lcl_FindPageDesc( aPageDescs, pSrc->GetName() ) )
2238 				MakePageDesc( pSrc->GetName() );
2239 		}
2240 
2241 		// 2. Schritt alle Attribute kopieren, richtige Parents setzen
2242 		for( nCnt = rSource.aPageDescs.Count(); nCnt; )
2243 		{
2244 			SwPageDesc *pSrc = rSource.aPageDescs[ --nCnt ];
2245 			CopyPageDesc( *pSrc, *::lcl_FindPageDesc( aPageDescs, pSrc->GetName() ));
2246 		}
2247 	}
2248 
2249 	//JP 08.04.99: und dann sind da noch die Numerierungs-Vorlagen
2250 	nCnt = rSource.GetNumRuleTbl().Count();
2251 	if( nCnt )
2252 	{
2253 		const SwNumRuleTbl& rArr = rSource.GetNumRuleTbl();
2254 		for( sal_uInt16 n = 0; n < nCnt; ++n )
2255 		{
2256 			const SwNumRule& rR = *rArr[ n ];
2257 			if( !rR.IsAutoRule() )
2258 			{
2259 				SwNumRule* pNew = FindNumRulePtr( rR.GetName());
2260 				if( pNew )
2261 					pNew->CopyNumRule( this, rR );
2262 				else
2263 					MakeNumRule( rR.GetName(), &rR );
2264 			}
2265 		}
2266 	}
2267 
2268     if (undoGuard.UndoWasEnabled())
2269     {
2270         // nodes array was modified!
2271         GetIDocumentUndoRedo().DelAllUndoObj();
2272     }
2273 
2274 	SetModified();
2275 }
2276 
FindFmtByName(const SvPtrarr & rFmtArr,const String & rName) const2277 SwFmt* SwDoc::FindFmtByName( const SvPtrarr& rFmtArr,
2278 									const String& rName ) const
2279 {
2280 	SwFmt* pFnd = 0;
2281 	for( sal_uInt16 n = 0; n < rFmtArr.Count(); n++ )
2282 	{
2283 		// ist die Vorlage schon im Doc vorhanden ??
2284 		if( ((SwFmt*)rFmtArr[n])->GetName() == rName )
2285 		{
2286 			pFnd = (SwFmt*)rFmtArr[n];
2287 			break;
2288 		}
2289 	}
2290 	return pFnd;
2291 }
2292 
MoveLeftMargin(const SwPaM & rPam,sal_Bool bRight,sal_Bool bModulus)2293 void SwDoc::MoveLeftMargin( const SwPaM& rPam, sal_Bool bRight, sal_Bool bModulus )
2294 {
2295 	SwHistory* pHistory = 0;
2296     if (GetIDocumentUndoRedo().DoesUndo())
2297     {
2298 		SwUndoMoveLeftMargin* pUndo = new SwUndoMoveLeftMargin( rPam, bRight,
2299 																bModulus );
2300         pHistory = &pUndo->GetHistory();
2301         GetIDocumentUndoRedo().AppendUndo( pUndo );
2302     }
2303 
2304 	const SvxTabStopItem& rTabItem = (SvxTabStopItem&)GetDefault( RES_PARATR_TABSTOP );
2305 	sal_uInt16 nDefDist = rTabItem.Count() ?
2306         static_cast<sal_uInt16>(rTabItem[0].GetTabPos()) : 1134;
2307 	const SwPosition &rStt = *rPam.Start(), &rEnd = *rPam.End();
2308 	SwNodeIndex aIdx( rStt.nNode );
2309 	while( aIdx <= rEnd.nNode )
2310 	{
2311 		SwTxtNode* pTNd = aIdx.GetNode().GetTxtNode();
2312 		if( pTNd )
2313 		{
2314             SvxLRSpaceItem aLS( (SvxLRSpaceItem&)pTNd->SwCntntNode::GetAttr( RES_LR_SPACE ) );
2315 
2316             // --> FME 2008-09-16 #i93873# See also lcl_MergeListLevelIndentAsLRSpaceItem in thints.cxx
2317             if ( pTNd->AreListLevelIndentsApplicable() )
2318             {
2319                 const SwNumRule* pRule = pTNd->GetNumRule();
2320                 if ( pRule )
2321                 {
2322                     const int nListLevel = pTNd->GetActualListLevel();
2323                     if ( nListLevel >= 0 )
2324                     {
2325                         const SwNumFmt& rFmt = pRule->Get(static_cast<sal_uInt16>(nListLevel));
2326                         if ( rFmt.GetPositionAndSpaceMode() == SvxNumberFormat::LABEL_ALIGNMENT )
2327                         {
2328                             aLS.SetTxtLeft( rFmt.GetIndentAt() );
2329                             aLS.SetTxtFirstLineOfst( static_cast<short>(rFmt.GetFirstLineIndent()) );
2330                         }
2331                     }
2332                 }
2333             }
2334 
2335 			long nNext = aLS.GetTxtLeft();
2336 			if( bModulus )
2337 				nNext = ( nNext / nDefDist ) * nDefDist;
2338 
2339 			if( bRight )
2340 				nNext += nDefDist;
2341 			else
2342 				nNext -= nDefDist;
2343 
2344             aLS.SetTxtLeft( nNext );
2345 
2346 			SwRegHistory aRegH( pTNd, *pTNd, pHistory );
2347             pTNd->SetAttr( aLS );
2348 		}
2349 		aIdx++;
2350 	}
2351 	SetModified();
2352 }
2353 
DontExpandFmt(const SwPosition & rPos,sal_Bool bFlag)2354 sal_Bool SwDoc::DontExpandFmt( const SwPosition& rPos, sal_Bool bFlag )
2355 {
2356 	sal_Bool bRet = sal_False;
2357 	SwTxtNode* pTxtNd = rPos.nNode.GetNode().GetTxtNode();
2358 	if( pTxtNd )
2359 	{
2360 		bRet = pTxtNd->DontExpandFmt( rPos.nContent, bFlag );
2361         if( bRet && GetIDocumentUndoRedo().DoesUndo() )
2362         {
2363             GetIDocumentUndoRedo().AppendUndo( new SwUndoDontExpandFmt(rPos) );
2364         }
2365     }
2366 	return bRet;
2367 }
2368 
MakeTableBoxFmt()2369 SwTableBoxFmt* SwDoc::MakeTableBoxFmt()
2370 {
2371 	SwTableBoxFmt* pFmt = new SwTableBoxFmt( GetAttrPool(), aEmptyStr,
2372 												pDfltFrmFmt );
2373 	SetModified();
2374 	return pFmt;
2375 }
2376 
MakeTableLineFmt()2377 SwTableLineFmt* SwDoc::MakeTableLineFmt()
2378 {
2379 	SwTableLineFmt* pFmt = new SwTableLineFmt( GetAttrPool(), aEmptyStr,
2380 												pDfltFrmFmt );
2381 	SetModified();
2382 	return pFmt;
2383 }
2384 
_CreateNumberFormatter()2385 void SwDoc::_CreateNumberFormatter()
2386 {
2387 	RTL_LOGFILE_CONTEXT_AUTHOR( aLog, "SW", "JP93722",  "SwDoc::_CreateNumberFormatter" );
2388 
2389 	ASSERT( !pNumberFormatter, "ist doch schon vorhanden" );
2390 
2391 
2392 	LanguageType eLang = LANGUAGE_SYSTEM; //System::GetLanguage();
2393 /*				((const SvxLanguageItem&)GetAttrPool().
2394 					GetDefaultItem( RES_CHRATR_LANGUAGE )).GetLanguage();
2395 */
2396 	Reference< XMultiServiceFactory > xMSF = ::comphelper::getProcessServiceFactory();
2397 	pNumberFormatter = new SvNumberFormatter( xMSF, eLang );
2398 	pNumberFormatter->SetEvalDateFormat( NF_EVALDATEFORMAT_FORMAT_INTL );
2399 	pNumberFormatter->SetYear2000(static_cast<sal_uInt16>(::utl::MiscCfg().GetYear2000()));
2400 
2401 }
2402 
SwTblNumFmtMerge(const SwDoc & rSrc,SwDoc & rDest)2403 SwTblNumFmtMerge::SwTblNumFmtMerge( const SwDoc& rSrc, SwDoc& rDest )
2404 	: pNFmt( 0 )
2405 {
2406 	// ein anderes Doc -> Numberformatter muessen gemergt werden
2407 	SvNumberFormatter* pN;
2408 	if( &rSrc != &rDest && 0 != ( pN = ((SwDoc&)rSrc).GetNumberFormatter( sal_False ) ))
2409 		( pNFmt = rDest.GetNumberFormatter( sal_True ))->MergeFormatter( *pN );
2410 
2411 	if( &rSrc != &rDest )
2412 		((SwGetRefFieldType*)rSrc.GetSysFldType( RES_GETREFFLD ))->
2413 			MergeWithOtherDoc( rDest );
2414 }
2415 
~SwTblNumFmtMerge()2416 SwTblNumFmtMerge::~SwTblNumFmtMerge()
2417 {
2418 	if( pNFmt )
2419 		pNFmt->ClearMergeTable();
2420 }
2421 
2422 
SetTxtFmtCollByAutoFmt(const SwPosition & rPos,sal_uInt16 nPoolId,const SfxItemSet * pSet)2423 void SwDoc::SetTxtFmtCollByAutoFmt( const SwPosition& rPos, sal_uInt16 nPoolId,
2424 									const SfxItemSet* pSet )
2425 {
2426 	SwPaM aPam( rPos );
2427 	SwTxtNode* pTNd = rPos.nNode.GetNode().GetTxtNode();
2428 
2429 	if( mbIsAutoFmtRedline && pTNd )
2430 	{
2431 		// dann das Redline Object anlegen
2432 		const SwTxtFmtColl& rColl = *pTNd->GetTxtColl();
2433 		SwRedline* pRedl = new SwRedline( nsRedlineType_t::REDLINE_FMTCOLL, aPam );
2434 		pRedl->SetMark();
2435 
2436 		// interressant sind nur die Items, die vom Set NICHT wieder
2437 		// in den Node gesetzt werden. Also muss man die Differenz nehmen
2438 		SwRedlineExtraData_FmtColl aExtraData( rColl.GetName(),
2439 												rColl.GetPoolFmtId() );
2440         if( pSet && pTNd->HasSwAttrSet() )
2441 		{
2442 			SfxItemSet aTmp( *pTNd->GetpSwAttrSet() );
2443 			aTmp.Differentiate( *pSet );
2444 			// das Adjust Item behalten wir extra
2445 			const SfxPoolItem* pItem;
2446 			if( SFX_ITEM_SET == pTNd->GetpSwAttrSet()->GetItemState(
2447 					RES_PARATR_ADJUST, sal_False, &pItem ))
2448 				aTmp.Put( *pItem );
2449 			aExtraData.SetItemSet( aTmp );
2450 		}
2451 		pRedl->SetExtraData( &aExtraData );
2452 
2453 // !!!!!!!!! Undo fehlt noch !!!!!!!!!!!!!!!!!!
2454 		AppendRedline( pRedl, true );
2455 	}
2456 
2457 	SetTxtFmtColl( aPam, GetTxtCollFromPool( nPoolId ) );
2458 
2459 	if( pSet && pTNd && pSet->Count() )
2460 	{
2461 		aPam.SetMark();
2462 		aPam.GetMark()->nContent.Assign( pTNd, pTNd->GetTxt().Len() );
2463         InsertItemSet( aPam, *pSet, 0 );
2464     }
2465 }
2466 
SetFmtItemByAutoFmt(const SwPaM & rPam,const SfxItemSet & rSet)2467 void SwDoc::SetFmtItemByAutoFmt( const SwPaM& rPam, const SfxItemSet& rSet )
2468 {
2469 	SwTxtNode* pTNd = rPam.GetPoint()->nNode.GetNode().GetTxtNode();
2470 
2471 	RedlineMode_t eOld = GetRedlineMode();
2472 
2473 	if( mbIsAutoFmtRedline && pTNd )
2474 	{
2475 		// dann das Redline Object anlegen
2476 		SwRedline* pRedl = new SwRedline( nsRedlineType_t::REDLINE_FORMAT, rPam );
2477 		if( !pRedl->HasMark() )
2478 			pRedl->SetMark();
2479 
2480 		// interressant sind nur die Items, die vom Set NICHT wieder
2481 		// in den Node gesetzt werden. Also muss man die Differenz nehmen
2482 		SwRedlineExtraData_Format aExtraData( rSet );
2483 
2484 /*
2485         if( pSet && pTNd->HasSwAttrSet() )
2486 		{
2487 			SfxItemSet aTmp( *pTNd->GetpSwAttrSet() );
2488 			aTmp.Differentiate( *pSet );
2489 			// das Adjust Item behalten wir extra
2490 			const SfxPoolItem* pItem;
2491 			if( SFX_ITEM_SET == pTNd->GetpSwAttrSet()->GetItemState(
2492 					RES_PARATR_ADJUST, sal_False, &pItem ))
2493 				aTmp.Put( *pItem );
2494 			aExtraData.SetItemSet( aTmp );
2495 		}
2496 */
2497 		pRedl->SetExtraData( &aExtraData );
2498 
2499 // !!!!!!!!! Undo fehlt noch !!!!!!!!!!!!!!!!!!
2500 		AppendRedline( pRedl, true );
2501 
2502 		SetRedlineMode_intern( (RedlineMode_t)(eOld | nsRedlineMode_t::REDLINE_IGNORE));
2503 	}
2504 
2505     InsertItemSet( rPam, rSet, nsSetAttrMode::SETATTR_DONTEXPAND );
2506 	SetRedlineMode_intern( eOld );
2507 }
2508 
ChgFmt(SwFmt & rFmt,const SfxItemSet & rSet)2509 void SwDoc::ChgFmt(SwFmt & rFmt, const SfxItemSet & rSet)
2510 {
2511     if (GetIDocumentUndoRedo().DoesUndo())
2512     {
2513         // copying <rSet> to <aSet>
2514         SfxItemSet aSet(rSet);
2515         // remove from <aSet> all items, which are already set at the format
2516         aSet.Differentiate(rFmt.GetAttrSet());
2517         // <aSet> contains now all *new* items for the format
2518 
2519         // copying current format item set to <aOldSet>
2520         SfxItemSet aOldSet(rFmt.GetAttrSet());
2521         // insert new items into <aOldSet>
2522         aOldSet.Put(aSet);
2523         // invalidate all new items in <aOldSet> in order to clear these items,
2524         // if the undo action is triggered.
2525         {
2526             SfxItemIter aIter(aSet);
2527 
2528             const SfxPoolItem * pItem = aIter.FirstItem();
2529             while (pItem != NULL)
2530             {
2531                 aOldSet.InvalidateItem(pItem->Which());
2532 
2533                 pItem = aIter.NextItem();
2534             }
2535         }
2536 
2537         SwUndo * pUndo = new SwUndoFmtAttr(aOldSet, rFmt);
2538 
2539         GetIDocumentUndoRedo().AppendUndo(pUndo);
2540     }
2541 
2542     rFmt.SetFmtAttr(rSet);
2543 }
2544 
RenameFmt(SwFmt & rFmt,const String & sNewName,sal_Bool bBroadcast)2545 void SwDoc::RenameFmt(SwFmt & rFmt, const String & sNewName,
2546                       sal_Bool bBroadcast)
2547 {
2548     SfxStyleFamily eFamily = SFX_STYLE_FAMILY_ALL;
2549 
2550     if (GetIDocumentUndoRedo().DoesUndo())
2551     {
2552         SwUndo * pUndo = NULL;
2553 
2554         switch (rFmt.Which())
2555         {
2556         case RES_CHRFMT:
2557             pUndo = new SwUndoRenameCharFmt(rFmt.GetName(), sNewName, this);
2558             eFamily = SFX_STYLE_FAMILY_PARA;
2559             break;
2560         case RES_TXTFMTCOLL:
2561             pUndo = new SwUndoRenameFmtColl(rFmt.GetName(), sNewName, this);
2562             eFamily = SFX_STYLE_FAMILY_CHAR;
2563             break;
2564         case RES_FRMFMT:
2565             pUndo = new SwUndoRenameFrmFmt(rFmt.GetName(), sNewName, this);
2566             eFamily = SFX_STYLE_FAMILY_FRAME;
2567             break;
2568 
2569         default:
2570             break;
2571         }
2572 
2573         if (pUndo)
2574         {
2575             GetIDocumentUndoRedo().AppendUndo(pUndo);
2576         }
2577     }
2578 
2579     rFmt.SetName(sNewName);
2580 
2581     if (bBroadcast)
2582         BroadcastStyleOperation(sNewName, eFamily, SFX_STYLESHEET_MODIFIED);
2583 }
2584 
2585 // --> OD 2006-09-27 #i69627#
2586 namespace docfunc
2587 {
HasOutlineStyleToBeWrittenAsNormalListStyle(SwDoc & rDoc)2588     bool HasOutlineStyleToBeWrittenAsNormalListStyle( SwDoc& rDoc )
2589     {
2590         // If a parent paragraph style of one of the parargraph styles, which
2591         // are assigned to the list levels of the outline style, has a list style
2592         // set or inherits a list style from its parent style, the outline style
2593         // has to be written as a normal list style to the OpenDocument file
2594         // format or the OpenOffice.org file format.
2595         bool bRet( false );
2596 
2597         const SwTxtFmtColls* pTxtFmtColls( rDoc.GetTxtFmtColls() );
2598         if ( pTxtFmtColls )
2599         {
2600             const sal_uInt16 nCount = pTxtFmtColls->Count();
2601             for ( sal_uInt16 i = 0; i < nCount; ++i )
2602             {
2603                 SwTxtFmtColl* pTxtFmtColl = (*pTxtFmtColls)[i];
2604 
2605                 if ( pTxtFmtColl->IsDefault() ||
2606                    //  pTxtFmtColl->GetOutlineLevel() == NO_NUMBERING ) //#outline level,zhaojianwei
2607 					! pTxtFmtColl->IsAssignedToListLevelOfOutlineStyle() )	//<-end,zhaojianwei
2608                 {
2609                     continue;
2610                 }
2611 
2612                 const SwTxtFmtColl* pParentTxtFmtColl =
2613                    dynamic_cast<const SwTxtFmtColl*>( pTxtFmtColl->DerivedFrom());
2614                 if ( !pParentTxtFmtColl )
2615                     continue;
2616 
2617                 if ( SFX_ITEM_SET == pParentTxtFmtColl->GetItemState( RES_PARATR_NUMRULE ) )
2618                 {
2619                     // --> OD 2009-11-12 #i106218#
2620                     // consider that the outline style is set
2621                     const SwNumRuleItem& rDirectItem = pParentTxtFmtColl->GetNumRule();
2622                     if ( rDirectItem.GetValue() != rDoc.GetOutlineNumRule()->GetName() )
2623                     {
2624                         bRet = true;
2625                         break;
2626                     }
2627                     // <--
2628                 }
2629             }
2630 
2631         }
2632         return bRet;
2633     }
2634 }
2635 // <--
2636