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