LCOV - code coverage report
Current view: top level - sw/source/core/txtnode - ndtxt.cxx (source / functions) Hit Total Coverage
Test: commit c8344322a7af75b84dd3ca8f78b05543a976dfd5 Lines: 1600 2160 74.1 %
Date: 2015-06-13 12:38:46 Functions: 114 127 89.8 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : #include <hintids.hxx>
      21             : #include <hints.hxx>
      22             : 
      23             : #include <comphelper/string.hxx>
      24             : #include <editeng/fontitem.hxx>
      25             : #include <editeng/formatbreakitem.hxx>
      26             : #include <editeng/escapementitem.hxx>
      27             : #include <editeng/lrspitem.hxx>
      28             : #include <editeng/rsiditem.hxx>
      29             : #include <editeng/tstpitem.hxx>
      30             : #include <svl/urihelper.hxx>
      31             : #include <svl/ctloptions.hxx>
      32             : #include <swmodule.hxx>
      33             : #include <txtfld.hxx>
      34             : #include <txtinet.hxx>
      35             : #include <fmtinfmt.hxx>
      36             : #include <fmtpdsc.hxx>
      37             : #include <txtatr.hxx>
      38             : #include <fmtrfmrk.hxx>
      39             : #include <txttxmrk.hxx>
      40             : #include <fchrfmt.hxx>
      41             : #include <txtftn.hxx>
      42             : #include <fmtflcnt.hxx>
      43             : #include <fmtfld.hxx>
      44             : #include <frmatr.hxx>
      45             : #include <charatr.hxx>
      46             : #include <ftnidx.hxx>
      47             : #include <ftninfo.hxx>
      48             : #include <fmtftn.hxx>
      49             : #include <fmtmeta.hxx>
      50             : #include <charfmt.hxx>
      51             : #include <ndtxt.hxx>
      52             : #include <doc.hxx>
      53             : #include <IDocumentUndoRedo.hxx>
      54             : #include <IDocumentSettingAccess.hxx>
      55             : #include <IDocumentListsAccess.hxx>
      56             : #include <IDocumentRedlineAccess.hxx>
      57             : #include <IDocumentLayoutAccess.hxx>
      58             : #include <docary.hxx>
      59             : #include <pam.hxx>
      60             : #include <fldbas.hxx>
      61             : #include <paratr.hxx>
      62             : #include <txtfrm.hxx>
      63             : #include <ftnfrm.hxx>
      64             : #include <ftnboss.hxx>
      65             : #include <rootfrm.hxx>
      66             : #include <pagedesc.hxx>
      67             : #include <expfld.hxx>
      68             : #include <section.hxx>
      69             : #include <mvsave.hxx>
      70             : #include <swcache.hxx>
      71             : #include <SwGrammarMarkUp.hxx>
      72             : #include <dcontact.hxx>
      73             : #include <redline.hxx>
      74             : #include <doctxm.hxx>
      75             : #include <IMark.hxx>
      76             : #include <scriptinfo.hxx>
      77             : #include <istyleaccess.hxx>
      78             : #include <SwStyleNameMapper.hxx>
      79             : #include <numrule.hxx>
      80             : #include <swtable.hxx>
      81             : #include <docsh.hxx>
      82             : #include <SwNodeNum.hxx>
      83             : #include <svl/intitem.hxx>
      84             : #include <list.hxx>
      85             : #include <sortedobjs.hxx>
      86             : #include <calbck.hxx>
      87             : #include <attrhint.hxx>
      88             : #include <memory>
      89             : 
      90             : //UUUU
      91             : #include <svx/sdr/attribute/sdrallfillattributeshelper.hxx>
      92             : #include <svl/itemiter.hxx>
      93             : 
      94             : using namespace ::com::sun::star;
      95             : 
      96             : typedef std::vector<SwTextAttr*> SwpHts;
      97             : 
      98      318162 : TYPEINIT1( SwTextNode, SwContentNode )
      99             : 
     100             : // unfortunately everyone can change Hints without ensuring order or the linking between them
     101             : #ifdef DBG_UTIL
     102             : #define CHECK_SWPHINTS(pNd)  { if( pNd->GetpSwpHints() && \
     103             :                                    !pNd->GetDoc()->IsInReading() ) \
     104             :                                   pNd->GetpSwpHints()->Check(true); }
     105             : #else
     106             : #define CHECK_SWPHINTS(pNd)
     107             : #endif
     108             : 
     109       10795 : SwTextNode *SwNodes::MakeTextNode( const SwNodeIndex & rWhere,
     110             :                                  SwTextFormatColl *pColl,
     111             :                                  SwAttrSet* pAutoAttr )
     112             : {
     113             :     OSL_ENSURE( pColl, "Collection pointer is 0." );
     114             : 
     115       10795 :     SwTextNode *pNode = new SwTextNode( rWhere, pColl, pAutoAttr );
     116             : 
     117       10795 :     SwNodeIndex aIdx( *pNode );
     118             : 
     119             :     // #125329#
     120             :     // call method <UpdateOutlineNode(..)> only for the document nodes array
     121       10795 :     if ( IsDocNodes() )
     122       10795 :         UpdateOutlineNode(*pNode);
     123             : 
     124             :     // if there is no layout or it is in a hidden section, MakeFrms is not needed
     125             :     const SwSectionNode* pSectNd;
     126       21602 :     if( !GetDoc()->getIDocumentLayoutAccess().GetCurrentViewShell() ||
     127         648 :         ( 0 != (pSectNd = pNode->FindSectionNode()) &&
     128          30 :             pSectNd->GetSection().IsHiddenFlag() ))
     129       10189 :         return pNode;
     130             : 
     131        1212 :     SwNodeIndex aTmp( rWhere );
     132             :     do {
     133             :         // max. 2 loops:
     134             :         // 1. take the successor
     135             :         // 2. take the predecessor
     136             : 
     137        1056 :         SwNode * pNd = & aTmp.GetNode();
     138        1056 :         switch (pNd->GetNodeType())
     139             :         {
     140             :         case ND_TABLENODE:
     141           4 :             static_cast<SwTableNode*>(pNd)->MakeFrms( aIdx );
     142           4 :             return pNode;
     143             : 
     144             :         case ND_SECTIONNODE:
     145           4 :             if( static_cast<SwSectionNode*>(pNd)->GetSection().IsHidden() ||
     146           2 :                 static_cast<SwSectionNode*>(pNd)->IsContentHidden() )
     147             :             {
     148           0 :                 SwNodeIndex aTmpIdx( *pNode );
     149           0 :                 pNd = FindPrvNxtFrmNode( aTmpIdx, pNode );
     150           0 :                 if( !pNd )
     151           0 :                     return pNode;
     152           0 :                 aTmp = *pNd;
     153           0 :                 break;
     154             :             }
     155           2 :             static_cast<SwSectionNode*>(pNd)->MakeFrms( aIdx );
     156           2 :             return pNode;
     157             : 
     158             :         case ND_TEXTNODE:
     159             :         case ND_GRFNODE:
     160             :         case ND_OLENODE:
     161         229 :             static_cast<SwContentNode*>(pNd)->MakeFrms( *pNode );
     162         229 :             return pNode;
     163             : 
     164             :         case ND_ENDNODE:
     165         475 :             if( pNd->StartOfSectionNode()->IsSectionNode() &&
     166           0 :                 aTmp.GetIndex() < rWhere.GetIndex() )
     167             :             {
     168           0 :                 if( pNd->StartOfSectionNode()->GetSectionNode()->GetSection().IsHiddenFlag())
     169             :                 {
     170           0 :                     if( !GoPrevSection( &aTmp, true, false ) ||
     171           0 :                         aTmp.GetNode().FindTableNode() !=
     172           0 :                             pNode->FindTableNode() )
     173           0 :                         return pNode;       // schade, das wars
     174             :                 }
     175             :                 else
     176           0 :                     aTmp = *pNd->StartOfSectionNode();
     177           0 :                 break;
     178             :             }
     179         477 :             else if( pNd->StartOfSectionNode()->IsTableNode() &&
     180           2 :                     aTmp.GetIndex() < rWhere.GetIndex() )
     181             :             {
     182             :                 // after a table node
     183           0 :                 aTmp = *pNd->StartOfSectionNode();
     184           0 :                 break;
     185             :             }
     186             :             // no break !!!
     187             :         default:
     188         821 :             if( rWhere == aTmp )
     189         450 :                 aTmp -= 2;
     190             :             else
     191         371 :                 return pNode;
     192         450 :             break;
     193             :         }
     194       10795 :     } while( true );
     195             : }
     196             : 
     197       55858 : SwTextNode::SwTextNode( const SwNodeIndex &rWhere, SwTextFormatColl *pTextColl, const SfxItemSet* pAutoAttr )
     198             : :   SwContentNode( rWhere, ND_TEXTNODE, pTextColl ),
     199             :     m_pSwpHints( 0 ),
     200             :     mpNodeNum( 0 ),
     201             :     m_Text(),
     202             :     m_pParaIdleData_Impl(0),
     203             :     m_bContainsHiddenChars(false),
     204             :     m_bHiddenCharsHidePara(false),
     205             :     m_bRecalcHiddenCharFlags(false),
     206             :     m_bLastOutlineState( false ),
     207             :     m_bNotifiable( false ),
     208             :     mbEmptyListStyleSetDueToSetOutlineLevelAttr( false ),
     209             :     mbInSetOrResetAttr( false ),
     210             :     mpList( 0 ),
     211             :     m_pNumStringCache(),
     212             :     m_wXParagraph(),
     213       55858 :     maFillAttributes()
     214             : {
     215       55858 :     InitSwParaStatistics( true );
     216             : 
     217       55858 :     if( pAutoAttr )
     218        3055 :         SetAttr( *pAutoAttr );
     219             : 
     220       55858 :     if (!IsInList() && GetNumRule() && !GetListId().isEmpty())
     221             :     {
     222             :         // #i101516#
     223             :         // apply paragraph style's assigned outline style list level as
     224             :         // list level of the paragraph, if it has none set already.
     225         414 :         if ( !HasAttrListLevel() &&
     226         207 :              pTextColl && pTextColl->IsAssignedToListLevelOfOutlineStyle() )
     227             :         {
     228           0 :             SetAttrListLevel( pTextColl->GetAssignedOutlineStyleLevel() );
     229             :         }
     230         207 :         AddToList();
     231             :     }
     232       55858 :     GetNodes().UpdateOutlineNode(*this);
     233             : 
     234       55858 :     m_bNotifiable = true;
     235             : 
     236       55858 :     m_bContainsHiddenChars = m_bHiddenCharsHidePara = false;
     237       55858 :     m_bRecalcHiddenCharFlags = true;
     238       55858 : }
     239             : 
     240      165048 : SwTextNode::~SwTextNode()
     241             : {
     242             :     // delete only removes the pointer not the array elements!
     243       55016 :     if ( m_pSwpHints )
     244             :     {
     245             :         // do not delete attributes twice when those delte their content
     246       17954 :         SwpHints* pTmpHints = m_pSwpHints;
     247       17954 :         m_pSwpHints = 0;
     248             : 
     249       74969 :         for( size_t j = pTmpHints->Count(); j; )
     250             :         {
     251             :             // first remove the attribute from the array otherwise
     252             :             // if would delete itself
     253       39061 :             DestroyAttr( pTmpHints->GetTextHint( --j ) );
     254             :         }
     255             : 
     256       17954 :         delete pTmpHints;
     257             :     }
     258             : 
     259             :     // must be removed from outline nodes by now
     260             : #if OSL_DEBUG_LEVEL > 0
     261             :     sal_uInt16 foo;
     262             :     assert(!GetNodes().GetOutLineNds().Seek_Entry(this, &foo));
     263             : #endif
     264             : 
     265       55016 :     RemoveFromList();
     266             : 
     267       55016 :     InitSwParaStatistics( false );
     268             : 
     269       55016 :     if (HasWriterListeners())
     270             :     {
     271        3313 :         DelFrms_TextNodePart();
     272             :     }
     273      110032 : }
     274             : 
     275       36977 : void SwTextNode::FileLoadedInitHints()
     276             : {
     277       36977 :     if (m_pSwpHints)
     278             :     {
     279       14798 :         m_pSwpHints->MergePortions(*this);
     280             :     }
     281       36977 : }
     282             : 
     283       36977 : SwContentFrm *SwTextNode::MakeFrm( SwFrm* pSib )
     284             : {
     285             :     // fdo#52028: ODF file import does not result in MergePortions being called
     286             :     // for every attribute, since that would be inefficient.  So call it here.
     287       36977 :     FileLoadedInitHints();
     288       36977 :     SwContentFrm *pFrm = new SwTextFrm( this, pSib );
     289       36977 :     return pFrm;
     290             : }
     291             : 
     292      841636 : sal_Int32 SwTextNode::Len() const
     293             : {
     294      841636 :     return m_Text.getLength();
     295             : }
     296             : 
     297             : // After a split node, it's necessary to actualize the ref-pointer of the ftnfrms.
     298        1376 : static void lcl_ChangeFootnoteRef( SwTextNode &rNode )
     299             : {
     300        1376 :     SwpHints *pSwpHints = rNode.GetpSwpHints();
     301        1376 :     if( pSwpHints && rNode.GetDoc()->getIDocumentLayoutAccess().GetCurrentViewShell() )
     302             :     {
     303           2 :         SwContentFrm* pFrm = NULL;
     304             :         // OD 07.11.2002 #104840# - local variable to remember first footnote
     305             :         // of node <rNode> in order to invalidate position of its first content.
     306             :         // Thus, in its <MakeAll()> it will checked its position relative to its reference.
     307           2 :         SwFootnoteFrm* pFirstFootnoteOfNode = 0;
     308           6 :         for( size_t j = pSwpHints->Count(); j; )
     309             :         {
     310           2 :             SwTextAttr* pHt = pSwpHints->GetTextHint(--j);
     311           2 :             if (RES_TXTATR_FTN == pHt->Which())
     312             :             {
     313           0 :                 if( !pFrm )
     314             :                 {
     315           0 :                     pFrm = SwIterator<SwContentFrm,SwTextNode>(rNode).First();
     316           0 :                     if (!pFrm)
     317        1376 :                         return;
     318             :                 }
     319           0 :                 SwTextFootnote *pAttr = static_cast<SwTextFootnote*>(pHt);
     320             :                 OSL_ENSURE( pAttr->GetStartNode(), "FootnoteAtr ohne StartNode." );
     321           0 :                 SwNodeIndex aIdx( *pAttr->GetStartNode(), 1 );
     322           0 :                 SwContentNode *pNd = aIdx.GetNode().GetContentNode();
     323           0 :                 if ( !pNd )
     324             :                     pNd = pFrm->GetAttrSet()->GetDoc()->
     325           0 :                             GetNodes().GoNextSection( &aIdx, true, false );
     326           0 :                 if ( !pNd )
     327           0 :                     continue;
     328             : 
     329           0 :                 SwIterator<SwContentFrm,SwContentNode> aIter( *pNd );
     330           0 :                 SwContentFrm* pContent = aIter.First();
     331           0 :                 if( pContent )
     332             :                 {
     333             :                     OSL_ENSURE( pContent->getRootFrm() == pFrm->getRootFrm(),
     334             :                             "lcl_ChangeFootnoteRef: Layout double?" );
     335           0 :                     SwFootnoteFrm *pFootnote = pContent->FindFootnoteFrm();
     336           0 :                     if( pFootnote && pFootnote->GetAttr() == pAttr )
     337             :                     {
     338           0 :                         while( pFootnote->GetMaster() )
     339           0 :                             pFootnote = pFootnote->GetMaster();
     340             :                         // #104840# - remember footnote frame
     341           0 :                         pFirstFootnoteOfNode = pFootnote;
     342           0 :                         while ( pFootnote )
     343             :                         {
     344           0 :                             pFootnote->SetRef( pFrm );
     345           0 :                             pFootnote = pFootnote->GetFollow();
     346           0 :                             static_cast<SwTextFrm*>(pFrm)->SetFootnote( true );
     347             :                         }
     348             :                     }
     349             : #if OSL_DEBUG_LEVEL > 0
     350             :                     while( 0 != (pContent = aIter.Next()) )
     351             :                     {
     352             :                         SwFootnoteFrm *pDbgFootnote = pContent->FindFootnoteFrm();
     353             :                         OSL_ENSURE( !pDbgFootnote || pDbgFootnote->GetRef() == pFrm,
     354             :                                 "lcl_ChangeFootnoteRef: Who's that guy?" );
     355             :                     }
     356             : #endif
     357           0 :                 }
     358             :             }
     359             :         } // end of for-loop on <SwpHints>
     360             :         // #104840# - invalidate
     361           2 :         if ( pFirstFootnoteOfNode )
     362             :         {
     363           0 :             SwContentFrm* pContent = pFirstFootnoteOfNode->ContainsContent();
     364           0 :             if ( pContent )
     365             :             {
     366           0 :                 pContent->_InvalidatePos();
     367             :             }
     368             :         }
     369             :     }
     370             : }
     371             : 
     372        1376 : SwContentNode *SwTextNode::SplitContentNode( const SwPosition &rPos )
     373             : {
     374        1376 :     bool parentIsOutline = IsOutline();
     375             : 
     376             :     // create a node "in front" of me
     377        1376 :     const sal_Int32 nSplitPos = rPos.nContent.GetIndex();
     378        1376 :     const sal_Int32 nTextLen = m_Text.getLength();
     379             :     SwTextNode* const pNode =
     380        1376 :         _MakeNewTextNode( rPos.nNode, false, nSplitPos==nTextLen );
     381             : 
     382             :     // the first paragraph gets the XmlId,
     383             :     // _except_ if it is empty and the second is not empty
     384        1376 :     if (nSplitPos != 0) {
     385        1121 :         pNode->RegisterAsCopyOf(*this, true);
     386        1121 :         if (nSplitPos == nTextLen)
     387             :         {
     388        1084 :             this->RemoveMetadataReference();
     389             :             // NB: SwUndoSplitNode will call pNode->JoinNext,
     390             :             // which is sufficient even in this case!
     391             :         }
     392             :     }
     393             : 
     394        1376 :     ResetAttr( RES_PARATR_LIST_ISRESTART );
     395        1376 :     ResetAttr( RES_PARATR_LIST_RESTARTVALUE );
     396        1376 :     ResetAttr( RES_PARATR_LIST_ISCOUNTED );
     397        1376 :     if ( GetNumRule() == 0 || (parentIsOutline && !IsOutline()) )
     398             :     {
     399        1367 :         ResetAttr( RES_PARATR_LIST_ID );
     400        1367 :         ResetAttr( RES_PARATR_LIST_LEVEL );
     401             :     }
     402             : 
     403        1376 :     if ( HasWriterListeners() && !m_Text.isEmpty() && (nTextLen / 2) < nSplitPos )
     404             :     {
     405             :         // optimization for SplitNode: If a split is at the end of a node then
     406             :         // move the frames from the current to the new one and create new ones
     407             :         // for the current one. As a result, no need for recreating the layout.
     408             : 
     409          53 :         LockModify();   // disable notifications
     410             : 
     411             :         // werden FlyFrames mit verschoben, so muessen diese nicht ihre
     412             :         // Frames zerstoeren. Im SwTextFly::SetAnchor wird es abgefragt!
     413          53 :         if ( HasHints() )
     414             :         {
     415           3 :             pNode->GetOrCreateSwpHints().SetInSplitNode(true);
     416             :         }
     417             : 
     418             :         //Ersten Teil des Inhalts in den neuen Node uebertragen und
     419             :         //im alten Node loeschen.
     420          53 :         SwIndex aIdx( this );
     421          53 :         CutText( pNode, aIdx, nSplitPos );
     422             : 
     423          53 :         if( GetWrong() )
     424             :         {
     425           4 :             pNode->SetWrong( GetWrong()->SplitList( nSplitPos ) );
     426             :         }
     427          53 :         SetWrongDirty( true );
     428             : 
     429          53 :         if( GetGrammarCheck() )
     430             :         {
     431           0 :             pNode->SetGrammarCheck( GetGrammarCheck()->SplitGrammarList( nSplitPos ) );
     432             :         }
     433          53 :         SetGrammarCheckDirty( true );
     434             : 
     435          53 :         SetWordCountDirty( true );
     436             : 
     437          53 :         if( GetSmartTags() )
     438             :         {
     439           0 :             pNode->SetSmartTags( GetSmartTags()->SplitList( nSplitPos ) );
     440             :         }
     441          53 :         SetSmartTagDirty( true );
     442             : 
     443          53 :         if ( pNode->HasHints() )
     444             :         {
     445           3 :             if ( pNode->m_pSwpHints->CanBeDeleted() )
     446             :             {
     447           1 :                 delete pNode->m_pSwpHints;
     448           1 :                 pNode->m_pSwpHints = 0;
     449             :             }
     450             :             else
     451             :             {
     452           2 :                 pNode->m_pSwpHints->SetInSplitNode(false);
     453             :             }
     454             : 
     455             :             // alle zeichengebundenen Rahmen, die im neuen Absatz laden
     456             :             // muessen aus den alten Frame entfernt werden:
     457             :             // JP 01.10.96: alle leeren und nicht zu expandierenden
     458             :             //              Attribute loeschen
     459           3 :             if ( HasHints() )
     460             :             {
     461           3 :                 for ( size_t j = m_pSwpHints->Count(); j; )
     462             :                 {
     463           1 :                     SwTextAttr* const pHt = m_pSwpHints->GetTextHint( --j );
     464           1 :                     if ( RES_TXTATR_FLYCNT == pHt ->Which() )
     465             :                     {
     466           0 :                         pHt->GetFlyCnt().GetFrameFormat()->DelFrms();
     467             :                     }
     468           1 :                     else if ( pHt->DontExpand() )
     469             :                     {
     470           0 :                         const sal_Int32* const pEnd = pHt->GetEnd();
     471           0 :                         if (pEnd && pHt->GetStart() == *pEnd )
     472             :                         {
     473             :                             // delete it!
     474           0 :                             m_pSwpHints->DeleteAtPos( j );
     475           0 :                             DestroyAttr( pHt );
     476             :                         }
     477             :                     }
     478             :                 }
     479             :             }
     480             : 
     481             :         }
     482             : 
     483         106 :         SwIterator<SwContentFrm,SwTextNode> aIter( *this );
     484         107 :         for( SwContentFrm* pFrm = aIter.First(); pFrm; pFrm = aIter.Next() )
     485             :         {
     486          54 :             pFrm->RegisterToNode( *pNode );
     487          54 :             if( pFrm->IsTextFrm() && !pFrm->IsFollow() && static_cast<SwTextFrm*>(pFrm)->GetOfst() )
     488           0 :                 static_cast<SwTextFrm*>(pFrm)->SetOfst( 0 );
     489             :         }
     490             : 
     491          53 :         if ( IsInCache() )
     492             :         {
     493          37 :             SwFrm::GetCache().Delete( this );
     494          37 :             SetInCache( false );
     495             :         }
     496             : 
     497          53 :         UnlockModify(); // Benachrichtigungen wieder freischalten
     498             : 
     499             :         // If there is an accessible layout we must call modify even
     500             :         // with length zero, because we have to notify about the changed
     501             :         // text node.
     502             :         const SwRootFrm *pRootFrm;
     503         106 :         if ( (nTextLen != nSplitPos) ||
     504          98 :             ( (pRootFrm = pNode->GetDoc()->getIDocumentLayoutAccess().GetCurrentLayout()) != 0 &&
     505          49 :               pRootFrm->IsAnyShellAccessible() ) )
     506             :         {
     507             :             // dann sage den Frames noch, das am Ende etwas "geloescht" wurde
     508           4 :             if( 1 == nTextLen - nSplitPos )
     509             :             {
     510           1 :                 SwDelChr aHint( nSplitPos );
     511           1 :                 pNode->NotifyClients( 0, &aHint );
     512             :             }
     513             :             else
     514             :             {
     515           3 :                 SwDelText aHint( nSplitPos, nTextLen - nSplitPos );
     516           3 :                 pNode->NotifyClients( 0, &aHint );
     517             :             }
     518             :         }
     519          53 :         if ( HasHints() )
     520             :         {
     521           1 :             MoveTextAttr_To_AttrSet();
     522             :         }
     523          53 :         pNode->MakeFrms( *this );       // neue Frames anlegen.
     524         106 :         lcl_ChangeFootnoteRef( *this );
     525             :     }
     526             :     else
     527             :     {
     528        1323 :         SwWrongList *pList = GetWrong();
     529        1323 :         SetWrong( 0, false );
     530        1323 :         SetWrongDirty( true );
     531             : 
     532        1323 :         SwGrammarMarkUp *pList3 = GetGrammarCheck();
     533        1323 :         SetGrammarCheck( 0, false );
     534        1323 :         SetGrammarCheckDirty( true );
     535             : 
     536        1323 :         SetWordCountDirty( true );
     537             : 
     538        1323 :         SwWrongList *pList2 = GetSmartTags();
     539        1323 :         SetSmartTags( 0, false );
     540        1323 :         SetSmartTagDirty( true );
     541             : 
     542        1323 :         SwIndex aIdx( this );
     543        1323 :         CutText( pNode, aIdx, nSplitPos );
     544             : 
     545             :         // JP 01.10.96: alle leeren und nicht zu expandierenden
     546             :         //              Attribute loeschen
     547        1323 :         if ( HasHints() )
     548             :         {
     549           9 :             for ( size_t j = m_pSwpHints->Count(); j; )
     550             :             {
     551           3 :                 SwTextAttr* const pHt = m_pSwpHints->GetTextHint( --j );
     552           3 :                 const sal_Int32* const pEnd = pHt->GetEnd();
     553           3 :                 if ( pHt->DontExpand() && pEnd && (pHt->GetStart() == *pEnd) )
     554             :                 {
     555             :                     // delete it!
     556           0 :                     m_pSwpHints->DeleteAtPos( j );
     557           0 :                     DestroyAttr( pHt );
     558             :                 }
     559             :             }
     560           3 :             MoveTextAttr_To_AttrSet();
     561             :         }
     562             : 
     563        1323 :         if( pList )
     564             :         {
     565           6 :             pNode->SetWrong( pList->SplitList( nSplitPos ) );
     566           6 :             SetWrong( pList, false );
     567             :         }
     568             : 
     569        1323 :         if( pList3 )
     570             :         {
     571           0 :             pNode->SetGrammarCheck( pList3->SplitGrammarList( nSplitPos ) );
     572           0 :             SetGrammarCheck( pList3, false );
     573             :         }
     574             : 
     575        1323 :         if( pList2 )
     576             :         {
     577           0 :             pNode->SetSmartTags( pList2->SplitList( nSplitPos ) );
     578           0 :             SetSmartTags( pList2, false );
     579             :         }
     580             : 
     581        1323 :         if ( HasWriterListeners() )
     582             :         {
     583         271 :             MakeFrms( *pNode );     // neue Frames anlegen.
     584             :         }
     585        1323 :         lcl_ChangeFootnoteRef( *pNode );
     586             :     }
     587             : 
     588             :     {
     589             :         //Hint fuer Pagedesc versenden. Das mueste eigntlich das Layout im
     590             :         //Paste der Frames selbst erledigen, aber das fuehrt dann wiederum
     591             :         //zu weiteren Folgefehlern, die mit Laufzeitkosten geloest werden
     592             :         //muesten. #56977# #55001# #56135#
     593             :         const SfxPoolItem *pItem;
     594        1700 :         if( HasWriterListeners() && SfxItemState::SET == pNode->GetSwAttrSet().
     595         324 :             GetItemState( RES_PAGEDESC, true, &pItem ) )
     596             :         {
     597           9 :             pNode->ModifyNotification( pItem, pItem );
     598             :         }
     599             :     }
     600        1376 :     return pNode;
     601             : }
     602             : 
     603           4 : void SwTextNode::MoveTextAttr_To_AttrSet()
     604             : {
     605             :     OSL_ENSURE( m_pSwpHints, "MoveTextAttr_To_AttrSet without SwpHints?" );
     606           8 :     for ( size_t i = 0; m_pSwpHints && i < m_pSwpHints->Count(); ++i )
     607             :     {
     608           4 :         SwTextAttr *pHt = m_pSwpHints->GetTextHint(i);
     609             : 
     610           4 :         if( pHt->GetStart() )
     611           0 :             break;
     612             : 
     613           4 :         const sal_Int32* pHtEndIdx = pHt->GetEnd();
     614             : 
     615           4 :         if( !pHtEndIdx )
     616           0 :             continue;
     617             : 
     618           4 :         if (*pHtEndIdx < m_Text.getLength() || pHt->IsCharFormatAttr())
     619           0 :             break;
     620             : 
     621           8 :         if( !pHt->IsDontMoveAttr() &&
     622           4 :             SetAttr( pHt->GetAttr() ) )
     623             :         {
     624           0 :             m_pSwpHints->DeleteAtPos(i);
     625           0 :             DestroyAttr( pHt );
     626           0 :             --i;
     627             :         }
     628             :     }
     629             : 
     630           4 : }
     631             : 
     632        3066 : SwContentNode *SwTextNode::JoinNext()
     633             : {
     634        3066 :     SwNodes& rNds = GetNodes();
     635        3066 :     SwNodeIndex aIdx( *this );
     636        3066 :     if( SwContentNode::CanJoinNext( &aIdx ) )
     637             :     {
     638        3066 :         SwDoc* pDoc = rNds.GetDoc();
     639        3066 :         const std::shared_ptr<sw::mark::ContentIdxStore> pContentStore(sw::mark::ContentIdxStore::Create());
     640        3066 :         pContentStore->Save(pDoc, aIdx.GetIndex(), SAL_MAX_INT32);
     641        3066 :         SwTextNode *pTextNode = aIdx.GetNode().GetTextNode();
     642        3066 :         sal_Int32 nOldLen = m_Text.getLength();
     643             : 
     644             :         // METADATA: merge
     645        3066 :         this->JoinMetadatable(*pTextNode, !this->Len(), !pTextNode->Len());
     646             : 
     647        3066 :         SwWrongList *pList = GetWrong();
     648        3066 :         if( pList )
     649             :         {
     650           9 :             pList->JoinList( pTextNode->GetWrong(), nOldLen );
     651           9 :             SetWrongDirty( true );
     652           9 :             SetWrong( 0, false );
     653             :         }
     654             :         else
     655             :         {
     656        3057 :             pList = pTextNode->GetWrong();
     657        3057 :             if( pList )
     658             :             {
     659           1 :                 pList->Move( 0, nOldLen );
     660           1 :                 SetWrongDirty( true );
     661           1 :                 pTextNode->SetWrong( 0, false );
     662             :             }
     663             :         }
     664             : 
     665        3066 :         SwGrammarMarkUp *pList3 = GetGrammarCheck();
     666        3066 :         if( pList3 )
     667             :         {
     668           0 :             pList3->JoinGrammarList( pTextNode->GetGrammarCheck(), nOldLen );
     669           0 :             SetGrammarCheckDirty( true );
     670           0 :             SetGrammarCheck( 0, false );
     671             :         }
     672             :         else
     673             :         {
     674        3066 :             pList3 = pTextNode->GetGrammarCheck();
     675        3066 :             if( pList3 )
     676             :             {
     677           0 :                 pList3->MoveGrammar( 0, nOldLen );
     678           0 :                 SetGrammarCheckDirty( true );
     679           0 :                 pTextNode->SetGrammarCheck( 0, false );
     680             :             }
     681             :         }
     682             : 
     683        3066 :         SwWrongList *pList2 = GetSmartTags();
     684        3066 :         if( pList2 )
     685             :         {
     686           0 :             pList2->JoinList( pTextNode->GetSmartTags(), nOldLen );
     687           0 :             SetSmartTagDirty( true );
     688           0 :             SetSmartTags( 0, false );
     689             :         }
     690             :         else
     691             :         {
     692        3066 :             pList2 = pTextNode->GetSmartTags();
     693        3066 :             if( pList2 )
     694             :             {
     695           0 :                 pList2->Move( 0, nOldLen );
     696           0 :                 SetSmartTagDirty( true );
     697           0 :                 pTextNode->SetSmartTags( 0, false );
     698             :             }
     699             :         }
     700             : 
     701             :         { // wg. SwIndex
     702        3066 :             pTextNode->CutText( this, SwIndex(pTextNode), pTextNode->Len() );
     703             :         }
     704             :         // verschiebe noch alle Bookmarks/TOXMarks
     705        3066 :         if( !pContentStore->Empty())
     706           2 :             pContentStore->Restore( pDoc, GetIndex(), nOldLen );
     707             : 
     708        3066 :         if( pTextNode->HasAnyIndex() )
     709             :         {
     710             :             // alle Crsr/StkCrsr/UnoCrsr aus dem Loeschbereich verschieben
     711           0 :             pDoc->CorrAbs( aIdx, SwPosition( *this ), nOldLen, true );
     712             :         }
     713        3066 :         rNds.Delete(aIdx);
     714        3066 :         SetWrong( pList, false );
     715        3066 :         SetGrammarCheck( pList3, false );
     716        3066 :         SetSmartTags( pList2, false );
     717        3066 :         InvalidateNumRule();
     718             :     }
     719             :     else {
     720             :         OSL_FAIL( "kein TextNode." );
     721             :     }
     722             : 
     723        3066 :     return this;
     724             : }
     725             : 
     726         109 : SwContentNode *SwTextNode::JoinPrev()
     727             : {
     728         109 :     SwNodes& rNds = GetNodes();
     729         109 :     SwNodeIndex aIdx( *this );
     730         109 :     if( SwContentNode::CanJoinPrev( &aIdx ) )
     731             :     {
     732         109 :         SwDoc* pDoc = rNds.GetDoc();
     733         109 :         const std::shared_ptr<sw::mark::ContentIdxStore> pContentStore(sw::mark::ContentIdxStore::Create());
     734         109 :         pContentStore->Save( pDoc, aIdx.GetIndex(), SAL_MAX_INT32);
     735         109 :         SwTextNode *pTextNode = aIdx.GetNode().GetTextNode();
     736         109 :         const sal_Int32 nLen = pTextNode->Len();
     737             : 
     738         109 :         SwWrongList *pList = pTextNode->GetWrong();
     739         109 :         if( pList )
     740             :         {
     741           1 :             pList->JoinList( GetWrong(), Len() );
     742           1 :             SetWrongDirty( true );
     743           1 :             pTextNode->SetWrong( 0, false );
     744           1 :             SetWrong( NULL );
     745             :         }
     746             :         else
     747             :         {
     748         108 :             pList = GetWrong();
     749         108 :             if( pList )
     750             :             {
     751           0 :                 pList->Move( 0, nLen );
     752           0 :                 SetWrongDirty( true );
     753           0 :                 SetWrong( 0, false );
     754             :             }
     755             :         }
     756             : 
     757         109 :         SwGrammarMarkUp *pList3 = pTextNode->GetGrammarCheck();
     758         109 :         if( pList3 )
     759             :         {
     760           0 :             pList3->JoinGrammarList( GetGrammarCheck(), Len() );
     761           0 :             SetGrammarCheckDirty( true );
     762           0 :             pTextNode->SetGrammarCheck( 0, false );
     763           0 :             SetGrammarCheck( NULL );
     764             :         }
     765             :         else
     766             :         {
     767         109 :             pList3 = GetGrammarCheck();
     768         109 :             if( pList3 )
     769             :             {
     770           0 :                 pList3->MoveGrammar( 0, nLen );
     771           0 :                 SetGrammarCheckDirty( true );
     772           0 :                 SetGrammarCheck( 0, false );
     773             :             }
     774             :         }
     775             : 
     776         109 :         SwWrongList *pList2 = pTextNode->GetSmartTags();
     777         109 :         if( pList2 )
     778             :         {
     779           0 :             pList2->JoinList( GetSmartTags(), Len() );
     780           0 :             SetSmartTagDirty( true );
     781           0 :             pTextNode->SetSmartTags( 0, false );
     782           0 :             SetSmartTags( NULL );
     783             :         }
     784             :         else
     785             :         {
     786         109 :             pList2 = GetSmartTags();
     787         109 :             if( pList2 )
     788             :             {
     789           0 :                 pList2->Move( 0, nLen );
     790           0 :                 SetSmartTagDirty( true );
     791           0 :                 SetSmartTags( 0, false );
     792             :             }
     793             :         }
     794             : 
     795             :         { // wg. SwIndex
     796         109 :             pTextNode->CutText( this, SwIndex(this), SwIndex(pTextNode), nLen );
     797             :         }
     798             :         // verschiebe noch alle Bookmarks/TOXMarks
     799         109 :         if( !pContentStore->Empty() )
     800           0 :             pContentStore->Restore( pDoc, GetIndex() );
     801             : 
     802         109 :         if( pTextNode->HasAnyIndex() )
     803             :         {
     804             :             // alle Crsr/StkCrsr/UnoCrsr aus dem Loeschbereich verschieben
     805           0 :             pDoc->CorrAbs( aIdx, SwPosition( *this ), nLen, true );
     806             :         }
     807         109 :         rNds.Delete(aIdx);
     808         109 :         SetWrong( pList, false );
     809         109 :         SetGrammarCheck( pList3, false );
     810         109 :         SetSmartTags( pList2, false );
     811         109 :         InvalidateNumRule();
     812             :     }
     813             :     else {
     814             :         OSL_FAIL( "kein TextNode." );
     815             :     }
     816             : 
     817         109 :     return this;
     818             : }
     819             : 
     820             : // erzeugt einen AttrSet mit Bereichen fuer Frame-/Para/Char-Attributen
     821       32005 : void SwTextNode::NewAttrSet( SwAttrPool& rPool )
     822             : {
     823             :     OSL_ENSURE( !mpAttrSet.get(), "AttrSet ist doch gesetzt" );
     824       32005 :     SwAttrSet aNewAttrSet( rPool, aTextNodeSetRange );
     825             : 
     826             :     // put names of parent style and conditional style:
     827       32005 :     const SwFormatColl* pAnyFormatColl = &GetAnyFormatColl();
     828       32005 :     const SwFormatColl* pFormatColl = GetFormatColl();
     829       64010 :     OUString sVal;
     830       32005 :     SwStyleNameMapper::FillProgName( pAnyFormatColl->GetName(), sVal, nsSwGetPoolIdFromName::GET_POOLID_TXTCOLL, true );
     831       64010 :     SfxStringItem aAnyFormatColl( RES_FRMATR_STYLE_NAME, sVal );
     832       32005 :     if ( pFormatColl != pAnyFormatColl )
     833           0 :         SwStyleNameMapper::FillProgName( pFormatColl->GetName(), sVal, nsSwGetPoolIdFromName::GET_POOLID_TXTCOLL, true );
     834       64010 :     SfxStringItem aFormatColl( RES_FRMATR_CONDITIONAL_STYLE_NAME, sVal );
     835       32005 :     aNewAttrSet.Put( aAnyFormatColl );
     836       32005 :     aNewAttrSet.Put( aFormatColl );
     837             : 
     838       32005 :     aNewAttrSet.SetParent( &pAnyFormatColl->GetAttrSet() );
     839       64010 :     mpAttrSet = GetDoc()->GetIStyleAccess().getAutomaticStyle( aNewAttrSet, IStyleAccess::AUTO_STYLE_PARA );
     840       32005 : }
     841             : 
     842             : // override SwIndexReg::Update => text hints do not need SwIndex for start/end!
     843      161106 : void SwTextNode::Update(
     844             :     SwIndex const & rPos,
     845             :     const sal_Int32 nChangeLen,
     846             :     const bool bNegative,
     847             :     const bool bDelete )
     848             : {
     849      161106 :     SetAutoCompleteWordDirty( true );
     850             : 
     851      161106 :     std::unique_ptr<SwpHts> pCollector;
     852      161106 :     const sal_Int32 nChangePos = rPos.GetIndex();
     853             : 
     854      161106 :     if ( HasHints() )
     855             :     {
     856       27590 :         if ( bNegative )
     857             :         {
     858        1631 :             std::vector<SwTextInputField*> aTextInputFields;
     859             : 
     860        1631 :             const sal_Int32 nChangeEnd = nChangePos + nChangeLen;
     861        6171 :             for ( size_t n = 0; n < m_pSwpHints->Count(); ++n )
     862             :             {
     863        4540 :                 bool bTextAttrChanged = false;
     864        4540 :                 bool bStartOfTextAttrChanged = false;
     865        4540 :                 SwTextAttr * const pHint = m_pSwpHints->GetTextHint(n);
     866        4540 :                 sal_Int32 &       rStart = pHint->GetStart();
     867        4540 :                 if ( rStart > nChangePos )
     868             :                 {
     869        1245 :                     if ( rStart > nChangeEnd )
     870             :                     {
     871         702 :                          rStart = rStart - nChangeLen;
     872             :                     }
     873             :                     else
     874             :                     {
     875         543 :                          rStart = nChangePos;
     876             :                     }
     877        1245 :                     bStartOfTextAttrChanged = true;
     878             :                 }
     879             : 
     880        4540 :                 sal_Int32 * const pEnd = pHint->GetEnd();
     881        4540 :                 if (pEnd)
     882             :                 {
     883        3338 :                     if ( *pEnd > nChangePos )
     884             :                     {
     885        1082 :                         if( *pEnd > nChangeEnd )
     886             :                         {
     887         699 :                             *pEnd = *pEnd - nChangeLen;
     888             :                         }
     889             :                         else
     890             :                         {
     891         383 :                             *pEnd = nChangePos;
     892             :                         }
     893        1082 :                         bTextAttrChanged = !bStartOfTextAttrChanged;
     894             :                     }
     895             :                 }
     896             : 
     897        4540 :                 if ( bTextAttrChanged
     898        4540 :                      && pHint->Which() == RES_TXTATR_INPUTFIELD )
     899             :                 {
     900           8 :                     SwTextInputField* pTextInputField = dynamic_cast<SwTextInputField*>(pHint);
     901           8 :                     if ( pTextInputField )
     902           8 :                         aTextInputFields.push_back(pTextInputField);
     903             :                 }
     904             :             }
     905             : 
     906             :             //wait until all the attribute positions are correct
     907             :             //before updating the field contents
     908        1639 :             for (SwTextInputField* pTextInputField : aTextInputFields)
     909             :             {
     910           8 :                 pTextInputField->UpdateFieldContent();
     911             :             }
     912             : 
     913        1631 :             m_pSwpHints->MergePortions( *this );
     914             :         }
     915             :         else
     916             :         {
     917       25959 :             bool bNoExp = false;
     918       25959 :             bool bResort = false;
     919       25959 :             bool bMergePortionsNeeded = false;
     920       25959 :             const int coArrSz = RES_TXTATR_WITHEND_END - RES_CHRATR_BEGIN;
     921       25959 :             std::vector<SwTextInputField*> aTextInputFields;
     922             : 
     923             :             bool aDontExp[ coArrSz ];
     924       25959 :             memset( &aDontExp, 0, coArrSz * sizeof(bool) );
     925             : 
     926      213482 :             for ( size_t n = 0; n < m_pSwpHints->Count(); ++n )
     927             :             {
     928      187523 :                 bool bTextAttrChanged = false;
     929      187523 :                 SwTextAttr * const pHint = m_pSwpHints->GetTextHint(n);
     930      187523 :                 sal_Int32 &       rStart = pHint->GetStart();
     931      187523 :                 sal_Int32 * const pEnd = pHint->GetEnd();
     932      187523 :                 if ( rStart >= nChangePos )
     933             :                 {
     934         436 :                     rStart = rStart + nChangeLen;
     935         436 :                     if ( pEnd )
     936             :                     {
     937         253 :                         *pEnd = *pEnd + nChangeLen;
     938             :                     }
     939             :                 }
     940      187087 :                 else if ( pEnd && (*pEnd >= nChangePos) )
     941             :                 {
     942       21358 :                     if ( (*pEnd > nChangePos) || IsIgnoreDontExpand() )
     943             :                     {
     944         134 :                         *pEnd = *pEnd + nChangeLen;
     945         134 :                         bTextAttrChanged = true;
     946             :                     }
     947             :                     else // *pEnd == nChangePos
     948             :                     {
     949       21224 :                         const sal_uInt16 nWhich = pHint->Which();
     950             : 
     951             :                         OSL_ENSURE(!isCHRATR(nWhich), "Update: char attr hint?");
     952       21224 :                         if (!(isCHRATR(nWhich) || isTXTATR_WITHEND(nWhich)))
     953           0 :                             continue;
     954             : 
     955       21224 :                         const sal_uInt16 nWhPos = nWhich - RES_CHRATR_BEGIN;
     956             : 
     957       21224 :                         if( aDontExp[ nWhPos ] )
     958         189 :                             continue;
     959             : 
     960       21035 :                         if ( pHint->DontExpand() )
     961             :                         {
     962       20811 :                             pHint->SetDontExpand( false );
     963       20811 :                             bResort = true;
     964             :                             // could have a continuation with IgnoreStart()...
     965       20811 :                             if (pHint->IsFormatIgnoreEnd())
     966             :                             {
     967           0 :                                 bMergePortionsNeeded = true;
     968             :                             }
     969       20811 :                             if ( pHint->IsCharFormatAttr() )
     970             :                             {
     971        3693 :                                 bNoExp = true;
     972        3693 :                                 aDontExp[ RES_TXTATR_CHARFMT - RES_CHRATR_BEGIN ] = true;
     973        3693 :                                 aDontExp[ RES_TXTATR_INETFMT - RES_CHRATR_BEGIN ] = true;
     974             :                             }
     975             :                             else
     976       17118 :                                 aDontExp[ nWhPos ] = true;
     977             :                         }
     978         224 :                         else if( bNoExp )
     979             :                         {
     980           2 :                             if ( !pCollector.get() )
     981             :                             {
     982           2 :                                pCollector.reset( new SwpHts );
     983             :                             }
     984           2 :                             for(SwpHts::iterator it =  pCollector->begin(); it != pCollector->end(); ++it)
     985             :                             {
     986           0 :                                SwTextAttr *pTmp = *it;
     987           0 :                                if( nWhich == pTmp->Which() )
     988             :                                {
     989           0 :                                    pCollector->erase( it );
     990             :                                    SwTextAttr::Destroy( pTmp,
     991           0 :                                        GetDoc()->GetAttrPool() );
     992           0 :                                    break;
     993             :                                }
     994             :                             }
     995             :                             SwTextAttr * const pTmp =
     996           2 :                             MakeTextAttr( *GetDoc(),
     997           4 :                                 pHint->GetAttr(), nChangePos, nChangePos + nChangeLen);
     998           2 :                             pCollector->push_back( pTmp );
     999             :                         }
    1000             :                         else
    1001             :                         {
    1002         222 :                             *pEnd = *pEnd + nChangeLen;
    1003         222 :                             bTextAttrChanged = true;
    1004             :                         }
    1005             :                     }
    1006             :                 }
    1007             : 
    1008      187334 :                 if ( bTextAttrChanged
    1009      187334 :                      && pHint->Which() == RES_TXTATR_INPUTFIELD )
    1010             :                 {
    1011           8 :                     SwTextInputField* pTextInputField = dynamic_cast<SwTextInputField*>(pHint);
    1012           8 :                     if ( pTextInputField )
    1013           8 :                         aTextInputFields.push_back(pTextInputField);
    1014             :                 }
    1015             :             }
    1016             : 
    1017             :             //wait until all the attribute positions are correct
    1018             :             //before updating the field contents
    1019       25967 :             for (SwTextInputField* pTextInputField : aTextInputFields)
    1020             :             {
    1021           8 :                 pTextInputField->UpdateFieldContent();
    1022             :             }
    1023             : 
    1024       25959 :             if (bMergePortionsNeeded)
    1025             :             {
    1026           0 :                 m_pSwpHints->MergePortions(*this); // does Resort too
    1027             :             }
    1028       25959 :             else if (bResort)
    1029             :             {
    1030       20063 :                 m_pSwpHints->Resort();
    1031       25959 :             }
    1032             :         }
    1033             :     }
    1034             : 
    1035      161106 :     bool bSortMarks = false;
    1036      322212 :     SwIndexReg aTmpIdxReg;
    1037      161106 :     if ( !bNegative && !bDelete )
    1038             :     {
    1039      154134 :         const SwRedlineTable& rTable = GetDoc()->getIDocumentRedlineAccess().GetRedlineTable();
    1040      283032 :         for ( size_t i = 0; i < rTable.size(); ++i )
    1041             :         {
    1042      128898 :             SwRangeRedline *const pRedl = rTable[ i ];
    1043      128898 :             if ( pRedl->HasMark() )
    1044             :             {
    1045      128313 :                 SwPosition* const pEnd = pRedl->End();
    1046      157503 :                 if ( this == &pEnd->nNode.GetNode() &&
    1047       29190 :                      *pRedl->GetPoint() != *pRedl->GetMark() )
    1048             :                 {
    1049       29190 :                     SwIndex & rIdx = pEnd->nContent;
    1050       29190 :                     if (nChangePos == rIdx.GetIndex())
    1051             :                     {
    1052        1489 :                         rIdx.Assign( &aTmpIdxReg, rIdx.GetIndex() );
    1053             :                     }
    1054             :                 }
    1055             :             }
    1056         585 :             else if ( this == &pRedl->GetPoint()->nNode.GetNode() )
    1057             :             {
    1058           8 :                 SwIndex & rIdx = pRedl->GetPoint()->nContent;
    1059           8 :                 if (nChangePos == rIdx.GetIndex())
    1060             :                 {
    1061           8 :                     rIdx.Assign( &aTmpIdxReg, rIdx.GetIndex() );
    1062             :                 }
    1063             :                 // the unused position must not be on a SwTextNode
    1064           8 :                 bool const isOneUsed(&pRedl->GetBound(true) == pRedl->GetPoint());
    1065             :                 assert(!pRedl->GetBound(!isOneUsed).nNode.GetNode().IsTextNode());
    1066             :                 assert(!pRedl->GetBound(!isOneUsed).nContent.GetIdxReg()); (void)isOneUsed;
    1067             :             }
    1068             :         }
    1069             : 
    1070             :         // Bookmarks must never grow to either side, when editing (directly) to the left or right (#i29942#)!
    1071             :         // And a bookmark with same start and end must remain to the left of the inserted text (used in XML import).
    1072             :         {
    1073      154134 :             bool bAtLeastOneBookmarkMoved = false;
    1074      154134 :             bool bAtLeastOneExpandedBookmarkAtInsertionPosition = false;
    1075             :             // A text node already knows its marks via its SwIndexes.
    1076      154134 :             std::set<const sw::mark::IMark*> aSeenMarks;
    1077             :             const SwIndex* next;
    1078     1818690 :             for (const SwIndex* pIndex = GetFirstIndex(); pIndex; pIndex = next )
    1079             :             {
    1080     1664556 :                 next = pIndex->GetNext();
    1081     1664556 :                 const sw::mark::IMark* pMark = pIndex->GetMark();
    1082     1664556 :                 if (!pMark)
    1083     2097631 :                     continue;
    1084             :                 // Only handle bookmarks once, if they start and end at this node as well.
    1085      790176 :                 if (aSeenMarks.find(pMark) != aSeenMarks.end())
    1086      348871 :                     continue;
    1087      441305 :                 aSeenMarks.insert(pMark);
    1088      441305 :                 const SwPosition* pEnd = &pMark->GetMarkEnd();
    1089      441305 :                 SwIndex & rEndIdx = const_cast<SwIndex&>(pEnd->nContent);
    1090      882610 :                 if( this == &pEnd->nNode.GetNode() &&
    1091      441305 :                     rPos.GetIndex() == rEndIdx.GetIndex() )
    1092             :                 {
    1093       15994 :                     rEndIdx.Assign( &aTmpIdxReg, rEndIdx.GetIndex() );
    1094       15994 :                     bAtLeastOneBookmarkMoved = true;
    1095             :                 }
    1096      425311 :                 else if ( !bAtLeastOneExpandedBookmarkAtInsertionPosition )
    1097             :                 {
    1098      373228 :                     if ( pMark->IsExpanded() )
    1099             :                     {
    1100      297694 :                         const SwPosition* pStart = &pMark->GetMarkStart();
    1101      595388 :                         if ( this == &pStart->nNode.GetNode()
    1102      297694 :                              && rPos.GetIndex() == pStart->nContent.GetIndex() )
    1103             :                         {
    1104        1034 :                             bAtLeastOneExpandedBookmarkAtInsertionPosition = true;
    1105             :                         }
    1106             :                     }
    1107             :                 }
    1108             :             }
    1109             : 
    1110      154134 :             bSortMarks = bAtLeastOneBookmarkMoved && bAtLeastOneExpandedBookmarkAtInsertionPosition;
    1111             :         }
    1112             : 
    1113             :         // at-char anchored flys shouldn't be moved, either.
    1114             : #if OSL_DEBUG_LEVEL > 0
    1115             :         std::list<SwFrameFormat*> checkFormats;
    1116             :         const SwFrameFormats& rFormats = *GetDoc()->GetSpzFrameFormats();
    1117             :         for (SwFrameFormats::const_iterator pFormat = rFormats.begin(); pFormat != rFormats.end(); ++pFormat)
    1118             :         {
    1119             :             const SwFormatAnchor& rAnchor = (*pFormat)->GetAnchor();
    1120             :             const SwPosition* pContentAnchor = rAnchor.GetContentAnchor();
    1121             :             if (rAnchor.GetAnchorId() == FLY_AT_CHAR && pContentAnchor)
    1122             :             {
    1123             :                 // The fly is at-char anchored and has an anchor position.
    1124             :                 SwIndex& rEndIdx = const_cast<SwIndex&>(pContentAnchor->nContent);
    1125             :                 if (&pContentAnchor->nNode.GetNode() == this && rEndIdx.GetIndex() == rPos.GetIndex())
    1126             :                 {
    1127             :                     // The anchor position is exactly our insert position.
    1128             :                     #if 0
    1129             :                     rEndIdx.Assign(&aTmpIdxReg, rEndIdx.GetIndex());
    1130             :                     #endif
    1131             :                     checkFormats.push_back( *pFormat );
    1132             :                 }
    1133             :             }
    1134             :         }
    1135             : #endif
    1136      154134 :         std::vector<SwFrameFormat*> const*const pFlys(GetAnchoredFlys());
    1137      186682 :         for (size_t i = 0; pFlys && i != pFlys->size(); ++i)
    1138             :         {
    1139       32548 :             SwFrameFormat const*const pFormat = (*pFlys)[i];
    1140       32548 :             const SwFormatAnchor& rAnchor = pFormat->GetAnchor();
    1141       32548 :             const SwPosition* pContentAnchor = rAnchor.GetContentAnchor();
    1142       32548 :             if (rAnchor.GetAnchorId() == FLY_AT_CHAR && pContentAnchor)
    1143             :             {
    1144             :                 // The fly is at-char anchored and has an anchor position.
    1145         379 :                 SwIndex& rEndIdx = const_cast<SwIndex&>(pContentAnchor->nContent);
    1146         379 :                 if (&pContentAnchor->nNode.GetNode() == this && rEndIdx.GetIndex() == rPos.GetIndex())
    1147             :                 {
    1148             :                     // The anchor position is exactly our insert position.
    1149         161 :                     rEndIdx.Assign(&aTmpIdxReg, rEndIdx.GetIndex());
    1150             : #if OSL_DEBUG_LEVEL > 0
    1151             :                     std::list<SwFrameFormat*>::iterator checkPos = std::find( checkFormats.begin(), checkFormats.end(), pFormat );
    1152             :                     assert( checkPos != checkFormats.end());
    1153             :                     checkFormats.erase( checkPos );
    1154             : #endif
    1155             :                 }
    1156             :             }
    1157             :         }
    1158             : #if OSL_DEBUG_LEVEL > 0
    1159             :         assert( checkFormats.empty());
    1160             : #endif
    1161             :     }
    1162             : 
    1163             :     // base class
    1164      161106 :     SwIndexReg::Update( rPos, nChangeLen, bNegative, bDelete );
    1165             : 
    1166      161106 :     if ( pCollector.get() )
    1167             :     {
    1168           2 :         const size_t nCount = pCollector->size();
    1169           4 :         for ( size_t i = 0; i < nCount; ++i )
    1170             :         {
    1171           2 :             m_pSwpHints->TryInsertHint( (*pCollector)[ i ], *this );
    1172             :         }
    1173             :     }
    1174             : 
    1175      161106 :     aTmpIdxReg.MoveTo( *this );
    1176      161106 :     if ( bSortMarks )
    1177             :     {
    1178           4 :         getIDocumentMarkAccess()->assureSortedMarkContainers();
    1179             :     }
    1180             : 
    1181             :     //Any drawing objects anchored into this text node may be sorted by their
    1182             :     //anchor position which may have changed here, so resort them
    1183      161106 :     SwContentFrm* pContentFrm = getLayoutFrm(GetDoc()->getIDocumentLayoutAccess().GetCurrentLayout());
    1184      161106 :     SwSortedObjs* pSortedObjs = pContentFrm ? pContentFrm->GetDrawObjs() : NULL;
    1185      161106 :     if (pSortedObjs)
    1186      161358 :         pSortedObjs->UpdateAll();
    1187      161106 : }
    1188             : 
    1189       79810 : void SwTextNode::_ChgTextCollUpdateNum( const SwTextFormatColl *pOldColl,
    1190             :                                         const SwTextFormatColl *pNewColl)
    1191             : {
    1192       79810 :     SwDoc* pDoc = GetDoc();
    1193             :     OSL_ENSURE( pDoc, "Kein Doc?" );
    1194             :     // erfrage die OutlineLevel und update gegebenenfalls das Nodes-Array,
    1195             :     // falls sich die Level geaendert haben !
    1196       42296 :     const int nOldLevel = pOldColl && pOldColl->IsAssignedToListLevelOfOutlineStyle() ?
    1197       80289 :                      pOldColl->GetAssignedOutlineStyleLevel() : MAXLEVEL;
    1198       79810 :     const int nNewLevel = pNewColl && pNewColl->IsAssignedToListLevelOfOutlineStyle() ?
    1199       80628 :                      pNewColl->GetAssignedOutlineStyleLevel() : MAXLEVEL;
    1200             : 
    1201       79810 :     if ( MAXLEVEL != nNewLevel && -1 != nNewLevel )
    1202             :     {
    1203         818 :         SetAttrListLevel(nNewLevel);
    1204             :     }
    1205       79810 :     if (pDoc)
    1206             :     {
    1207       79810 :         pDoc->GetNodes().UpdateOutlineNode(*this);
    1208             :     }
    1209             : 
    1210       79810 :     SwNodes& rNds = GetNodes();
    1211             :     // Update beim Level 0 noch die Fussnoten !!
    1212      159369 :     if( ( !nNewLevel || !nOldLevel) && pDoc && !pDoc->GetFootnoteIdxs().empty() &&
    1213       79822 :         FTNNUM_CHAPTER == pDoc->GetFootnoteInfo().eNum &&
    1214           0 :         rNds.IsDocNodes() )
    1215             :     {
    1216           0 :         SwNodeIndex aTmpIndex( rNds, GetIndex());
    1217             : 
    1218           0 :         pDoc->GetFootnoteIdxs().UpdateFootnote( aTmpIndex);
    1219             :     }
    1220             : 
    1221       79810 :     if( pNewColl && RES_CONDTXTFMTCOLL == pNewColl->Which() )
    1222             :     {
    1223             :         // Erfrage die akt. Condition des TextNodes:
    1224         422 :         ChkCondColl();
    1225             :     }
    1226       79810 : }
    1227             : 
    1228             : // Wenn man sich genau am Ende einer Text- bzw. INetvorlage befindet,
    1229             : // bekommt diese das DontExpand-Flag verpasst
    1230             : 
    1231       73455 : bool SwTextNode::DontExpandFormat( const SwIndex& rIdx, bool bFlag,
    1232             :                                 bool bFormatToTextAttributes )
    1233             : {
    1234       73455 :     const sal_Int32 nIdx = rIdx.GetIndex();
    1235       73455 :     if (bFormatToTextAttributes && nIdx == m_Text.getLength())
    1236             :     {
    1237       73277 :         FormatToTextAttr( this );
    1238             :     }
    1239             : 
    1240       73455 :     bool bRet = false;
    1241       73455 :     if ( HasHints() )
    1242             :     {
    1243       23065 :         const size_t nEndCnt = m_pSwpHints->GetEndCount();
    1244       23065 :         size_t nPos = nEndCnt;
    1245       76998 :         while( nPos )
    1246             :         {
    1247       30868 :             SwTextAttr *pTmp = m_pSwpHints->GetEnd( --nPos );
    1248       30868 :             sal_Int32 *pEnd = pTmp->GetEnd();
    1249       30868 :             if( !pEnd || *pEnd > nIdx )
    1250        1341 :                 continue;
    1251       29527 :             if( nIdx != *pEnd )
    1252        8679 :                 nPos = 0;
    1253       62116 :             else if( bFlag != pTmp->DontExpand() && !pTmp->IsLockExpandFlag()
    1254       41268 :                      && *pEnd > pTmp->GetStart())
    1255             :             {
    1256       20420 :                 bRet = true;
    1257       20420 :                 m_pSwpHints->NoteInHistory( pTmp );
    1258       20420 :                 pTmp->SetDontExpand( bFlag );
    1259             :             }
    1260             :         }
    1261             :     }
    1262       73455 :     return bRet;
    1263             : }
    1264             : 
    1265         434 : static bool lcl_GetTextAttrDefault(sal_Int32 nIndex, sal_Int32 nHintStart, sal_Int32 nHintEnd)
    1266             : {
    1267         434 :     return ((nHintStart <= nIndex) && (nIndex <  nHintEnd));
    1268             : }
    1269          59 : static bool lcl_GetTextAttrExpand(sal_Int32 nIndex, sal_Int32 nHintStart, sal_Int32 nHintEnd)
    1270             : {
    1271          59 :     return ((nHintStart <  nIndex) && (nIndex <= nHintEnd));
    1272             : }
    1273          73 : static bool lcl_GetTextAttrParent(sal_Int32 nIndex, sal_Int32 nHintStart, sal_Int32 nHintEnd)
    1274             : {
    1275          73 :     return ((nHintStart <  nIndex) && (nIndex <  nHintEnd));
    1276             : }
    1277             : 
    1278             : static void
    1279      438133 : lcl_GetTextAttrs(
    1280             :     ::std::vector<SwTextAttr *> *const pVector,
    1281             :     SwTextAttr **const ppTextAttr,
    1282             :     SwpHints *const pSwpHints,
    1283             :     sal_Int32 const nIndex, RES_TXTATR const nWhich,
    1284             :     enum SwTextNode::GetTextAttrMode const eMode)
    1285             : {
    1286      438133 :     size_t const nSize = (pSwpHints) ? pSwpHints->Count() : 0;
    1287      438133 :     sal_Int32 nPreviousIndex(0); // index of last hint with nWhich
    1288      438133 :     bool (*pMatchFunc)(sal_Int32, sal_Int32, sal_Int32)=0;
    1289      438133 :     switch (eMode)
    1290             :     {
    1291       55057 :         case SwTextNode::DEFAULT:   pMatchFunc = &lcl_GetTextAttrDefault; break;
    1292          32 :         case SwTextNode::EXPAND:    pMatchFunc = &lcl_GetTextAttrExpand;  break;
    1293      383044 :         case SwTextNode::PARENT:    pMatchFunc = &lcl_GetTextAttrParent;  break;
    1294             :         default: assert(false);
    1295             :     }
    1296             : 
    1297     1209030 :     for( size_t i = 0; i < nSize; ++i )
    1298             :     {
    1299      798454 :         SwTextAttr *const pHint = pSwpHints->GetTextHint(i);
    1300      798454 :         sal_Int32 const nHintStart = pHint->GetStart();
    1301      798454 :         if (nIndex < nHintStart)
    1302             :         {
    1303      465690 :             return; // hints are sorted by start, so we are done...
    1304             :         }
    1305             : 
    1306      770897 :         if (pHint->Which() != nWhich)
    1307             :         {
    1308      770321 :             continue;
    1309             :         }
    1310             : 
    1311         576 :         sal_Int32 const*const pEndIdx = pHint->GetEnd();
    1312             :         // cannot have hint with no end and no dummy char
    1313             :         assert(pEndIdx || pHint->HasDummyChar());
    1314             :             // Wenn bExpand gesetzt ist, wird das Verhalten bei Eingabe
    1315             :             // simuliert, d.h. der Start wuede verschoben, das Ende expandiert,
    1316             :         bool const bContained( (pEndIdx)
    1317         566 :             ? (*pMatchFunc)(nIndex, nHintStart, *pEndIdx)
    1318        1142 :             : (nHintStart == nIndex) );
    1319         576 :         if (bContained)
    1320             :         {
    1321         257 :             if (pVector)
    1322             :             {
    1323          70 :                 if (nPreviousIndex < nHintStart)
    1324             :                 {
    1325           8 :                     pVector->clear(); // clear hints that are outside pHint
    1326           8 :                     nPreviousIndex = nHintStart;
    1327             :                 }
    1328          70 :                 pVector->push_back(pHint);
    1329             :             }
    1330             :             else
    1331             :             {
    1332         187 :                 *ppTextAttr = pHint; // and possibly overwrite outer hint
    1333             :             }
    1334         257 :             if (!pEndIdx)
    1335             :             {
    1336           0 :                 break;
    1337             :             }
    1338             :         }
    1339             :     }
    1340             : }
    1341             : 
    1342             : ::std::vector<SwTextAttr *>
    1343          56 : SwTextNode::GetTextAttrsAt(sal_Int32 const nIndex, RES_TXTATR const nWhich,
    1344             :                         enum GetTextAttrMode const eMode) const
    1345             : {
    1346          56 :     ::std::vector<SwTextAttr *> ret;
    1347          56 :     lcl_GetTextAttrs(& ret, 0, m_pSwpHints, nIndex, nWhich, eMode);
    1348          56 :     return ret;
    1349             : }
    1350             : 
    1351             : SwTextAttr *
    1352      438077 : SwTextNode::GetTextAttrAt(sal_Int32 const nIndex, RES_TXTATR const nWhich,
    1353             :                         enum GetTextAttrMode const eMode) const
    1354             : {
    1355             :     assert(    (nWhich == RES_TXTATR_META)
    1356             :             || (nWhich == RES_TXTATR_METAFIELD)
    1357             :             || (nWhich == RES_TXTATR_AUTOFMT)
    1358             :             || (nWhich == RES_TXTATR_INETFMT)
    1359             :             || (nWhich == RES_TXTATR_CJK_RUBY)
    1360             :             || (nWhich == RES_TXTATR_UNKNOWN_CONTAINER)
    1361             :             || (nWhich == RES_TXTATR_INPUTFIELD ) );
    1362             :             // "GetTextAttrAt() will give wrong result for this hint!")
    1363             : 
    1364      438077 :     SwTextAttr * pRet(0);
    1365      438077 :     lcl_GetTextAttrs(0, & pRet, m_pSwpHints, nIndex, nWhich, eMode);
    1366      438077 :     return pRet;
    1367             : }
    1368             : 
    1369       82499 : const SwTextInputField* SwTextNode::GetOverlappingInputField( const SwTextAttr& rTextAttr ) const
    1370             : {
    1371       82499 :     const SwTextInputField* pTextInputField = NULL;
    1372             : 
    1373       82499 :     pTextInputField = dynamic_cast<const SwTextInputField*>(GetTextAttrAt( rTextAttr.GetStart(), RES_TXTATR_INPUTFIELD, PARENT ));
    1374             : 
    1375       82499 :     if ( pTextInputField == NULL && rTextAttr.End() != NULL )
    1376             :     {
    1377       76497 :         pTextInputField = dynamic_cast<const SwTextInputField*>(GetTextAttrAt( *(rTextAttr.End()), RES_TXTATR_INPUTFIELD, PARENT ));
    1378             :     }
    1379             : 
    1380       82499 :     return pTextInputField;
    1381             : }
    1382             : 
    1383       12207 : void SwTextNode::DelFrms_TextNodePart()
    1384             : {
    1385       12207 :     SetWrong( NULL );
    1386       12207 :     SetWrongDirty( true );
    1387             : 
    1388       12207 :     SetGrammarCheck( NULL );
    1389       12207 :     SetGrammarCheckDirty( true );
    1390             : 
    1391       12207 :     SetSmartTags( NULL );
    1392       12207 :     SetSmartTagDirty( true );
    1393             : 
    1394       12207 :     SetWordCountDirty( true );
    1395       12207 :     SetAutoCompleteWordDirty( true );
    1396       12207 : }
    1397             : 
    1398      115788 : SwTextField* SwTextNode::GetFieldTextAttrAt(
    1399             :     const sal_Int32 nIndex,
    1400             :     const bool bIncludeInputFieldAtStart ) const
    1401             : {
    1402      115788 :     SwTextField* pTextField = NULL;
    1403             : 
    1404      115788 :     pTextField = dynamic_cast<SwTextField*>(GetTextAttrForCharAt( nIndex, RES_TXTATR_FIELD ));
    1405      115788 :     if ( pTextField == NULL )
    1406             :     {
    1407      114649 :         pTextField = dynamic_cast<SwTextField*>(GetTextAttrForCharAt( nIndex, RES_TXTATR_ANNOTATION ));
    1408             :     }
    1409      115788 :     if ( pTextField == NULL )
    1410             :     {
    1411             :         pTextField =
    1412             :             dynamic_cast<SwTextField*>( GetTextAttrAt(
    1413             :                 nIndex,
    1414             :                 RES_TXTATR_INPUTFIELD,
    1415      114338 :                 bIncludeInputFieldAtStart ? DEFAULT : PARENT ));
    1416             :     }
    1417             : 
    1418      115788 :     return pTextField;
    1419             : }
    1420             : 
    1421           0 : static SwCharFormat* lcl_FindCharFormat( const SwCharFormats* pCharFormats, const OUString& rName )
    1422             : {
    1423           0 :     if( !rName.isEmpty() )
    1424             :     {
    1425           0 :         const size_t nArrLen = pCharFormats->size();
    1426           0 :         for( size_t i = 1; i < nArrLen; i++ )
    1427             :         {
    1428           0 :             SwCharFormat* pFormat = (*pCharFormats)[ i ];
    1429           0 :             if( pFormat->GetName()==rName )
    1430           0 :                 return pFormat;
    1431             :         }
    1432             :     }
    1433           0 :     return NULL;
    1434             : }
    1435             : 
    1436        3063 : void lcl_CopyHint(
    1437             :     const sal_uInt16 nWhich,
    1438             :     const SwTextAttr * const pHt,
    1439             :     SwTextAttr *const pNewHt,
    1440             :     SwDoc *const pOtherDoc,
    1441             :     SwTextNode *const pDest )
    1442             : {
    1443             :     assert(nWhich == pHt->Which()); // wrong hint-id
    1444        3063 :     switch( nWhich )
    1445             :     {
    1446             :     // copy nodesarray section with footnote content
    1447             :     case RES_TXTATR_FTN :
    1448             :             assert(pDest); // "lcl_CopyHint: no destination text node?"
    1449           0 :             static_cast<const SwTextFootnote*>(pHt)->CopyFootnote( *static_cast<SwTextFootnote*>(pNewHt), *pDest);
    1450           0 :             break;
    1451             : 
    1452             :     // Beim Kopieren von Feldern in andere Dokumente
    1453             :     // muessen die Felder bei ihren neuen Feldtypen angemeldet werden.
    1454             : 
    1455             :     // TabellenFormel muessen relativ kopiert werden.
    1456             :     case RES_TXTATR_FIELD :
    1457             :         {
    1458         757 :             if( pOtherDoc != NULL )
    1459             :             {
    1460             :                 static_txtattr_cast<const SwTextField*>(pHt)->CopyTextField(
    1461          44 :                         static_txtattr_cast<SwTextField*>(pNewHt));
    1462             :             }
    1463             : 
    1464             :             // Tabellenformel ??
    1465         757 :             const SwFormatField& rField = pHt->GetFormatField();
    1466        1514 :             if( RES_TABLEFLD == rField.GetField()->GetTyp()->Which()
    1467         757 :                 && static_cast<const SwTableField*>(rField.GetField())->IsIntrnlName())
    1468             :             {
    1469             :                 // wandel die interne in eine externe Formel um
    1470             :                 const SwTableNode* const pDstTableNd =
    1471           0 :                     static_txtattr_cast<const SwTextField*>(pHt)->GetTextNode().FindTableNode();
    1472           0 :                 if( pDstTableNd )
    1473             :                 {
    1474             :                     SwTableField* const pTableField =
    1475             :                         const_cast<SwTableField*>(static_cast<const SwTableField*>(
    1476           0 :                             pNewHt->GetFormatField().GetField()));
    1477           0 :                     pTableField->PtrToBoxNm( &pDstTableNd->GetTable() );
    1478             :                 }
    1479             :             }
    1480             :         }
    1481         757 :         break;
    1482             : 
    1483             :     case RES_TXTATR_INPUTFIELD :
    1484             :     case RES_TXTATR_ANNOTATION :
    1485           9 :         if( pOtherDoc != NULL )
    1486             :         {
    1487             :             static_txtattr_cast<const SwTextField*>(pHt)->CopyTextField(
    1488           9 :                     static_txtattr_cast<SwTextField*>(pNewHt));
    1489             :         }
    1490           9 :         break;
    1491             : 
    1492             :     case RES_TXTATR_TOXMARK :
    1493           0 :         if( pOtherDoc && pDest && pDest->GetpSwpHints()
    1494           0 :             && pDest->GetpSwpHints()->Contains( pNewHt ) )
    1495             :         {
    1496             :             // Beim Kopieren von TOXMarks(Client) in andere Dokumente
    1497             :             // muss der Verzeichnis (Modify) ausgetauscht werden
    1498           0 :             static_txtattr_cast<SwTextTOXMark*>(pNewHt)->CopyTOXMark(pOtherDoc);
    1499             :         }
    1500           0 :         break;
    1501             : 
    1502             :     case RES_TXTATR_CHARFMT :
    1503             :         // Wenn wir es mit einer Zeichenvorlage zu tun haben,
    1504             :         // muessen wir natuerlich auch die Formate kopieren.
    1505         488 :         if( pDest && pDest->GetpSwpHints()
    1506         488 :             && pDest->GetpSwpHints()->Contains( pNewHt ) )
    1507             :         {
    1508             :             SwCharFormat* pFormat =
    1509         244 :                 static_cast<SwCharFormat*>(pHt->GetCharFormat().GetCharFormat());
    1510             : 
    1511         244 :             if (pOtherDoc)
    1512             :             {
    1513           0 :                 pFormat = pOtherDoc->CopyCharFormat( *pFormat );
    1514             :             }
    1515             :             const_cast<SwFormatCharFormat&>( static_cast<const SwFormatCharFormat&>(
    1516         244 :                 pNewHt->GetCharFormat() ) ).SetCharFormat( pFormat );
    1517             :         }
    1518         244 :         break;
    1519             :     case RES_TXTATR_INETFMT :
    1520             :         {
    1521             :             // Wenn wir es mit benutzerdefinierten INet-Zeichenvorlagen
    1522             :             // zu tun haben, muessen wir natuerlich auch die Formate kopieren.
    1523          59 :             if( pOtherDoc && pDest && pDest->GetpSwpHints()
    1524          59 :                 && pDest->GetpSwpHints()->Contains( pNewHt ) )
    1525             :             {
    1526             :                 const SwDoc* const pDoc = static_txtattr_cast<
    1527           0 :                         const SwTextINetFormat*>(pHt)->GetTextNode().GetDoc();
    1528           0 :                 if ( pDoc )
    1529             :                 {
    1530           0 :                     const SwCharFormats* pCharFormats = pDoc->GetCharFormats();
    1531           0 :                     const SwFormatINetFormat& rFormat = pHt->GetINetFormat();
    1532             :                     SwCharFormat* pFormat;
    1533           0 :                     pFormat = lcl_FindCharFormat( pCharFormats, rFormat.GetINetFormat() );
    1534           0 :                     if( pFormat )
    1535           0 :                         pOtherDoc->CopyCharFormat( *pFormat );
    1536           0 :                     pFormat = lcl_FindCharFormat( pCharFormats, rFormat.GetVisitedFormat() );
    1537           0 :                     if( pFormat )
    1538           0 :                         pOtherDoc->CopyCharFormat( *pFormat );
    1539             :                 }
    1540             :             }
    1541             :             //JP 24.04.98: Bug 49753 - ein TextNode muss am Attribut
    1542             :             //              gesetzt sein, damit die Vorlagen erzeugt
    1543             :             //              werden koenne
    1544          59 :             SwTextINetFormat *const pINetHt = static_txtattr_cast<SwTextINetFormat*>(pNewHt);
    1545          59 :             if ( !pINetHt->GetpTextNode() )
    1546             :             {
    1547           0 :                 pINetHt->ChgTextNode( pDest );
    1548             :             }
    1549             : 
    1550             :             //JP 22.10.97: Bug 44875 - Verbindung zum Format herstellen
    1551          59 :             pINetHt->GetCharFormat();
    1552          59 :             break;
    1553             :         }
    1554             :     case RES_TXTATR_META:
    1555             :     case RES_TXTATR_METAFIELD:
    1556             :         OSL_ENSURE( pNewHt, "copying Meta should not fail!" );
    1557             :         OSL_ENSURE( pDest
    1558             :                     && (CH_TXTATR_INWORD == pDest->GetText()[pNewHt->GetStart()]),
    1559             :             "missing CH_TXTATR?");
    1560           0 :         break;
    1561             :     }
    1562        3063 : }
    1563             : 
    1564             : //  Beschreibung    kopiert Attribute an der Position nStart in pDest.
    1565             : //  BP 7.6.93:      Es werden mit Absicht nur die Attribute _mit_ EndIdx
    1566             : //                  kopiert! CopyAttr wird vornehmlich dann gerufen,
    1567             : //                  wenn Attribute fuer einen Node mit leerem String
    1568             : //                  gesetzt werden sollen.
    1569        7584 : void SwTextNode::CopyAttr( SwTextNode *pDest, const sal_Int32 nTextStartIdx,
    1570             :                           const sal_Int32 nOldPos )
    1571             : {
    1572        7584 :     if ( HasHints() )    // keine Attribute, keine Kekse
    1573             :     {
    1574        1657 :         SwDoc* const pOtherDoc = (pDest->GetDoc() != GetDoc()) ?
    1575        1657 :                 pDest->GetDoc() : 0;
    1576             : 
    1577        1749 :         for ( size_t i = 0; i < m_pSwpHints->Count(); ++i )
    1578             :         {
    1579          92 :             SwTextAttr *const pHt = m_pSwpHints->GetTextHint(i);
    1580          92 :             sal_Int32 const nAttrStartIdx = pHt->GetStart();
    1581          92 :             if ( nTextStartIdx < nAttrStartIdx )
    1582           0 :                 break; // ueber das Textende, da nLen == 0
    1583             : 
    1584          92 :             const sal_Int32 *const pEndIdx = pHt->GetEnd();
    1585          92 :             if ( pEndIdx && !pHt->HasDummyChar() )
    1586             :             {
    1587          92 :                 sal_uInt16 const nWhich = pHt->Which();
    1588          92 :                 if (RES_TXTATR_INPUTFIELD != nWhich // fdo#74981 skip fields
    1589          91 :                     && (    *pEndIdx > nTextStartIdx
    1590          91 :                         || (*pEndIdx == nTextStartIdx
    1591          91 :                             && nAttrStartIdx == nTextStartIdx)))
    1592             :                 {
    1593          91 :                     if ( RES_TXTATR_REFMARK != nWhich )
    1594             :                     {
    1595             :                         // attribute in the area => copy
    1596             :                         SwTextAttr *const pNewHt =
    1597          91 :                             pDest->InsertItem( pHt->GetAttr(), nOldPos, nOldPos, SetAttrMode::IS_COPY);
    1598          91 :                         if ( pNewHt )
    1599             :                         {
    1600             :                             lcl_CopyHint( nWhich, pHt, pNewHt,
    1601          81 :                                 pOtherDoc, pDest );
    1602             :                         }
    1603             :                     }
    1604           0 :                     else if( !pOtherDoc
    1605           0 :                              ? GetDoc()->IsCopyIsMove()
    1606           0 :                              : 0 == pOtherDoc->GetRefMark( pHt->GetRefMark().GetRefName() ) )
    1607             :                     {
    1608             :                         pDest->InsertItem(
    1609           0 :                             pHt->GetAttr(), nOldPos, nOldPos, SetAttrMode::IS_COPY);
    1610             :                     }
    1611             :                 }
    1612             :             }
    1613             :         }
    1614             :     }
    1615             : 
    1616        7584 :     if( this != pDest )
    1617             :     {
    1618             :         // Frames benachrichtigen, sonst verschwinden die Footnote-Nummern
    1619             :         SwUpdateAttr aHint(
    1620             :             nOldPos,
    1621             :             nOldPos,
    1622        7584 :             0);
    1623             : 
    1624        7584 :         pDest->ModifyNotification( 0, &aHint );
    1625             :     }
    1626        7584 : }
    1627             : 
    1628             : // kopiert Zeichen und Attibute in pDest, wird angehaengt
    1629             : // introduction of new optional parameter to control, if all attributes have to be copied.
    1630        6914 : void SwTextNode::CopyText( SwTextNode *const pDest,
    1631             :                       const SwIndex &rStart,
    1632             :                       const sal_Int32 nLen,
    1633             :                       const bool bForceCopyOfAllAttrs )
    1634             : {
    1635        6914 :     SwIndex const aIdx( pDest, pDest->m_Text.getLength() );
    1636        6914 :     CopyText( pDest, aIdx, rStart, nLen, bForceCopyOfAllAttrs );
    1637        6914 : }
    1638             : 
    1639             : // introduction of new optional parameter to control, if all attributes have to be copied.
    1640        7214 : void SwTextNode::CopyText( SwTextNode *const pDest,
    1641             :                       const SwIndex &rDestStart,
    1642             :                       const SwIndex &rStart,
    1643             :                       sal_Int32 nLen,
    1644             :                       const bool bForceCopyOfAllAttrs )
    1645             : {
    1646        7214 :     sal_Int32 nTextStartIdx = rStart.GetIndex();
    1647        7214 :     sal_Int32 nDestStart = rDestStart.GetIndex();      // alte Pos merken
    1648             : 
    1649        7214 :     if (pDest->GetDoc()->IsClipBoard() && this->GetNum())
    1650             :     {
    1651             :         // #i111677# cache expansion of source (for clipboard)
    1652             :         pDest->m_pNumStringCache.reset( (nTextStartIdx != 0)
    1653           0 :             ? new OUString // fdo#49076: numbering only if copy from para start
    1654           0 :             : new OUString(this->GetNumString()));
    1655             :     }
    1656             : 
    1657        7214 :     if( !nLen )
    1658             :     {
    1659             :         // wurde keine Laenge angegeben, dann Kopiere die Attribute
    1660             :         // an der Position rStart.
    1661        4134 :         CopyAttr( pDest, nTextStartIdx, nDestStart );
    1662             : 
    1663             :         // harte Absatz umspannende Attribute kopieren
    1664        4134 :         if( HasSwAttrSet() )
    1665             :         {
    1666             :             // alle, oder nur die CharAttribute ?
    1667             :             // #i96213#
    1668        1102 :             if ( !bForceCopyOfAllAttrs &&
    1669         156 :                  ( nDestStart ||
    1670         312 :                    pDest->HasSwAttrSet() ||
    1671         156 :                    nLen != pDest->GetText().getLength()))
    1672             :             {
    1673           0 :                 SfxItemSet aCharSet( pDest->GetDoc()->GetAttrPool(),
    1674             :                                     RES_CHRATR_BEGIN, RES_CHRATR_END-1,
    1675             :                                     RES_TXTATR_INETFMT, RES_TXTATR_INETFMT,
    1676             :                                     RES_TXTATR_CHARFMT, RES_TXTATR_CHARFMT,
    1677             :                                     RES_UNKNOWNATR_BEGIN, RES_UNKNOWNATR_END-1,
    1678           0 :                                     0 );
    1679           0 :                 aCharSet.Put( *GetpSwAttrSet() );
    1680           0 :                 if( aCharSet.Count() )
    1681             :                 {
    1682           0 :                     pDest->SetAttr( aCharSet, nDestStart, nDestStart );
    1683           0 :                 }
    1684             :             }
    1685             :             else
    1686             :             {
    1687        1102 :                 GetpSwAttrSet()->CopyToModify( *pDest );
    1688             :             }
    1689             :         }
    1690        8268 :         return;
    1691             :     }
    1692             : 
    1693             :     // 1. Text kopieren
    1694        3080 :     const sal_Int32 oldLen = pDest->m_Text.getLength();
    1695             :     //JP 15.02.96: Bug 25537 - Attributbehandlung am Ende fehlt! Darum
    1696             :     //              ueber die InsertMethode den Text einfuegen und nicht
    1697             :     //              selbst direkt
    1698             :     pDest->InsertText( m_Text.copy(nTextStartIdx, nLen), rDestStart,
    1699        3080 :                    SwInsertFlags::EMPTYEXPAND );
    1700             : 
    1701             :     // um reale Groesse Updaten !
    1702        3080 :     nLen = pDest->m_Text.getLength() - oldLen;
    1703        3080 :     if ( !nLen ) // string not longer?
    1704           0 :         return;
    1705             : 
    1706        3080 :     SwDoc* const pOtherDoc = (pDest->GetDoc() != GetDoc()) ? pDest->GetDoc() : 0;
    1707             : 
    1708             :     // harte Absatz umspannende Attribute kopieren
    1709        3080 :     if( HasSwAttrSet() )
    1710             :     {
    1711             :         // alle, oder nur die CharAttribute ?
    1712             :         // #i96213#
    1713        1833 :         if ( !bForceCopyOfAllAttrs &&
    1714          69 :              ( nDestStart ||
    1715         137 :                pDest->HasSwAttrSet() ||
    1716          68 :                nLen != pDest->GetText().getLength()))
    1717             :         {
    1718           5 :             SfxItemSet aCharSet( pDest->GetDoc()->GetAttrPool(),
    1719             :                 RES_CHRATR_BEGIN, RES_CHRATR_END-1,
    1720             :                 RES_TXTATR_INETFMT, RES_TXTATR_INETFMT,
    1721             :                 RES_TXTATR_CHARFMT, RES_TXTATR_CHARFMT,
    1722             :                 RES_UNKNOWNATR_BEGIN, RES_UNKNOWNATR_END-1,
    1723           5 :                 0 );
    1724           5 :             aCharSet.Put( *GetpSwAttrSet() );
    1725           5 :             if( aCharSet.Count() )
    1726             :             {
    1727           5 :                 pDest->SetAttr( aCharSet, nDestStart, nDestStart + nLen );
    1728           5 :             }
    1729             :         }
    1730             :         else
    1731             :         {
    1732        1823 :             GetpSwAttrSet()->CopyToModify( *pDest );
    1733             :         }
    1734             :     }
    1735             : 
    1736             :     bool const bUndoNodes = !pOtherDoc
    1737        3080 :                             && GetDoc()->GetIDocumentUndoRedo().IsUndoNodes(GetNodes());
    1738             : 
    1739             :     // Ende erst jetzt holen, weil beim Kopieren in sich selbst der
    1740             :     // Start-Index und alle Attribute vorher aktualisiert werden.
    1741        3080 :     nTextStartIdx = rStart.GetIndex();
    1742        3080 :     const sal_Int32 nEnd = nTextStartIdx + nLen;
    1743             : 
    1744             :     // 2. Attribute kopieren
    1745             :     // durch das Attribute-Array, bis der Anfang des Geltungsbereiches
    1746             :     // des Attributs hinter dem zu kopierenden Bereich liegt
    1747        3080 :     const size_t nSize = m_pSwpHints ? m_pSwpHints->Count() : 0;
    1748             : 
    1749             :     // wird in sich selbst kopiert, dann kann beim Einfuegen ein
    1750             :     // Attribut geloescht werden. Darum erst ins Tmp-Array kopieren und
    1751             :     // dann erst ins eigene uebertragen.
    1752        3080 :     SwpHts aArr;
    1753             : 
    1754             :     // Del-Array fuer alle RefMarks ohne Ausdehnung
    1755        6160 :     SwpHts aRefMrkArr;
    1756             : 
    1757        3080 :     sal_Int32 nDeletedDummyChars(0);
    1758             :     //Achtung: kann ungueltig sein!!
    1759        6040 :     for (size_t n = 0; n < nSize; ++n)
    1760             :     {
    1761        3823 :         const sal_Int32 nAttrStartIdx = (*m_pSwpHints)[n]->GetStart();
    1762        3823 :         if (!( nAttrStartIdx < nEnd))
    1763         863 :             break;
    1764             : 
    1765        2960 :         SwTextAttr * const pHt = m_pSwpHints->GetTextHint(n);
    1766        2960 :         const sal_Int32 * const pEndIdx = pHt->GetEnd();
    1767        2960 :         const sal_uInt16 nWhich = pHt->Which();
    1768             : 
    1769             :         // JP 26.04.94: REFMARK's werden nie kopiert. Hat das Refmark aber
    1770             :         //              keinen Bereich umspannt, so steht im Text ein 255
    1771             :         //              dieses muss entfernt werden. Trick: erst kopieren,
    1772             :         //              erkennen und sammeln, nach dem kopieren Loeschen.
    1773             :         //              Nimmt sein Zeichen mit ins Grab !!
    1774             :         // JP 14.08.95: Duerfen RefMarks gemovt werden?
    1775             :         const bool bCopyRefMark = RES_TXTATR_REFMARK == nWhich
    1776        2960 :                                   && ( bUndoNodes
    1777           0 :                                        || ( !pOtherDoc
    1778           0 :                                             ? GetDoc()->IsCopyIsMove()
    1779        2960 :                                             : 0 == pOtherDoc->GetRefMark( pHt->GetRefMark().GetRefName() ) ) );
    1780             : 
    1781        2960 :         if ( pEndIdx
    1782        2022 :              && RES_TXTATR_REFMARK == nWhich
    1783           0 :              && !bCopyRefMark )
    1784             :         {
    1785           0 :             continue;
    1786             :         }
    1787             : 
    1788             :         // Input Fields are only copied, if completely covered by copied text
    1789        2960 :         if ( nWhich == RES_TXTATR_INPUTFIELD )
    1790             :         {
    1791             :             OSL_ENSURE( pEndIdx != NULL,
    1792             :                     "<SwTextNode::CopyText(..)> - RES_TXTATR_INPUTFIELD without EndIndex!" );
    1793           4 :             if ( nAttrStartIdx < nTextStartIdx
    1794           4 :                  || ( pEndIdx != NULL
    1795           4 :                       && *(pEndIdx) > nEnd ) )
    1796             :             {
    1797           0 :                 continue;
    1798             :             }
    1799             :         }
    1800             : 
    1801        2960 :         sal_Int32 nAttrStt = 0;
    1802        2960 :         sal_Int32 nAttrEnd = 0;
    1803             : 
    1804        2960 :         if( nAttrStartIdx < nTextStartIdx )
    1805             :         {
    1806             :             // start is before selection
    1807             :             // copy hints with end and CH_TXTATR only if dummy char is copied
    1808           0 :             if ( pEndIdx && (*pEndIdx > nTextStartIdx) && !pHt->HasDummyChar() )
    1809             :             {
    1810             :                 // attribute with extent and the end is in the selection
    1811           0 :                 nAttrStt = nDestStart;
    1812           0 :                 nAttrEnd = (*pEndIdx > nEnd)
    1813             :                     ? rDestStart.GetIndex()
    1814           0 :                     : nDestStart + (*pEndIdx) - nTextStartIdx;
    1815             :             }
    1816             :             else
    1817             :             {
    1818           0 :                 continue;
    1819             :             }
    1820             :         }
    1821             :         else
    1822             :         {
    1823             :             // start is in the selection
    1824        2960 :             nAttrStt = nDestStart + ( nAttrStartIdx - nTextStartIdx );
    1825        2960 :             if( pEndIdx )
    1826             :             {
    1827        2022 :                 nAttrEnd = *pEndIdx > nEnd
    1828             :                     ? rDestStart.GetIndex()
    1829        2022 :                     : nDestStart + ( *pEndIdx - nTextStartIdx );
    1830             :             }
    1831             :             else
    1832             :             {
    1833         938 :                 nAttrEnd = nAttrStt;
    1834             :             }
    1835             :         }
    1836             : 
    1837        2960 :         SwTextAttr * pNewHt = 0;
    1838             : 
    1839        2960 :         if( pDest == this )
    1840             :         {
    1841             :             // copy the hint here, but insert it later
    1842           0 :             pNewHt = MakeTextAttr( *GetDoc(), pHt->GetAttr(),
    1843           0 :                     nAttrStt, nAttrEnd, COPY, pDest );
    1844             : 
    1845           0 :             lcl_CopyHint(nWhich, pHt, pNewHt, 0, pDest);
    1846           0 :             aArr.push_back( pNewHt );
    1847             :         }
    1848             :         else
    1849             :         {
    1850             :             pNewHt = pDest->InsertItem(
    1851        2960 :                 pHt->GetAttr(),
    1852             :                 nAttrStt - nDeletedDummyChars,
    1853             :                 nAttrEnd - nDeletedDummyChars,
    1854        5920 :                 SetAttrMode::NOTXTATRCHR | SetAttrMode::IS_COPY);
    1855        2960 :             if (pNewHt)
    1856             :             {
    1857        2960 :                 lcl_CopyHint( nWhich, pHt, pNewHt, pOtherDoc, pDest );
    1858             :             }
    1859           0 :             else if (pHt->HasDummyChar())
    1860             :             {
    1861             :                 // The attribute that has failed to be copied would insert
    1862             :                 // dummy char, so positions of the following attributes have
    1863             :                 // to be shifted by one to compensate for that missing char.
    1864           0 :                 ++nDeletedDummyChars;
    1865             :             }
    1866             :         }
    1867             : 
    1868        2960 :         if( RES_TXTATR_REFMARK == nWhich && !pEndIdx && !bCopyRefMark )
    1869             :         {
    1870           0 :             aRefMrkArr.push_back( pNewHt );
    1871             :         }
    1872             :     }
    1873             : 
    1874             :     // nur falls im Array Attribute stehen (kann nur beim Kopieren
    1875             :     // sich selbst passieren!!)
    1876        3080 :     for ( size_t i = 0; i < aArr.size(); ++i )
    1877             :     {
    1878           0 :         InsertHint( aArr[ i ], SetAttrMode::NOTXTATRCHR );
    1879             :     }
    1880             : 
    1881        3080 :     if( pDest->GetpSwpHints() )
    1882             :     {
    1883        1965 :         for ( size_t i = 0; i < aRefMrkArr.size(); ++i )
    1884             :         {
    1885           0 :             SwTextAttr * const pNewHt = aRefMrkArr[i];
    1886           0 :             if( pNewHt->GetEnd() )
    1887             :             {
    1888           0 :                 pDest->GetpSwpHints()->Delete( pNewHt );
    1889           0 :                 pDest->DestroyAttr( pNewHt );
    1890             :             }
    1891             :             else
    1892             :             {
    1893           0 :                 const SwIndex aIdx( pDest, pNewHt->GetStart() );
    1894           0 :                 pDest->EraseText( aIdx, 1 );
    1895             :             }
    1896             :         }
    1897             :     }
    1898             : 
    1899             :     CHECK_SWPHINTS(this);
    1900        3080 :     CHECK_SWPHINTS(pDest);
    1901             : }
    1902             : 
    1903      154410 : OUString SwTextNode::InsertText( const OUString & rStr, const SwIndex & rIdx,
    1904             :         const SwInsertFlags nMode )
    1905             : {
    1906             :     assert(rIdx <= m_Text.getLength()); // invalid index
    1907             : 
    1908      154410 :     const sal_Int32 aPos = rIdx.GetIndex();
    1909      154410 :     sal_Int32 nLen = m_Text.getLength() - aPos;
    1910      154410 :     sal_Int32 const nOverflow(rStr.getLength() - GetSpaceLeft());
    1911             :     SAL_WARN_IF(nOverflow > 0, "sw.core",
    1912             :             "SwTextNode::InsertText: node text with insertion > capacity.");
    1913             :     OUString const sInserted(
    1914      154410 :         (nOverflow > 0) ? rStr.copy(0, rStr.getLength() - nOverflow) : rStr);
    1915      154410 :     if (sInserted.isEmpty())
    1916             :     {
    1917         287 :         return sInserted;
    1918             :     }
    1919      154123 :     m_Text = m_Text.replaceAt(aPos, 0, sInserted);
    1920             :     assert(GetSpaceLeft()>=0);
    1921      154123 :     nLen = m_Text.getLength() - aPos - nLen;
    1922             :     assert(nLen != 0);
    1923             : 
    1924      154123 :     bool bOldExpFlg = IsIgnoreDontExpand();
    1925      154123 :     if (nMode & SwInsertFlags::FORCEHINTEXPAND)
    1926             :     {
    1927          61 :         SetIgnoreDontExpand( true );
    1928             :     }
    1929             : 
    1930      154123 :     Update( rIdx, nLen ); // text content changed!
    1931             : 
    1932      154123 :     if (nMode & SwInsertFlags::FORCEHINTEXPAND)
    1933             :     {
    1934          61 :         SetIgnoreDontExpand( bOldExpFlg );
    1935             :     }
    1936             : 
    1937             :     // analog zu Insert(char) in txtedt.cxx:
    1938             :     // 1) bei bHintExp leere Hints an rIdx.GetIndex suchen und aufspannen
    1939             :     // 2) bei bHintExp == false mitgezogene Feldattribute zuruecksetzen
    1940             : 
    1941      154123 :     if ( HasHints() )
    1942             :     {
    1943       25945 :         bool bMergePortionsNeeded(false);
    1944      400706 :         for ( size_t i = 0; i < m_pSwpHints->Count() &&
    1945      187457 :                 rIdx >= (*m_pSwpHints)[i]->GetStart(); ++i )
    1946             :         {
    1947      187304 :             SwTextAttr * const pHt = m_pSwpHints->GetTextHint( i );
    1948      187304 :             sal_Int32 * const pEndIdx = pHt->GetEnd();
    1949      187304 :             if( !pEndIdx )
    1950      116133 :                 continue;
    1951             : 
    1952       71171 :             if( rIdx == *pEndIdx )
    1953             :             {
    1954        1479 :                 if (  (nMode & SwInsertFlags::NOHINTEXPAND) ||
    1955         882 :                     (!(nMode & SwInsertFlags::FORCEHINTEXPAND)
    1956         528 :                      && pHt->DontExpand()) )
    1957             :                 {
    1958             :                     // bei leeren Attributen auch Start veraendern
    1959           9 :                     if( rIdx == pHt->GetStart() )
    1960           9 :                         pHt->GetStart() = pHt->GetStart() - nLen;
    1961           9 :                     *pEndIdx = *pEndIdx - nLen;
    1962           9 :                     m_pSwpHints->DeleteAtPos(i);
    1963             :                     // could be that pHt has IsFormatIgnoreEnd set, and it's
    1964             :                     // not a RSID-only hint - now we have the inserted text
    1965             :                     // between pHt and its continuation... which we don't know.
    1966             :                     // punt the job to MergePortions below.
    1967           9 :                     if (pHt->IsFormatIgnoreEnd())
    1968             :                     {
    1969           0 :                         bMergePortionsNeeded = true;
    1970             :                     }
    1971           9 :                     InsertHint( pHt, SetAttrMode::NOHINTADJUST );
    1972             :                 }
    1973             :                 // empty hints at insert position?
    1974         570 :                 else if ( (nMode & SwInsertFlags::EMPTYEXPAND)
    1975         570 :                         && (*pEndIdx == pHt->GetStart()) )
    1976             :                 {
    1977           1 :                     pHt->GetStart() = pHt->GetStart() - nLen;
    1978           1 :                     const size_t nAktLen = m_pSwpHints->Count();
    1979           1 :                     m_pSwpHints->DeleteAtPos(i);
    1980           1 :                     InsertHint( pHt/* AUTOSTYLES:, SetAttrMode::NOHINTADJUST*/ );
    1981           1 :                     if ( nAktLen > m_pSwpHints->Count() && i )
    1982             :                     {
    1983           0 :                         --i;
    1984             :                     }
    1985           1 :                     continue;
    1986             :                 }
    1987             :                 else
    1988             :                 {
    1989         284 :                     continue;
    1990             :                 }
    1991             :             }
    1992      283544 :             if ( !(nMode & SwInsertFlags::NOHINTEXPAND) &&
    1993      212868 :                  rIdx == nLen && pHt->GetStart() == rIdx.GetIndex() &&
    1994         103 :                  !pHt->IsDontExpandStartAttr() )
    1995             :             {
    1996             :                 // Kein Feld, am Absatzanfang, HintExpand
    1997         102 :                 m_pSwpHints->DeleteAtPos(i);
    1998         102 :                 pHt->GetStart() = pHt->GetStart() - nLen;
    1999             :                 // no effect on format ignore flags here (para start)
    2000         102 :                 InsertHint( pHt, SetAttrMode::NOHINTADJUST );
    2001             :             }
    2002             :         }
    2003       25945 :         if (bMergePortionsNeeded)
    2004             :         {
    2005           0 :             m_pSwpHints->MergePortions(*this);
    2006             :         }
    2007       25945 :         TryDeleteSwpHints();
    2008             :     }
    2009             : 
    2010      154123 :     if ( HasWriterListeners() )
    2011             :     {
    2012       10312 :         SwInsText aHint( aPos, nLen );
    2013       10312 :         NotifyClients( 0, &aHint );
    2014             :     }
    2015             : 
    2016             :     // By inserting a character, the hidden flags
    2017             :     // at the TextNode can become invalid:
    2018      154123 :     SetCalcHiddenCharFlags();
    2019             : 
    2020             :     CHECK_SWPHINTS(this);
    2021      154123 :     return sInserted;
    2022             : }
    2023             : 
    2024        4443 : void SwTextNode::CutText( SwTextNode * const pDest,
    2025             :             const SwIndex & rStart, const sal_Int32 nLen )
    2026             : {
    2027             :     assert(pDest); // Cut requires a destination
    2028        4443 :     SwIndex aDestStt(pDest, pDest->GetText().getLength());
    2029        4443 :     CutImpl( pDest, aDestStt, rStart, nLen, false );
    2030        4443 : }
    2031             : 
    2032        4675 : void SwTextNode::CutImpl( SwTextNode * const pDest, const SwIndex & rDestStart,
    2033             :          const SwIndex & rStart, sal_Int32 nLen, const bool bUpdate )
    2034             : {
    2035             :     assert(pDest); // Cut requires a destination
    2036             : 
    2037             :     assert(GetDoc() == pDest->GetDoc()); // must be same document
    2038             : 
    2039             :     assert(pDest != this); // destination must be different node
    2040             : 
    2041        4675 :     if( !nLen )
    2042             :     {
    2043             :         // wurde keine Laenge angegeben, dann Kopiere die Attribute
    2044             :         // an der Position rStart.
    2045        3448 :         CopyAttr( pDest, rStart.GetIndex(), rDestStart.GetIndex() );
    2046        6896 :         return;
    2047             :     }
    2048             : 
    2049        1227 :     sal_Int32 nTextStartIdx = rStart.GetIndex();
    2050        1227 :     sal_Int32 nDestStart = rDestStart.GetIndex();      // alte Pos merken
    2051        1227 :     const sal_Int32 nInitSize = pDest->m_Text.getLength();
    2052             : 
    2053        2454 :     pDest->m_Text = pDest->m_Text.replaceAt(nDestStart, 0,
    2054        1227 :                         m_Text.copy(nTextStartIdx, nLen));
    2055        1227 :     m_Text = m_Text.replaceAt(nTextStartIdx, nLen, "");
    2056        1227 :     if (GetSpaceLeft() < 0)
    2057             :     {   // FIXME: could only happen when called from SwRangeRedline::Show.
    2058             :         // unfortunately can't really do anything here to handle that...
    2059           0 :         abort();
    2060             :     }
    2061        1227 :     nLen = pDest->m_Text.getLength() - nInitSize; // update w/ current size!
    2062        1227 :     if (!nLen)                 // String nicht gewachsen ??
    2063           0 :         return;
    2064             : 
    2065        1227 :     if (bUpdate)
    2066             :     {
    2067             :         // Update aller Indizies
    2068          54 :         pDest->Update( rDestStart, nLen, false, true);
    2069             :     }
    2070             : 
    2071             :     CHECK_SWPHINTS(pDest);
    2072             : 
    2073        1227 :     const sal_Int32 nEnd = rStart.GetIndex() + nLen;
    2074             :     bool const bUndoNodes =
    2075        1227 :         GetDoc()->GetIDocumentUndoRedo().IsUndoNodes(GetNodes());
    2076             : 
    2077             :     // harte Absatz umspannende Attribute kopieren
    2078        1227 :     if (HasSwAttrSet())
    2079             :     {
    2080             :         // alle, oder nur die CharAttribute ?
    2081        1251 :         if( nInitSize || pDest->HasSwAttrSet() ||
    2082          76 :             nLen != pDest->GetText().getLength())
    2083             :         {
    2084        1099 :             SfxItemSet aCharSet( pDest->GetDoc()->GetAttrPool(),
    2085             :                                 RES_CHRATR_BEGIN, RES_CHRATR_END-1,
    2086             :                                 RES_TXTATR_INETFMT, RES_TXTATR_INETFMT,
    2087             :                                 RES_TXTATR_CHARFMT, RES_TXTATR_CHARFMT,
    2088             :                                 RES_UNKNOWNATR_BEGIN, RES_UNKNOWNATR_END-1,
    2089        1099 :                                 0 );
    2090        1099 :             aCharSet.Put( *GetpSwAttrSet() );
    2091        1099 :             if( aCharSet.Count() )
    2092        1061 :                 pDest->SetAttr( aCharSet, nDestStart, nDestStart + nLen );
    2093             :         }
    2094             :         else
    2095             :         {
    2096          76 :             GetpSwAttrSet()->CopyToModify( *pDest );
    2097             :         }
    2098             :     }
    2099             : 
    2100             :     // 2. Attribute verschieben
    2101             :     // durch das Attribute-Array, bis der Anfang des Geltungsbereiches
    2102             :     // des Attributs hinter dem zu verschiebenden Bereich liegt
    2103        1227 :     bool bMergePortionsNeeded(false);
    2104        1227 :     size_t nAttrCnt = 0;
    2105        2522 :     while (m_pSwpHints && (nAttrCnt < m_pSwpHints->Count()))
    2106             :     {
    2107          70 :         SwTextAttr * const pHt = m_pSwpHints->GetTextHint(nAttrCnt);
    2108          70 :         const sal_Int32 nAttrStartIdx = pHt->GetStart();
    2109          70 :         if (!( nAttrStartIdx < nEnd ))
    2110           2 :             break;
    2111          68 :         const sal_Int32 * const pEndIdx = pHt->GetEnd();
    2112          68 :         const sal_uInt16 nWhich = pHt->Which();
    2113          68 :         SwTextAttr *pNewHt = 0;
    2114             : 
    2115             :         // if the hint has a dummy character, then it must not be split!
    2116          68 :         if(nAttrStartIdx < nTextStartIdx)
    2117             :         {
    2118             :             // Anfang liegt vor dem Bereich
    2119           0 :             if (!pHt->HasDummyChar() && ( RES_TXTATR_REFMARK != nWhich
    2120           0 :                 || bUndoNodes ) && pEndIdx && *pEndIdx > nTextStartIdx)
    2121             :             {
    2122             :                 // Attribut mit einem Bereich
    2123             :                 // und das Ende des Attribut liegt im Bereich
    2124           0 :                 pNewHt = MakeTextAttr( *pDest->GetDoc(), pHt->GetAttr(),
    2125             :                                 nDestStart,
    2126             :                                 nDestStart + (
    2127           0 :                                     *pEndIdx > nEnd
    2128             :                                         ? nLen
    2129           0 :                                         : *pEndIdx - nTextStartIdx ) );
    2130             :             }
    2131             :         }
    2132             :         else
    2133             :         {
    2134             :             // der Anfang liegt vollstaendig im Bereich
    2135         148 :             if (!pEndIdx || *pEndIdx < nEnd ||
    2136          44 :                 (!bUndoNodes && RES_TXTATR_REFMARK == nWhich)
    2137          90 :                 || pHt->HasDummyChar() )
    2138             :             {
    2139             :                 // do not delete note and later add it -> sidebar flickering
    2140          46 :                 if (GetDoc()->GetDocShell())
    2141             :                 {
    2142          46 :                     GetDoc()->GetDocShell()->Broadcast( SfxSimpleHint(SFX_HINT_USER04));
    2143             :                 }
    2144             :                 // Attribut verschieben
    2145          46 :                 m_pSwpHints->Delete( pHt );
    2146             :                 // die Start/End Indicies neu setzen
    2147          46 :                 if (pHt->IsFormatIgnoreStart() || pHt->IsFormatIgnoreEnd())
    2148             :                 {
    2149           0 :                     bMergePortionsNeeded = true;
    2150             :                 }
    2151          46 :                 pHt->GetStart() =
    2152          46 :                         nDestStart + (nAttrStartIdx - nTextStartIdx);
    2153          46 :                 if (pEndIdx)
    2154             :                 {
    2155         108 :                     *pHt->GetEnd() = nDestStart + (
    2156          36 :                                     *pEndIdx > nEnd
    2157             :                                         ? nLen
    2158          72 :                                         : *pEndIdx - nTextStartIdx );
    2159             :                 }
    2160             :                 pDest->InsertHint( pHt,
    2161             :                           SetAttrMode::NOTXTATRCHR
    2162          46 :                         | SetAttrMode::DONTREPLACE );
    2163          46 :                 if (GetDoc()->GetDocShell())
    2164             :                 {
    2165          46 :                     GetDoc()->GetDocShell()->Broadcast( SfxSimpleHint(SFX_HINT_USER04));
    2166             :                 }
    2167          46 :                 continue;           // while-Schleife weiter, ohne ++ !
    2168             :             }
    2169             :                 // das Ende liegt dahinter
    2170          22 :             else if (RES_TXTATR_REFMARK != nWhich || bUndoNodes)
    2171             :             {
    2172          22 :                 pNewHt = MakeTextAttr( *GetDoc(), pHt->GetAttr(),
    2173          22 :                               nDestStart + (nAttrStartIdx - nTextStartIdx),
    2174          22 :                               nDestStart + (*pEndIdx > nEnd
    2175             :                                              ? nLen
    2176          66 :                                              : *pEndIdx - nTextStartIdx));
    2177             :             }
    2178             :         }
    2179          22 :         if (pNewHt)
    2180             :         {
    2181             :             const bool bSuccess( pDest->InsertHint( pNewHt,
    2182             :                           SetAttrMode::NOTXTATRCHR
    2183             :                         | SetAttrMode::DONTREPLACE
    2184          22 :                         | SetAttrMode::IS_COPY) );
    2185          22 :             if (bSuccess)
    2186             :             {
    2187          22 :                 lcl_CopyHint( nWhich, pHt, pNewHt, nullptr, pDest );
    2188             :             }
    2189             :         }
    2190          22 :         ++nAttrCnt;
    2191             :     }
    2192             :     // sollten jetzt noch leere Attribute rumstehen, dann haben diese
    2193             :     // eine hoehere Praezedenz. Also herausholen und das Array updaten.
    2194             :     // Die dabei entstehenden leeren Hints werden von den gesicherten
    2195             :     // "uebergeplaettet".   (Bug: 6977)
    2196        1227 :     if (m_pSwpHints && nAttrCnt < m_pSwpHints->Count())
    2197             :     {
    2198           2 :         SwpHts aArr;
    2199           6 :         while (nAttrCnt < m_pSwpHints->Count())
    2200             :         {
    2201           2 :             SwTextAttr * const pHt = m_pSwpHints->GetTextHint(nAttrCnt);
    2202           2 :             if (nEnd != pHt->GetStart())
    2203           0 :                 break;
    2204           2 :             const sal_Int32 * const pEndIdx = pHt->GetEnd();
    2205           2 :             if (pEndIdx && *pEndIdx == nEnd)
    2206             :             {
    2207           2 :                 aArr.push_back( pHt );
    2208           2 :                 m_pSwpHints->Delete( pHt );
    2209             :             }
    2210             :             else
    2211             :             {
    2212           0 :                 ++nAttrCnt;
    2213             :             }
    2214             :         }
    2215           2 :         Update( rStart, nLen, true, true );
    2216             : 
    2217           4 :         for (size_t n = 0; n < aArr.size(); ++n)
    2218             :         {
    2219           2 :             SwTextAttr * const pHt = aArr[ n ];
    2220           2 :             pHt->GetStart() = *pHt->GetEnd() = rStart.GetIndex();
    2221           2 :             InsertHint( pHt );
    2222           2 :         }
    2223             :     }
    2224             :     else
    2225             :     {
    2226        1225 :         Update( rStart, nLen, true, true );
    2227             :     }
    2228             : 
    2229        1227 :     if (bMergePortionsNeeded)
    2230             :     {
    2231           0 :         m_pSwpHints->MergePortions(*this);
    2232             :     }
    2233             : 
    2234             :     CHECK_SWPHINTS(this);
    2235             : 
    2236        1227 :     TryDeleteSwpHints();
    2237             : 
    2238             :     // Frames benachrichtigen;
    2239        1227 :     SwInsText aInsHint( nDestStart, nLen );
    2240        1227 :     pDest->ModifyNotification( 0, &aInsHint );
    2241        2454 :     SwDelText aDelHint( nTextStartIdx, nLen );
    2242        2454 :     ModifyNotification( 0, &aDelHint );
    2243             : }
    2244             : 
    2245        5680 : void SwTextNode::EraseText(const SwIndex &rIdx, const sal_Int32 nCount,
    2246             :         const SwInsertFlags nMode )
    2247             : {
    2248             :     assert(rIdx <= m_Text.getLength()); // invalid index
    2249             : 
    2250        5680 :     const sal_Int32 nStartIdx = rIdx.GetIndex();
    2251             :     const sal_Int32 nCnt = (nCount==SAL_MAX_INT32)
    2252        5680 :                       ? m_Text.getLength() - nStartIdx : nCount;
    2253        5680 :     const sal_Int32 nEndIdx = nStartIdx + nCnt;
    2254        5680 :     m_Text = m_Text.replaceAt(nStartIdx, nCnt, "");
    2255             : 
    2256             :     /* GCAttr(); alle leeren weggwerfen ist zu brutal.
    2257             :      * Es duerfen nur die wegggeworfen werden,
    2258             :      * die im Bereich liegen und nicht am Ende des Bereiches liegen
    2259             :      */
    2260             : 
    2261       13337 :     for ( size_t i = 0; m_pSwpHints && i < m_pSwpHints->Count(); ++i )
    2262             :     {
    2263        7956 :         SwTextAttr *pHt = m_pSwpHints->GetTextHint(i);
    2264             : 
    2265        7956 :         const sal_Int32 nHintStart = pHt->GetStart();
    2266             : 
    2267        7956 :         if ( nHintStart < nStartIdx )
    2268        3082 :             continue;
    2269             : 
    2270        4874 :         if ( nHintStart > nEndIdx )
    2271         299 :             break; // hints are sorted by end, so break here
    2272             : 
    2273        4575 :         const sal_Int32* pHtEndIdx = pHt->GetEnd();
    2274        4575 :         const sal_uInt16 nWhich = pHt->Which();
    2275             : 
    2276        4575 :         if( !pHtEndIdx )
    2277             :         {
    2278             :                     // attribute with neither end nor CH_TXTATR?
    2279             :             assert(pHt->HasDummyChar());
    2280       12156 :             if (isTXTATR(nWhich) &&
    2281        8104 :                 (nHintStart >= nStartIdx) && (nHintStart < nEndIdx))
    2282             :             {
    2283        3786 :                 m_pSwpHints->DeleteAtPos(i);
    2284        3786 :                 DestroyAttr( pHt );
    2285        3786 :                 --i;
    2286             :             }
    2287        4052 :             continue;
    2288             :         }
    2289             : 
    2290             :        assert(!( (nHintStart < nEndIdx) && (*pHtEndIdx > nEndIdx)
    2291             :                     && pHt->HasDummyChar() )
    2292             :                 // next line: deleting exactly dummy char: DeleteAttributes
    2293             :                 || ((nHintStart == nStartIdx) && (nHintStart + 1 == nEndIdx)));
    2294             :                 // "ERROR: deleting left-overlapped attribute with CH_TXTATR");
    2295             : 
    2296             :         // Delete the hint if:
    2297             :         // 1. The hint ends before the deletion end position or
    2298             :         // 2. The hint ends at the deletion end position and
    2299             :         //    we are not in empty expand mode and
    2300             :         //    the hint is a [toxmark|refmark|ruby|inputfield] text attribute
    2301             :         // 3. deleting exactly the dummy char of an hint with end and dummy
    2302             :         //    char deletes the hint
    2303        1823 :         if (   (*pHtEndIdx < nEndIdx)
    2304        1004 :             || ( (*pHtEndIdx == nEndIdx)     &&
    2305        1599 :                  !(SwInsertFlags::EMPTYEXPAND & nMode)  &&
    2306         269 :                  (  (RES_TXTATR_TOXMARK == nWhich)  ||
    2307         269 :                     (RES_TXTATR_REFMARK == nWhich)  ||
    2308         268 :                     (RES_TXTATR_CJK_RUBY == nWhich) ||
    2309             :                     (RES_TXTATR_INPUTFIELD == nWhich) ) )
    2310        1724 :             || ( (nHintStart < nEndIdx)     &&
    2311         213 :                  pHt->HasDummyChar()        )
    2312             :            )
    2313             :         {
    2314          63 :             m_pSwpHints->DeleteAtPos(i);
    2315          63 :             DestroyAttr( pHt );
    2316          63 :             --i;
    2317             :         }
    2318             :     }
    2319             : 
    2320             :     OSL_ENSURE(rIdx.GetIndex() == nStartIdx, "huh? start index has changed?");
    2321             : 
    2322        5680 :     TryDeleteSwpHints();
    2323             : 
    2324        5680 :     Update( rIdx, nCnt, true );
    2325             : 
    2326        5680 :     if( 1 == nCnt )
    2327             :     {
    2328        5112 :         SwDelChr aHint( nStartIdx );
    2329        5112 :         NotifyClients( 0, &aHint );
    2330             :     }
    2331             :     else
    2332             :     {
    2333         568 :         SwDelText aHint( nStartIdx, nCnt );
    2334         568 :         NotifyClients( 0, &aHint );
    2335             :     }
    2336             : 
    2337             :     OSL_ENSURE(rIdx.GetIndex() == nStartIdx, "huh? start index has changed?");
    2338             : 
    2339             :     // By deleting a character, the hidden flags
    2340             :     // at the TextNode can become invalid:
    2341        5680 :     SetCalcHiddenCharFlags();
    2342             : 
    2343             :     CHECK_SWPHINTS(this);
    2344        5680 : }
    2345             : 
    2346           1 : void SwTextNode::GCAttr()
    2347             : {
    2348           1 :     if ( !HasHints() )
    2349           1 :         return;
    2350             : 
    2351           1 :     bool   bChanged = false;
    2352           1 :     sal_Int32 nMin = m_Text.getLength();
    2353           1 :     sal_Int32 nMax = 0;
    2354           1 :     const bool bAll = nMin != 0; // Bei leeren Absaetzen werden nur die
    2355             :                            // INet-Formate entfernt.
    2356             : 
    2357           2 :     for ( size_t i = 0; m_pSwpHints && i < m_pSwpHints->Count(); ++i )
    2358             :     {
    2359           1 :         SwTextAttr * const pHt = m_pSwpHints->GetTextHint(i);
    2360             : 
    2361             :         // wenn Ende und Start gleich sind --> loeschen
    2362           1 :         const sal_Int32 * const pEndIdx = pHt->GetEnd();
    2363           2 :         if (pEndIdx && !pHt->HasDummyChar() && (*pEndIdx == pHt->GetStart())
    2364           2 :             && ( bAll || pHt->Which() == RES_TXTATR_INETFMT ) )
    2365             :         {
    2366           0 :             bChanged = true;
    2367           0 :             nMin = std::min( nMin, pHt->GetStart() );
    2368           0 :             nMax = std::max( nMax, *pHt->GetEnd() );
    2369           0 :             DestroyAttr( m_pSwpHints->Cut(i) );
    2370           0 :             --i;
    2371             :         }
    2372             :         else
    2373             :         {
    2374           1 :             pHt->SetDontExpand( false );
    2375             :         }
    2376             :     }
    2377           1 :     TryDeleteSwpHints();
    2378             : 
    2379           1 :     if(bChanged)
    2380             :     {
    2381             :         //TextFrm's reagieren auf aHint, andere auf aNew
    2382             :         SwUpdateAttr aHint(
    2383             :             nMin,
    2384             :             nMax,
    2385           0 :             0);
    2386             : 
    2387           0 :         NotifyClients( 0, &aHint );
    2388           0 :         SwFormatChg aNew( GetTextColl() );
    2389           0 :         NotifyClients( 0, &aNew );
    2390             :     }
    2391             : }
    2392             : 
    2393             : // #i23726#
    2394      833863 : SwNumRule* SwTextNode::_GetNumRule(bool bInParent) const
    2395             : {
    2396      833863 :     SwNumRule* pRet = 0;
    2397             : 
    2398      833863 :     const SfxPoolItem* pItem = GetNoCondAttr( RES_PARATR_NUMRULE, bInParent );
    2399      833863 :     bool bNoNumRule = false;
    2400      833863 :     if ( pItem )
    2401             :     {
    2402             :         OUString sNumRuleName =
    2403      104016 :             static_cast<const SwNumRuleItem *>(pItem)->GetValue();
    2404      104016 :         if (!sNumRuleName.isEmpty())
    2405             :         {
    2406       99623 :             pRet = GetDoc()->FindNumRulePtr( sNumRuleName );
    2407             :         }
    2408             :         else // numbering is turned off
    2409        4393 :             bNoNumRule = true;
    2410             :     }
    2411             : 
    2412      833863 :     if ( !bNoNumRule )
    2413             :     {
    2414      843827 :         if ( pRet && pRet == GetDoc()->GetOutlineNumRule() &&
    2415       13642 :              ( !HasSwAttrSet() ||
    2416             :                SfxItemState::SET !=
    2417        6319 :                 GetpSwAttrSet()->GetItemState( RES_PARATR_NUMRULE, false ) ) )
    2418             :         {
    2419        7034 :             SwTextFormatColl* pColl = GetTextColl();
    2420        7034 :             if ( pColl )
    2421             :             {
    2422        7034 :                 const SwNumRuleItem& rDirectItem = pColl->GetNumRule( false );
    2423        7034 :                 if ( rDirectItem.GetValue().isEmpty() )
    2424             :                 {
    2425           0 :                     pRet = 0L;
    2426             :                 }
    2427             :             }
    2428             :         }
    2429             :     }
    2430             : 
    2431      833863 :     return pRet;
    2432             : }
    2433             : 
    2434      833863 : SwNumRule* SwTextNode::GetNumRule(bool bInParent) const
    2435             : {
    2436      833863 :     return _GetNumRule(bInParent);
    2437             : }
    2438             : 
    2439        5458 : void SwTextNode::NumRuleChgd()
    2440             : {
    2441        5458 :     if ( IsInList() )
    2442             :     {
    2443        5458 :         SwNumRule* pNumRule = GetNumRule();
    2444        5458 :         if ( pNumRule && pNumRule != GetNum()->GetNumRule() )
    2445             :         {
    2446           0 :             mpNodeNum->ChangeNumRule( *pNumRule );
    2447             :         }
    2448             :     }
    2449             : 
    2450        5458 :     if( IsInCache() )
    2451             :     {
    2452         103 :         SwFrm::GetCache().Delete( this );
    2453         103 :         SetInCache( false );
    2454             :     }
    2455        5458 :     SetInSwFntCache( false );
    2456             : 
    2457             :     // Sending "noop" modify in order to cause invalidations of registered
    2458             :     // <SwTextFrm> instances to get the list style change respectively the change
    2459             :     // in the list tree reflected in the layout.
    2460             :     // Important note:
    2461             :     {
    2462        5458 :         SvxLRSpaceItem& rLR = (SvxLRSpaceItem&)GetSwAttrSet().GetLRSpace();
    2463        5458 :         NotifyClients( &rLR, &rLR );
    2464             :     }
    2465             : 
    2466        5458 :     SetWordCountDirty( true );
    2467        5458 : }
    2468             : 
    2469             : // -> #i27615#
    2470       95100 : bool SwTextNode::IsNumbered() const
    2471             : {
    2472       95100 :     SwNumRule* pRule = GetNum() ? GetNum()->GetNumRule() : 0L;
    2473       95100 :     return pRule && IsCountedInList();
    2474             : }
    2475             : 
    2476         629 : bool SwTextNode::HasMarkedLabel() const
    2477             : {
    2478         629 :     bool bResult = false;
    2479             : 
    2480         629 :     if ( IsInList() )
    2481             :     {
    2482             :         bResult =
    2483         621 :             GetDoc()->getIDocumentListsAccess().getListByName( GetListId() )->IsListLevelMarked( GetActualListLevel() );
    2484             :     }
    2485             : 
    2486         629 :     return bResult;
    2487             : }
    2488             : // <- #i27615#
    2489             : 
    2490       37514 : SwTextNode* SwTextNode::_MakeNewTextNode( const SwNodeIndex& rPos, bool bNext,
    2491             :                                        bool bChgFollow )
    2492             : {
    2493             :     /* hartes PageBreak/PageDesc/ColumnBreak aus AUTO-Set ignorieren */
    2494       37514 :     SwAttrSet* pNewAttrSet = 0;
    2495             :     // #i75353#
    2496       37514 :     bool bClearHardSetNumRuleWhenFormatCollChanges( false );
    2497       37514 :     if( HasSwAttrSet() )
    2498             :     {
    2499        3051 :         pNewAttrSet = new SwAttrSet( *GetpSwAttrSet() );
    2500        3051 :         const SfxItemSet* pTmpSet = GetpSwAttrSet();
    2501             : 
    2502        3051 :         if( bNext )     // der naechste erbt keine Breaks!
    2503        1920 :             pTmpSet = pNewAttrSet;
    2504             : 
    2505             :         // PageBreaks/PageDesc/ColBreak rausschmeissen.
    2506        3051 :         bool bRemoveFromCache = false;
    2507        3051 :         std::vector<sal_uInt16> aClearWhichIds;
    2508        3051 :         if ( bNext )
    2509        1920 :             bRemoveFromCache = ( 0 != pNewAttrSet->ClearItem( RES_PAGEDESC ) );
    2510             :         else
    2511        1131 :             aClearWhichIds.push_back( RES_PAGEDESC );
    2512             : 
    2513        3051 :         if( SfxItemState::SET == pTmpSet->GetItemState( RES_BREAK, false ) )
    2514             :         {
    2515         532 :             if ( bNext )
    2516         222 :                 pNewAttrSet->ClearItem( RES_BREAK );
    2517             :             else
    2518         310 :                 aClearWhichIds.push_back( RES_BREAK );
    2519         532 :             bRemoveFromCache = true;
    2520             :         }
    2521        3051 :         if( SfxItemState::SET == pTmpSet->GetItemState( RES_KEEP, false ) )
    2522             :         {
    2523           0 :             if ( bNext )
    2524           0 :                 pNewAttrSet->ClearItem( RES_KEEP );
    2525             :             else
    2526           0 :                 aClearWhichIds.push_back( RES_KEEP );
    2527           0 :             bRemoveFromCache = true;
    2528             :         }
    2529        3051 :         if( SfxItemState::SET == pTmpSet->GetItemState( RES_PARATR_SPLIT, false ) )
    2530             :         {
    2531           0 :             if ( bNext )
    2532           0 :                 pNewAttrSet->ClearItem( RES_PARATR_SPLIT );
    2533             :             else
    2534           0 :                 aClearWhichIds.push_back( RES_PARATR_SPLIT );
    2535           0 :             bRemoveFromCache = true;
    2536             :         }
    2537        3051 :         if(SfxItemState::SET == pTmpSet->GetItemState(RES_PARATR_NUMRULE, false))
    2538             :         {
    2539         592 :             SwNumRule * pRule = GetNumRule();
    2540             : 
    2541         592 :             if (pRule && IsOutline())
    2542             :             {
    2543          15 :                 if ( bNext )
    2544          15 :                     pNewAttrSet->ClearItem(RES_PARATR_NUMRULE);
    2545             :                 else
    2546             :                 {
    2547             :                     // #i75353#
    2548             :                     // No clear of hard set numbering rule at an outline paragraph at this point.
    2549             :                     // Only if the paragraph style changes - see below.
    2550           0 :                     bClearHardSetNumRuleWhenFormatCollChanges = true;
    2551             :                 }
    2552          15 :                 bRemoveFromCache = true;
    2553             :             }
    2554             :         }
    2555             : 
    2556        3051 :         if ( !aClearWhichIds.empty() )
    2557        1131 :             bRemoveFromCache = 0 != ClearItemsFromAttrSet( aClearWhichIds );
    2558             : 
    2559        3051 :         if( !bNext && bRemoveFromCache && IsInCache() )
    2560             :         {
    2561          12 :             SwFrm::GetCache().Delete( this );
    2562          12 :             SetInCache( false );
    2563        3051 :         }
    2564             :     }
    2565       37514 :     SwNodes& rNds = GetNodes();
    2566             : 
    2567       37514 :     SwTextFormatColl* pColl = GetTextColl();
    2568             : 
    2569       37514 :     SwTextNode *pNode = new SwTextNode( rPos, pColl, pNewAttrSet );
    2570             : 
    2571       37514 :     delete pNewAttrSet;
    2572             : 
    2573       37514 :     const SwNumRule* pRule = GetNumRule();
    2574       37514 :     if( pRule && pRule == pNode->GetNumRule() && rNds.IsDocNodes() ) // #115901#
    2575             :     {
    2576             :         // #i55459#
    2577             :         // - correction: parameter <bNext> has to be checked, as it was in the
    2578             :         //   previous implementation.
    2579         747 :         if ( !bNext && !IsCountedInList() )
    2580           0 :             SetCountedInList(true);
    2581             :     }
    2582             : 
    2583             :     // jetzt kann es sein, das durch die Nummerierung dem neuen Node eine
    2584             :     // Vorlage aus dem Pool zugewiesen wurde. Dann darf diese nicht
    2585             :     // nochmal uebergeplaettet werden !!
    2586       37514 :     if( pColl != pNode->GetTextColl() ||
    2587       37461 :         ( bChgFollow && pColl != GetTextColl() ))
    2588           0 :         return pNode;       // mehr duerfte nicht gemacht werden oder ????
    2589             : 
    2590       37514 :     pNode->_ChgTextCollUpdateNum( 0, pColl ); // fuer Nummerierung/Gliederung
    2591       37514 :     if( bNext || !bChgFollow )
    2592       36191 :         return pNode;
    2593             : 
    2594        1323 :     SwTextFormatColl *pNextColl = &pColl->GetNextTextFormatColl();
    2595             :     // #i101870#
    2596             :     // perform action on different paragraph styles before applying the new paragraph style
    2597        1323 :     if (pNextColl != pColl)
    2598             :     {
    2599             :         // #i75353#
    2600           1 :         if ( bClearHardSetNumRuleWhenFormatCollChanges )
    2601             :         {
    2602           0 :             std::vector<sal_uInt16> aClearWhichIds;
    2603           0 :             aClearWhichIds.push_back( RES_PARATR_NUMRULE );
    2604           0 :             if ( ClearItemsFromAttrSet( aClearWhichIds ) != 0 && IsInCache() )
    2605             :             {
    2606           0 :                 SwFrm::GetCache().Delete( this );
    2607           0 :                 SetInCache( false );
    2608           0 :             }
    2609             :         }
    2610             :     }
    2611        1323 :     ChgFormatColl( pNextColl );
    2612             : 
    2613        1323 :     return pNode;
    2614             : }
    2615             : 
    2616       36138 : SwContentNode* SwTextNode::AppendNode( const SwPosition & rPos )
    2617             : {
    2618             :     // Position hinter dem eingefuegt wird
    2619       36138 :     SwNodeIndex aIdx( rPos.nNode, 1 );
    2620       36138 :     SwTextNode* pNew = _MakeNewTextNode( aIdx, true );
    2621             : 
    2622             :     // reset list attributes at appended text node
    2623       36138 :     pNew->ResetAttr( RES_PARATR_LIST_ISRESTART );
    2624       36138 :     pNew->ResetAttr( RES_PARATR_LIST_RESTARTVALUE );
    2625       36138 :     pNew->ResetAttr( RES_PARATR_LIST_ISCOUNTED );
    2626       36138 :     if ( pNew->GetNumRule() == 0 )
    2627             :     {
    2628       35400 :         pNew->ResetAttr( RES_PARATR_LIST_ID );
    2629       35400 :         pNew->ResetAttr( RES_PARATR_LIST_LEVEL );
    2630             :     }
    2631             : 
    2632       36138 :     if (!IsInList() && GetNumRule() && !GetListId().isEmpty())
    2633             :     {
    2634           0 :         AddToList();
    2635             :     }
    2636             : 
    2637       36138 :     if( HasWriterListeners() )
    2638        1765 :         MakeFrms( *pNew );
    2639       36138 :     return pNew;
    2640             : }
    2641             : 
    2642      250160 : SwTextAttr * SwTextNode::GetTextAttrForCharAt(
    2643             :     const sal_Int32 nIndex,
    2644             :     const RES_TXTATR nWhich ) const
    2645             : {
    2646      250160 :     if ( HasHints() )
    2647             :     {
    2648      161686 :         for ( size_t i = 0; i < m_pSwpHints->Count(); ++i )
    2649             :         {
    2650      133080 :             SwTextAttr * const pHint = m_pSwpHints->GetTextHint(i);
    2651      133080 :             const sal_Int32 nStartPos = pHint->GetStart();
    2652      133080 :             if ( nIndex < nStartPos )
    2653             :             {
    2654       20757 :                 return 0;
    2655             :             }
    2656      112323 :             if ( (nIndex == nStartPos) && pHint->HasDummyChar() )
    2657             :             {
    2658       16546 :                 return ( RES_TXTATR_END == nWhich || nWhich == pHint->Which() )
    2659       52248 :                        ? pHint : 0;
    2660             :             }
    2661             :         }
    2662             :     }
    2663      197016 :     return 0;
    2664             : }
    2665             : 
    2666             : namespace
    2667             : {
    2668             : 
    2669      121656 : inline sal_uInt16 lcl_BoundListLevel(const int nActualLevel)
    2670             : {
    2671      121656 :     return static_cast<sal_uInt16>( std::min( std::max(nActualLevel, 0), MAXLEVEL-1 ) );
    2672             : }
    2673             : 
    2674             : }
    2675             : 
    2676             : // -> #i29560#
    2677        5207 : bool SwTextNode::HasNumber() const
    2678             : {
    2679        5207 :     bool bResult = false;
    2680             : 
    2681        5207 :     const SwNumRule* pRule = GetNum() ? GetNum()->GetNumRule() : 0L;
    2682        5207 :     if ( pRule )
    2683             :     {
    2684        3996 :         SwNumFormat aFormat(pRule->Get(lcl_BoundListLevel(GetActualListLevel())));
    2685             : 
    2686             :         // #i40041#
    2687        7718 :         bResult = aFormat.IsEnumeration() &&
    2688        7718 :             SVX_NUM_NUMBER_NONE != aFormat.GetNumberingType();
    2689             :     }
    2690             : 
    2691        5207 :     return bResult;
    2692             : }
    2693             : 
    2694    11462342 : bool SwTextNode::HasBullet() const
    2695             : {
    2696    11462342 :     bool bResult = false;
    2697             : 
    2698    11462342 :     const SwNumRule* pRule = GetNum() ? GetNum()->GetNumRule() : 0L;
    2699    11462342 :     if ( pRule )
    2700             :     {
    2701         934 :         SwNumFormat aFormat(pRule->Get(lcl_BoundListLevel(GetActualListLevel())));
    2702             : 
    2703         934 :         bResult = aFormat.IsItemize();
    2704             :     }
    2705             : 
    2706    11462342 :     return bResult;
    2707             : }
    2708             : // <- #i29560#
    2709             : 
    2710             : // #128041# - introduce parameter <_bInclPrefixAndSuffixStrings>
    2711             : //i53420 added max outline parameter
    2712    11466434 : OUString SwTextNode::GetNumString( const bool _bInclPrefixAndSuffixStrings,
    2713             :         const unsigned int _nRestrictToThisLevel ) const
    2714             : {
    2715    11466434 :     if (GetDoc()->IsClipBoard() && m_pNumStringCache.get())
    2716             :     {
    2717             :         // #i111677# do not expand number strings in clipboard documents
    2718           0 :         return *m_pNumStringCache;
    2719             :     }
    2720    11466434 :     const SwNumRule* pRule = GetNum() ? GetNum()->GetNumRule() : 0L;
    2721    11472643 :     if ( pRule &&
    2722        6209 :          IsCountedInList() )
    2723             :     {
    2724             :         SvxNumberType const& rNumberType(
    2725        6209 :                 pRule->Get( lcl_BoundListLevel(GetActualListLevel()) ) );
    2726        6943 :         if (rNumberType.IsTextFormat() ||
    2727             : 
    2728         734 :             (style::NumberingType::NUMBER_NONE == rNumberType.GetNumberingType()))
    2729             :         {
    2730        5923 :             return pRule->MakeNumString( GetNum()->GetNumberVector(),
    2731             :                                      _bInclPrefixAndSuffixStrings,
    2732             :                                      false,
    2733       11846 :                                      _nRestrictToThisLevel );
    2734             :         }
    2735             :     }
    2736             : 
    2737    11460511 :     return OUString();
    2738             : }
    2739             : 
    2740      637942 : long SwTextNode::GetLeftMarginWithNum( bool bTextLeft ) const
    2741             : {
    2742      637942 :     long nRet = 0;
    2743      637942 :     const SwNumRule* pRule = GetNum() ? GetNum()->GetNumRule() : 0L;
    2744      637942 :     if( pRule )
    2745             :     {
    2746       57861 :         const SwNumFormat& rFormat = pRule->Get(lcl_BoundListLevel(GetActualListLevel()));
    2747             : 
    2748       57861 :         if ( rFormat.GetPositionAndSpaceMode() == SvxNumberFormat::LABEL_WIDTH_AND_POSITION )
    2749             :         {
    2750        5298 :             nRet = rFormat.GetAbsLSpace();
    2751             : 
    2752        5298 :             if( !bTextLeft )
    2753             :             {
    2754        7740 :                 if( 0 > rFormat.GetFirstLineOffset() &&
    2755        3869 :                     nRet > -rFormat.GetFirstLineOffset() )
    2756        2270 :                     nRet = nRet + rFormat.GetFirstLineOffset();
    2757             :                 else
    2758        1601 :                     nRet = 0;
    2759             :             }
    2760             : 
    2761        5298 :             if( pRule->IsAbsSpaces() )
    2762           0 :                 nRet = nRet - GetSwAttrSet().GetLRSpace().GetLeft();
    2763             :         }
    2764       52563 :         else if ( rFormat.GetPositionAndSpaceMode() == SvxNumberFormat::LABEL_ALIGNMENT )
    2765             :         {
    2766       52563 :             if ( AreListLevelIndentsApplicable() )
    2767             :             {
    2768       32576 :                 nRet = rFormat.GetIndentAt();
    2769             :                 // #i90401#
    2770             :                 // Only negative first line indents have consider for the left margin
    2771       56410 :                 if ( !bTextLeft &&
    2772       23834 :                      rFormat.GetFirstLineIndent() < 0 )
    2773             :                 {
    2774       23271 :                     nRet = nRet + rFormat.GetFirstLineIndent();
    2775             :                 }
    2776             :             }
    2777             :         }
    2778             :     }
    2779             : 
    2780      637942 :     return nRet;
    2781             : }
    2782             : 
    2783      187912 : bool SwTextNode::GetFirstLineOfsWithNum( short& rFLOffset ) const
    2784             : {
    2785             :     // #i95907#
    2786      187912 :     rFLOffset = 0;
    2787             : 
    2788             :     // #i51089#
    2789      187912 :     const SwNumRule* pRule = GetNum() ? GetNum()->GetNumRule() : 0L;
    2790      187912 :     if ( pRule )
    2791             :     {
    2792       14618 :         if ( IsCountedInList() )
    2793             :         {
    2794       14484 :             const SwNumFormat& rFormat = pRule->Get(lcl_BoundListLevel(GetActualListLevel()));
    2795       14484 :             if ( rFormat.GetPositionAndSpaceMode() == SvxNumberFormat::LABEL_WIDTH_AND_POSITION )
    2796             :             {
    2797        1375 :                 rFLOffset = rFormat.GetFirstLineOffset();
    2798             : 
    2799        1375 :                 if (!getIDocumentSettingAccess()->get(DocumentSettingId::IGNORE_FIRST_LINE_INDENT_IN_NUMBERING))
    2800             :                 {
    2801        1366 :                     SvxLRSpaceItem aItem = GetSwAttrSet().GetLRSpace();
    2802        1366 :                     rFLOffset = rFLOffset + aItem.GetTextFirstLineOfst();
    2803             :                 }
    2804             :             }
    2805       13109 :             else if ( rFormat.GetPositionAndSpaceMode() == SvxNumberFormat::LABEL_ALIGNMENT )
    2806             :             {
    2807       13109 :                 if ( AreListLevelIndentsApplicable() )
    2808             :                 {
    2809        8687 :                     rFLOffset = rFormat.GetFirstLineIndent();
    2810             :                 }
    2811        4422 :                 else if (!getIDocumentSettingAccess()->get(DocumentSettingId::IGNORE_FIRST_LINE_INDENT_IN_NUMBERING))
    2812             :                 {
    2813        4422 :                     SvxLRSpaceItem aItem = GetSwAttrSet().GetLRSpace();
    2814        4422 :                     rFLOffset = aItem.GetTextFirstLineOfst();
    2815             :                 }
    2816             :             }
    2817             :         }
    2818             : 
    2819       14618 :         return true;
    2820             :     }
    2821             : 
    2822      173294 :     rFLOffset = GetSwAttrSet().GetLRSpace().GetTextFirstLineOfst();
    2823      173294 :     return false;
    2824             : }
    2825             : 
    2826           0 : SwTwips SwTextNode::GetAdditionalIndentForStartingNewList() const
    2827             : {
    2828           0 :     SwTwips nAdditionalIndent = 0;
    2829             : 
    2830           0 :     const SwNumRule* pRule = GetNum() ? GetNum()->GetNumRule() : 0L;
    2831           0 :     if ( pRule )
    2832             :     {
    2833           0 :         const SwNumFormat& rFormat = pRule->Get(lcl_BoundListLevel(GetActualListLevel()));
    2834           0 :         if ( rFormat.GetPositionAndSpaceMode() == SvxNumberFormat::LABEL_WIDTH_AND_POSITION )
    2835             :         {
    2836           0 :             nAdditionalIndent = GetSwAttrSet().GetLRSpace().GetLeft();
    2837             : 
    2838           0 :             if (getIDocumentSettingAccess()->get(DocumentSettingId::IGNORE_FIRST_LINE_INDENT_IN_NUMBERING))
    2839             :             {
    2840           0 :                 nAdditionalIndent = nAdditionalIndent -
    2841           0 :                                     GetSwAttrSet().GetLRSpace().GetTextFirstLineOfst();
    2842             :             }
    2843             :         }
    2844           0 :         else if ( rFormat.GetPositionAndSpaceMode() == SvxNumberFormat::LABEL_ALIGNMENT )
    2845             :         {
    2846           0 :             if ( AreListLevelIndentsApplicable() )
    2847             :             {
    2848           0 :                 nAdditionalIndent = rFormat.GetIndentAt() + rFormat.GetFirstLineIndent();
    2849             :             }
    2850             :             else
    2851             :             {
    2852           0 :                 nAdditionalIndent = GetSwAttrSet().GetLRSpace().GetLeft();
    2853           0 :                 if (getIDocumentSettingAccess()->get(DocumentSettingId::IGNORE_FIRST_LINE_INDENT_IN_NUMBERING))
    2854             :                 {
    2855           0 :                     nAdditionalIndent = nAdditionalIndent -
    2856           0 :                                         GetSwAttrSet().GetLRSpace().GetTextFirstLineOfst();
    2857             :                 }
    2858             :             }
    2859             :         }
    2860             :     }
    2861             :     else
    2862             :     {
    2863           0 :         nAdditionalIndent = GetSwAttrSet().GetLRSpace().GetLeft();
    2864             :     }
    2865             : 
    2866           0 :     return nAdditionalIndent;
    2867             : }
    2868             : 
    2869             : // #i96772#
    2870       36498 : void SwTextNode::ClearLRSpaceItemDueToListLevelIndents( SvxLRSpaceItem& o_rLRSpaceItem ) const
    2871             : {
    2872       36498 :     if ( AreListLevelIndentsApplicable() )
    2873             :     {
    2874        1836 :         const SwNumRule* pRule = GetNumRule();
    2875        1836 :         if ( pRule && GetActualListLevel() >= 0 )
    2876             :         {
    2877        1836 :             const SwNumFormat& rFormat = pRule->Get(lcl_BoundListLevel(GetActualListLevel()));
    2878        1836 :             if ( rFormat.GetPositionAndSpaceMode() == SvxNumberFormat::LABEL_ALIGNMENT )
    2879             :             {
    2880        1747 :                 SvxLRSpaceItem aLR( RES_LR_SPACE );
    2881        1747 :                 o_rLRSpaceItem = aLR;
    2882             :             }
    2883             :         }
    2884             :     }
    2885       36498 : }
    2886             : 
    2887             : // #i91133#
    2888      184321 : long SwTextNode::GetLeftMarginForTabCalculation() const
    2889             : {
    2890      184321 :     long nLeftMarginForTabCalc = 0;
    2891             : 
    2892      184321 :     bool bLeftMarginForTabCalcSetToListLevelIndent( false );
    2893      184321 :     const SwNumRule* pRule = GetNum() ? GetNum()->GetNumRule() : 0;
    2894      184321 :     if( pRule )
    2895             :     {
    2896       14673 :         const SwNumFormat& rFormat = pRule->Get(lcl_BoundListLevel(GetActualListLevel()));
    2897       14673 :         if ( rFormat.GetPositionAndSpaceMode() == SvxNumberFormat::LABEL_ALIGNMENT )
    2898             :         {
    2899       13246 :             if ( AreListLevelIndentsApplicable() )
    2900             :             {
    2901        8742 :                 nLeftMarginForTabCalc = rFormat.GetIndentAt();
    2902        8742 :                 bLeftMarginForTabCalcSetToListLevelIndent = true;
    2903             :             }
    2904             :         }
    2905             :     }
    2906      184321 :     if ( !bLeftMarginForTabCalcSetToListLevelIndent )
    2907             :     {
    2908      175579 :         nLeftMarginForTabCalc = GetSwAttrSet().GetLRSpace().GetTextLeft();
    2909             :     }
    2910             : 
    2911      184321 :     return nLeftMarginForTabCalc;
    2912             : }
    2913             : 
    2914           0 : static void Replace0xFF(
    2915             :     SwTextNode const& rNode,
    2916             :     OUStringBuffer & rText,
    2917             :     sal_Int32 & rTextStt,
    2918             :     sal_Int32 nEndPos,
    2919             :     bool const bExpandFields,
    2920             :     bool const bExpandFootnote = true )
    2921             : {
    2922           0 :     if (rNode.GetpSwpHints())
    2923             :     {
    2924           0 :         sal_Unicode cSrchChr = CH_TXTATR_BREAKWORD;
    2925           0 :         for( int nSrchIter = 0; 2 > nSrchIter; ++nSrchIter, cSrchChr = CH_TXTATR_INWORD )
    2926             :         {
    2927           0 :             sal_Int32 nPos = rText.indexOf(cSrchChr);
    2928           0 :             while (-1 != nPos && nPos < nEndPos)
    2929             :             {
    2930             :                 const SwTextAttr* const pAttr =
    2931           0 :                     rNode.GetTextAttrForCharAt(rTextStt + nPos);
    2932           0 :                 if( pAttr )
    2933             :                 {
    2934           0 :                     switch( pAttr->Which() )
    2935             :                     {
    2936             :                     case RES_TXTATR_FIELD:
    2937             :                     case RES_TXTATR_ANNOTATION:
    2938           0 :                         rText.remove(nPos, 1);
    2939           0 :                         if( bExpandFields )
    2940             :                         {
    2941             :                             const OUString aExpand(
    2942           0 :                                 static_txtattr_cast<SwTextField const*>(pAttr)->GetFormatField().GetField()->ExpandField(true));
    2943           0 :                             rText.insert(nPos, aExpand);
    2944           0 :                             nPos = nPos + aExpand.getLength();
    2945           0 :                             nEndPos = nEndPos + aExpand.getLength();
    2946           0 :                             rTextStt = rTextStt - aExpand.getLength();
    2947             :                         }
    2948           0 :                         ++rTextStt;
    2949           0 :                         break;
    2950             : 
    2951             :                     case RES_TXTATR_FTN:
    2952           0 :                         rText.remove(nPos, 1);
    2953           0 :                         if( bExpandFields && bExpandFootnote )
    2954             :                         {
    2955           0 :                             const SwFormatFootnote& rFootnote = pAttr->GetFootnote();
    2956           0 :                             OUString sExpand;
    2957           0 :                             if( !rFootnote.GetNumStr().isEmpty() )
    2958           0 :                                 sExpand = rFootnote.GetNumStr();
    2959           0 :                             else if( rFootnote.IsEndNote() )
    2960           0 :                                 sExpand = rNode.GetDoc()->GetEndNoteInfo().aFormat.
    2961           0 :                                                 GetNumStr( rFootnote.GetNumber() );
    2962             :                             else
    2963           0 :                                 sExpand = rNode.GetDoc()->GetFootnoteInfo().aFormat.
    2964           0 :                                                 GetNumStr( rFootnote.GetNumber() );
    2965           0 :                             rText.insert(nPos, sExpand);
    2966           0 :                             nPos = nPos + sExpand.getLength();
    2967           0 :                             nEndPos = nEndPos + sExpand.getLength();
    2968           0 :                             rTextStt = rTextStt - sExpand.getLength();
    2969             :                         }
    2970           0 :                         ++rTextStt;
    2971           0 :                         break;
    2972             : 
    2973             :                     default:
    2974           0 :                         rText.remove(nPos, 1);
    2975           0 :                         ++rTextStt;
    2976             :                     }
    2977             :                 }
    2978             :                 else
    2979           0 :                     ++nPos, ++nEndPos;
    2980           0 :                 nPos = rText.indexOf(cSrchChr, nPos);
    2981             :             }
    2982             :         }
    2983             :     }
    2984           0 : }
    2985             : 
    2986             : // Expand fields
    2987             : // #i83479# - handling of new parameters
    2988        3683 : OUString SwTextNode::GetExpandText(  const sal_Int32 nIdx,
    2989             :                                    const sal_Int32 nLen,
    2990             :                                    const bool bWithNum,
    2991             :                                    const bool bAddSpaceAfterListLabelStr,
    2992             :                                    const bool bWithSpacesForLevel,
    2993             :                                    const bool bWithFootnote ) const
    2994             : 
    2995             : {
    2996        3683 :     ExpandMode eMode = ExpandMode::ExpandFields;
    2997        3683 :     if (bWithFootnote)
    2998        3683 :         eMode |= ExpandMode::ExpandFootnote;
    2999             : 
    3000        3683 :     ModelToViewHelper aConversionMap(*this, eMode);
    3001        7366 :     OUString aExpandText = aConversionMap.getViewText();
    3002        3683 :     const sal_Int32 nExpandBegin = aConversionMap.ConvertToViewPosition( nIdx );
    3003        3683 :     sal_Int32 nEnd = nLen == -1 ? GetText().getLength() : nIdx + nLen;
    3004        3683 :     const sal_Int32 nExpandEnd = aConversionMap.ConvertToViewPosition( nEnd );
    3005        7366 :     OUStringBuffer aText(aExpandText.copy(nExpandBegin, nExpandEnd-nExpandBegin));
    3006             : 
    3007             :     // remove dummy characters of Input Fields
    3008        3683 :     comphelper::string::remove(aText, CH_TXT_ATR_INPUTFIELDSTART);
    3009        3683 :     comphelper::string::remove(aText, CH_TXT_ATR_INPUTFIELDEND);
    3010             : 
    3011        3683 :     if( bWithNum )
    3012             :     {
    3013           0 :         if ( !GetNumString().isEmpty() )
    3014             :         {
    3015           0 :             if ( bAddSpaceAfterListLabelStr )
    3016             :             {
    3017           0 :                 const sal_Unicode aSpace = ' ';
    3018           0 :                 aText.insert(0, aSpace);
    3019             :             }
    3020           0 :             aText.insert(0, GetNumString());
    3021             :         }
    3022             :     }
    3023             : 
    3024        3683 :     if (bWithSpacesForLevel)
    3025             :     {
    3026           0 :         const sal_Unicode aSpace = ' ';
    3027           0 :         for (int nLevel = GetActualListLevel(); nLevel > 0; --nLevel)
    3028             :         {
    3029           0 :             aText.insert(0, aSpace);
    3030           0 :             aText.insert(0, aSpace);
    3031             :         }
    3032             :     }
    3033             : 
    3034        7366 :     return aText.makeStringAndClear();
    3035             : }
    3036             : 
    3037           0 : bool SwTextNode::GetExpandText( SwTextNode& rDestNd, const SwIndex* pDestIdx,
    3038             :                         sal_Int32 nIdx, sal_Int32 nLen, bool bWithNum,
    3039             :                         bool bWithFootnote, bool bReplaceTabsWithSpaces ) const
    3040             : {
    3041           0 :     if( &rDestNd == this )
    3042           0 :         return false;
    3043             : 
    3044           0 :     SwIndex aDestIdx(&rDestNd, rDestNd.GetText().getLength());
    3045           0 :     if( pDestIdx )
    3046           0 :         aDestIdx = *pDestIdx;
    3047           0 :     const sal_Int32 nDestStt = aDestIdx.GetIndex();
    3048             : 
    3049             :     // Text einfuegen
    3050           0 :     OUStringBuffer buf(GetText());
    3051           0 :     if( bReplaceTabsWithSpaces )
    3052           0 :         buf.replace('\t', ' ');
    3053             : 
    3054             :     // mask hidden characters
    3055           0 :     const sal_Unicode cChar = CH_TXTATR_BREAKWORD;
    3056           0 :     SwScriptInfo::MaskHiddenRanges(*this, buf, 0, buf.getLength(), cChar);
    3057             : 
    3058           0 :     buf.remove(0, nIdx);
    3059           0 :     if (nLen != -1)
    3060             :     {
    3061           0 :         buf.truncate(nLen);
    3062             :     }
    3063             :     // remove dummy characters of Input Fields
    3064             :     {
    3065           0 :         comphelper::string::remove(buf, CH_TXT_ATR_INPUTFIELDSTART);
    3066           0 :         comphelper::string::remove(buf, CH_TXT_ATR_INPUTFIELDEND);
    3067             :     }
    3068           0 :     rDestNd.InsertText(buf.makeStringAndClear(), aDestIdx);
    3069           0 :     nLen = aDestIdx.GetIndex() - nDestStt;
    3070             : 
    3071             :     // alle FontAttribute mit CHARSET Symbol in dem Bereich setzen
    3072           0 :     if ( HasHints() )
    3073             :     {
    3074           0 :         sal_Int32 nInsPos = nDestStt - nIdx;
    3075           0 :         for ( size_t i = 0; i < m_pSwpHints->Count(); ++i )
    3076             :         {
    3077           0 :             const SwTextAttr* pHt = (*m_pSwpHints)[i];
    3078           0 :             const sal_Int32 nAttrStartIdx = pHt->GetStart();
    3079           0 :             const sal_uInt16 nWhich = pHt->Which();
    3080           0 :             if (nIdx + nLen <= nAttrStartIdx)
    3081           0 :                 break;      // ueber das Textende
    3082             : 
    3083           0 :             const sal_Int32 *pEndIdx = pHt->End();
    3084           0 :             if( pEndIdx && *pEndIdx > nIdx &&
    3085           0 :                 ( RES_CHRATR_FONT == nWhich ||
    3086           0 :                   RES_TXTATR_CHARFMT == nWhich ||
    3087             :                   RES_TXTATR_AUTOFMT == nWhich ))
    3088             :             {
    3089             :                 const SvxFontItem* const pFont =
    3090             :                     static_cast<const SvxFontItem*>(
    3091           0 :                         CharFormat::GetItem( *pHt, RES_CHRATR_FONT ));
    3092           0 :                 if ( pFont && RTL_TEXTENCODING_SYMBOL == pFont->GetCharSet() )
    3093             :                 {
    3094             :                     // attribute in area => copy
    3095             :                     rDestNd.InsertItem( *const_cast<SvxFontItem*>(pFont),
    3096           0 :                             nInsPos + nAttrStartIdx, nInsPos + *pEndIdx );
    3097           0 :                 }
    3098             :             }
    3099           0 :             else if ( pHt->HasDummyChar() && (nAttrStartIdx >= nIdx) )
    3100             :             {
    3101           0 :                 aDestIdx = nInsPos + nAttrStartIdx;
    3102           0 :                 switch( nWhich )
    3103             :                 {
    3104             :                 case RES_TXTATR_FIELD:
    3105             :                 case RES_TXTATR_ANNOTATION:
    3106             :                     {
    3107             :                         OUString const aExpand(
    3108           0 :                             static_txtattr_cast<SwTextField const*>(pHt)->GetFormatField().GetField()->ExpandField(true));
    3109           0 :                         if (!aExpand.isEmpty())
    3110             :                         {
    3111           0 :                             ++aDestIdx;     // dahinter einfuegen;
    3112             :                             OUString const ins(
    3113           0 :                                 rDestNd.InsertText( aExpand, aDestIdx));
    3114             :                             SAL_INFO_IF(ins.getLength() != aExpand.getLength(),
    3115             :                                     "sw.core", "GetExpandText lossage");
    3116           0 :                             aDestIdx = nInsPos + nAttrStartIdx;
    3117           0 :                             nInsPos += ins.getLength();
    3118             :                         }
    3119           0 :                         rDestNd.EraseText( aDestIdx, 1 );
    3120           0 :                         --nInsPos;
    3121             :                     }
    3122           0 :                     break;
    3123             : 
    3124             :                 case RES_TXTATR_FTN:
    3125             :                     {
    3126           0 :                         if ( bWithFootnote )
    3127             :                         {
    3128           0 :                             const SwFormatFootnote& rFootnote = pHt->GetFootnote();
    3129           0 :                             OUString sExpand;
    3130           0 :                             if( !rFootnote.GetNumStr().isEmpty() )
    3131           0 :                                 sExpand = rFootnote.GetNumStr();
    3132           0 :                             else if( rFootnote.IsEndNote() )
    3133           0 :                                 sExpand = GetDoc()->GetEndNoteInfo().aFormat.
    3134           0 :                                 GetNumStr( rFootnote.GetNumber() );
    3135             :                             else
    3136           0 :                                 sExpand = GetDoc()->GetFootnoteInfo().aFormat.
    3137           0 :                                                 GetNumStr( rFootnote.GetNumber() );
    3138           0 :                             if( !sExpand.isEmpty() )
    3139             :                             {
    3140           0 :                                 ++aDestIdx;     // insert behind
    3141             :                                 SvxEscapementItem aItem(
    3142           0 :                                         SVX_ESCAPEMENT_SUPERSCRIPT );
    3143             :                                 rDestNd.InsertItem(
    3144             :                                         aItem,
    3145             :                                         aDestIdx.GetIndex(),
    3146           0 :                                         aDestIdx.GetIndex() );
    3147           0 :                                 OUString const ins( rDestNd.InsertText(sExpand, aDestIdx, SwInsertFlags::EMPTYEXPAND));
    3148             :                                 SAL_INFO_IF(ins.getLength() != sExpand.getLength(),
    3149             :                                         "sw.core", "GetExpandText lossage");
    3150           0 :                                 aDestIdx = nInsPos + nAttrStartIdx;
    3151           0 :                                 nInsPos += ins.getLength();
    3152           0 :                             }
    3153             :                         }
    3154           0 :                         rDestNd.EraseText( aDestIdx, 1 );
    3155           0 :                         --nInsPos;
    3156             :                     }
    3157           0 :                     break;
    3158             : 
    3159             :                 default:
    3160           0 :                     rDestNd.EraseText( aDestIdx, 1 );
    3161           0 :                     --nInsPos;
    3162             :                 }
    3163             :             }
    3164             :         }
    3165             :     }
    3166             : 
    3167           0 :     if( bWithNum )
    3168             :     {
    3169           0 :         aDestIdx = nDestStt;
    3170           0 :         rDestNd.InsertText( GetNumString(), aDestIdx );
    3171             :     }
    3172             : 
    3173           0 :     aDestIdx = 0;
    3174           0 :     sal_Int32 nStartDelete(-1);
    3175           0 :     while (aDestIdx < rDestNd.GetText().getLength())
    3176             :     {
    3177           0 :         sal_Unicode const cur(rDestNd.GetText()[aDestIdx.GetIndex()]);
    3178           0 :         if (   (cChar == cur) // filter substituted hidden text
    3179           0 :             || (CH_TXT_ATR_FIELDSTART  == cur) // filter all fieldmarks
    3180           0 :             || (CH_TXT_ATR_FIELDEND    == cur)
    3181           0 :             || (CH_TXT_ATR_FORMELEMENT == cur))
    3182             :         {
    3183           0 :             if (-1 == nStartDelete)
    3184             :             {
    3185           0 :                 nStartDelete = aDestIdx.GetIndex(); // start deletion range
    3186             :             }
    3187           0 :             ++aDestIdx;
    3188           0 :             if (aDestIdx < rDestNd.GetText().getLength())
    3189             :             {
    3190           0 :                 continue;
    3191             :             } // else: end of paragraph => delete, see below
    3192             :         }
    3193             :         else
    3194             :         {
    3195           0 :             if (-1 == nStartDelete)
    3196             :             {
    3197           0 :                 ++aDestIdx;
    3198           0 :                 continue;
    3199             :             } // else: delete, see below
    3200             :         }
    3201             :         assert(-1 != nStartDelete); // without delete range, would have continued
    3202             :         rDestNd.EraseText(
    3203             :             SwIndex(&rDestNd, nStartDelete),
    3204           0 :             aDestIdx.GetIndex() - nStartDelete);
    3205             :         assert(aDestIdx.GetIndex() == nStartDelete);
    3206           0 :         nStartDelete = -1; // reset
    3207             :     }
    3208             : 
    3209           0 :     return true;
    3210             : }
    3211             : 
    3212           0 : OUString SwTextNode::GetRedlineText( sal_Int32 nIdx, sal_Int32 nLen,
    3213             :                                    bool bExpandFields, bool bWithNum ) const
    3214             : {
    3215           0 :     std::vector<sal_Int32> aRedlArr;
    3216           0 :     const SwDoc* pDoc = GetDoc();
    3217           0 :     sal_uInt16 nRedlPos = pDoc->getIDocumentRedlineAccess().GetRedlinePos( *this, nsRedlineType_t::REDLINE_DELETE );
    3218           0 :     if( USHRT_MAX != nRedlPos )
    3219             :     {
    3220             :         // es existiert fuer den Node irgendein Redline-Delete-Object
    3221           0 :         const sal_uLong nNdIdx = GetIndex();
    3222           0 :         for( ; nRedlPos < pDoc->getIDocumentRedlineAccess().GetRedlineTable().size() ; ++nRedlPos )
    3223             :         {
    3224           0 :             const SwRangeRedline* pTmp = pDoc->getIDocumentRedlineAccess().GetRedlineTable()[ nRedlPos ];
    3225           0 :             if( nsRedlineType_t::REDLINE_DELETE == pTmp->GetType() )
    3226             :             {
    3227           0 :                 const SwPosition *pRStt = pTmp->Start(), *pREnd = pTmp->End();
    3228           0 :                 if( pRStt->nNode < nNdIdx )
    3229             :                 {
    3230           0 :                     if( pREnd->nNode > nNdIdx )
    3231             :                         // Absatz ist komplett geloescht
    3232           0 :                         return OUString();
    3233           0 :                     else if( pREnd->nNode == nNdIdx )
    3234             :                     {
    3235             :                         // von 0 bis nContent ist alles geloescht
    3236           0 :                         aRedlArr.push_back( 0 );
    3237           0 :                         aRedlArr.push_back( pREnd->nContent.GetIndex() );
    3238             :                     }
    3239             :                 }
    3240           0 :                 else if( pRStt->nNode == nNdIdx )
    3241             :                 {
    3242             :                     //aRedlArr.Insert( pRStt->nContent.GetIndex(), aRedlArr.Count() );
    3243           0 :                     aRedlArr.push_back( pRStt->nContent.GetIndex() );
    3244           0 :                     if( pREnd->nNode == nNdIdx )
    3245           0 :                         aRedlArr.push_back( pREnd->nContent.GetIndex() );
    3246             :                     else
    3247             :                     {
    3248           0 :                         aRedlArr.push_back(GetText().getLength());
    3249           0 :                         break;      // mehr kann nicht kommen
    3250             :                     }
    3251             :                 }
    3252             :                 else
    3253           0 :                     break;      // mehr kann nicht kommen
    3254             :             }
    3255             :         }
    3256             :     }
    3257             : 
    3258           0 :     OUStringBuffer aText((nLen > GetText().getLength())
    3259           0 :                 ? GetText().copy(nIdx)
    3260           0 :                 : GetText().copy(nIdx, nLen));
    3261             : 
    3262           0 :     sal_Int32 nTextStt = nIdx;
    3263           0 :     sal_Int32 nIdxEnd = nIdx + aText.getLength();
    3264           0 :     for( size_t n = 0; n < aRedlArr.size(); n += 2 )
    3265             :     {
    3266           0 :         sal_Int32 nStt = aRedlArr[ n ];
    3267           0 :         sal_Int32 nEnd = aRedlArr[ n+1 ];
    3268           0 :         if( ( nIdx <= nStt && nStt <= nIdxEnd ) ||
    3269           0 :             ( nIdx <= nEnd && nEnd <= nIdxEnd ))
    3270             :         {
    3271           0 :             if( nStt < nIdx ) nStt = nIdx;
    3272           0 :             if( nIdxEnd < nEnd ) nEnd = nIdxEnd;
    3273           0 :             const sal_Int32 nDelCnt = nEnd - nStt;
    3274           0 :             aText.remove(nStt - nTextStt, nDelCnt);
    3275           0 :             Replace0xFF(*this, aText, nTextStt, nStt - nTextStt, bExpandFields);
    3276           0 :             nTextStt += nDelCnt;
    3277             :         }
    3278           0 :         else if( nStt >= nIdxEnd )
    3279           0 :             break;
    3280             :     }
    3281           0 :     Replace0xFF(*this, aText, nTextStt, aText.getLength(), bExpandFields);
    3282             : 
    3283           0 :     if( bWithNum )
    3284           0 :         aText.insert(0, GetNumString());
    3285           0 :     return aText.makeStringAndClear();
    3286             : }
    3287             : 
    3288          12 : void SwTextNode::ReplaceText( const SwIndex& rStart, const sal_Int32 nDelLen,
    3289             :                              const OUString & rStr)
    3290             : {
    3291             :     assert( rStart.GetIndex() < m_Text.getLength()     // index out of bounds
    3292             :          && rStart.GetIndex() + nDelLen <= m_Text.getLength());
    3293             : 
    3294          12 :     sal_Int32 const nOverflow(rStr.getLength() - nDelLen - GetSpaceLeft());
    3295             :     SAL_WARN_IF(nOverflow > 0, "sw.core",
    3296             :             "SwTextNode::ReplaceText: node text with insertion > node capacity.");
    3297             :     OUString const sInserted(
    3298          12 :         (nOverflow > 0) ? rStr.copy(0, rStr.getLength() - nOverflow) : rStr);
    3299          12 :     if (sInserted.isEmpty() && 0 == nDelLen)
    3300             :     {
    3301          13 :         return; // nothing to do
    3302             :     }
    3303             : 
    3304          11 :     const sal_Int32 nStartPos = rStart.GetIndex();
    3305          11 :     sal_Int32 nEndPos = nStartPos + nDelLen;
    3306          11 :     sal_Int32 nLen = nDelLen;
    3307         117 :     for( sal_Int32 nPos = nStartPos; nPos < nEndPos; ++nPos )
    3308             :     {
    3309         212 :         if ((CH_TXTATR_BREAKWORD == m_Text[nPos]) ||
    3310         106 :             (CH_TXTATR_INWORD    == m_Text[nPos]))
    3311             :         {
    3312           0 :             SwTextAttr *const pHint = GetTextAttrForCharAt( nPos );
    3313           0 :             if (pHint)
    3314             :             {
    3315             :                assert(!( pHint->GetEnd() && pHint->HasDummyChar()
    3316             :                             && (pHint->GetStart() < nEndPos)
    3317             :                             && (*pHint->GetEnd()   > nEndPos) ));
    3318             :                     // "deleting left-overlapped attribute with CH_TXTATR"
    3319           0 :                 DeleteAttribute( pHint );
    3320           0 :                 --nEndPos;
    3321           0 :                 --nLen;
    3322             :             }
    3323             :         }
    3324             :     }
    3325             : 
    3326          11 :     bool bOldExpFlg = IsIgnoreDontExpand();
    3327          11 :     SetIgnoreDontExpand( true );
    3328             : 
    3329          11 :     if (nLen && sInserted.getLength())
    3330             :     {
    3331             :         // dann das 1. Zeichen ersetzen den Rest loschen und einfuegen
    3332             :         // Dadurch wird die Attributierung des 1. Zeichen expandiert!
    3333           9 :         m_Text = m_Text.replaceAt(nStartPos, 1, sInserted.copy(0, 1));
    3334             : 
    3335           9 :         ++const_cast<SwIndex&>(rStart);
    3336           9 :         m_Text = m_Text.replaceAt(rStart.GetIndex(), nLen - 1, "");
    3337           9 :         Update( rStart, nLen - 1, true );
    3338             : 
    3339           9 :         OUString aTmpText( sInserted.copy(1) );
    3340           9 :         m_Text = m_Text.replaceAt(rStart.GetIndex(), 0, aTmpText);
    3341           9 :         Update( rStart, aTmpText.getLength(), false );
    3342             :     }
    3343             :     else
    3344             :     {
    3345           2 :         m_Text = m_Text.replaceAt(nStartPos, nLen, "");
    3346           2 :         Update( rStart, nLen, true );
    3347             : 
    3348           2 :         m_Text = m_Text.replaceAt(nStartPos, 0, sInserted);
    3349           2 :         Update( rStart, sInserted.getLength(), false );
    3350             :     }
    3351             : 
    3352          11 :     SetIgnoreDontExpand( bOldExpFlg );
    3353          22 :     SwDelText aDelHint( nStartPos, nDelLen );
    3354          11 :     NotifyClients( 0, &aDelHint );
    3355             : 
    3356          22 :     SwInsText aHint( nStartPos, sInserted.getLength() );
    3357          22 :     NotifyClients( 0, &aHint );
    3358             : }
    3359             : 
    3360             : namespace {
    3361         150 :     static void lcl_ResetParAttrs( SwTextNode &rTextNode )
    3362             :     {
    3363         150 :         std::set<sal_uInt16> aAttrs;
    3364         150 :         aAttrs.insert( aAttrs.end(), RES_PARATR_LIST_ID );
    3365         150 :         aAttrs.insert( aAttrs.end(), RES_PARATR_LIST_LEVEL );
    3366         150 :         aAttrs.insert( aAttrs.end(), RES_PARATR_LIST_ISRESTART );
    3367         150 :         aAttrs.insert( aAttrs.end(), RES_PARATR_LIST_RESTARTVALUE );
    3368         150 :         aAttrs.insert( aAttrs.end(), RES_PARATR_LIST_ISCOUNTED );
    3369         300 :         SwPaM aPam( rTextNode );
    3370             :         // #i96644#
    3371             :         // suppress side effect "send data changed events"
    3372         300 :         rTextNode.GetDoc()->ResetAttrs( aPam, false, aAttrs, false );
    3373         150 :     }
    3374             : 
    3375             :     // Helper method for special handling of modified attributes at text node.
    3376             :     // The following is handled:
    3377             :     // (1) on changing the paragraph style - RES_FMT_CHG:
    3378             :     // Check, if list style of the text node is changed. If yes, add respectively
    3379             :     // remove the text node to the corresponding list.
    3380             :     // (2) on changing the attributes - RES_ATTRSET_CHG:
    3381             :     // Same as (1).
    3382             :     // (3) on changing the list style - RES_PARATR_NUMRULE:
    3383             :     // Same as (1).
    3384      329773 :     void HandleModifyAtTextNode( SwTextNode& rTextNode,
    3385             :                                 const SfxPoolItem* pOldValue,
    3386             :                                 const SfxPoolItem* pNewValue )
    3387             :     {
    3388             :         const sal_uInt16 nWhich = pOldValue ? pOldValue->Which() :
    3389      329773 :                               pNewValue ? pNewValue->Which() : 0 ;
    3390      329773 :         bool bNumRuleSet = false;
    3391      329773 :         bool bParagraphStyleChanged = false;
    3392      329773 :         OUString sNumRule;
    3393      659546 :         OUString sOldNumRule;
    3394      329773 :         switch ( nWhich )
    3395             :         {
    3396             :             case RES_FMT_CHG:
    3397             :             {
    3398       23281 :                 bParagraphStyleChanged = true;
    3399       23281 :                 if( rTextNode.GetNodes().IsDocNodes() )
    3400             :                 {
    3401             :                     const SwNumRule* pFormerNumRuleAtTextNode =
    3402       18486 :                         rTextNode.GetNum() ? rTextNode.GetNum()->GetNumRule() : 0;
    3403       18486 :                     if ( pFormerNumRuleAtTextNode )
    3404             :                     {
    3405         219 :                         sOldNumRule = pFormerNumRuleAtTextNode->GetName();
    3406             :                     }
    3407       18486 :                     if ( rTextNode.IsEmptyListStyleDueToSetOutlineLevelAttr() )
    3408             :                     {
    3409           0 :                         const SwNumRuleItem& rNumRuleItem = rTextNode.GetTextColl()->GetNumRule();
    3410           0 :                         if ( !rNumRuleItem.GetValue().isEmpty() )
    3411             :                         {
    3412           0 :                             rTextNode.ResetEmptyListStyleDueToResetOutlineLevelAttr();
    3413             :                         }
    3414             :                     }
    3415       18486 :                     const SwNumRule* pNumRuleAtTextNode = rTextNode.GetNumRule();
    3416       18486 :                     if ( pNumRuleAtTextNode )
    3417             :                     {
    3418         263 :                         bNumRuleSet = true;
    3419         263 :                         sNumRule = pNumRuleAtTextNode->GetName();
    3420             :                     }
    3421             :                 }
    3422       23281 :                 break;
    3423             :             }
    3424             :             case RES_ATTRSET_CHG:
    3425             :             {
    3426      222664 :                 const SfxPoolItem* pItem = 0;
    3427             :                 const SwNumRule* pFormerNumRuleAtTextNode =
    3428      222664 :                     rTextNode.GetNum() ? rTextNode.GetNum()->GetNumRule() : 0;
    3429      222664 :                 if ( pFormerNumRuleAtTextNode )
    3430             :                 {
    3431        9858 :                     sOldNumRule = pFormerNumRuleAtTextNode->GetName();
    3432             :                 }
    3433             : 
    3434      222664 :                 const SwAttrSetChg* pSet = dynamic_cast<const SwAttrSetChg*>(pNewValue);
    3435      222664 :                 if ( pSet && pSet->GetChgSet()->GetItemState( RES_PARATR_NUMRULE, false, &pItem ) ==
    3436             :                         SfxItemState::SET )
    3437             :                 {
    3438             :                     // #i70748#
    3439         167 :                     rTextNode.ResetEmptyListStyleDueToResetOutlineLevelAttr();
    3440         167 :                     bNumRuleSet = true;
    3441             :                 }
    3442             :                 // #i70748#
    3443             :                 // The new list style set at the paragraph.
    3444      222664 :                 const SwNumRule* pNumRuleAtTextNode = rTextNode.GetNumRule();
    3445      222664 :                 if ( pNumRuleAtTextNode )
    3446             :                 {
    3447       10007 :                     sNumRule = pNumRuleAtTextNode->GetName();
    3448             :                 }
    3449      222664 :                 break;
    3450             :             }
    3451             :             case RES_PARATR_NUMRULE:
    3452             :             {
    3453           0 :                 if ( rTextNode.GetNodes().IsDocNodes() )
    3454             :                 {
    3455             :                     const SwNumRule* pFormerNumRuleAtTextNode =
    3456           0 :                         rTextNode.GetNum() ? rTextNode.GetNum()->GetNumRule() : 0;
    3457           0 :                     if ( pFormerNumRuleAtTextNode )
    3458             :                     {
    3459           0 :                         sOldNumRule = pFormerNumRuleAtTextNode->GetName();
    3460             :                     }
    3461             : 
    3462           0 :                     if ( pNewValue )
    3463             :                     {
    3464             :                         // #i70748#
    3465           0 :                         rTextNode.ResetEmptyListStyleDueToResetOutlineLevelAttr();
    3466           0 :                         bNumRuleSet = true;
    3467             :                     }
    3468             :                     // #i70748#
    3469             :                     // The new list style set at the paragraph.
    3470           0 :                     const SwNumRule* pNumRuleAtTextNode = rTextNode.GetNumRule();
    3471           0 :                     if ( pNumRuleAtTextNode )
    3472             :                     {
    3473           0 :                         sNumRule = pNumRuleAtTextNode->GetName();
    3474             :                     }
    3475             :                 }
    3476           0 :                 break;
    3477             :             }
    3478             :         }
    3479      329773 :         if ( sNumRule != sOldNumRule )
    3480             :         {
    3481         493 :             if ( bNumRuleSet )
    3482             :             {
    3483         343 :                 if (sNumRule.isEmpty())
    3484             :                 {
    3485           0 :                     rTextNode.RemoveFromList();
    3486           0 :                     if ( bParagraphStyleChanged )
    3487             :                     {
    3488           0 :                         lcl_ResetParAttrs(rTextNode);
    3489             :                     }
    3490             :                 }
    3491             :                 else
    3492             :                 {
    3493         343 :                     rTextNode.RemoveFromList();
    3494             :                     // If new list style is the outline style, apply outline
    3495             :                     // level as the list level.
    3496         343 :                     if (sNumRule==SwNumRule::GetOutlineRuleName())
    3497             :                     {
    3498             :                         // #i70748#
    3499             :                         OSL_ENSURE( rTextNode.GetTextColl()->IsAssignedToListLevelOfOutlineStyle(),
    3500             :                                 "<HandleModifyAtTextNode()> - text node with outline style, but its paragraph style is not assigned to outline style." );
    3501             :                         const int nNewListLevel =
    3502         317 :                             rTextNode.GetTextColl()->GetAssignedOutlineStyleLevel();
    3503         317 :                         if ( 0 <= nNewListLevel && nNewListLevel < MAXLEVEL )
    3504             :                         {
    3505         317 :                             rTextNode.SetAttrListLevel( nNewListLevel );
    3506             :                         }
    3507             :                     }
    3508         343 :                     rTextNode.AddToList();
    3509             :                 }
    3510             :             }
    3511             :             else // <sNumRule.Len() == 0 && sOldNumRule.Len() != 0>
    3512             :             {
    3513         150 :                 rTextNode.RemoveFromList();
    3514         150 :                 if ( bParagraphStyleChanged )
    3515             :                 {
    3516         150 :                     lcl_ResetParAttrs(rTextNode);
    3517             :                     // #i70748#
    3518         150 :                     if ( dynamic_cast<const SfxUInt16Item &>(rTextNode.GetAttr( RES_PARATR_OUTLINELEVEL, false )).GetValue() > 0 )
    3519             :                     {
    3520           0 :                         rTextNode.SetEmptyListStyleDueToSetOutlineLevelAttr();
    3521             :                     }
    3522             :                 }
    3523             :             }
    3524             :         }
    3525      329280 :         else if (!sNumRule.isEmpty() && !rTextNode.IsInList())
    3526             :         {
    3527           0 :             rTextNode.AddToList();
    3528      329773 :         }
    3529      329773 :     }
    3530             :     // End of method <HandleModifyAtTextNode>
    3531             : }
    3532             : 
    3533      372280 : void SwTextNode::Modify( const SfxPoolItem* pOldValue, const SfxPoolItem* pNewValue )
    3534             : {
    3535      372280 :     bool bWasNotifiable = m_bNotifiable;
    3536      372280 :     m_bNotifiable = false;
    3537             : 
    3538             :     // Override Modify so that deleting styles works properly (outline
    3539             :     // numbering!).
    3540             :     // Never call _ChgTextCollUpdateNum for Nodes in Undo.
    3541      679396 :     if( pOldValue && pNewValue && RES_FMT_CHG == pOldValue->Which() &&
    3542      382205 :         GetRegisteredIn() == static_cast<const SwFormatChg*>(pNewValue)->pChangedFormat &&
    3543         112 :         GetNodes().IsDocNodes() )
    3544             :     {
    3545             :         _ChgTextCollUpdateNum(
    3546             :                         static_cast<const SwTextFormatColl*>(static_cast<const SwFormatChg*>(pOldValue)->pChangedFormat),
    3547         112 :                         static_cast<const SwTextFormatColl*>(static_cast<const SwFormatChg*>(pNewValue)->pChangedFormat) );
    3548             :     }
    3549             : 
    3550             :     //UUUU reset fill information
    3551      372280 :     if(maFillAttributes.get())
    3552             :     {
    3553       69530 :         const sal_uInt16 nWhich = pNewValue ? pNewValue->Which() : 0;
    3554       69530 :         bool bReset(RES_FMT_CHG == nWhich); // ..on format change (e.g. style changed)
    3555             : 
    3556       69530 :         if(!bReset && RES_ATTRSET_CHG == nWhich) // ..on ItemChange from DrawingLayer FillAttributes
    3557             :         {
    3558       61232 :             SfxItemIter aIter(*static_cast<const SwAttrSetChg*>(pNewValue)->GetChgSet());
    3559             : 
    3560      122568 :             for(const SfxPoolItem* pItem = aIter.FirstItem(); pItem && !bReset; pItem = aIter.NextItem())
    3561             :             {
    3562       61336 :                 bReset = !IsInvalidItem(pItem) && pItem->Which() >= XATTR_FILL_FIRST && pItem->Which() <= XATTR_FILL_LAST;
    3563       61232 :             }
    3564             :         }
    3565             : 
    3566       69530 :         if(bReset)
    3567             :         {
    3568          60 :             maFillAttributes.reset();
    3569             :         }
    3570             :     }
    3571             : 
    3572      372280 :     if ( !mbInSetOrResetAttr )
    3573             :     {
    3574      316305 :         HandleModifyAtTextNode( *this, pOldValue, pNewValue );
    3575             :     }
    3576             : 
    3577      372280 :     SwContentNode::Modify( pOldValue, pNewValue );
    3578             : 
    3579      372280 :     SwDoc * pDoc = GetDoc();
    3580             :     // #125329# - assure that text node is in document nodes array
    3581      372280 :     if ( pDoc && !pDoc->IsInDtor() && &pDoc->GetNodes() == &GetNodes() )
    3582             :     {
    3583      308226 :         pDoc->GetNodes().UpdateOutlineNode(*this);
    3584             :     }
    3585             : 
    3586      372280 :     m_bNotifiable = bWasNotifiable;
    3587             : 
    3588      372280 :     if (pOldValue && (RES_REMOVE_UNO_OBJECT == pOldValue->Which()))
    3589             :     {   // invalidate cached uno object
    3590             :         SetXParagraph(::com::sun::star::uno::Reference<
    3591           0 :                 ::com::sun::star::text::XTextContent>(0));
    3592             :     }
    3593      372280 : }
    3594             : 
    3595       42184 : SwFormatColl* SwTextNode::ChgFormatColl( SwFormatColl *pNewColl )
    3596             : {
    3597             :     OSL_ENSURE( pNewColl,"ChgFormatColl: Collectionpointer has value 0." );
    3598             :     OSL_ENSURE( HAS_BASE( SwTextFormatColl, pNewColl ),
    3599             :                 "ChgFormatColl: is not a Text Collection pointer." );
    3600             : 
    3601       42184 :     SwTextFormatColl *pOldColl = GetTextColl();
    3602       42184 :     if( pNewColl != pOldColl )
    3603             :     {
    3604       13468 :         SetCalcHiddenCharFlags();
    3605       13468 :         SwContentNode::ChgFormatColl( pNewColl );
    3606             :         OSL_ENSURE( !mbInSetOrResetAttr,
    3607             :                 "DEBUG OSL_ENSURE(ON - <SwTextNode::ChgFormatColl(..)> called during <Set/ResetAttr(..)>" );
    3608       13468 :         if ( !mbInSetOrResetAttr )
    3609             :         {
    3610       13468 :             SwFormatChg aTmp1( pOldColl );
    3611       26936 :             SwFormatChg aTmp2( pNewColl );
    3612       26936 :             HandleModifyAtTextNode( *this, &aTmp1, &aTmp2  );
    3613             :         }
    3614             : 
    3615             :         //UUUU reset fill information on parent style change
    3616       13468 :         if(maFillAttributes.get())
    3617             :         {
    3618          23 :             maFillAttributes.reset();
    3619             :         }
    3620             :     }
    3621             : 
    3622             :     // nur wenn im normalen Nodes-Array
    3623       42184 :     if( GetNodes().IsDocNodes() )
    3624             :     {
    3625       42184 :         _ChgTextCollUpdateNum( pOldColl, static_cast<SwTextFormatColl *>(pNewColl) );
    3626             :     }
    3627             : 
    3628       42184 :     GetNodes().UpdateOutlineNode(*this);
    3629             : 
    3630       42184 :     return pOldColl;
    3631             : }
    3632             : 
    3633        5620 : SwNodeNum* SwTextNode::CreateNum() const
    3634             : {
    3635        5620 :     if ( !mpNodeNum )
    3636             :     {
    3637        5620 :         mpNodeNum = new SwNodeNum( const_cast<SwTextNode*>(this) );
    3638             :     }
    3639        5620 :     return mpNodeNum;
    3640             : }
    3641             : 
    3642           0 : SwNumberTree::tNumberVector SwTextNode::GetNumberVector() const
    3643             : {
    3644           0 :     if ( GetNum() )
    3645             :     {
    3646           0 :         return GetNum()->GetNumberVector();
    3647             :     }
    3648             :     else
    3649             :     {
    3650           0 :         SwNumberTree::tNumberVector aResult;
    3651           0 :         return aResult;
    3652             :     }
    3653             : }
    3654             : 
    3655      518959 : bool SwTextNode::IsOutline() const
    3656             : {
    3657      518959 :     bool bResult = false;
    3658             : 
    3659      518959 :     if ( GetAttrOutlineLevel() > 0 )
    3660             :     {
    3661       16679 :         bResult = !IsInRedlines();
    3662             :     }
    3663             :     else
    3664             :     {
    3665      502280 :         const SwNumRule* pRule( GetNum() ? GetNum()->GetNumRule() : 0L );
    3666      502280 :         if ( pRule && pRule->IsOutlineRule() )
    3667             :         {
    3668          15 :             bResult = !IsInRedlines();
    3669             :         }
    3670             :     }
    3671             : 
    3672      518959 :     return bResult;
    3673             : }
    3674             : 
    3675      498187 : bool SwTextNode::IsOutlineStateChanged() const
    3676             : {
    3677      498187 :     return IsOutline() != m_bLastOutlineState;
    3678             : }
    3679             : 
    3680        1924 : void SwTextNode::UpdateOutlineState()
    3681             : {
    3682        1924 :     m_bLastOutlineState = IsOutline();
    3683        1924 : }
    3684             : 
    3685      537370 : int SwTextNode::GetAttrOutlineLevel() const
    3686             : {
    3687      537370 :     return static_cast<const SfxUInt16Item &>(GetAttr(RES_PARATR_OUTLINELEVEL)).GetValue();
    3688             : }
    3689             : 
    3690           0 : void SwTextNode::SetAttrOutlineLevel(int nLevel)
    3691             : {
    3692             :     assert(0 <= nLevel && nLevel <= MAXLEVEL); // Level Out Of Range
    3693           0 :     if ( 0 <= nLevel && nLevel <= MAXLEVEL )
    3694             :     {
    3695             :         SetAttr( SfxUInt16Item( RES_PARATR_OUTLINELEVEL,
    3696           0 :                                 static_cast<sal_uInt16>(nLevel) ) );
    3697             :     }
    3698           0 : }
    3699             : 
    3700             : // #i70748#
    3701             : 
    3702         285 : void SwTextNode::SetEmptyListStyleDueToSetOutlineLevelAttr()
    3703             : {
    3704         285 :     if ( !mbEmptyListStyleSetDueToSetOutlineLevelAttr )
    3705             :     {
    3706         280 :         SetAttr( SwNumRuleItem() );
    3707         280 :         mbEmptyListStyleSetDueToSetOutlineLevelAttr = true;
    3708             :     }
    3709         285 : }
    3710             : 
    3711       12104 : void SwTextNode::ResetEmptyListStyleDueToResetOutlineLevelAttr()
    3712             : {
    3713       12104 :     if ( mbEmptyListStyleSetDueToSetOutlineLevelAttr )
    3714             :     {
    3715           5 :         ResetAttr( RES_PARATR_NUMRULE );
    3716           5 :         mbEmptyListStyleSetDueToSetOutlineLevelAttr = false;
    3717             :     }
    3718       12104 : }
    3719             : 
    3720        5276 : void SwTextNode::SetAttrListLevel( int nLevel )
    3721             : {
    3722        5276 :     if ( nLevel < 0 || nLevel >= MAXLEVEL )
    3723             :     {
    3724             :         assert(false); // invalid level
    3725        5276 :         return;
    3726             :     }
    3727             : 
    3728             :     SfxInt16Item aNewListLevelItem( RES_PARATR_LIST_LEVEL,
    3729        5276 :                                     static_cast<sal_Int16>(nLevel) );
    3730        5276 :     SetAttr( aNewListLevelItem );
    3731             : }
    3732             : 
    3733       39436 : bool SwTextNode::HasAttrListLevel() const
    3734             : {
    3735       43917 :     return GetpSwAttrSet() &&
    3736       43917 :            GetpSwAttrSet()->GetItemState( RES_PARATR_LIST_LEVEL, false ) == SfxItemState::SET;
    3737             : }
    3738             : 
    3739       14862 : int SwTextNode::GetAttrListLevel() const
    3740             : {
    3741       14862 :     int nAttrListLevel = 0;
    3742             : 
    3743             :     const SfxInt16Item& aListLevelItem =
    3744       14862 :         dynamic_cast<const SfxInt16Item&>(GetAttr( RES_PARATR_LIST_LEVEL ));
    3745       14862 :     nAttrListLevel = static_cast<int>(aListLevelItem.GetValue());
    3746             : 
    3747       14862 :     return nAttrListLevel;
    3748             : }
    3749             : 
    3750      213175 : int SwTextNode::GetActualListLevel() const
    3751             : {
    3752      213175 :     return GetNum() ? GetNum()->GetLevelInListTree() : -1;
    3753             : }
    3754             : 
    3755          23 : void SwTextNode::SetListRestart( bool bRestart )
    3756             : {
    3757          23 :     if ( !bRestart )
    3758             :     {
    3759             :         // attribute not contained in paragraph style's attribute set. Thus,
    3760             :         // it can be reset to the attribute pool default by resetting the attribute.
    3761           0 :         ResetAttr( RES_PARATR_LIST_ISRESTART );
    3762             :     }
    3763             :     else
    3764             :     {
    3765             :         SfxBoolItem aNewIsRestartItem( RES_PARATR_LIST_ISRESTART,
    3766          23 :                                        true );
    3767          23 :         SetAttr( aNewIsRestartItem );
    3768             :     }
    3769          23 : }
    3770             : 
    3771       42724 : bool SwTextNode::IsListRestart() const
    3772             : {
    3773             :     const SfxBoolItem& aIsRestartItem =
    3774       42724 :         dynamic_cast<const SfxBoolItem&>(GetAttr( RES_PARATR_LIST_ISRESTART ));
    3775             : 
    3776       42724 :     return aIsRestartItem.GetValue();
    3777             : }
    3778             : 
    3779             : /** Returns if the paragraph has a visible numbering or bullet.
    3780             :     This includes all kinds of numbering/bullet/outlines.
    3781             :     The concrete list label string has to be checked, too.
    3782             :  */
    3783       21809 : bool SwTextNode::HasVisibleNumberingOrBullet() const
    3784             : {
    3785       21809 :     const SwNumRule* pRule = GetNum() ? GetNum()->GetNumRule() : 0L;
    3786       21809 :     if ( pRule && IsCountedInList())
    3787             :     {
    3788             :         // #i87154#
    3789             :         // Correction of #newlistlevelattrs#:
    3790             :         // The numbering type has to be checked for bullet lists.
    3791       21663 :         const SwNumFormat& rFormat = pRule->Get( lcl_BoundListLevel(GetActualListLevel()) );
    3792       24725 :         return SVX_NUM_NUMBER_NONE != rFormat.GetNumberingType() ||
    3793       24725 :                !pRule->MakeNumString( *(GetNum()) ).isEmpty();
    3794             :     }
    3795             : 
    3796         146 :     return false;
    3797             : }
    3798             : 
    3799          10 : void SwTextNode::SetAttrListRestartValue( SwNumberTree::tSwNumTreeNumber nNumber )
    3800             : {
    3801          10 :     const bool bChanged( HasAttrListRestartValue()
    3802           0 :                          ? GetAttrListRestartValue() != nNumber
    3803          10 :                          : nNumber != USHRT_MAX );
    3804             : 
    3805          10 :     if ( bChanged || !HasAttrListRestartValue() )
    3806             :     {
    3807          10 :         if ( nNumber == USHRT_MAX )
    3808             :         {
    3809           0 :             ResetAttr( RES_PARATR_LIST_RESTARTVALUE );
    3810             :         }
    3811             :         else
    3812             :         {
    3813             :             SfxInt16Item aNewListRestartValueItem( RES_PARATR_LIST_RESTARTVALUE,
    3814          10 :                                                    static_cast<sal_Int16>(nNumber) );
    3815          10 :             SetAttr( aNewListRestartValueItem );
    3816             :         }
    3817             :     }
    3818          10 : }
    3819             : 
    3820       37922 : bool SwTextNode::HasAttrListRestartValue() const
    3821             : {
    3822       41381 :     return GetpSwAttrSet() &&
    3823       41381 :            GetpSwAttrSet()->GetItemState( RES_PARATR_LIST_RESTARTVALUE, false ) == SfxItemState::SET;
    3824             : }
    3825          16 : SwNumberTree::tSwNumTreeNumber SwTextNode::GetAttrListRestartValue() const
    3826             : {
    3827             :     OSL_ENSURE( HasAttrListRestartValue(),
    3828             :             "<SwTextNode::GetAttrListRestartValue()> - only ask for list restart value, if attribute is set at text node." );
    3829             : 
    3830             :     const SfxInt16Item& aListRestartValueItem =
    3831          16 :         dynamic_cast<const SfxInt16Item&>(GetAttr( RES_PARATR_LIST_RESTARTVALUE ));
    3832          16 :     return static_cast<SwNumberTree::tSwNumTreeNumber>(aListRestartValueItem.GetValue());
    3833             : }
    3834             : 
    3835         227 : SwNumberTree::tSwNumTreeNumber SwTextNode::GetActualListStartValue() const
    3836             : {
    3837         227 :     SwNumberTree::tSwNumTreeNumber nListRestartValue = 1;
    3838             : 
    3839         227 :     if ( IsListRestart() && HasAttrListRestartValue() )
    3840             :     {
    3841          16 :         nListRestartValue = GetAttrListRestartValue();
    3842             :     }
    3843             :     else
    3844             :     {
    3845         211 :         SwNumRule* pRule = GetNumRule();
    3846         211 :         if ( pRule )
    3847             :         {
    3848             :             const SwNumFormat* pFormat =
    3849         211 :                     pRule->GetNumFormat( static_cast<sal_uInt16>(GetAttrListLevel()) );
    3850         211 :             if ( pFormat )
    3851             :             {
    3852         211 :                 nListRestartValue = pFormat->GetStart();
    3853             :             }
    3854             :         }
    3855             :     }
    3856             : 
    3857         227 :     return nListRestartValue;
    3858             : }
    3859             : 
    3860       77268 : bool SwTextNode::IsNotifiable() const
    3861             : {
    3862       77268 :     return m_bNotifiable && IsNotificationEnabled();
    3863             : }
    3864             : 
    3865       83445 : bool SwTextNode::IsNotificationEnabled() const
    3866             : {
    3867       83445 :     bool bResult = false;
    3868       83445 :     const SwDoc * pDoc = GetDoc();
    3869       83445 :     if( pDoc )
    3870             :     {
    3871       83445 :         bResult = !(pDoc->IsInReading() || pDoc->IsInDtor());
    3872             :     }
    3873       83445 :     return bResult;
    3874             : }
    3875             : 
    3876         874 : void SwTextNode::SetCountedInList( bool bCounted )
    3877             : {
    3878         874 :     if ( bCounted )
    3879             :     {
    3880             :         // attribute not contained in paragraph style's attribute set. Thus,
    3881             :         // it can be reset to the attribute pool default by resetting the attribute.
    3882         844 :         ResetAttr( RES_PARATR_LIST_ISCOUNTED );
    3883             :     }
    3884             :     else
    3885             :     {
    3886          30 :         SfxBoolItem aIsCountedInListItem( RES_PARATR_LIST_ISCOUNTED, false );
    3887          30 :         SetAttr( aIsCountedInListItem );
    3888             :     }
    3889         874 : }
    3890             : 
    3891      124655 : bool SwTextNode::IsCountedInList() const
    3892             : {
    3893             :     const SfxBoolItem& aIsCountedInListItem =
    3894      124655 :         dynamic_cast<const SfxBoolItem&>(GetAttr( RES_PARATR_LIST_ISCOUNTED ));
    3895             : 
    3896      124655 :     return aIsCountedInListItem.GetValue();
    3897             : }
    3898             : 
    3899        5914 : void SwTextNode::AddToList()
    3900             : {
    3901        5914 :     if ( IsInList() )
    3902             :     {
    3903             :         OSL_FAIL( "<SwTextNode::AddToList()> - the text node is already added to a list. Serious defect -> please inform OD" );
    3904        5914 :         return;
    3905             :     }
    3906             : 
    3907        5914 :     const OUString sListId = GetListId();
    3908        5914 :     if (!sListId.isEmpty())
    3909             :     {
    3910        5620 :         SwList* pList = GetDoc()->getIDocumentListsAccess().getListByName( sListId );
    3911        5620 :         if ( pList == 0 )
    3912             :         {
    3913             :             // Create corresponding list.
    3914           0 :             SwNumRule* pNumRule = GetNumRule();
    3915           0 :             if ( pNumRule )
    3916             :             {
    3917           0 :                 pList = GetDoc()->getIDocumentListsAccess().createList( sListId, GetNumRule()->GetName() );
    3918             :             }
    3919             :         }
    3920             :         OSL_ENSURE( pList != 0,
    3921             :                 "<SwTextNode::AddToList()> - no list for given list id. Serious defect -> please inform OD" );
    3922        5620 :         if ( pList )
    3923             :         {
    3924        5620 :             pList->InsertListItem( *CreateNum(), GetAttrListLevel() );
    3925        5620 :             mpList = pList;
    3926             :         }
    3927        5914 :     }
    3928             : }
    3929             : 
    3930      117902 : void SwTextNode::RemoveFromList()
    3931             : {
    3932      117902 :     if ( IsInList() )
    3933             :     {
    3934        5620 :         SwList::RemoveListItem( *mpNodeNum );
    3935        5620 :         mpList = 0;
    3936        5620 :         delete mpNodeNum;
    3937        5620 :         mpNodeNum = 0L;
    3938             : 
    3939        5620 :         SetWordCountDirty( true );
    3940             :     }
    3941      117902 : }
    3942             : 
    3943      505237 : bool SwTextNode::IsInList() const
    3944             : {
    3945      505237 :     return GetNum() != 0 && GetNum()->GetParent() != 0;
    3946             : }
    3947             : 
    3948           0 : bool SwTextNode::IsFirstOfNumRule() const
    3949             : {
    3950           0 :     bool bResult = false;
    3951             : 
    3952           0 :     if ( GetNum() && GetNum()->GetNumRule())
    3953           0 :         bResult = GetNum()->IsFirst();
    3954             : 
    3955           0 :     return bResult;
    3956             : }
    3957             : 
    3958         211 : void SwTextNode::SetListId(OUString const& rListId)
    3959             : {
    3960             :     const SfxStringItem& rListIdItem =
    3961         211 :             dynamic_cast<const SfxStringItem&>(GetAttr( RES_PARATR_LIST_ID ));
    3962         211 :     if (rListIdItem.GetValue() != rListId)
    3963             :     {
    3964         211 :         if (rListId.isEmpty())
    3965             :         {
    3966           0 :             ResetAttr( RES_PARATR_LIST_ID );
    3967             :         }
    3968             :         else
    3969             :         {
    3970         211 :             SfxStringItem aNewListIdItem(RES_PARATR_LIST_ID, rListId);
    3971         211 :             SetAttr( aNewListIdItem );
    3972             :         }
    3973             :     }
    3974         211 : }
    3975             : 
    3976       13598 : OUString SwTextNode::GetListId() const
    3977             : {
    3978       13598 :     OUString sListId;
    3979             : 
    3980             :     const SfxStringItem& rListIdItem =
    3981       13598 :                 dynamic_cast<const SfxStringItem&>(GetAttr( RES_PARATR_LIST_ID ));
    3982       13598 :     sListId = rListIdItem.GetValue();
    3983             : 
    3984             :     // As long as no explicit list id attribute is set, use the list id of
    3985             :     // the list, which has been created for the applied list style.
    3986       13598 :     if (sListId.isEmpty())
    3987             :     {
    3988       11901 :         SwNumRule* pRule = GetNumRule();
    3989       11901 :         if ( pRule )
    3990             :         {
    3991       11554 :             sListId = pRule->GetDefaultListId();
    3992             :         }
    3993             :     }
    3994             : 
    3995       13598 :     return sListId;
    3996             : }
    3997             : 
    3998             : /** Determines, if the list level indent attributes can be applied to the
    3999             :     paragraph.
    4000             : 
    4001             :     The list level indents can be applied to the paragraph under the one
    4002             :     of following conditions:
    4003             :     - the list style is directly applied to the paragraph and the paragraph
    4004             :       has no own indent attributes.
    4005             :     - the list style is applied to the paragraph through one of its paragraph
    4006             :       styles, the paragraph has no own indent attributes and on the paragraph
    4007             :       style hierarchy from the paragraph to the paragraph style with the
    4008             :       list style no indent attributes are found.
    4009             : 
    4010             :     @return boolean
    4011             : */
    4012      147373 : bool SwTextNode::AreListLevelIndentsApplicable() const
    4013             : {
    4014      147373 :     bool bAreListLevelIndentsApplicable( true );
    4015             : 
    4016      147373 :     if ( !GetNum() || !GetNum()->GetNumRule() )
    4017             :     {
    4018             :         // no list style applied to paragraph
    4019       49323 :         bAreListLevelIndentsApplicable = false;
    4020             :     }
    4021      196100 :     else if ( HasSwAttrSet() &&
    4022       98050 :               GetpSwAttrSet()->GetItemState( RES_LR_SPACE, false ) == SfxItemState::SET )
    4023             :     {
    4024             :         // paragraph has hard-set indent attributes
    4025       34831 :         bAreListLevelIndentsApplicable = false;
    4026             :     }
    4027      126438 :     else if ( HasSwAttrSet() &&
    4028       63219 :               GetpSwAttrSet()->GetItemState( RES_PARATR_NUMRULE, false ) == SfxItemState::SET )
    4029             :     {
    4030             :         // list style is directly applied to paragraph and paragraph has no
    4031             :         // hard-set indent attributes
    4032       59338 :         bAreListLevelIndentsApplicable = true;
    4033             :     }
    4034             :     else
    4035             :     {
    4036             :         // list style is applied through one of the paragraph styles and
    4037             :         // paragraph has no hard-set indent attributes
    4038             : 
    4039             :         // check, paragraph's
    4040        3881 :         const SwTextFormatColl* pColl = GetTextColl();
    4041        7762 :         while ( pColl )
    4042             :         {
    4043        3881 :             if ( pColl->GetAttrSet().GetItemState( RES_LR_SPACE, false ) == SfxItemState::SET )
    4044             :             {
    4045             :                 // indent attributes found in the paragraph style hierarchy.
    4046           0 :                 bAreListLevelIndentsApplicable = false;
    4047           0 :                 break;
    4048             :             }
    4049             : 
    4050        3881 :             if ( pColl->GetAttrSet().GetItemState( RES_PARATR_NUMRULE, false ) == SfxItemState::SET )
    4051             :             {
    4052             :                 // paragraph style with the list style found and until now no
    4053             :                 // indent attributes are found in the paragraph style hierarchy.
    4054        3881 :                 bAreListLevelIndentsApplicable = true;
    4055        3881 :                 break;
    4056             :             }
    4057             : 
    4058           0 :             pColl = dynamic_cast<const SwTextFormatColl*>(pColl->DerivedFrom());
    4059             :             OSL_ENSURE( pColl,
    4060             :                     "<SwTextNode::AreListLevelIndentsApplicable()> - something wrong in paragraph's style hierarchy. The applied list style is not found." );
    4061             :         }
    4062             :     }
    4063             : 
    4064      147373 :     return bAreListLevelIndentsApplicable;
    4065             : }
    4066             : 
    4067             : /** Retrieves the list tab stop position, if the paragraph's list level defines
    4068             :     one and this list tab stop has to merged into the tap stops of the paragraph
    4069             : 
    4070             :     @param nListTabStopPosition
    4071             :     output parameter - containing the list tab stop position
    4072             : 
    4073             :     @return boolean - indicating, if a list tab stop position is provided
    4074             : */
    4075      184833 : bool SwTextNode::GetListTabStopPosition( long& nListTabStopPosition ) const
    4076             : {
    4077      184833 :     bool bListTanStopPositionProvided( false );
    4078             : 
    4079      184833 :     const SwNumRule* pNumRule = GetNum() ? GetNum()->GetNumRule() : 0;
    4080      184833 :     if ( pNumRule && HasVisibleNumberingOrBullet() && GetActualListLevel() >= 0 )
    4081             :     {
    4082       14096 :         const SwNumFormat& rFormat = pNumRule->Get( static_cast<sal_uInt16>(GetActualListLevel()) );
    4083       26790 :         if ( rFormat.GetPositionAndSpaceMode() == SvxNumberFormat::LABEL_ALIGNMENT &&
    4084       12694 :              rFormat.GetLabelFollowedBy() == SvxNumberFormat::LISTTAB )
    4085             :         {
    4086       11899 :             bListTanStopPositionProvided = true;
    4087       11899 :             nListTabStopPosition = rFormat.GetListtabPos();
    4088             : 
    4089       11899 :             if ( getIDocumentSettingAccess()->get(DocumentSettingId::TABS_RELATIVE_TO_INDENT) )
    4090             :             {
    4091             :                 // tab stop position are treated to be relative to the "before text"
    4092             :                 // indent value of the paragraph. Thus, adjust <nListTabStopPos>.
    4093        1297 :                 if ( AreListLevelIndentsApplicable() )
    4094             :                 {
    4095        1297 :                     nListTabStopPosition -= rFormat.GetIndentAt();
    4096             :                 }
    4097           0 :                 else if (!getIDocumentSettingAccess()->get(DocumentSettingId::IGNORE_FIRST_LINE_INDENT_IN_NUMBERING))
    4098             :                 {
    4099           0 :                     SvxLRSpaceItem aItem = GetSwAttrSet().GetLRSpace();
    4100           0 :                     nListTabStopPosition -= aItem.GetTextLeft();
    4101             :                 }
    4102             :             }
    4103             :         }
    4104             :     }
    4105             : 
    4106      184833 :     return bListTanStopPositionProvided;
    4107             : }
    4108             : 
    4109        6998 : OUString SwTextNode::GetLabelFollowedBy() const
    4110             : {
    4111        6998 :     const SwNumRule* pNumRule = GetNum() ? GetNum()->GetNumRule() : 0;
    4112        6998 :     if ( pNumRule && HasVisibleNumberingOrBullet() && GetActualListLevel() >= 0 )
    4113             :     {
    4114        6998 :         const SwNumFormat& rFormat = pNumRule->Get( static_cast<sal_uInt16>(GetActualListLevel()) );
    4115        6998 :         if ( rFormat.GetPositionAndSpaceMode() == SvxNumberFormat::LABEL_ALIGNMENT )
    4116             :         {
    4117        6561 :             switch ( rFormat.GetLabelFollowedBy() )
    4118             :             {
    4119             :                 case SvxNumberFormat::LISTTAB:
    4120             :                 {
    4121        6210 :                     return OUString("\t");
    4122             :                 }
    4123             :                 break;
    4124             :                 case SvxNumberFormat::SPACE:
    4125             :                 {
    4126          63 :                     return OUString(" ");
    4127             :                 }
    4128             :                 break;
    4129             :                 case SvxNumberFormat::NOTHING:
    4130             :                 {
    4131             :                     // intentionally left blank.
    4132             :                 }
    4133         288 :                 break;
    4134             :                 default:
    4135             :                 {
    4136             :                     OSL_FAIL( "<SwTextNode::GetLabelFollowedBy()> - unknown SvxNumberFormat::GetLabelFollowedBy() return value" );
    4137             :                 }
    4138             :             }
    4139             :         }
    4140             :     }
    4141             : 
    4142         725 :     return OUString();
    4143             : }
    4144             : 
    4145       34175 : void SwTextNode::CalcHiddenCharFlags() const
    4146             : {
    4147             :     sal_Int32 nStartPos;
    4148             :     sal_Int32 nEndPos;
    4149             :     // Update of the flags is done inside GetBoundsOfHiddenRange()
    4150       34175 :     SwScriptInfo::GetBoundsOfHiddenRange( *this, 0, nStartPos, nEndPos );
    4151       34175 : }
    4152             : 
    4153             : // #i12836# enhanced pdf export
    4154    11461694 : bool SwTextNode::IsHidden() const
    4155             : {
    4156    11461694 :     if ( HasHiddenParaField() || HasHiddenCharAttribute( true ) )
    4157         135 :         return true;
    4158             : 
    4159    11461559 :     const SwSectionNode* pSectNd = FindSectionNode();
    4160    11461559 :     if ( pSectNd && pSectNd->GetSection().IsHiddenFlag() )
    4161           0 :         return true;
    4162             : 
    4163    11461559 :     return false;
    4164             : }
    4165             : 
    4166             : namespace {
    4167             :     // Helper class for special handling of setting attributes at text node:
    4168             :     // In constructor an instance of the helper class recognize whose attributes
    4169             :     // are set and perform corresponding actions before the intrinsic set of
    4170             :     // attributes has been taken place.
    4171             :     // In the destructor - after the attributes have been set at the text
    4172             :     // node - corresponding actions are performed.
    4173             :     // The following is handled:
    4174             :     // (1) When the list style attribute - RES_PARATR_NUMRULE - is set,
    4175             :     //     (A) list style attribute is empty -> the text node is removed from
    4176             :     //         its list.
    4177             :     //     (B) list style attribute is not empty
    4178             :     //         (a) text node has no list style -> add text node to its list after
    4179             :     //             the attributes have been set.
    4180             :     //         (b) text node has list style -> change of list style is notified
    4181             :     //             after the attributes have been set.
    4182             :     // (2) When the list id attribute - RES_PARATR_LIST_ID - is set and changed,
    4183             :     //     the text node is removed from its current list before the attributes
    4184             :     //     are set and added to its new list after the attributes have been set.
    4185             :     // (3) Notify list tree, if list level - RES_PARATR_LIST_LEVEL - is set
    4186             :     //     and changed after the attributes have been set
    4187             :     // (4) Notify list tree, if list restart - RES_PARATR_LIST_ISRESTART - is set
    4188             :     //     and changed after the attributes have been set
    4189             :     // (5) Notify list tree, if list restart value - RES_PARATR_LIST_RESTARTVALUE -
    4190             :     //     is set and changed after the attributes have been set
    4191             :     // (6) Notify list tree, if count in list - RES_PARATR_LIST_ISCOUNTED - is set
    4192             :     //     and changed after the attributes have been set
    4193             :     // (7) Set or Reset emtpy list style due to changed outline level - RES_PARATR_OUTLINELEVEL.
    4194             :     class HandleSetAttrAtTextNode
    4195             :     {
    4196             :         public:
    4197             :             HandleSetAttrAtTextNode( SwTextNode& rTextNode,
    4198             :                                     const SfxPoolItem& pItem );
    4199             :             HandleSetAttrAtTextNode( SwTextNode& rTextNode,
    4200             :                                     const SfxItemSet& rItemSet );
    4201             :             ~HandleSetAttrAtTextNode();
    4202             : 
    4203             :         private:
    4204             :             SwTextNode& mrTextNode;
    4205             :             bool mbAddTextNodeToList;
    4206             :             bool mbUpdateListLevel;
    4207             :             bool mbUpdateListRestart;
    4208             :             bool mbUpdateListCount;
    4209             :             // #i70748#
    4210             :             bool mbOutlineLevelSet;
    4211             :     };
    4212             : 
    4213       11889 :     HandleSetAttrAtTextNode::HandleSetAttrAtTextNode( SwTextNode& rTextNode,
    4214             :                                                     const SfxPoolItem& pItem )
    4215             :         : mrTextNode( rTextNode ),
    4216             :           mbAddTextNodeToList( false ),
    4217             :           mbUpdateListLevel( false ),
    4218             :           mbUpdateListRestart( false ),
    4219             :           mbUpdateListCount( false ),
    4220             :           // #i70748#
    4221       11889 :           mbOutlineLevelSet( false )
    4222             :     {
    4223       11889 :         switch ( pItem.Which() )
    4224             :         {
    4225             :             // handle RES_PARATR_NUMRULE
    4226             :             case RES_PARATR_NUMRULE:
    4227             :             {
    4228         829 :                 mrTextNode.RemoveFromList();
    4229             : 
    4230             :                 const SwNumRuleItem& pNumRuleItem =
    4231         829 :                                 dynamic_cast<const SwNumRuleItem&>(pItem);
    4232         829 :                 if ( !pNumRuleItem.GetValue().isEmpty() )
    4233             :                 {
    4234         505 :                     mbAddTextNodeToList = true;
    4235             :                     // #i105562#
    4236             : 
    4237         505 :                     mrTextNode.ResetEmptyListStyleDueToResetOutlineLevelAttr();
    4238             :                 }
    4239             :             }
    4240         829 :             break;
    4241             : 
    4242             :             // handle RES_PARATR_LIST_ID
    4243             :             case RES_PARATR_LIST_ID:
    4244             :             {
    4245             :                 const SfxStringItem& pListIdItem =
    4246         211 :                                         dynamic_cast<const SfxStringItem&>(pItem);
    4247             :                 OSL_ENSURE( pListIdItem.GetValue().getLength() > 0,
    4248             :                         "<HandleSetAttrAtTextNode(..)> - empty list id attribute not excepted. Serious defect -> please inform OD." );
    4249         211 :                 const OUString sListIdOfTextNode = rTextNode.GetListId();
    4250         211 :                 if ( pListIdItem.GetValue() != sListIdOfTextNode )
    4251             :                 {
    4252           0 :                     mbAddTextNodeToList = true;
    4253           0 :                     if ( mrTextNode.IsInList() )
    4254             :                     {
    4255           0 :                         mrTextNode.RemoveFromList();
    4256             :                     }
    4257         211 :                 }
    4258             :             }
    4259         211 :             break;
    4260             : 
    4261             :             // handle RES_PARATR_LIST_LEVEL
    4262             :             case RES_PARATR_LIST_LEVEL:
    4263             :             {
    4264             :                 const SfxInt16Item& aListLevelItem =
    4265        5276 :                                     dynamic_cast<const SfxInt16Item&>(pItem);
    4266        5276 :                 if ( aListLevelItem.GetValue() != mrTextNode.GetAttrListLevel() )
    4267             :                 {
    4268         968 :                     mbUpdateListLevel = true;
    4269             :                 }
    4270             :             }
    4271        5276 :             break;
    4272             : 
    4273             :             // handle RES_PARATR_LIST_ISRESTART
    4274             :             case RES_PARATR_LIST_ISRESTART:
    4275             :             {
    4276             :                 const SfxBoolItem& aListIsRestartItem =
    4277          23 :                                     dynamic_cast<const SfxBoolItem&>(pItem);
    4278          46 :                 if ( aListIsRestartItem.GetValue() !=
    4279          23 :                                     mrTextNode.IsListRestart() )
    4280             :                 {
    4281          23 :                     mbUpdateListRestart = true;
    4282             :                 }
    4283             :             }
    4284          23 :             break;
    4285             : 
    4286             :             // handle RES_PARATR_LIST_RESTARTVALUE
    4287             :             case RES_PARATR_LIST_RESTARTVALUE:
    4288             :             {
    4289             :                 const SfxInt16Item& aListRestartValueItem =
    4290          10 :                                     dynamic_cast<const SfxInt16Item&>(pItem);
    4291          10 :                 if ( !mrTextNode.HasAttrListRestartValue() ||
    4292           0 :                      aListRestartValueItem.GetValue() != mrTextNode.GetAttrListRestartValue() )
    4293             :                 {
    4294          10 :                     mbUpdateListRestart = true;
    4295             :                 }
    4296             :             }
    4297          10 :             break;
    4298             : 
    4299             :             // handle RES_PARATR_LIST_ISCOUNTED
    4300             :             case RES_PARATR_LIST_ISCOUNTED:
    4301             :             {
    4302             :                 const SfxBoolItem& aIsCountedInListItem =
    4303          30 :                                     dynamic_cast<const SfxBoolItem&>(pItem);
    4304          60 :                 if ( aIsCountedInListItem.GetValue() !=
    4305          30 :                                     mrTextNode.IsCountedInList() )
    4306             :                 {
    4307          30 :                     mbUpdateListCount = true;
    4308             :                 }
    4309             :             }
    4310          30 :             break;
    4311             : 
    4312             :             // #i70748#
    4313             :             // handle RES_PARATR_OUTLINELEVEL
    4314             :             case RES_PARATR_OUTLINELEVEL:
    4315             :             {
    4316             :                 const SfxUInt16Item& aOutlineLevelItem =
    4317           0 :                                     dynamic_cast<const SfxUInt16Item&>(pItem);
    4318           0 :                 if ( aOutlineLevelItem.GetValue() != mrTextNode.GetAttrOutlineLevel() )
    4319             :                 {
    4320           0 :                     mbOutlineLevelSet = true;
    4321             :                 }
    4322             :             }
    4323           0 :             break;
    4324             :         }
    4325             : 
    4326       11889 :     }
    4327             : 
    4328       81357 :     HandleSetAttrAtTextNode::HandleSetAttrAtTextNode( SwTextNode& rTextNode,
    4329             :                                                     const SfxItemSet& rItemSet )
    4330             :         : mrTextNode( rTextNode ),
    4331             :           mbAddTextNodeToList( false ),
    4332             :           mbUpdateListLevel( false ),
    4333             :           mbUpdateListRestart( false ),
    4334             :           mbUpdateListCount( false ),
    4335             :           // #i70748#
    4336       81357 :           mbOutlineLevelSet( false )
    4337             :     {
    4338       81357 :         const SfxPoolItem* pItem = 0;
    4339             :         // handle RES_PARATR_NUMRULE
    4340       81357 :         if ( rItemSet.GetItemState( RES_PARATR_NUMRULE, false, &pItem ) == SfxItemState::SET )
    4341             :         {
    4342        4243 :             mrTextNode.RemoveFromList();
    4343             : 
    4344             :             const SwNumRuleItem* pNumRuleItem =
    4345        4243 :                             dynamic_cast<const SwNumRuleItem*>(pItem);
    4346        4243 :             if ( !pNumRuleItem->GetValue().isEmpty() )
    4347             :             {
    4348        3925 :                 mbAddTextNodeToList = true;
    4349             :                 // #i70748#
    4350        3925 :                 mrTextNode.ResetEmptyListStyleDueToResetOutlineLevelAttr();
    4351             :             }
    4352             :         }
    4353             : 
    4354             :         // handle RES_PARATR_LIST_ID
    4355       81357 :         if ( rItemSet.GetItemState( RES_PARATR_LIST_ID, false, &pItem ) == SfxItemState::SET )
    4356             :         {
    4357             :             const SfxStringItem* pListIdItem =
    4358         113 :                                     dynamic_cast<const SfxStringItem*>(pItem);
    4359         113 :             const OUString sListIdOfTextNode = mrTextNode.GetListId();
    4360         226 :             if ( pListIdItem &&
    4361         113 :                  pListIdItem->GetValue() != sListIdOfTextNode )
    4362             :             {
    4363          53 :                 mbAddTextNodeToList = true;
    4364          53 :                 if ( mrTextNode.IsInList() )
    4365             :                 {
    4366           0 :                     mrTextNode.RemoveFromList();
    4367             :                 }
    4368         113 :             }
    4369             :         }
    4370             : 
    4371             :         // handle RES_PARATR_LIST_LEVEL
    4372       81357 :         if ( rItemSet.GetItemState( RES_PARATR_LIST_LEVEL, false, &pItem ) == SfxItemState::SET )
    4373             :         {
    4374             :             const SfxInt16Item* pListLevelItem =
    4375        2997 :                                 dynamic_cast<const SfxInt16Item*>(pItem);
    4376        2997 :             if (pListLevelItem && pListLevelItem->GetValue() != mrTextNode.GetAttrListLevel())
    4377             :             {
    4378        1066 :                 mbUpdateListLevel = true;
    4379             :             }
    4380             :         }
    4381             : 
    4382             :         // handle RES_PARATR_LIST_ISRESTART
    4383       81357 :         if ( rItemSet.GetItemState( RES_PARATR_LIST_ISRESTART, false, &pItem ) == SfxItemState::SET )
    4384             :         {
    4385             :             const SfxBoolItem* pListIsRestartItem =
    4386          10 :                                 dynamic_cast<const SfxBoolItem*>(pItem);
    4387          10 :             if (pListIsRestartItem && pListIsRestartItem->GetValue() != mrTextNode.IsListRestart())
    4388             :             {
    4389          10 :                 mbUpdateListRestart = true;
    4390             :             }
    4391             :         }
    4392             : 
    4393             :         // handle RES_PARATR_LIST_RESTARTVALUE
    4394       81357 :         if ( rItemSet.GetItemState( RES_PARATR_LIST_RESTARTVALUE, false, &pItem ) == SfxItemState::SET )
    4395             :         {
    4396             :             const SfxInt16Item* pListRestartValueItem =
    4397           0 :                                 dynamic_cast<const SfxInt16Item*>(pItem);
    4398           0 :             if ( !mrTextNode.HasAttrListRestartValue() || (pListRestartValueItem &&
    4399           0 :                  pListRestartValueItem->GetValue() != mrTextNode.GetAttrListRestartValue()) )
    4400             :             {
    4401           0 :                 mbUpdateListRestart = true;
    4402             :             }
    4403             :         }
    4404             : 
    4405             :         // handle RES_PARATR_LIST_ISCOUNTED
    4406       81357 :         if ( rItemSet.GetItemState( RES_PARATR_LIST_ISCOUNTED, false, &pItem ) == SfxItemState::SET )
    4407             :         {
    4408             :             const SfxBoolItem* pIsCountedInListItem =
    4409           0 :                                 dynamic_cast<const SfxBoolItem*>(pItem);
    4410           0 :             if (pIsCountedInListItem && pIsCountedInListItem->GetValue() !=
    4411           0 :                 mrTextNode.IsCountedInList())
    4412             :             {
    4413           0 :                 mbUpdateListCount = true;
    4414             :             }
    4415             :         }
    4416             : 
    4417             :         // #i70748#
    4418             :         // handle RES_PARATR_OUTLINELEVEL
    4419       81357 :         if ( rItemSet.GetItemState( RES_PARATR_OUTLINELEVEL, false, &pItem ) == SfxItemState::SET )
    4420             :         {
    4421             :             const SfxUInt16Item* pOutlineLevelItem =
    4422         881 :                                 dynamic_cast<const SfxUInt16Item*>(pItem);
    4423        1762 :             if (pOutlineLevelItem && pOutlineLevelItem->GetValue() !=
    4424         881 :                 mrTextNode.GetAttrOutlineLevel())
    4425             :             {
    4426         444 :                 mbOutlineLevelSet = true;
    4427             :             }
    4428             :         }
    4429       81357 :     }
    4430             : 
    4431       93246 :     HandleSetAttrAtTextNode::~HandleSetAttrAtTextNode()
    4432             :     {
    4433       93246 :         if ( mbAddTextNodeToList )
    4434             :         {
    4435        4430 :             SwNumRule* pNumRuleAtTextNode = mrTextNode.GetNumRule();
    4436        4430 :             if ( pNumRuleAtTextNode )
    4437             :             {
    4438        4425 :                 mrTextNode.AddToList();
    4439             :             }
    4440             :         }
    4441             :         else
    4442             :         {
    4443       88816 :             if ( mbUpdateListLevel && mrTextNode.IsInList() )
    4444             :             {
    4445         316 :                 const_cast<SwNodeNum*>(mrTextNode.GetNum())->SetLevelInListTree(
    4446         632 :                                                     mrTextNode.GetAttrListLevel() );
    4447             :             }
    4448             : 
    4449       88816 :             if ( mbUpdateListRestart && mrTextNode.IsInList() )
    4450             :             {
    4451          33 :                 SwNodeNum* pNodeNum = const_cast<SwNodeNum*>(mrTextNode.GetNum());
    4452          33 :                 pNodeNum->InvalidateMe();
    4453          33 :                 pNodeNum->NotifyInvalidSiblings();
    4454             :             }
    4455             : 
    4456       88816 :             if ( mbUpdateListCount && mrTextNode.IsInList() )
    4457             :             {
    4458          30 :                 const_cast<SwNodeNum*>(mrTextNode.GetNum())->InvalidateAndNotifyTree();
    4459             :             }
    4460             :         }
    4461             : 
    4462             :         // #i70748#
    4463       93246 :         if (mbOutlineLevelSet)
    4464             :         {
    4465         444 :             mrTextNode.GetNodes().UpdateOutlineNode(mrTextNode);
    4466         444 :             if (mrTextNode.GetAttrOutlineLevel() == 0)
    4467             :             {
    4468           8 :                 mrTextNode.ResetEmptyListStyleDueToResetOutlineLevelAttr();
    4469             :             }
    4470             :             else
    4471             :             {
    4472         436 :                 const SfxPoolItem* pItem = 0;
    4473         872 :                 if ( mrTextNode.GetSwAttrSet().GetItemState( RES_PARATR_NUMRULE,
    4474         436 :                                                             true, &pItem )
    4475             :                                                                 != SfxItemState::SET )
    4476             :                 {
    4477         280 :                     mrTextNode.SetEmptyListStyleDueToSetOutlineLevelAttr();
    4478             :                 }
    4479             :             }
    4480             :         }
    4481       93246 :     }
    4482             :     // End of class <HandleSetAttrAtTextNode>
    4483             : }
    4484             : 
    4485       11889 : bool SwTextNode::SetAttr( const SfxPoolItem& pItem )
    4486             : {
    4487       11889 :     const bool bOldIsSetOrResetAttr( mbInSetOrResetAttr );
    4488       11889 :     mbInSetOrResetAttr = true;
    4489             : 
    4490       11889 :     HandleSetAttrAtTextNode aHandleSetAttr( *this, pItem );
    4491             : 
    4492       11889 :     bool bRet = SwContentNode::SetAttr( pItem );
    4493             : 
    4494       11889 :     mbInSetOrResetAttr = bOldIsSetOrResetAttr;
    4495             : 
    4496       11889 :     return bRet;
    4497             : }
    4498             : 
    4499       81357 : bool SwTextNode::SetAttr( const SfxItemSet& rSet )
    4500             : {
    4501       81357 :     const bool bOldIsSetOrResetAttr( mbInSetOrResetAttr );
    4502       81357 :     mbInSetOrResetAttr = true;
    4503             : 
    4504       81357 :     HandleSetAttrAtTextNode aHandleSetAttr( *this, rSet );
    4505             : 
    4506       81357 :     bool bRet = SwContentNode::SetAttr( rSet );
    4507             : 
    4508       81357 :     mbInSetOrResetAttr = bOldIsSetOrResetAttr;
    4509             : 
    4510       81357 :     return bRet;
    4511             : }
    4512             : 
    4513             : namespace {
    4514             :     // Helper class for special handling of resetting attributes at text node:
    4515             :     // In constructor an instance of the helper class recognize whose attributes
    4516             :     // are reset and perform corresponding actions before the intrinsic reset of
    4517             :     // attributes has been taken place.
    4518             :     // In the destructor - after the attributes have been reset at the text
    4519             :     // node - corresponding actions are performed.
    4520             :     // The following is handled:
    4521             :     // (1) When the list style attribute - RES_PARATR_NUMRULE - is reset,
    4522             :     //     the text is removed from its list before the attributes have been reset.
    4523             :     // (2) When the list id attribute - RES_PARATR_LIST_ID - is reset,
    4524             :     //     the text is removed from its list before the attributes have been reset.
    4525             :     // (3) Notify list tree, if list level - RES_PARATR_LIST_LEVEL - is reset.
    4526             :     // (4) Notify list tree, if list restart - RES_PARATR_LIST_ISRESTART - is reset.
    4527             :     // (5) Notify list tree, if list restart value - RES_PARATR_LIST_RESTARTVALUE - is reset.
    4528             :     // (6) Notify list tree, if count in list - RES_PARATR_LIST_ISCOUNTED - is reset.
    4529             :     // (7) Reset empty list style, if outline level attribute - RES_PARATR_OUTLINELEVEL - is reset.
    4530             :     class HandleResetAttrAtTextNode
    4531             :     {
    4532             :         public:
    4533             :             HandleResetAttrAtTextNode( SwTextNode& rTextNode,
    4534             :                                       const sal_uInt16 nWhich1,
    4535             :                                       const sal_uInt16 nWhich2 );
    4536             :             HandleResetAttrAtTextNode( SwTextNode& rTextNode,
    4537             :                                       const std::vector<sal_uInt16>& rWhichArr );
    4538             :             explicit HandleResetAttrAtTextNode( SwTextNode& rTextNode );
    4539             : 
    4540             :             ~HandleResetAttrAtTextNode();
    4541             : 
    4542             :         private:
    4543             :             SwTextNode& mrTextNode;
    4544             :             bool mbListStyleOrIdReset;
    4545             :             bool mbUpdateListLevel;
    4546             :             bool mbUpdateListRestart;
    4547             :             bool mbUpdateListCount;
    4548             :     };
    4549             : 
    4550      194830 :     HandleResetAttrAtTextNode::HandleResetAttrAtTextNode( SwTextNode& rTextNode,
    4551             :                                                         const sal_uInt16 nWhich1,
    4552             :                                                         const sal_uInt16 nWhich2 )
    4553             :         : mrTextNode( rTextNode ),
    4554             :           mbListStyleOrIdReset( false ),
    4555             :           mbUpdateListLevel( false ),
    4556             :           mbUpdateListRestart( false ),
    4557      194830 :           mbUpdateListCount( false )
    4558             :     {
    4559      194830 :         bool bRemoveFromList( false );
    4560      194830 :         if ( nWhich2 != 0 && nWhich2 > nWhich1 )
    4561             :         {
    4562             :             // RES_PARATR_NUMRULE and RES_PARATR_LIST_ID
    4563           1 :             if ( nWhich1 <= RES_PARATR_NUMRULE && RES_PARATR_NUMRULE <= nWhich2 )
    4564             :             {
    4565           0 :                 bRemoveFromList = mrTextNode.GetNumRule() != 0;
    4566           0 :                 mbListStyleOrIdReset = true;
    4567             :             }
    4568           1 :             else if ( nWhich1 <= RES_PARATR_LIST_ID && RES_PARATR_LIST_ID <= nWhich2 )
    4569             :             {
    4570           0 :                 bRemoveFromList = mrTextNode.GetpSwAttrSet() &&
    4571           0 :                     mrTextNode.GetpSwAttrSet()->GetItemState( RES_PARATR_LIST_ID, false ) == SfxItemState::SET;
    4572             :                 // #i92898#
    4573           0 :                 mbListStyleOrIdReset = true;
    4574             :             }
    4575             : 
    4576           1 :             if ( !bRemoveFromList )
    4577             :             {
    4578             :                 // RES_PARATR_LIST_LEVEL
    4579           0 :                 mbUpdateListLevel = ( nWhich1 <= RES_PARATR_LIST_LEVEL &&
    4580           1 :                                       RES_PARATR_LIST_LEVEL <= nWhich2 &&
    4581           1 :                                       mrTextNode.HasAttrListLevel() );
    4582             : 
    4583             :                 // RES_PARATR_LIST_ISRESTART and RES_PARATR_LIST_RESTARTVALUE
    4584             :                 mbUpdateListRestart =
    4585           0 :                     ( nWhich1 <= RES_PARATR_LIST_ISRESTART && RES_PARATR_LIST_ISRESTART <= nWhich2 &&
    4586           2 :                       mrTextNode.IsListRestart() ) ||
    4587           0 :                     ( nWhich1 <= RES_PARATR_LIST_RESTARTVALUE && RES_PARATR_LIST_RESTARTVALUE <= nWhich2 &&
    4588           1 :                       mrTextNode.HasAttrListRestartValue() );
    4589             : 
    4590             :                 // RES_PARATR_LIST_ISCOUNTED
    4591             :                 mbUpdateListCount =
    4592           1 :                     ( nWhich1 <= RES_PARATR_LIST_ISCOUNTED && RES_PARATR_LIST_ISCOUNTED <= nWhich2 &&
    4593           1 :                       !mrTextNode.IsCountedInList() );
    4594             :             }
    4595             : 
    4596             :             // #i70748#
    4597             :             // RES_PARATR_OUTLINELEVEL
    4598           2 :             if ( nWhich1 <= RES_PARATR_OUTLINELEVEL && RES_PARATR_OUTLINELEVEL <= nWhich2 )
    4599             :             {
    4600           0 :                 mrTextNode.ResetEmptyListStyleDueToResetOutlineLevelAttr();
    4601             :             }
    4602             :         }
    4603             :         else
    4604             :         {
    4605             :             // RES_PARATR_NUMRULE and RES_PARATR_LIST_ID
    4606      194829 :             if ( nWhich1 == RES_PARATR_NUMRULE )
    4607             :             {
    4608        7151 :                 bRemoveFromList = mrTextNode.GetNumRule() != 0;
    4609        7151 :                 mbListStyleOrIdReset = true;
    4610             :             }
    4611      187678 :             else if ( nWhich1 == RES_PARATR_LIST_ID )
    4612             :             {
    4613       39382 :                 bRemoveFromList = mrTextNode.GetpSwAttrSet() &&
    4614       39382 :                     mrTextNode.GetpSwAttrSet()->GetItemState( RES_PARATR_LIST_ID, false ) == SfxItemState::SET;
    4615             :                 // #i92898#
    4616       36923 :                 mbListStyleOrIdReset = true;
    4617             :             }
    4618             :             // #i70748#
    4619             :             // RES_PARATR_OUTLINELEVEL
    4620      150755 :             else if ( nWhich1 == RES_PARATR_OUTLINELEVEL )
    4621             :             {
    4622           0 :                 mrTextNode.ResetEmptyListStyleDueToResetOutlineLevelAttr();
    4623             :             }
    4624             : 
    4625      194829 :             if ( !bRemoveFromList )
    4626             :             {
    4627             :                 // RES_PARATR_LIST_LEVEL
    4628      231085 :                 mbUpdateListLevel = nWhich1 == RES_PARATR_LIST_LEVEL &&
    4629      231085 :                                     mrTextNode.HasAttrListLevel();
    4630             : 
    4631             :                 // RES_PARATR_LIST_ISRESTART and RES_PARATR_LIST_RESTARTVALUE
    4632       37663 :                 mbUpdateListRestart = ( nWhich1 == RES_PARATR_LIST_ISRESTART &&
    4633      388338 :                                         mrTextNode.IsListRestart() ) ||
    4634       37663 :                                       ( nWhich1 == RES_PARATR_LIST_RESTARTVALUE &&
    4635      231832 :                                         mrTextNode.HasAttrListRestartValue() );
    4636             : 
    4637             :                 // RES_PARATR_LIST_ISCOUNTED
    4638      232676 :                 mbUpdateListCount = nWhich1 == RES_PARATR_LIST_ISCOUNTED &&
    4639      232676 :                                     !mrTextNode.IsCountedInList();
    4640             :             }
    4641             :         }
    4642             : 
    4643      194830 :         if ( bRemoveFromList && mrTextNode.IsInList() )
    4644             :         {
    4645         660 :             mrTextNode.RemoveFromList();
    4646             :         }
    4647      194830 :     }
    4648             : 
    4649        4511 :     HandleResetAttrAtTextNode::HandleResetAttrAtTextNode( SwTextNode& rTextNode,
    4650             :                                                         const std::vector<sal_uInt16>& rWhichArr )
    4651             :         : mrTextNode( rTextNode ),
    4652             :           mbListStyleOrIdReset( false ),
    4653             :           mbUpdateListLevel( false ),
    4654             :           mbUpdateListRestart( false ),
    4655        4511 :           mbUpdateListCount( false )
    4656             :     {
    4657        4511 :         bool bRemoveFromList( false );
    4658             :         {
    4659        4511 :             std::vector<sal_uInt16>::const_iterator it;
    4660       61821 :             for ( it = rWhichArr.begin(); it != rWhichArr.end(); ++it)
    4661             :             {
    4662             :                 // RES_PARATR_NUMRULE and RES_PARATR_LIST_ID
    4663       57310 :                 if ( *it == RES_PARATR_NUMRULE )
    4664             :                 {
    4665        1200 :                     bRemoveFromList = bRemoveFromList ||
    4666        1200 :                                       mrTextNode.GetNumRule() != 0;
    4667         600 :                     mbListStyleOrIdReset = true;
    4668             :                 }
    4669       56710 :                 else if ( *it == RES_PARATR_LIST_ID )
    4670             :                 {
    4671           0 :                     bRemoveFromList = bRemoveFromList ||
    4672           0 :                         ( mrTextNode.GetpSwAttrSet() &&
    4673           0 :                           mrTextNode.GetpSwAttrSet()->GetItemState( RES_PARATR_LIST_ID, false ) == SfxItemState::SET );
    4674             :                     // #i92898#
    4675           0 :                     mbListStyleOrIdReset = true;
    4676             :                 }
    4677             :                 // #i70748#
    4678             :                 // RES_PARATR_OUTLINELEVEL
    4679       56710 :                 else if ( *it == RES_PARATR_OUTLINELEVEL )
    4680             :                 {
    4681           0 :                     mrTextNode.ResetEmptyListStyleDueToResetOutlineLevelAttr();
    4682             :                 }
    4683             : 
    4684       57310 :                 if ( !bRemoveFromList )
    4685             :                 {
    4686             :                     // RES_PARATR_LIST_LEVEL
    4687      115088 :                     mbUpdateListLevel = mbUpdateListLevel ||
    4688       58377 :                                         ( *it == RES_PARATR_LIST_LEVEL &&
    4689       58378 :                                           mrTextNode.HasAttrListLevel() );
    4690             : 
    4691             :                     // RES_PARATR_LIST_ISRESTART and RES_PARATR_LIST_RESTARTVALUE
    4692       56710 :                     mbUpdateListRestart = mbUpdateListRestart ||
    4693       56710 :                                           ( *it == RES_PARATR_LIST_ISRESTART &&
    4694      113420 :                                             mrTextNode.IsListRestart() ) ||
    4695       56710 :                                           ( *it == RES_PARATR_LIST_RESTARTVALUE &&
    4696       56710 :                                             mrTextNode.HasAttrListRestartValue() );
    4697             : 
    4698             :                     // RES_PARATR_LIST_ISCOUNTED
    4699      113420 :                     mbUpdateListCount = mbUpdateListCount ||
    4700       56710 :                                         ( *it == RES_PARATR_LIST_ISCOUNTED &&
    4701       56710 :                                           !mrTextNode.IsCountedInList() );
    4702             :                 }
    4703             :             }
    4704             :         }
    4705             : 
    4706        4511 :         if ( bRemoveFromList && mrTextNode.IsInList() )
    4707             :         {
    4708         600 :             mrTextNode.RemoveFromList();
    4709             :         }
    4710        4511 :     }
    4711             : 
    4712        7499 :     HandleResetAttrAtTextNode::HandleResetAttrAtTextNode( SwTextNode& rTextNode )
    4713             :         : mrTextNode( rTextNode ),
    4714             :           mbListStyleOrIdReset( false ),
    4715             :           mbUpdateListLevel( false ),
    4716             :           mbUpdateListRestart( false ),
    4717        7499 :           mbUpdateListCount( false )
    4718             :     {
    4719        7499 :         mbListStyleOrIdReset = true;
    4720        7499 :         if ( rTextNode.IsInList() )
    4721             :         {
    4722         440 :             rTextNode.RemoveFromList();
    4723             :         }
    4724             :         // #i70748#
    4725        7499 :         mrTextNode.ResetEmptyListStyleDueToResetOutlineLevelAttr();
    4726        7499 :     }
    4727             : 
    4728      206840 :     HandleResetAttrAtTextNode::~HandleResetAttrAtTextNode()
    4729             :     {
    4730      206840 :         if ( mbListStyleOrIdReset && !mrTextNode.IsInList() )
    4731             :         {
    4732             :             // check, if in spite of the reset of the list style or the list id
    4733             :             // the paragraph still has to be added to a list.
    4734       52173 :             if (mrTextNode.GetNumRule() && !mrTextNode.GetListId().isEmpty())
    4735             :             {
    4736             :                 // #i96062#
    4737             :                 // If paragraph has no list level attribute set and list style
    4738             :                 // is the outline style, apply outline level as the list level.
    4739        3566 :                 if ( !mrTextNode.HasAttrListLevel() &&
    4740        3696 :                      mrTextNode.GetNumRule()->GetName()==SwNumRule::GetOutlineRuleName() &&
    4741         282 :                      mrTextNode.GetTextColl()->IsAssignedToListLevelOfOutlineStyle() )
    4742             :                 {
    4743         282 :                     int nNewListLevel = mrTextNode.GetTextColl()->GetAssignedOutlineStyleLevel();
    4744         282 :                     if ( 0 <= nNewListLevel && nNewListLevel < MAXLEVEL )
    4745             :                     {
    4746         282 :                         mrTextNode.SetAttrListLevel( nNewListLevel );
    4747             :                     }
    4748             :                 }
    4749         645 :                 mrTextNode.AddToList();
    4750             :             }
    4751             :             // #i70748#
    4752             :             // #i105562#
    4753       56183 :             else if ( mrTextNode.GetpSwAttrSet() &&
    4754        4655 :                       dynamic_cast<const SfxUInt16Item &>(mrTextNode.GetAttr( RES_PARATR_OUTLINELEVEL, false )).GetValue() > 0 )
    4755             :             {
    4756           5 :                 mrTextNode.SetEmptyListStyleDueToSetOutlineLevelAttr();
    4757             :             }
    4758             :         }
    4759             : 
    4760      206840 :         if ( mrTextNode.IsInList() )
    4761             :         {
    4762        4088 :             if ( mbUpdateListLevel )
    4763             :             {
    4764         440 :                 SwNodeNum* pNodeNum = const_cast<SwNodeNum*>(mrTextNode.GetNum());
    4765         440 :                 pNodeNum->SetLevelInListTree( mrTextNode.GetAttrListLevel() );
    4766             :             }
    4767             : 
    4768        4088 :             if ( mbUpdateListRestart )
    4769             :             {
    4770           0 :                 SwNodeNum* pNodeNum = const_cast<SwNodeNum*>(mrTextNode.GetNum());
    4771           0 :                 pNodeNum->InvalidateMe();
    4772           0 :                 pNodeNum->NotifyInvalidSiblings();
    4773             :             }
    4774             : 
    4775        4088 :             if ( mbUpdateListCount )
    4776             :             {
    4777           0 :                 SwNodeNum* pNodeNum = const_cast<SwNodeNum*>(mrTextNode.GetNum());
    4778           0 :                 pNodeNum->InvalidateAndNotifyTree();
    4779             :             }
    4780             :         }
    4781      206840 :     }
    4782             :     // End of class <HandleResetAttrAtTextNode>
    4783             : }
    4784             : 
    4785      194830 : bool SwTextNode::ResetAttr( sal_uInt16 nWhich1, sal_uInt16 nWhich2 )
    4786             : {
    4787      194830 :     const bool bOldIsSetOrResetAttr( mbInSetOrResetAttr );
    4788      194830 :     mbInSetOrResetAttr = true;
    4789             : 
    4790      194830 :     HandleResetAttrAtTextNode aHandleResetAttr( *this, nWhich1, nWhich2 );
    4791             : 
    4792      194830 :     bool bRet = SwContentNode::ResetAttr( nWhich1, nWhich2 );
    4793             : 
    4794      194830 :     mbInSetOrResetAttr = bOldIsSetOrResetAttr;
    4795             : 
    4796      194830 :     return bRet;
    4797             : }
    4798             : 
    4799        4511 : bool SwTextNode::ResetAttr( const std::vector<sal_uInt16>& rWhichArr )
    4800             : {
    4801        4511 :     const bool bOldIsSetOrResetAttr( mbInSetOrResetAttr );
    4802        4511 :     mbInSetOrResetAttr = true;
    4803             : 
    4804        4511 :     HandleResetAttrAtTextNode aHandleResetAttr( *this, rWhichArr );
    4805             : 
    4806        4511 :     bool bRet = SwContentNode::ResetAttr( rWhichArr );
    4807             : 
    4808        4511 :     mbInSetOrResetAttr = bOldIsSetOrResetAttr;
    4809             : 
    4810        4511 :     return bRet;
    4811             : }
    4812             : 
    4813        7499 : sal_uInt16 SwTextNode::ResetAllAttr()
    4814             : {
    4815        7499 :     const bool bOldIsSetOrResetAttr( mbInSetOrResetAttr );
    4816        7499 :     mbInSetOrResetAttr = true;
    4817             : 
    4818        7499 :     HandleResetAttrAtTextNode aHandleResetAttr( *this );
    4819             : 
    4820        7499 :     const sal_uInt16 nRet = SwContentNode::ResetAllAttr();
    4821             : 
    4822        7499 :     mbInSetOrResetAttr = bOldIsSetOrResetAttr;
    4823             : 
    4824        7499 :     return nRet;
    4825             : }
    4826             : 
    4827           0 : void SwTextNode::dumpAsXml(xmlTextWriterPtr pWriter) const
    4828             : {
    4829           0 :     xmlTextWriterStartElement(pWriter, BAD_CAST("swTextNode"));
    4830           0 :     xmlTextWriterWriteFormatAttribute(pWriter, BAD_CAST("ptr"), "%p", this);
    4831           0 :     xmlTextWriterWriteAttribute(pWriter, BAD_CAST("index"), BAD_CAST(OString::number(GetIndex()).getStr()));
    4832             : 
    4833           0 :     OUString sText = GetText();
    4834           0 :     for (int i = 0; i < 32; ++i)
    4835           0 :         sText = sText.replace(i, '*');
    4836           0 :     xmlTextWriterStartElement(pWriter, BAD_CAST("m_Text"));
    4837           0 :     xmlTextWriterWriteString(pWriter, BAD_CAST(sText.toUtf8().getStr()));
    4838           0 :     xmlTextWriterEndElement(pWriter);
    4839             : 
    4840           0 :     if (GetFormatColl())
    4841             :     {
    4842           0 :         xmlTextWriterStartElement(pWriter, BAD_CAST("swTextFormatColl"));
    4843           0 :         xmlTextWriterWriteAttribute(pWriter, BAD_CAST("name"), BAD_CAST(GetFormatColl()->GetName().toUtf8().getStr()));
    4844           0 :         xmlTextWriterEndElement(pWriter);
    4845             :     }
    4846             : 
    4847           0 :     if (HasSwAttrSet())
    4848             :     {
    4849           0 :         xmlTextWriterStartElement(pWriter, BAD_CAST("swAttrSet"));
    4850           0 :         GetSwAttrSet().dumpAsXml(pWriter);
    4851           0 :         xmlTextWriterEndElement(pWriter);
    4852             :     }
    4853             : 
    4854           0 :     if (HasHints())
    4855             :     {
    4856           0 :         xmlTextWriterStartElement(pWriter, BAD_CAST("swpHints"));
    4857           0 :         const SwpHints& rHints = GetSwpHints();
    4858           0 :         for (size_t i = 0; i < rHints.Count(); ++i)
    4859           0 :             rHints.GetTextHint(i)->dumpAsXml(pWriter);
    4860           0 :         xmlTextWriterEndElement(pWriter);
    4861             :     }
    4862             : 
    4863           0 :     if (GetNumRule())
    4864           0 :         GetNumRule()->dumpAsXml(pWriter);
    4865             : 
    4866           0 :     xmlTextWriterEndElement(pWriter);
    4867           0 : }
    4868             : 
    4869           0 : sal_uInt32 SwTextNode::GetRsid( sal_Int32 nStt, sal_Int32 nEnd ) const
    4870             : {
    4871           0 :     SfxItemSet aSet( (SfxItemPool&) (GetDoc()->GetAttrPool()), RES_CHRATR_RSID, RES_CHRATR_RSID );
    4872           0 :     if ( GetAttr(aSet, nStt, nEnd) )
    4873             :     {
    4874           0 :         const SvxRsidItem* pRsid = static_cast<const SvxRsidItem*>(aSet.GetItem(RES_CHRATR_RSID));
    4875           0 :         if( pRsid )
    4876           0 :             return pRsid->GetValue();
    4877             :     }
    4878             : 
    4879           0 :     return 0;
    4880             : }
    4881             : 
    4882         316 : sal_uInt32 SwTextNode::GetParRsid() const
    4883             : {
    4884         316 :     return reinterpret_cast<const SvxRsidItem&>(GetAttr( RES_PARATR_RSID )).GetValue();
    4885             : }
    4886             : 
    4887           0 : bool SwTextNode::CompareParRsid( const SwTextNode &rTextNode ) const
    4888             : {
    4889           0 :     sal_uInt32 nThisRsid = GetParRsid();
    4890           0 :     sal_uInt32 nRsid = rTextNode.GetParRsid();
    4891             : 
    4892           0 :     return nThisRsid == nRsid;
    4893             : }
    4894             : 
    4895           0 : bool SwTextNode::CompareRsid( const SwTextNode &rTextNode, sal_Int32 nStt1, sal_Int32 nStt2,
    4896             :                             sal_Int32 nEnd1, sal_Int32 nEnd2 ) const
    4897             : 
    4898             : {
    4899           0 :     sal_uInt32 nThisRsid = GetRsid( nStt1, nEnd1 ? nEnd1 : nStt1 );
    4900           0 :     sal_uInt32 nRsid = rTextNode.GetRsid( nStt2, nEnd2 ? nEnd2 : nStt2 );
    4901             : 
    4902           0 :     return nThisRsid == nRsid;
    4903             : }
    4904             : 
    4905             : // sw::Metadatable
    4906         124 : ::sfx2::IXmlIdRegistry& SwTextNode::GetRegistry()
    4907             : {
    4908         124 :     return GetDoc()->GetXmlIdRegistry();
    4909             : }
    4910             : 
    4911        3823 : bool SwTextNode::IsInClipboard() const
    4912             : {
    4913        3823 :     return GetDoc()->IsClipBoard();
    4914             : }
    4915             : 
    4916        3833 : bool SwTextNode::IsInUndo() const
    4917             : {
    4918        3833 :     return GetDoc()->GetIDocumentUndoRedo().IsUndoNodes(GetNodes());
    4919             : }
    4920             : 
    4921         158 : bool SwTextNode::IsInContent() const
    4922             : {
    4923         158 :     return !GetDoc()->IsInHeaderFooter( SwNodeIndex(*this) );
    4924             : }
    4925             : 
    4926      232577 : void SwTextNode::SwClientNotify( const SwModify& rModify, const SfxHint& rHint )
    4927             : {
    4928      232577 :     SwClient::SwClientNotify(rModify, rHint);
    4929      232577 :     const SwAttrHint* pHint = dynamic_cast<const SwAttrHint*>(&rHint);
    4930      232577 :     if ( pHint && pHint->GetId() == RES_CONDTXTFMTCOLL && &rModify == GetRegisteredIn() )
    4931         126 :         ChkCondColl();
    4932      232577 : }
    4933             : 
    4934             : #include <unoparagraph.hxx>
    4935             : 
    4936             : uno::Reference< rdf::XMetadatable >
    4937           1 : SwTextNode::MakeUnoObject()
    4938             : {
    4939             :     const uno::Reference<rdf::XMetadatable> xMeta(
    4940           1 :             SwXParagraph::CreateXParagraph(*GetDoc(), this), uno::UNO_QUERY);
    4941           1 :     return xMeta;
    4942             : }
    4943             : 
    4944             : //UUUU
    4945       81581 : drawinglayer::attribute::SdrAllFillAttributesHelperPtr SwTextNode::getSdrAllFillAttributesHelper() const
    4946             : {
    4947             :     // create SdrAllFillAttributesHelper on demand
    4948       81581 :     if(!maFillAttributes.get())
    4949             :     {
    4950       30098 :         const_cast< SwTextNode* >(this)->maFillAttributes.reset(new drawinglayer::attribute::SdrAllFillAttributesHelper(GetSwAttrSet()));
    4951             :     }
    4952             : 
    4953       81581 :     return maFillAttributes;
    4954         177 : }
    4955             : 
    4956             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.11