[Libreoffice-commits] core.git: Branch 'private/jmux/mailmerge-fixes' - 23 commits - avmedia/source connectivity/source fpicker/source include/oox mysqlc/source sal/rtl sfx2/source svx/source sw/inc sw/source vcl/quartz

Jan-Marek Glogowski glogow at fbihome.de
Wed Jul 2 02:19:00 PDT 2014


Rebased ref, commits from common ancestor:
commit 77f4ef0e2686d910af603b48c4320ff424aee459
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Wed Jul 2 11:17:17 2014 +0200

    Fixes multiple-page-anchored-draws.odt
    
    Change-Id: I5ad726da647df8621bc0a16caa78a28b7d2d01c1

diff --git a/sw/source/core/doc/docnew.cxx b/sw/source/core/doc/docnew.cxx
index e63beca..1f053a0 100644
--- a/sw/source/core/doc/docnew.cxx
+++ b/sw/source/core/doc/docnew.cxx
@@ -1229,6 +1229,9 @@ else
             }
         }
 
+        if ( pTargetShell )
+            pTargetShell->CalcLayout();
+
         // finally copy page bound frames
         const SwFrmFmts *pSpzFrmFmts = rSource.GetSpzFrmFmts();
         for ( sal_uInt16 i = 0; i < pSpzFrmFmts->size(); ++i )
commit b61168c6b622e33e7a4fb9ec2116c9e7ca6b3741
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Tue Jul 1 15:45:47 2014 +0200

    Fix single node CopyRange
    
    Change-Id: Iadf21d3928303c2ab8df0d93dabd969ed1ff7e09

diff --git a/sw/inc/doc.hxx b/sw/inc/doc.hxx
index d0e31aa..b276d4d 100644
--- a/sw/inc/doc.hxx
+++ b/sw/inc/doc.hxx
@@ -469,7 +469,8 @@ private:
     void CopyFlyInFlyImpl(  const SwNodeRange& rRg,
                             const sal_Int32 nEndContentIndex,
                             const SwNodeIndex& rStartIdx,
-                            const bool bCopyFlyAtFly = false ) const;
+                            const bool bCopyFlyAtFly = false,
+                            const bool bMergedFirstNode = false ) const;
     sal_Int8 SetFlyFrmAnchor( SwFrmFmt& rFlyFmt, SfxItemSet& rSet, bool bNewFrms );
 
     typedef SwFmt* (SwDoc:: *FNCopyFmt)( const OUString&, SwFmt*, bool, bool );
@@ -902,7 +903,8 @@ public:
                             const SwPaM* pCopiedPaM = NULL,
                             bool bMakeNewFrms = true,
                             bool bDelRedlines = true,
-                            bool bCopyFlyAtFly = false ) const;
+                            bool bCopyFlyAtFly = false,
+                            bool bSkipFirstNode = false ) const;
 
     //UUUU Helper that checks for unique items for DrawingLayer items of type NameOrIndex
     // and evtl. corrects that items to ensure unique names for that type. This call may
diff --git a/sw/source/core/docnode/ndcopy.cxx b/sw/source/core/docnode/ndcopy.cxx
index 5443c9f..771e9d7 100644
--- a/sw/source/core/docnode/ndcopy.cxx
+++ b/sw/source/core/docnode/ndcopy.cxx
@@ -673,7 +673,7 @@ SwDoc::CopyRange( SwPaM& rPam, SwPosition& rPos, const bool bCopyAll ) const
     bool bColumnSel = pDoc->IsClipBoard() && pDoc->IsColumnSelection();
 
     // Catch if there's no copy to do
-    if( !rPam.HasMark() || ( *pStt >= *pEnd && !bColumnSel ) )
+    if( !rPam.HasMark() || ( *pStt > *pEnd && !bColumnSel ) )
         return false;
 
     // Prevent copying in Flys that are anchored in the area
@@ -923,7 +923,7 @@ bool SwDoc::CopyImpl( SwPaM& rPam, SwPosition& rPos,
     SwPosition* pEnd = rPam.End();
 
     // Catch when there's no copy to do.
-    if( !rPam.HasMark() || ( *pStt >= *pEnd && !bColumnSel ) ||
+    if( !rPam.HasMark() || ( *pStt > *pEnd && !bColumnSel ) ||
         //JP 29.6.2001: 88963 - dont copy if inspos is in region of start to end
         //JP 15.11.2001: don't test inclusive the end, ever exclusive
         ( pDoc == this && *pStt <= rPos && rPos < *pEnd ))
@@ -1011,6 +1011,8 @@ bool SwDoc::CopyImpl( SwPaM& rPam, SwPosition& rPos,
         pNumRuleToPropagate = 0;
     }
 
+    bool bHandledStartNode = false;
+
     // This do/while block is only there so that we can break out of it!
     do {
         if( pSttTxtNd )
@@ -1018,6 +1020,8 @@ bool SwDoc::CopyImpl( SwPaM& rPam, SwPosition& rPos,
             // Don't copy the beginning completely?
             if( !bCopyCollFmt || bColumnSel || pStt->nContent.GetIndex() )
             {
+                bHandledStartNode = true;
+
                 SwIndex aDestIdx( rPos.nContent );
                 bool bCopyOk = false;
                 if( !pDestTxtNd )
@@ -1093,18 +1097,11 @@ bool SwDoc::CopyImpl( SwPaM& rPam, SwPosition& rPos,
                         pEnd->nContent -= nCpyLen;
                 }
 
-                if( bOneNode )
+                if( bCopyCollFmt && bOneNode )
                 {
-                    if( bCopyCollFmt )
-                    {
-                        pSttTxtNd->CopyCollFmt( *pDestTxtNd );
-                        POP_NUMRULE_STATE
-                    }
-
-                    break;
+                    pSttTxtNd->CopyCollFmt( *pDestTxtNd );
+                    POP_NUMRULE_STATE
                 }
-
-                aRg.aStart++;
             }
         }
         else if( pDestTxtNd )
@@ -1161,7 +1158,7 @@ bool SwDoc::CopyImpl( SwPaM& rPam, SwPosition& rPos,
         }
 
         pDestTxtNd = aInsPos.GetNode().GetTxtNode();
-        if( pEndTxtNd )
+        if( pEndTxtNd && (!bOneNode || !bHandledStartNode) )
         {
             SwIndex aDestIdx( rPos.nContent );
             if( !pDestTxtNd )
@@ -1205,7 +1202,7 @@ bool SwDoc::CopyImpl( SwPaM& rPam, SwPosition& rPos,
         if( bCopyAll || aRg.aStart != aRg.aEnd )
         {
             SfxItemSet aBrkSet( pDoc->GetAttrPool(), aBreakSetRange );
-            if( pSttTxtNd && bCopyCollFmt && pDestTxtNd->HasSwAttrSet() )
+            if( !bOneNode && pSttTxtNd && bCopyCollFmt && pDestTxtNd->HasSwAttrSet() )
             {
                 aBrkSet.Put( *pDestTxtNd->GetpSwAttrSet() );
                 if( SFX_ITEM_SET == aBrkSet.GetItemState( RES_BREAK, false ) )
@@ -1217,13 +1214,15 @@ bool SwDoc::CopyImpl( SwPaM& rPam, SwPosition& rPos,
             if( aInsPos == pEnd->nNode )
             {
                 SwNodeIndex aSaveIdx( aInsPos, -1 );
-                CopyWithFlyInFly( aRg, 0,aInsPos, &rPam, bMakeNewFrms, false );
+                CopyWithFlyInFly( aRg, 0, aInsPos, &rPam, bMakeNewFrms,
+                                  false, false, bHandledStartNode );
                 ++aSaveIdx;
                 pEnd->nNode = aSaveIdx;
                 pEnd->nContent.Assign( aSaveIdx.GetNode().GetTxtNode(), 0 );
             }
             else
-                CopyWithFlyInFly( aRg, pEnd->nContent.GetIndex(), aInsPos, &rPam, bMakeNewFrms, false );
+                CopyWithFlyInFly( aRg, pEnd->nContent.GetIndex(), aInsPos, &rPam,
+                                  bMakeNewFrms, false, false, bHandledStartNode );
 
             bCopyBookmarks = false;
 
@@ -1312,7 +1311,8 @@ void SwDoc::CopyWithFlyInFly(
     const SwPaM* pCopiedPaM,
     const bool bMakeNewFrms,
     const bool bDelRedlines,
-    const bool bCopyFlyAtFly ) const
+    const bool bCopyFlyAtFly,
+    const bool bMergedFirstNode ) const
 {
     SwDoc* pDest = rInsPos.GetNode().GetDoc();
 
@@ -1320,13 +1320,17 @@ void SwDoc::CopyWithFlyInFly(
 
     SwNodeIndex aSavePos( rInsPos, -1 );
     bool bEndIsEqualEndPos = rInsPos == rRg.aEnd;
-    GetNodes()._CopyNodes( rRg, rInsPos, bMakeNewFrms, true );
-    ++aSavePos;
-    if( bEndIsEqualEndPos )
+    SwNodeRange aRg( rRg );
+    if ( bMergedFirstNode )
+        aRg.aStart++;
+    if ( aRg.aStart <= aRg.aEnd )
+        GetNodes()._CopyNodes( aRg, rInsPos, bMakeNewFrms, true );
+    if ( !bMergedFirstNode )
+        ++aSavePos;
+    if ( bEndIsEqualEndPos )
         ((SwNodeIndex&)rRg.aEnd) = aSavePos;
 
     aRedlRest.Restore();
-
 #if OSL_DEBUG_LEVEL > 0
     {
         //JP 17.06.99: Bug 66973 - check count only if the selection is in
@@ -1340,9 +1344,9 @@ void SwDoc::CopyWithFlyInFly(
             !aTmpI.GetNode().IsEndNode() )
         {
             // If the range starts with a SwStartNode, it isn't copied
-            sal_uInt16 offset = (rRg.aStart.GetNode().GetNodeType() != ND_STARTNODE) ? 1 : 0;
+            sal_uInt16 offset = (aRg.aStart.GetNode().GetNodeType() != ND_STARTNODE) ? 1 : 0;
             OSL_ENSURE( rInsPos.GetIndex() - aSavePos.GetIndex() ==
-                    rRg.aEnd.GetIndex() - rRg.aStart.GetIndex() - 1 + offset,
+                    aRg.aEnd.GetIndex() - aRg.aStart.GetIndex() - 1 + offset,
                     "An insufficient number of nodes were copied!" );
         }
     }
@@ -1350,7 +1354,7 @@ void SwDoc::CopyWithFlyInFly(
 
     {
         ::sw::UndoGuard const undoGuard(pDest->GetIDocumentUndoRedo());
-        CopyFlyInFlyImpl( rRg, nEndContentIndex, aSavePos, bCopyFlyAtFly );
+        CopyFlyInFlyImpl( rRg, nEndContentIndex, aSavePos, bCopyFlyAtFly, bMergedFirstNode );
     }
 
     SwNodeRange aCpyRange( aSavePos, rInsPos );
@@ -1392,7 +1396,8 @@ void SwDoc::CopyFlyInFlyImpl(
     const SwNodeRange& rRg,
     const sal_Int32 nEndContentIndex,
     const SwNodeIndex& rStartIdx,
-    const bool bCopyFlyAtFly ) const
+    const bool bCopyFlyAtFly,
+    const bool bMergedFirstNode ) const
 {
     // First collect all Flys, sort them according to their ordering number,
     // and then only copy them. This maintains the ordering numbers (which are only
@@ -1512,6 +1517,9 @@ void SwDoc::CopyFlyInFlyImpl(
 
                 ++aIdx;
             }
+            if ( bMergedFirstNode )
+                nAnchorTxtNdNumInRange--;
+
             if ( !bAnchorTxtNdFound )
             {
                 // This case can *not* happen, but to be robust take the first
commit 5a504655a5f25346d19ec2fbba3cf9b6e975cd9e
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Tue Jul 1 21:42:30 2014 +0200

    Normalize SwDBManager::Merge{MailFiles,Documents}
    
    There is still a difference, if run mail merge throught one or
    the other function (MM wizard or UNO).
    
    Change-Id: Ia372bd3edea4c8dfb58e045fc8fed2efcb2a4fde

diff --git a/sw/source/uibase/dbui/dbmgr.cxx b/sw/source/uibase/dbui/dbmgr.cxx
index 61bfd68..0601873 100644
--- a/sw/source/uibase/dbui/dbmgr.cxx
+++ b/sw/source/uibase/dbui/dbmgr.cxx
@@ -942,21 +942,23 @@ bool SwDBManager::MergeMailFiles(SwWrtShell* pSourceShell,
 
                 //copy the styles from the source to the target document
                 pTargetView->GetDocShell()->_LoadStyles( *pSourceDocSh, true );
+
                 //determine the page style and number used at the start of the source document
                 pSourceShell->SttEndDoc(true);
                 nStartingPageNo = pSourceShell->GetVirtPageNum();
                 sStartingPageDesc = sModifiedStartingPageDesc = pSourceShell->GetPageDesc(
                                             pSourceShell->GetCurPageDesc()).GetName();
-                // copy compatibility options
-                lcl_CopyCompatibilityOptions( *pSourceShell, *pTargetShell);
-                // #72821# copy dynamic defaults
-                lcl_CopyDynamicDefaults( *pSourceShell->GetDoc(), *pTargetShell->GetDoc() );
+
                 // #i72517#
                 const SwPageDesc* pSourcePageDesc = pSourceShell->FindPageDescByName( sStartingPageDesc );
                 const SwFrmFmt& rMaster = pSourcePageDesc->GetMaster();
                 bPageStylesWithHeaderFooter = rMaster.GetHeader().IsActive()  ||
                                                 rMaster.GetFooter().IsActive();
 
+                // copy compatibility options
+                lcl_CopyCompatibilityOptions( *pSourceShell, *pTargetShell);
+                // #72821# copy dynamic defaults
+                lcl_CopyDynamicDefaults( *pSourceShell->GetDoc(), *pTargetShell->GetDoc() );
             }
 
             PrintMonitor aPrtMonDlg(&pSourceShell->GetView().GetEditWin(), PrintMonitor::MONITOR_TYPE_PRINT);
@@ -1046,18 +1048,25 @@ bool SwDBManager::MergeMailFiles(SwWrtShell* pSourceShell,
                             lcl_SaveDoc( xWorkDocSh, "WorkDoc", nDocNo );
 #endif
 
-                        {
                             //create a view frame for the document
-                            SfxViewFrame* pWorkFrame = SfxViewFrame::LoadHiddenDocument( *xWorkDocSh, 0 );
+                            SwView* pWorkView = static_cast< SwView* >( SfxViewFrame::LoadHiddenDocument( *xWorkDocSh, 0 )->GetViewShell() );
                             //request the layout calculation
-                            SwWrtShell& rWorkShell =
-                                    static_cast< SwView* >(pWorkFrame->GetViewShell())->GetWrtShell();
-                            rWorkShell.CalcLayout();
-                            SwDoc* pWorkDoc = ((SwDocShell*)(&xWorkDocSh))->GetDoc();
+                            SwWrtShell& rWorkShell = pWorkView->GetWrtShell();
+                            pWorkView->AttrChangedNotify( &rWorkShell );// in order for SelectShell to be called
+
+                            SwDoc* pWorkDoc = rWorkShell.GetDoc();
                             SwDBManager* pOldDBManager = pWorkDoc->GetDBManager();
                             pWorkDoc->SetDBManager( this );
+                            pWorkDoc->EmbedAllLinks();
+
+                            // #i69485# lock fields to prevent access to the result set while calculating layout
+                            rWorkShell.LockExpFlds();
+                            rWorkShell.CalcLayout();
+                            rWorkShell.UnlockExpFlds();
+
                             SfxGetpApp()->NotifyEvent(SfxEventHint(SW_EVENT_FIELD_MERGE, SwDocShell::GetEventName(STR_SW_EVENT_FIELD_MERGE), xWorkDocSh));
-                            pWorkDoc->UpdateFlds(NULL, false);
+//                            pWorkDoc->UpdateFlds(NULL, false);
+                            rWorkShell.SwViewShell::UpdateFlds();
                             SfxGetpApp()->NotifyEvent(SfxEventHint(SW_EVENT_FIELD_MERGE_FINISHED, SwDocShell::GetEventName(STR_SW_EVENT_FIELD_MERGE_FINISHED), xWorkDocSh));
 
                             pWorkDoc->RemoveInvisibleContent();
@@ -1226,7 +1235,7 @@ bool SwDBManager::MergeMailFiles(SwWrtShell* pSourceShell,
                                 }
                             }
                             pWorkDoc->SetDBManager( pOldDBManager );
-                        }
+
                         xWorkDocSh->DoClose();
                     }
                 }
@@ -2728,7 +2737,8 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
 
     SwWrtShell& rSourceShell = rSourceView.GetWrtShell();
     bool bSynchronizedDoc = rSourceShell.IsLabelDoc() && rSourceShell.GetSectionFmtCount() > 1;
-    //save the settings of the first
+
+    //determine the page style and number used at the start of the source document
     rSourceShell.SttEndDoc(true);
     sal_uInt16 nStartingPageNo = rSourceShell.GetVirtPageNum();
     OUString sModifiedStartingPageDesc;
@@ -2752,11 +2762,13 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
 
         SwView* pTargetView = static_cast<SwView*>( pTargetFrame->GetViewShell() );
         rMMConfig.SetTargetView(pTargetView);
+
         //initiate SelectShell() to create sub shells
         pTargetView->AttrChangedNotify( &pTargetView->GetWrtShell() );
         SwWrtShell* pTargetShell = pTargetView->GetWrtShellPtr();
         SwDoc* pTargetDoc = pTargetShell->GetDoc();
 
+        //copy the styles from the source to the target document
         pTargetView->GetDocShell()->_LoadStyles( *rSourceView.GetDocShell(), true );
 
         // #i63806#
@@ -2807,6 +2819,7 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
                 SwDBManager* pWorkDBManager = pWorkDoc->GetDBManager();
                 pWorkDoc->SetDBManager( this );
                 pWorkDoc->EmbedAllLinks();
+
                 SwUndoId nLastUndoId(UNDO_EMPTY);
                 if (rWorkShell.GetLastUndoInfo(0, & nLastUndoId))
                 {
@@ -2815,14 +2828,16 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
                         rWorkShell.Undo();
                     }
                 }
+
                 // #i69485# lock fields to prevent access to the result set while calculating layout
                 rWorkShell.LockExpFlds();
                 // create a layout
                 rWorkShell.CalcLayout();
                 rWorkShell.UnlockExpFlds();
-                SfxGetpApp()->NotifyEvent(SfxEventHint(SW_EVENT_FIELD_MERGE, SwDocShell::GetEventName(STR_SW_EVENT_FIELD_MERGE), rWorkShell.GetView().GetViewFrame()->GetObjectShell()));
+
+            SfxGetpApp()->NotifyEvent(SfxEventHint(SW_EVENT_FIELD_MERGE, SwDocShell::GetEventName(STR_SW_EVENT_FIELD_MERGE), rWorkShell.GetView().GetViewFrame()->GetObjectShell()));
             rWorkShell.SwViewShell::UpdateFlds();
-                SfxGetpApp()->NotifyEvent(SfxEventHint(SW_EVENT_FIELD_MERGE_FINISHED, SwDocShell::GetEventName(STR_SW_EVENT_FIELD_MERGE_FINISHED), rWorkShell.GetView().GetViewFrame()->GetObjectShell()));
+            SfxGetpApp()->NotifyEvent(SfxEventHint(SW_EVENT_FIELD_MERGE_FINISHED, SwDocShell::GetEventName(STR_SW_EVENT_FIELD_MERGE_FINISHED), rWorkShell.GetView().GetViewFrame()->GetObjectShell()));
 
             // strip invisible content and convert fields to text
             rWorkShell.RemoveInvisibleContent();
@@ -2843,7 +2858,7 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
                 //create a new pagestyle
                 //copy the pagedesc from the current document to the new document and change the name of the to-be-applied style
                 OUString sNewPageDescName = lcl_FindUniqueName(pTargetShell, sStartingPageDesc, nDocNo );
-                pTargetShell->GetDoc()->MakePageDesc( sNewPageDescName );
+                pTargetDoc->MakePageDesc( sNewPageDescName );
                 pTargetPageDesc = pTargetShell->FindPageDescByName( sNewPageDescName );
                 const SwPageDesc* pWorkPageDesc = rWorkShell.FindPageDescByName( sStartingPageDesc );
 
@@ -2857,9 +2872,6 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
             else
                 pTargetPageDesc = pTargetShell->FindPageDescByName( sModifiedStartingPageDesc );
 
-            if(nDocNo == 1)
-                pTargetShell->SetPageStyle( sModifiedStartingPageDesc );
-
             sal_uInt16 nPageCountBefore = pTargetShell->GetPageCnt();
             OSL_ENSURE(!pTargetShell->GetTableFmt(),"target document ends with a table - paragraph should be appended");
 
commit e35993b87146279a9601108babdae201cb42cab0
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Tue Jul 1 21:37:11 2014 +0200

    MM: Use SwDoc::Append for SwFeShell::Paste
    
    Same as the SwDBManager::MergeDocuments change.
    
    Change-Id: I44684bce187bb949dafc35a49b0aea9b46465cda

diff --git a/sw/source/uibase/dbui/dbmgr.cxx b/sw/source/uibase/dbui/dbmgr.cxx
index 4bc0d0e..61bfd68 100644
--- a/sw/source/uibase/dbui/dbmgr.cxx
+++ b/sw/source/uibase/dbui/dbmgr.cxx
@@ -921,6 +921,8 @@ bool SwDBManager::MergeMailFiles(SwWrtShell* pSourceShell,
             OUString sStartingPageDesc;
             sal_uInt16 nStartingPageNo = 0;
             bool bPageStylesWithHeaderFooter = false;
+            SwDoc* pTargetDoc;
+
             if(bAsSingleFile || rMergeDescriptor.bCreateSingleFile)
             {
                 // create a target docshell to put the merged document into
@@ -936,6 +938,8 @@ bool SwDBManager::MergeMailFiles(SwWrtShell* pSourceShell,
                 //initiate SelectShell() to create sub shells
                 pTargetView->AttrChangedNotify( &pTargetView->GetWrtShell() );
                 pTargetShell = pTargetView->GetWrtShellPtr();
+                pTargetDoc = pTargetShell->GetDoc();
+
                 //copy the styles from the source to the target document
                 pTargetView->GetDocShell()->_LoadStyles( *pSourceDocSh, true );
                 //determine the page style and number used at the start of the source document
@@ -1079,62 +1083,37 @@ bool SwDBManager::MergeMailFiles(SwWrtShell* pSourceShell,
                                 }
 
                                 // insert the document into the target document
-                                rWorkShell.SttEndDoc(false);
-                                rWorkShell.SttEndDoc(true);
-                                rWorkShell.SelAll();
-                                pTargetShell->SwCrsrShell::SttEndDoc( false );
-                                //#i72517# the headers and footers are still those from the source - update in case of fields inside header/footer
-                                if( !nDocNo && bPageStylesWithHeaderFooter )
-                                    pTargetShell->GetView().GetDocShell()->_LoadStyles( *rWorkShell.GetView().GetDocShell(), true );
+
                                 //#i72517# put the styles to the target document
                                 //if the source uses headers or footers each new copy need to copy a new page styles
+                                SwPageDesc* pTargetPageDesc;
                                 if(bPageStylesWithHeaderFooter)
                                 {
                                     //create a new pagestyle
                                     //copy the pagedesc from the current document to the new document and change the name of the to-be-applied style
-
-                                    SwDoc* pTargetDoc = pTargetShell->GetDoc();
-                                    SwPageDesc* pSourcePageDesc = rWorkShell.FindPageDescByName( sStartingPageDesc );
                                     OUString sNewPageDescName = lcl_FindUniqueName(pTargetShell, sStartingPageDesc, nDocNo );
                                     pTargetDoc->MakePageDesc( sNewPageDescName );
-                                    SwPageDesc* pTargetPageDesc = pTargetShell->FindPageDescByName( sNewPageDescName );
-                                    if(pSourcePageDesc && pTargetPageDesc)
+                                    pTargetPageDesc = pTargetShell->FindPageDescByName( sNewPageDescName );
+                                    const SwPageDesc* pWorkPageDesc = rWorkShell.FindPageDescByName( sStartingPageDesc );
+
+                                    if(pWorkPageDesc && pTargetPageDesc)
                                     {
-                                        pTargetDoc->CopyPageDesc( *pSourcePageDesc, *pTargetPageDesc, false );
+                                        pTargetDoc->CopyPageDesc( *pWorkPageDesc, *pTargetPageDesc, false );
                                         sModifiedStartingPageDesc = sNewPageDescName;
-                                        lcl_CopyFollowPageDesc( *pTargetShell, *pSourcePageDesc, *pTargetPageDesc, nDocNo );
+                                        lcl_CopyFollowPageDesc( *pTargetShell, *pWorkPageDesc, *pTargetPageDesc, nDocNo );
                                     }
                                 }
-
-                                if(nDocNo > 1)
-                                    pTargetShell->InsertPageBreak( &sModifiedStartingPageDesc, nStartingPageNo );
                                 else
-                                    pTargetShell->SetPageStyle(sModifiedStartingPageDesc);
-                                OSL_ENSURE(!pTargetShell->GetTableFmt(),"target document ends with a table - paragraph should be appended");
-                                //#i51359# add a second paragraph in case there's only one
-                                {
-                                    SwNodeIndex aIdx( pWorkDoc->GetNodes().GetEndOfExtras(), 2 );
-                                    SwPosition aTestPos( aIdx );
-                                    SwCursor aTestCrsr(aTestPos,0,false);
-                                    if(!aTestCrsr.MovePara(fnParaNext, fnParaStart))
-                                    {
-                                        //append a paragraph
-                                        pWorkDoc->AppendTxtNode( aTestPos );
-                                    }
-                                }
+                                    pTargetPageDesc = pTargetShell->FindPageDescByName( sModifiedStartingPageDesc );
 
 #ifdef DBG_UTIL
                                 if ( nDocNo <= MAX_DOC_DUMP )
                                     lcl_SaveDoc( xWorkDocSh, "WorkDoc", nDocNo );
 #endif
-                                pTargetShell->Paste( rWorkShell.GetDoc(), true );
+                                pTargetDoc->Append( *(rWorkShell.GetDoc()), nStartingPageNo, pTargetPageDesc, nDocNo == 1 );
 
                                 //convert fields in page styles (header/footer - has to be done after the first document has been pasted
-                                if(1 == nDocNo)
-                                {
-                                    pTargetShell->CalcLayout();
-                                    pTargetShell->ConvertFieldsToText();
-                                }
+                                pTargetShell->CalcLayout();
 #ifdef DBG_UTIL
                                 if ( nDocNo <= MAX_DOC_DUMP )
                                     lcl_SaveDoc( xTargetDocShell, "MergeDoc" );
commit ecf13fe0e9990987d8fc6678f2abad635c848ed4
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Tue Jul 1 21:31:35 2014 +0200

    Add debug documents to SwDBManager::MergeMailFiles
    
    Just like the debug documents in SwDBManager::MergeDocuments.
    
    Change-Id: I275575853c80d4e19d6df5ba9d8dc689353d7c85

diff --git a/sw/source/uibase/dbui/dbmgr.cxx b/sw/source/uibase/dbui/dbmgr.cxx
index 71b51af..4bc0d0e 100644
--- a/sw/source/uibase/dbui/dbmgr.cxx
+++ b/sw/source/uibase/dbui/dbmgr.cxx
@@ -808,6 +808,33 @@ static void lcl_RemoveSectionLinks( SwWrtShell& rWorkShell )
     rWorkShell.SetLabelDoc( false );
 }
 
+#ifdef DBG_UTIL
+
+#define MAX_DOC_DUMP 3
+
+static void lcl_SaveDoc( SfxObjectShell *xTargetDocShell,
+                         const char *name, int no = 0 )
+{
+    boost::scoped_ptr< utl::TempFile > aTempFile;
+    OUString sExt( ".odt" );
+    OUString basename = OUString::createFromAscii( name );
+    if (no > 0 )
+        basename += OUString::number(no) + "-";
+    aTempFile.reset( new utl::TempFile( basename, true, &sExt ) );
+    OSL_ENSURE( aTempFile.get(), "Temporary file not available" );
+    INetURLObject aTempFileURL( aTempFile->GetURL() );
+    SfxMedium* pDstMed = new SfxMedium(
+        aTempFileURL.GetMainURL( INetURLObject::NO_DECODE ),
+        STREAM_STD_READWRITE );
+    xTargetDocShell->DoSaveAs( *pDstMed );
+    xTargetDocShell->DoSaveCompleted( pDstMed );
+    if( xTargetDocShell->GetError() )
+        SAL_WARN( "sw.mailmerge", "Error saving: " << aTempFile->GetURL() );
+    else
+        SAL_INFO( "sw.mailmerge", "Saved doc as: " << aTempFile->GetURL() );
+}
+#endif
+
 bool SwDBManager::MergeMailFiles(SwWrtShell* pSourceShell,
         const SwMergeDescriptor& rMergeDescriptor)
 {
@@ -899,6 +926,9 @@ bool SwDBManager::MergeMailFiles(SwWrtShell* pSourceShell,
                 // create a target docshell to put the merged document into
                 xTargetDocShell = new SwDocShell( SFX_CREATE_MODE_STANDARD );
                 xTargetDocShell->DoInitNew( 0 );
+#ifdef DBG_UTIL
+                lcl_SaveDoc( xTargetDocShell, "MergeDoc" );
+#endif
                 SfxViewFrame* pTargetFrame = SfxViewFrame::LoadHiddenDocument( *xTargetDocShell, 0 );
 
                 pTargetView = static_cast<SwView*>( pTargetFrame->GetViewShell() );
@@ -1007,6 +1037,10 @@ bool SwDBManager::MergeMailFiles(SwWrtShell* pSourceShell,
                         // The SfxObjectShell will be closed explicitly later but it is more safe to use SfxObjectShellLock here
                         // copy the source document
                         SfxObjectShellLock xWorkDocSh = pSourceDocSh->GetDoc()->CreateCopy( true );
+#ifdef DBG_UTIL
+                        if ( nDocNo <= MAX_DOC_DUMP )
+                            lcl_SaveDoc( xWorkDocSh, "WorkDoc", nDocNo );
+#endif
 
                         {
                             //create a view frame for the document
@@ -1088,6 +1122,11 @@ bool SwDBManager::MergeMailFiles(SwWrtShell* pSourceShell,
                                         pWorkDoc->AppendTxtNode( aTestPos );
                                     }
                                 }
+
+#ifdef DBG_UTIL
+                                if ( nDocNo <= MAX_DOC_DUMP )
+                                    lcl_SaveDoc( xWorkDocSh, "WorkDoc", nDocNo );
+#endif
                                 pTargetShell->Paste( rWorkShell.GetDoc(), true );
 
                                 //convert fields in page styles (header/footer - has to be done after the first document has been pasted
@@ -1096,6 +1135,10 @@ bool SwDBManager::MergeMailFiles(SwWrtShell* pSourceShell,
                                     pTargetShell->CalcLayout();
                                     pTargetShell->ConvertFieldsToText();
                                 }
+#ifdef DBG_UTIL
+                                if ( nDocNo <= MAX_DOC_DUMP )
+                                    lcl_SaveDoc( xTargetDocShell, "MergeDoc" );
+#endif
                             }
                             else
                             {
@@ -2648,33 +2691,6 @@ uno::Reference<XResultSet> SwDBManager::createCursor(const OUString& _sDataSourc
     return xResultSet;
 }
 
-#ifdef DBG_UTIL
-
-#define MAX_DOC_DUMP 3
-
-static void lcl_SaveDoc( SfxObjectShell *xTargetDocShell,
-                         const char *name, int no = 0 )
-{
-    boost::scoped_ptr< utl::TempFile > aTempFile;
-    OUString sExt( ".odt" );
-    OUString basename = OUString::createFromAscii( name );
-    if (no > 0 )
-        basename += OUString::number(no) + "-";
-    aTempFile.reset( new utl::TempFile( basename, true, &sExt ) );
-    OSL_ENSURE( aTempFile.get(), "Temporary file not available" );
-    INetURLObject aTempFileURL( aTempFile->GetURL() );
-    SfxMedium* pDstMed = new SfxMedium(
-        aTempFileURL.GetMainURL( INetURLObject::NO_DECODE ),
-        STREAM_STD_READWRITE );
-    xTargetDocShell->DoSaveAs( *pDstMed );
-    xTargetDocShell->DoSaveCompleted( pDstMed );
-    if( xTargetDocShell->GetError() )
-        SAL_WARN( "sw.mailmerge", "Error saving: " << aTempFile->GetURL() );
-    else
-        SAL_INFO( "sw.mailmerge", "Saved doc as: " << aTempFile->GetURL() );
-}
-#endif
-
 // merge all data into one resulting document and return the number of merged documents
 sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
                             SwView& rSourceView )
commit 71d25bb94698675a46fb01b735f58921817d31e3
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Tue Jul 1 15:48:01 2014 +0200

    Add debug messages for sw.{createcopy,docappend}
    
    This adds a lot of SAL_INFO messages to SwDoc::CreateCopy and
    SwDoc::Append.
    
    Change-Id: Ie924e20698bec84482fcc5496175a9e29245729e

diff --git a/sw/source/core/doc/docnew.cxx b/sw/source/core/doc/docnew.cxx
index c34eb66..e63beca 100644
--- a/sw/source/core/doc/docnew.cxx
+++ b/sw/source/core/doc/docnew.cxx
@@ -994,6 +994,11 @@ void SwDoc::ReplaceCompatabilityOptions(const SwDoc& rSource)
     m_pDocumentSettingManager->ReplaceCompatibilityOptions(rSource.GetDocumentSettingManager());
 }
 
+#define CNTNT_DOC( doc ) \
+    ((doc)->GetNodes().GetEndOfContent().GetIndex() - (doc)->GetNodes().GetEndOfExtras().GetIndex() - 2)
+#define CNTNT_IDX( idx ) \
+    ((idx).GetNode().GetIndex() - GetNodes().GetEndOfExtras().GetIndex() - 1)
+
 SfxObjectShell* SwDoc::CreateCopy(bool bCallInitNew ) const
 {
     SwDoc* pRet = new SwDoc;
@@ -1017,7 +1022,14 @@ SfxObjectShell* SwDoc::CreateCopy(bool bCallInitNew ) const
 
     pRet->ReplaceStyles(*this);
 
+#ifdef DBG_UTIL
+    SAL_INFO( "sw.createcopy", "CC-Nd-Src: " << CNTNT_DOC( this ) );
+    SAL_INFO( "sw.createcopy", "CC-Nd: " << CNTNT_DOC( pRet ) );
+#endif
     pRet->Append(*this, 0, NULL, bCallInitNew);
+#ifdef DBG_UTIL
+    SAL_INFO( "sw.createcopy", "CC-Nd: " << CNTNT_DOC( pRet ) );
+#endif
 
     // remove the temporary shell if it is there as it was done before
     pRet->SetTmpDocShell( (SfxObjectShell*) NULL );
@@ -1048,9 +1060,35 @@ void SwDoc::Append( const SwDoc& rSource, sal_uInt16 nStartPageNumber,
     else
         aCpyPam = SwPaM( aSourceIdx, aSourceEndIdx );
 
+#ifdef DBG_UTIL
+    SAL_INFO( "sw.docappend", "NodeType 0x" << std::hex << (int) aSourceIdx.GetNode().GetNodeType()
+                              << std::dec << " " << aSourceIdx.GetNode().GetIndex() );
+    aSourceIdx++;
+    SAL_INFO( "sw.docappend", "NodeType 0x" << std::hex << (int) aSourceIdx.GetNode().GetNodeType()
+                                            << std::dec << " " << aSourceIdx.GetNode().GetIndex() );
+    if ( aSourceIdx.GetNode().GetNodeType() != ND_ENDNODE ) {
+        aSourceIdx++;
+        SAL_INFO( "sw.docappend", "NodeType 0x" << std::hex << (int) aSourceIdx.GetNode().GetNodeType() << std::dec );
+        aSourceIdx--;
+    }
+    aSourceIdx--;
+    SAL_INFO( "sw.docappend", ".." );
+    SAL_INFO( "sw.docappend", "NodeType 0x" << std::hex << (int) aSourceEndIdx.GetNode().GetNodeType()
+                              << std::dec << " " << aSourceEndIdx.GetNode().GetIndex() );
+    aSourceEndIdx++;
+    SAL_INFO( "sw.docappend", "NodeType 0x" << std::hex << (int) aSourceEndIdx.GetNode().GetNodeType()
+                              << std::dec << " " << aSourceEndIdx.GetNode().GetIndex() );
+    aSourceEndIdx--;
+    SAL_INFO( "sw.docappend", "Src-Nd: " << CNTNT_DOC( &rSource ) );
+    SAL_INFO( "sw.docappend", "Nd: " << CNTNT_DOC( this ) );
+#endif
+
     SwWrtShell* pTargetShell = GetDocShell()->GetWrtShell();
     sal_uInt16 nPhysPageNumber = 0;
     if ( pTargetShell ) {
+#ifdef DBG_UTIL
+        SAL_INFO( "sw.docappend", "Has target write shell" );
+#endif
         pTargetShell->StartAllAction();
 
         // Otherwise we have to handle SwDummySectionNodes as first node
@@ -1067,7 +1105,13 @@ void SwDoc::Append( const SwDoc& rSource, sal_uInt16 nStartPageNumber,
         // We always start on an odd physical page number
         if (1 == nPhysPageNumber % 2)
             nPhysPageNumber++;
+#ifdef DBG_UTIL
+    SAL_INFO( "sw.docappend", "PPNo " << nPhysPageNumber );
+#endif
     }
+#ifdef DBG_UTIL
+    SAL_INFO( "sw.docappend", "Nd: " << CNTNT_DOC( this ) );
+#endif
 
     // -1, otherwise aFixupIdx would move to new EOC
     SwNodeIndex aFixupIdx( GetNodes().GetEndOfContent(), -1 );
@@ -1076,6 +1120,13 @@ void SwDoc::Append( const SwDoc& rSource, sal_uInt16 nStartPageNumber,
     SwNodeIndex aTargetIdx( GetNodes().GetEndOfContent() );
     SwPaM aInsertPam( aTargetIdx );
 
+#ifdef DBG_UTIL
+    SAL_INFO( "sw.docappend", "Pam-Nd: " << aCpyPam.GetNode( true ).GetIndex() - aCpyPam.GetNode( false ).GetIndex() + 1
+                              << " (0x" << std::hex << (int) aCpyPam.GetNode( false ).GetNodeType() << std::dec
+                              << " " << aCpyPam.GetNode( false ).GetIndex()
+                              << " - 0x" << std::hex << (int) aCpyPam.GetNode( true ).GetNodeType() << std::dec
+                              << " " << aCpyPam.GetNode( true ).GetIndex() << ")" );
+#endif
 
     GetIDocumentUndoRedo().StartUndo( UNDO_INSGLOSSARY, NULL );
     LockExpFlds();
@@ -1091,9 +1142,14 @@ void SwDoc::Append( const SwDoc& rSource, sal_uInt16 nStartPageNumber,
             SwNodeIndex aIndexBefore(rInsPos.nNode);
 
             aIndexBefore--;
-
+#ifdef DBG_UTIL
+    SAL_INFO( "sw.docappend", "CopyRange In: " << CNTNT_DOC( this ) );
+#endif
             rSource.CopyRange( aCpyPam, rInsPos, true );
             // Note: aCpyPam is invalid now
+#ifdef DBG_UTIL
+    SAL_INFO( "sw.docappend", "CopyRange Out: " << CNTNT_DOC( this ) );
+#endif
 
             ++aIndexBefore;
             SwPaM aPaM(SwPosition(aIndexBefore),
@@ -1122,10 +1178,23 @@ void SwDoc::Append( const SwDoc& rSource, sal_uInt16 nStartPageNumber,
             if ( nStartPageNumber || pTargetPageDesc ) {
                 // Changes the index of aFixupIdx
                 SwTxtNode *aTxtNd = dynamic_cast<  SwTxtNode* >( GetNodes().GoNext(&aFixupIdx) );
+#ifdef DBG_UTIL
+    SAL_INFO( "sw.docappend", "Idx " << CNTNT_IDX( aDelIdx ) );
+    SAL_INFO( "sw.docappend", "Idx " << CNTNT_IDX( aFixupIdx ) );
+#endif
                 if ( aTxtNd ) {
                     SfxPoolItem *pNewItem = aTxtNd->GetAttr( RES_PAGEDESC ).Clone();
+#ifdef DBG_UTIL
+    SAL_INFO( "sw.docappend", "Which: " << pNewItem->Which() << " " << RES_PAGEDESC );
+#endif
                     SwFmtPageDesc *aDesc = dynamic_cast< SwFmtPageDesc* >( pNewItem );
                     if ( aDesc ) {
+#ifdef DBG_UTIL
+if ( aDesc->GetPageDesc() )
+        SAL_INFO( "sw.docappend", "PD Update " << aDesc->GetPageDesc()->GetName() );
+else
+        SAL_INFO( "sw.docappend", "PD New" );
+#endif
                         if ( nStartPageNumber )
                             aDesc->SetNumOffset( nStartPageNumber );
                         if ( pTargetPageDesc )
@@ -1134,6 +1203,10 @@ void SwDoc::Append( const SwDoc& rSource, sal_uInt16 nStartPageNumber,
                     }
                     delete pNewItem;
                 }
+
+#ifdef DBG_UTIL
+    SAL_INFO( "sw.docappend", "Idx " << CNTNT_IDX( aDelIdx ) );
+#endif
                 iDelNodes++;
             }
 
@@ -1147,6 +1220,11 @@ void SwDoc::Append( const SwDoc& rSource, sal_uInt16 nStartPageNumber,
                 if ( pTargetShell )
                     pTargetShell->SttEndDoc( false );
                 aDelIdx -= (iDelNodes - 1);
+#ifdef DBG_UTIL
+    SAL_INFO( "sw.docappend", "iDelNodes: " << iDelNodes
+                              << "  Idx: " << aDelIdx.GetNode().GetIndex()
+                              << "  EOE: " << GetNodes().GetEndOfExtras().GetIndex() );
+#endif
                 GetNodes().Delete( aDelIdx, iDelNodes );
             }
         }
@@ -1159,6 +1237,10 @@ void SwDoc::Append( const SwDoc& rSource, sal_uInt16 nStartPageNumber,
             SwFmtAnchor aAnchor( rCpyFmt.GetAnchor() );
             if (FLY_AT_PAGE != aAnchor.GetAnchorId())
                 continue;
+#ifdef DBG_UTIL
+    SAL_INFO( "sw.docappend", "PaAn: " << aAnchor.GetPageNum()
+                              << " => " << aAnchor.GetPageNum() + nPhysPageNumber );
+#endif
             if ( nPhysPageNumber )
                 aAnchor.SetPageNum( aAnchor.GetPageNum() + nPhysPageNumber );
             CopyLayoutFmt( rCpyFmt, aAnchor, true, true );
commit 1392a8074230c9d129de6ed63ba10cbeab3aac74
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Tue Jul 1 13:02:58 2014 +0200

    Refactor NumRule handling in CopyImpl
    
    The bug fix for i#86492 added a lot of duplicated code. This moves
    the code into their own functions and uses macros to make the
    resulting code even more readable.
    
    Change-Id: Ifa0ece26f3152f1f8d8c65173b459e8c14c5b43a

diff --git a/sw/source/core/docnode/ndcopy.cxx b/sw/source/core/docnode/ndcopy.cxx
index 1f49b0d..5443c9f 100644
--- a/sw/source/core/docnode/ndcopy.cxx
+++ b/sw/source/core/docnode/ndcopy.cxx
@@ -849,6 +849,69 @@ static bool lcl_ContainsOnlyParagraphsInList( const SwPaM& rPam )
     return bRet;
 }
 
+#define NUMRULE_STATE \
+     int aNumRuleState = SFX_ITEM_UNKNOWN; \
+     SwNumRuleItem aNumRuleItem; \
+     int aListIdState = SFX_ITEM_UNKNOWN; \
+     SfxStringItem aListIdItem( RES_PARATR_LIST_ID, OUString() ); \
+
+#define PUSH_NUMRULE_STATE \
+     lcl_PushNumruleState( aNumRuleState, aNumRuleItem, aListIdState, aListIdItem, pDestTxtNd );
+
+#define POP_NUMRULE_STATE \
+     lcl_PopNumruleState( aNumRuleState, aNumRuleItem, aListIdState, aListIdItem, pDestTxtNd, rPam );
+
+static void lcl_PushNumruleState( int &aNumRuleState, SwNumRuleItem &aNumRuleItem,
+                                  int &aListIdState, SfxStringItem &aListIdItem,
+                                  const SwTxtNode *pDestTxtNd )
+{
+    // Safe numrule item at destination.
+    // #i86492# - Safe also <ListId> item of destination.
+    const SfxItemSet * pAttrSet = pDestTxtNd->GetpSwAttrSet();
+    if (pAttrSet != NULL)
+    {
+        const SfxPoolItem * pItem = NULL;
+        aNumRuleState = pAttrSet->GetItemState(RES_PARATR_NUMRULE, false, &pItem);
+        if (SFX_ITEM_SET == aNumRuleState)
+            aNumRuleItem = *((SwNumRuleItem *) pItem);
+
+        aListIdState =
+            pAttrSet->GetItemState(RES_PARATR_LIST_ID, false, &pItem);
+        if (SFX_ITEM_SET == aListIdState)
+        {
+            aListIdItem.SetValue( static_cast<const SfxStringItem*>(pItem)->GetValue() );
+        }
+    }
+}
+
+static void lcl_PopNumruleState( int aNumRuleState, const SwNumRuleItem &aNumRuleItem,
+                                 int aListIdState, const SfxStringItem &aListIdItem,
+                                 SwTxtNode *pDestTxtNd, const SwPaM& rPam )
+{
+    /* If only a part of one paragraph is copied
+       restore the numrule at the destination. */
+    // #i86492# - restore also <ListId> item
+    if ( !lcl_MarksWholeNode(rPam) )
+    {
+        if (SFX_ITEM_SET == aNumRuleState)
+        {
+            pDestTxtNd->SetAttr(aNumRuleItem);
+        }
+        else
+        {
+            pDestTxtNd->ResetAttr(RES_PARATR_NUMRULE);
+        }
+        if (SFX_ITEM_SET == aListIdState)
+        {
+            pDestTxtNd->SetAttr(aListIdItem);
+        }
+        else
+        {
+            pDestTxtNd->ResetAttr(RES_PARATR_LIST_ID);
+        }
+    }
+}
+
 bool SwDoc::CopyImpl( SwPaM& rPam, SwPosition& rPos,
         const bool bMakeNewFrms, const bool bCopyAll,
         SwPaM *const pCpyRange ) const
@@ -1012,28 +1075,10 @@ bool SwDoc::CopyImpl( SwPaM& rPam, SwPosition& rPos,
                     }
                 }
 
-                // Safe numrule item at destination.
-                // #i86492# - Safe also <ListId> item of destination.
-                int aNumRuleState = SFX_ITEM_UNKNOWN;
-                SwNumRuleItem aNumRuleItem;
-                int aListIdState = SFX_ITEM_UNKNOWN;
-                SfxStringItem aListIdItem( RES_PARATR_LIST_ID, OUString() );
+                NUMRULE_STATE
+                if( bCopyCollFmt && bOneNode )
                 {
-                    const SfxItemSet * pAttrSet = pDestTxtNd->GetpSwAttrSet();
-                    if (pAttrSet != NULL)
-                    {
-                        const SfxPoolItem * pItem = NULL;
-                        aNumRuleState = pAttrSet->GetItemState(RES_PARATR_NUMRULE, false, &pItem);
-                        if (SFX_ITEM_SET == aNumRuleState)
-                            aNumRuleItem = *((SwNumRuleItem *) pItem);
-
-                        aListIdState =
-                            pAttrSet->GetItemState(RES_PARATR_LIST_ID, false, &pItem);
-                        if (SFX_ITEM_SET == aListIdState)
-                        {
-                            aListIdItem.SetValue( static_cast<const SfxStringItem*>(pItem)->GetValue() );
-                        }
-                    }
+                    PUSH_NUMRULE_STATE
                 }
 
                 if( !bCopyOk )
@@ -1053,29 +1098,7 @@ bool SwDoc::CopyImpl( SwPaM& rPam, SwPosition& rPos,
                     if( bCopyCollFmt )
                     {
                         pSttTxtNd->CopyCollFmt( *pDestTxtNd );
-
-                        /* If only a part of one paragraph is copied
-                           restore the numrule at the destination. */
-                        // #i86492# - restore also <ListId> item
-                        if ( !lcl_MarksWholeNode(rPam) )
-                        {
-                            if (SFX_ITEM_SET == aNumRuleState)
-                            {
-                                pDestTxtNd->SetAttr(aNumRuleItem);
-                            }
-                            else
-                            {
-                                pDestTxtNd->ResetAttr(RES_PARATR_NUMRULE);
-                            }
-                            if (SFX_ITEM_SET == aListIdState)
-                            {
-                                pDestTxtNd->SetAttr(aListIdItem);
-                            }
-                            else
-                            {
-                                pDestTxtNd->ResetAttr(RES_PARATR_LIST_ID);
-                            }
-                        }
+                        POP_NUMRULE_STATE
                     }
 
                     break;
@@ -1157,31 +1180,14 @@ bool SwDoc::CopyImpl( SwPaM& rPam, SwPosition& rPos,
                 bStartIsTxtNode = true;
             }
 
-            // Save numrule at destination
-            // #i86492# - Safe also <ListId> item of destination.
-            int aNumRuleState = SFX_ITEM_UNKNOWN;
-            SwNumRuleItem aNumRuleItem;
-            int aListIdState = SFX_ITEM_UNKNOWN;
-            SfxStringItem aListIdItem( RES_PARATR_LIST_ID, OUString() );
-            {
-                const SfxItemSet* pAttrSet = pDestTxtNd->GetpSwAttrSet();
-                if (pAttrSet != NULL)
-                {
-                    const SfxPoolItem * pItem = NULL;
-
-                    aNumRuleState =
-                        pAttrSet->GetItemState(RES_PARATR_NUMRULE, false, &pItem);
-                    if (SFX_ITEM_SET == aNumRuleState)
-                        aNumRuleItem = *((SwNumRuleItem *) pItem);
+            const bool bEmptyDestNd = pDestTxtNd->GetTxt().isEmpty();
 
-                    aListIdState =
-                        pAttrSet->GetItemState(RES_PARATR_LIST_ID, false, &pItem);
-                    if (SFX_ITEM_SET == aListIdState)
-                        aListIdItem.SetValue( static_cast<const SfxStringItem*>(pItem)->GetValue() );
-                }
+            NUMRULE_STATE
+            if( bCopyCollFmt && ( bOneNode || bEmptyDestNd ))
+            {
+                PUSH_NUMRULE_STATE
             }
 
-            const bool bEmptyDestNd = pDestTxtNd->GetTxt().isEmpty();
             pEndTxtNd->CopyText( pDestTxtNd, aDestIdx, SwIndex( pEndTxtNd ),
                             pEnd->nContent.GetIndex() );
 
@@ -1189,31 +1195,9 @@ bool SwDoc::CopyImpl( SwPaM& rPam, SwPosition& rPos,
             if( bCopyCollFmt && ( bOneNode || bEmptyDestNd ))
             {
                 pEndTxtNd->CopyCollFmt( *pDestTxtNd );
-
                 if ( bOneNode )
                 {
-                    /* If only a part of one paragraph is copied
-                       restore the numrule at the destination. */
-                    // #i86492# - restore also <ListId> item
-                    if ( !lcl_MarksWholeNode(rPam) )
-                    {
-                        if (SFX_ITEM_SET == aNumRuleState)
-                        {
-                            pDestTxtNd->SetAttr(aNumRuleItem);
-                        }
-                        else
-                        {
-                            pDestTxtNd->ResetAttr(RES_PARATR_NUMRULE);
-                        }
-                        if (SFX_ITEM_SET == aListIdState)
-                        {
-                            pDestTxtNd->SetAttr(aListIdItem);
-                        }
-                        else
-                        {
-                            pDestTxtNd->ResetAttr(RES_PARATR_LIST_ID);
-                        }
-                    }
+                    POP_NUMRULE_STATE
                 }
             }
         }
commit f2ca891d818a8345d2c81b28556a7cb7dfd10971
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Tue Jul 1 15:25:10 2014 +0200

    Append fixup
    
    Change-Id: I84ee5290ded20803d1496daa52325c3651a9bc97

diff --git a/sw/inc/doc.hxx b/sw/inc/doc.hxx
index ec80dd3..d0e31aa 100644
--- a/sw/inc/doc.hxx
+++ b/sw/inc/doc.hxx
@@ -1885,8 +1885,8 @@ public:
     ::sw::UndoManager const& GetUndoManager() const;
 
     SfxObjectShell* CreateCopy(bool bCallInitNew) const;
-    void Append( const SwDoc& rSource, int nStartPageNumber,
-                 SwPageDesc* pTargetPageDesc, int nPhysPageNumber );
+    void Append( const SwDoc& rSource, sal_uInt16 nStartPageNumber,
+                 SwPageDesc* pTargetPageDesc, bool bDeletePrevious = false );
 
     /**
      * Dumps the entire nodes structure to the given destination (file nodes.xml in the current directory by default)
diff --git a/sw/source/core/doc/docnew.cxx b/sw/source/core/doc/docnew.cxx
index b0a83b3..c34eb66 100644
--- a/sw/source/core/doc/docnew.cxx
+++ b/sw/source/core/doc/docnew.cxx
@@ -92,6 +92,7 @@
 #include <DocumentDrawModelManager.hxx>
 #include <unochart.hxx>
 #include <fldbas.hxx>
+#include <wrtsh.hxx>
 
 #include <cmdid.h>
 
@@ -1016,13 +1017,7 @@ SfxObjectShell* SwDoc::CreateCopy(bool bCallInitNew ) const
 
     pRet->ReplaceStyles(*this);
 
-    pRet->Append(*this, 0, NULL, 0);
-
-    if ( bCallInitNew ) {
-        // delete leading page / initial content from target document
-        SwNodeIndex aDeleteIdx( pRet->GetNodes().GetEndOfExtras(), 2 );
-        pRet->GetNodes().Delete( aDeleteIdx, 1 );
-    }
+    pRet->Append(*this, 0, NULL, bCallInitNew);
 
     // remove the temporary shell if it is there as it was done before
     pRet->SetTmpDocShell( (SfxObjectShell*) NULL );
@@ -1033,20 +1028,54 @@ SfxObjectShell* SwDoc::CreateCopy(bool bCallInitNew ) const
 }
 
 // appends all pages of source SwDoc - based on SwFEShell::Paste( SwDoc* )
-void SwDoc::Append( const SwDoc& rSource, int nStartPageNumber,
-                    SwPageDesc* pTargetPageDesc, int nPhysPageNumber )
+void SwDoc::Append( const SwDoc& rSource, sal_uInt16 nStartPageNumber,
+                    SwPageDesc* pTargetPageDesc, bool bDeletePrevious )
 {
-    // GetEndOfExtras + 1 = StartOfContent
+    // GetEndOfExtras + 1 = StartOfContent == no content node!
+    // this prevents CopyRange to merge any starting text nodes of the first
+    // source paragraph!
+    // additionally it ensures, that we have at least two nodes in the SwPaM.
     SwNodeIndex aSourceIdx( rSource.GetNodes().GetEndOfExtras(), 1 );
-    SwPaM aCpyPam( aSourceIdx ); //DocStart
+    SwNodeIndex aSourceEndIdx( rSource.GetNodes().GetEndOfContent(), -1 );
+    SwPaM aCpyPam( aSourceIdx );
+
+    if ( aSourceEndIdx.GetNode().IsTxtNode() ) {
+        aCpyPam.SetMark();
+        // moves to the last content node before EOC; for single paragraph
+        // documents this would result in [n, n], which is considered empty
+        aCpyPam.Move( fnMoveForward, fnGoDoc );
+    }
+    else
+        aCpyPam = SwPaM( aSourceIdx, aSourceEndIdx );
+
+    SwWrtShell* pTargetShell = GetDocShell()->GetWrtShell();
+    sal_uInt16 nPhysPageNumber = 0;
+    if ( pTargetShell ) {
+        pTargetShell->StartAllAction();
+
+        // Otherwise we have to handle SwDummySectionNodes as first node
+        if ( pTargetPageDesc ) {
+            OUString name = pTargetPageDesc->GetName();
+            pTargetShell->InsertPageBreak( &name, nStartPageNumber );
+        }
+
+        // -1 for the page break + -1, becauce it's an offset
+        nPhysPageNumber = pTargetShell->GetPhyPageNum() - 2;
+        if (bDeletePrevious)
+            nPhysPageNumber--;
 
-    // Append at the end of document / content
+        // We always start on an odd physical page number
+        if (1 == nPhysPageNumber % 2)
+            nPhysPageNumber++;
+    }
+
+    // -1, otherwise aFixupIdx would move to new EOC
+    SwNodeIndex aFixupIdx( GetNodes().GetEndOfContent(), -1 );
+
+    // append at the end of document / content
     SwNodeIndex aTargetIdx( GetNodes().GetEndOfContent() );
-    SwPaM aInsertPam( aTargetIdx ); //replaces PCURCRSR from SwFEShell::Paste()
-    aTargetIdx--;
+    SwPaM aInsertPam( aTargetIdx );
 
-    aCpyPam.SetMark();
-    aCpyPam.Move( fnMoveForward, fnGoDoc );
 
     GetIDocumentUndoRedo().StartUndo( UNDO_INSGLOSSARY, NULL );
     LockExpFlds();
@@ -1085,24 +1114,44 @@ void SwDoc::Append( const SwDoc& rSource, int nStartPageNumber,
             }
         }
 
-        // update the PageDesc pool item
-        if ( nStartPageNumber || pTargetPageDesc ) {
-            SwTxtNode *aTxtNd = dynamic_cast<  SwTxtNode* >( GetNodes().GoNext(&aTargetIdx) );
-            if ( aTxtNd ) {
-                SfxPoolItem *pNewItem = aTxtNd->GetAttr( RES_PAGEDESC ).Clone();
-                SwFmtPageDesc *aDesc = dynamic_cast< SwFmtPageDesc* >( pNewItem );
-                if ( aDesc ) {
-                    if ( nStartPageNumber )
-                        aDesc->SetNumOffset( nStartPageNumber );
-                    if ( pTargetPageDesc )
-                        aDesc->RegisterToPageDesc( *pTargetPageDesc );
-                    aTxtNd->SetAttr( *aDesc );
+        {
+            sal_uInt16 iDelNodes = 0;
+            SwNodeIndex aDelIdx( aFixupIdx );
+
+            // update the PageDesc format item
+            if ( nStartPageNumber || pTargetPageDesc ) {
+                // Changes the index of aFixupIdx
+                SwTxtNode *aTxtNd = dynamic_cast<  SwTxtNode* >( GetNodes().GoNext(&aFixupIdx) );
+                if ( aTxtNd ) {
+                    SfxPoolItem *pNewItem = aTxtNd->GetAttr( RES_PAGEDESC ).Clone();
+                    SwFmtPageDesc *aDesc = dynamic_cast< SwFmtPageDesc* >( pNewItem );
+                    if ( aDesc ) {
+                        if ( nStartPageNumber )
+                            aDesc->SetNumOffset( nStartPageNumber );
+                        if ( pTargetPageDesc )
+                            aDesc->RegisterToPageDesc( *pTargetPageDesc );
+                        aTxtNd->SetAttr( *aDesc );
+                    }
+                    delete pNewItem;
                 }
-                delete pNewItem;
+                iDelNodes++;
+            }
+
+            if ( bDeletePrevious )
+                iDelNodes++;
+
+            if ( iDelNodes ) {
+                // delete leading empty page(s), e.g. from InsertPageBreak or
+                // new SwDoc. this has to be done before copying the page bound
+                // frames, otherwise the drawing layer gets confused.
+                if ( pTargetShell )
+                    pTargetShell->SttEndDoc( false );
+                aDelIdx -= (iDelNodes - 1);
+                GetNodes().Delete( aDelIdx, iDelNodes );
             }
         }
 
-        // additionally copy page bound frames
+        // finally copy page bound frames
         const SwFrmFmts *pSpzFrmFmts = rSource.GetSpzFrmFmts();
         for ( sal_uInt16 i = 0; i < pSpzFrmFmts->size(); ++i )
         {
@@ -1110,7 +1159,7 @@ void SwDoc::Append( const SwDoc& rSource, int nStartPageNumber,
             SwFmtAnchor aAnchor( rCpyFmt.GetAnchor() );
             if (FLY_AT_PAGE != aAnchor.GetAnchorId())
                 continue;
-            if ( nStartPageNumber )
+            if ( nPhysPageNumber )
                 aAnchor.SetPageNum( aAnchor.GetPageNum() + nPhysPageNumber );
             CopyLayoutFmt( rCpyFmt, aAnchor, true, true );
         }
@@ -1120,6 +1169,9 @@ void SwDoc::Append( const SwDoc& rSource, int nStartPageNumber,
 
     UnlockExpFlds();
     UpdateFlds(NULL, false);
+
+    if ( pTargetShell )
+        pTargetShell->EndAllAction();
 }
 
 sal_uInt16 SwTxtFmtColls::GetPos(const SwTxtFmtColl* p) const
diff --git a/sw/source/core/docnode/ndcopy.cxx b/sw/source/core/docnode/ndcopy.cxx
index 5575934..1f49b0d 100644
--- a/sw/source/core/docnode/ndcopy.cxx
+++ b/sw/source/core/docnode/ndcopy.cxx
@@ -1355,8 +1355,10 @@ void SwDoc::CopyWithFlyInFly(
             !rRg.aStart.GetNode().IsSectionNode() &&
             !aTmpI.GetNode().IsEndNode() )
         {
+            // If the range starts with a SwStartNode, it isn't copied
+            sal_uInt16 offset = (rRg.aStart.GetNode().GetNodeType() != ND_STARTNODE) ? 1 : 0;
             OSL_ENSURE( rInsPos.GetIndex() - aSavePos.GetIndex() ==
-                    rRg.aEnd.GetIndex() - rRg.aStart.GetIndex(),
+                    rRg.aEnd.GetIndex() - rRg.aStart.GetIndex() - 1 + offset,
                     "An insufficient number of nodes were copied!" );
         }
     }
diff --git a/sw/source/uibase/dbui/dbmgr.cxx b/sw/source/uibase/dbui/dbmgr.cxx
index e8e63db..71b51af 100644
--- a/sw/source/uibase/dbui/dbmgr.cxx
+++ b/sw/source/uibase/dbui/dbmgr.cxx
@@ -2769,7 +2769,6 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
         const SwFrmFmt& rMaster = pSourcePageDesc->GetMaster();
         bool bPageStylesWithHeaderFooter = rMaster.GetHeader().IsActive()  ||
                                         rMaster.GetFooter().IsActive();
-        SwNodes *pTargetNodes = &pTargetShell->GetDoc()->GetNodes();
 
         // copy compatibility options
         lcl_CopyCompatibilityOptions( rSourceShell, *pTargetShell);
@@ -2840,10 +2839,6 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
             }
 
             // insert the document into the target document
-            rWorkShell.SttEndDoc(false);
-            rWorkShell.SttEndDoc(true);
-            rWorkShell.SelAll();
-            pTargetShell->SttEndDoc(false);
 
             //#i63806# put the styles to the target document
             //if the source uses headers or footers each new copy need to copy a new page styles
@@ -2868,7 +2863,7 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
                 pTargetPageDesc = pTargetShell->FindPageDescByName( sModifiedStartingPageDesc );
 
             if(nDocNo == 1)
-                pTargetShell->SetPageStyle(sModifiedStartingPageDesc);
+                pTargetShell->SetPageStyle( sModifiedStartingPageDesc );
 
             sal_uInt16 nPageCountBefore = pTargetShell->GetPageCnt();
             OSL_ENSURE(!pTargetShell->GetTableFmt(),"target document ends with a table - paragraph should be appended");
@@ -2877,18 +2872,7 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
             if ( nDocNo <= MAX_DOC_DUMP )
                 lcl_SaveDoc( xWorkDocSh, "WorkDoc", nDocNo );
 #endif
-
-            if (nDocNo == 1 ) {
-                pTargetDoc->Append( *(rWorkShell.GetDoc()), 0, pTargetPageDesc, 0 );
-
-                // delete the leading empty page from the initial SwDoc
-                pTargetShell->SttEndDoc( false );
-                SwNodeIndex aDeleteIdx( pTargetNodes->GetEndOfExtras(), 2 );
-                pTargetNodes->Delete( aDeleteIdx, 1 );
-            }
-            else
-                pTargetDoc->Append( *(rWorkShell.GetDoc()), nStartingPageNo,
-                                    pTargetPageDesc, pTargetShell->GetPhyPageNum() );
+            pTargetDoc->Append( *(rWorkShell.GetDoc()), nStartingPageNo, pTargetPageDesc, nDocNo == 1 );
 
             // #i72820# calculate layout to be able to find the correct page index
             pTargetShell->CalcLayout();
commit f4f6e08a3d835132d1ce11a034a94017b619b3b6
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Sat Jun 28 01:41:17 2014 +0200

    MM: introduce SwDoc::Append helper function
    
    This drops all the specialized, workaround code from MM, introduced
    to use the SwFEShell::Paste function.
    
    There is still a little common codepath, therefore this adds
    comments to always update both functions.
    
    Change-Id: I704b3ef3257dd977dac95e16e25049ff8ade97ed

diff --git a/sw/inc/doc.hxx b/sw/inc/doc.hxx
index ac31da1..ec80dd3 100644
--- a/sw/inc/doc.hxx
+++ b/sw/inc/doc.hxx
@@ -1883,7 +1883,10 @@ public:
     ::sw::MetaFieldManager & GetMetaFieldManager();
     ::sw::UndoManager      & GetUndoManager();
     ::sw::UndoManager const& GetUndoManager() const;
+
     SfxObjectShell* CreateCopy(bool bCallInitNew) const;
+    void Append( const SwDoc& rSource, int nStartPageNumber,
+                 SwPageDesc* pTargetPageDesc, int nPhysPageNumber );
 
     /**
      * Dumps the entire nodes structure to the given destination (file nodes.xml in the current directory by default)
diff --git a/sw/inc/fesh.hxx b/sw/inc/fesh.hxx
index 2660c5a..749e735 100644
--- a/sw/inc/fesh.hxx
+++ b/sw/inc/fesh.hxx
@@ -219,7 +219,7 @@ public:
 
     /// Copy and Paste methods for internal clipboard.
     bool Copy( SwDoc* pClpDoc, const OUString* pNewClpTxt = 0 );
-    bool Paste( SwDoc* pClpDoc, bool bIncludingPageFrames = false, bool bIncludeFullDocument = false);
+    bool Paste( SwDoc* pClpDoc, bool bIncludingPageFrames = false );
 
     /// Paste some pages into another doc - used in mailmerge.
     bool PastePages( SwFEShell& rToFill, sal_uInt16 nStartPage, sal_uInt16 nEndPage);
diff --git a/sw/source/core/doc/docnew.cxx b/sw/source/core/doc/docnew.cxx
index 7d586ac..b0a83b3 100644
--- a/sw/source/core/doc/docnew.cxx
+++ b/sw/source/core/doc/docnew.cxx
@@ -1003,7 +1003,8 @@ SfxObjectShell* SwDoc::CreateCopy(bool bCallInitNew ) const
     SfxObjectShell* pRetShell = new SwDocShell( pRet, SFX_CREATE_MODE_STANDARD );
     if( bCallInitNew )
     {
-        // it could happen that DoInitNew creates model, that increases the refcount of the object
+        // it could happen that DoInitNew creates model,
+        // that increases the refcount of the object
         pRetShell->DoInitNew();
     }
 
@@ -1015,30 +1016,54 @@ SfxObjectShell* SwDoc::CreateCopy(bool bCallInitNew ) const
 
     pRet->ReplaceStyles(*this);
 
-    // Based on the simplified codepath from SwFEShell::Paste()
+    pRet->Append(*this, 0, NULL, 0);
 
+    if ( bCallInitNew ) {
+        // delete leading page / initial content from target document
+        SwNodeIndex aDeleteIdx( pRet->GetNodes().GetEndOfExtras(), 2 );
+        pRet->GetNodes().Delete( aDeleteIdx, 1 );
+    }
+
+    // remove the temporary shell if it is there as it was done before
+    pRet->SetTmpDocShell( (SfxObjectShell*) NULL );
+
+    pRet->release();
+
+    return pRetShell;
+}
+
+// appends all pages of source SwDoc - based on SwFEShell::Paste( SwDoc* )
+void SwDoc::Append( const SwDoc& rSource, int nStartPageNumber,
+                    SwPageDesc* pTargetPageDesc, int nPhysPageNumber )
+{
     // GetEndOfExtras + 1 = StartOfContent
-    SwNodeIndex aSourceIdx( GetNodes().GetEndOfExtras(), 1 );
-    SwPaM aCpyPam( aSourceIdx ); // DocStart
+    SwNodeIndex aSourceIdx( rSource.GetNodes().GetEndOfExtras(), 1 );
+    SwPaM aCpyPam( aSourceIdx ); //DocStart
 
-    SwNodeIndex aTargetIdx( pRet->GetNodes().GetEndOfContent() );
-    SwPaM aInsertPam( aTargetIdx );
+    // Append at the end of document / content
+    SwNodeIndex aTargetIdx( GetNodes().GetEndOfContent() );
+    SwPaM aInsertPam( aTargetIdx ); //replaces PCURCRSR from SwFEShell::Paste()
+    aTargetIdx--;
 
     aCpyPam.SetMark();
     aCpyPam.Move( fnMoveForward, fnGoDoc );
 
-    pRet->LockExpFlds();
+    GetIDocumentUndoRedo().StartUndo( UNDO_INSGLOSSARY, NULL );
+    LockExpFlds();
 
     {
+        // **
+        // ** refer to SwFEShell::Paste, if you change the following code **
+        // **
+
         SwPosition& rInsPos = *aInsertPam.GetPoint();
-        SwPosition aInsertPosition( rInsPos );
 
         {
             SwNodeIndex aIndexBefore(rInsPos.nNode);
 
             aIndexBefore--;
 
-            CopyRange( aCpyPam, rInsPos, true );
+            rSource.CopyRange( aCpyPam, rInsPos, true );
             // Note: aCpyPam is invalid now
 
             ++aIndexBefore;
@@ -1047,37 +1072,54 @@ SfxObjectShell* SwDoc::CreateCopy(bool bCallInitNew ) const
 
             aPaM.GetDoc()->MakeUniqueNumRules(aPaM);
 
-            // No need to update the rsid, as pRet is an empty doc
+            // Update the rsid of each pasted text node
+            SwNodes &rDestNodes = GetNodes();
+            sal_uLong const nEndIdx = aPaM.End()->nNode.GetIndex();
+
+            for (sal_uLong nIdx = aPaM.Start()->nNode.GetIndex();
+                    nIdx <= nEndIdx; ++nIdx)
+            {
+                SwTxtNode *const pTxtNode = rDestNodes[nIdx]->GetTxtNode();
+                if ( pTxtNode )
+                    UpdateParRsid( pTxtNode );
+            }
+        }
+
+        // update the PageDesc pool item
+        if ( nStartPageNumber || pTargetPageDesc ) {
+            SwTxtNode *aTxtNd = dynamic_cast<  SwTxtNode* >( GetNodes().GoNext(&aTargetIdx) );
+            if ( aTxtNd ) {
+                SfxPoolItem *pNewItem = aTxtNd->GetAttr( RES_PAGEDESC ).Clone();
+                SwFmtPageDesc *aDesc = dynamic_cast< SwFmtPageDesc* >( pNewItem );
+                if ( aDesc ) {
+                    if ( nStartPageNumber )
+                        aDesc->SetNumOffset( nStartPageNumber );
+                    if ( pTargetPageDesc )
+                        aDesc->RegisterToPageDesc( *pTargetPageDesc );
+                    aTxtNd->SetAttr( *aDesc );
+                }
+                delete pNewItem;
+            }
         }
 
         // additionally copy page bound frames
-        for ( sal_uInt16 i = 0; i < GetSpzFrmFmts()->size(); ++i )
+        const SwFrmFmts *pSpzFrmFmts = rSource.GetSpzFrmFmts();
+        for ( sal_uInt16 i = 0; i < pSpzFrmFmts->size(); ++i )
         {
-            const SwFrmFmt& rCpyFmt = *(*GetSpzFrmFmts())[i];
+            const SwFrmFmt& rCpyFmt = *(*pSpzFrmFmts)[i];
             SwFmtAnchor aAnchor( rCpyFmt.GetAnchor() );
             if (FLY_AT_PAGE != aAnchor.GetAnchorId())
                 continue;
-            pRet->CopyLayoutFmt( rCpyFmt, aAnchor, true, true );
+            if ( nStartPageNumber )
+                aAnchor.SetPageNum( aAnchor.GetPageNum() + nPhysPageNumber );
+            CopyLayoutFmt( rCpyFmt, aAnchor, true, true );
         }
     }
 
-    pRet->UnlockExpFlds();
-    pRet->UpdateFlds( NULL, false );
+    GetIDocumentUndoRedo().EndUndo( UNDO_INSGLOSSARY, NULL );
 
-    // End of SwFEShell::Paste() codepath
-
-    if ( bCallInitNew ) {
-        // delete leading page / initial content from target document
-        SwNodeIndex aDeleteIdx( pRet->GetNodes().GetEndOfExtras(), 2 );
-        pRet->GetNodes().Delete( aDeleteIdx, 1 );
-    }
-
-    // remove the temporary shell if it is there as it was done before
-    pRet->SetTmpDocShell( (SfxObjectShell*)NULL );
-
-    pRet->release();
-
-    return pRetShell;
+    UnlockExpFlds();
+    UpdateFlds(NULL, false);
 }
 
 sal_uInt16 SwTxtFmtColls::GetPos(const SwTxtFmtColl* p) const
diff --git a/sw/source/core/frmedt/fecopy.cxx b/sw/source/core/frmedt/fecopy.cxx
index 628d9c1..8debb4c 100644
--- a/sw/source/core/frmedt/fecopy.cxx
+++ b/sw/source/core/frmedt/fecopy.cxx
@@ -668,13 +668,13 @@ namespace {
     typedef std::pair< PaMPtr, PositionPtr > Insertion;
 }
 
-bool SwFEShell::Paste( SwDoc* pClpDoc, bool bIncludingPageFrames, bool bIncludeFullDocument )
+bool SwFEShell::Paste( SwDoc* pClpDoc, bool bIncludingPageFrames )
 {
     SET_CURR_SHELL( this );
     OSL_ENSURE( pClpDoc, "no clipboard document"  );
     const sal_uInt16 nStartPageNumber = GetPhyPageNum();
     // then till end of the nodes array
-    SwNodeIndex aIdx( pClpDoc->GetNodes().GetEndOfExtras(), (bIncludeFullDocument) ? 1 : 2 );
+    SwNodeIndex aIdx( pClpDoc->GetNodes().GetEndOfExtras(), 2 );
     SwPaM aCpyPam( aIdx ); //DocStart
 
     // If there are table formulas in the area, then display the table first
@@ -1022,6 +1022,10 @@ bool SwFEShell::Paste( SwDoc* pClpDoc, bool bIncludingPageFrames, bool bIncludeF
                 GetDoc()->ClearBoxNumAttrs( rInsPos.nNode );
             }
 
+            // **
+            // ** Update SwDoc::Append, if you change the following code **
+            // **
+
             // find out if the clipboard document starts with a table
             bool bStartWithTable = 0 != aCpyPam.Start()->nNode.GetNode().FindTableNode();
             SwPosition aInsertPosition( rInsPos );
diff --git a/sw/source/uibase/dbui/dbmgr.cxx b/sw/source/uibase/dbui/dbmgr.cxx
index 529c3929..e8e63db 100644
--- a/sw/source/uibase/dbui/dbmgr.cxx
+++ b/sw/source/uibase/dbui/dbmgr.cxx
@@ -2760,6 +2760,10 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
         //initiate SelectShell() to create sub shells
         pTargetView->AttrChangedNotify( &pTargetView->GetWrtShell() );
         SwWrtShell* pTargetShell = pTargetView->GetWrtShellPtr();
+        SwDoc* pTargetDoc = pTargetShell->GetDoc();
+
+        pTargetView->GetDocShell()->_LoadStyles( *rSourceView.GetDocShell(), true );
+
         // #i63806#
         const SwPageDesc* pSourcePageDesc = rSourceShell.FindPageDescByName( sStartingPageDesc );
         const SwFrmFmt& rMaster = pSourcePageDesc->GetMaster();
@@ -2848,8 +2852,6 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
             {
                 //create a new pagestyle
                 //copy the pagedesc from the current document to the new document and change the name of the to-be-applied style
-
-                SwDoc* pTargetDoc = pTargetShell->GetDoc();
                 OUString sNewPageDescName = lcl_FindUniqueName(pTargetShell, sStartingPageDesc, nDocNo );
                 pTargetShell->GetDoc()->MakePageDesc( sNewPageDescName );
                 pTargetPageDesc = pTargetShell->FindPageDescByName( sNewPageDescName );
@@ -2862,65 +2864,31 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
                     lcl_CopyFollowPageDesc( *pTargetShell, *pWorkPageDesc, *pTargetPageDesc, nDocNo );
                 }
             }
-            if(nDocNo == 1 || bPageStylesWithHeaderFooter)
-                pTargetView->GetDocShell()->_LoadStyles( *rSourceView.GetDocShell(), true );
-            if(nDocNo > 1)
-                pTargetShell->InsertPageBreak( &sModifiedStartingPageDesc, nStartingPageNo );
             else
+                pTargetPageDesc = pTargetShell->FindPageDescByName( sModifiedStartingPageDesc );
+
+            if(nDocNo == 1)
                 pTargetShell->SetPageStyle(sModifiedStartingPageDesc);
 
             sal_uInt16 nPageCountBefore = pTargetShell->GetPageCnt();
             OSL_ENSURE(!pTargetShell->GetTableFmt(),"target document ends with a table - paragraph should be appended");
-            bool para_added = false;
-
-            //#i51359# add a second paragraph in case there's only one
-            {
-                SwNodeIndex aIdx( pWorkDoc->GetNodes().GetEndOfExtras(), 2 );
-                SwPosition aTestPos( aIdx );
-                SwCursor aTestCrsr( aTestPos, 0, false );
-                if ( !aTestCrsr.MovePara(fnParaNext, fnParaStart) )
-                {
-                    //append a paragraph
-                    pWorkDoc->AppendTxtNode( aTestPos );
-                    para_added = true;
-                }
-            }
 
 #ifdef DBG_UTIL
             if ( nDocNo <= MAX_DOC_DUMP )
                 lcl_SaveDoc( xWorkDocSh, "WorkDoc", nDocNo );
 #endif
 
-            SwNodeIndex fixupIdx( pTargetNodes->GetEndOfContent(), -1 );
-            pTargetShell->Paste( rWorkShell.GetDoc(), true, true );
-
-            if (bPageStylesWithHeaderFooter) {
-                // set the real page desc and update the number offset for the pasted document
-                fixupIdx += 2;
-                SwTxtNode *aTxtNd = fixupIdx.GetNode().GetTxtNode();
-                if ( aTxtNd ) {
-                    SfxPoolItem *pNewItem = aTxtNd->GetAttr( RES_PAGEDESC ).Clone();
-                    SwFmtPageDesc *aDesc = dynamic_cast< SwFmtPageDesc* >( pNewItem );
-                    if ( aDesc ) {
-                        aDesc->SetNumOffset( nStartingPageNo );
-                        aDesc->RegisterToPageDesc( *pTargetPageDesc );
-                        aTxtNd->SetAttr( *aDesc );
-                    }
-                    delete pNewItem;
-                }
+            if (nDocNo == 1 ) {
+                pTargetDoc->Append( *(rWorkShell.GetDoc()), 0, pTargetPageDesc, 0 );
 
-                // delete the leading empty page from InsertPageBreak
-                fixupIdx -= 2;
-                pTargetNodes->Delete( fixupIdx, 2 );
-            }
-
-            if ( para_added ) {
-                // Move cursor to the start or Delete will assert because
-                // of the cursors SwIndex ref on the deleting node.
-                pTargetShell->SttEndDoc( true );
-                SwNodeIndex aTargetIdx( pTargetNodes->GetEndOfContent(), -1 );
-                pTargetNodes->Delete( aTargetIdx, 1 );
+                // delete the leading empty page from the initial SwDoc
+                pTargetShell->SttEndDoc( false );
+                SwNodeIndex aDeleteIdx( pTargetNodes->GetEndOfExtras(), 2 );
+                pTargetNodes->Delete( aDeleteIdx, 1 );
             }
+            else
+                pTargetDoc->Append( *(rWorkShell.GetDoc()), nStartingPageNo,
+                                    pTargetPageDesc, pTargetShell->GetPhyPageNum() );
 
             // #i72820# calculate layout to be able to find the correct page index
             pTargetShell->CalcLayout();
commit bb586d81085cf1715055436a0a915e77f66ff462
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Mon Jun 23 09:27:27 2014 +0200

    MM: always copy the internal document
    
    There is really no need to create the first document via UNO
    createClone(), which is also slower then the internal copy.
    
    Actually createClone also calls createCopy, but without
    initializing the document.
    
    Change-Id: I23437b0f3ad663942a02be575b39883f9a3b8587

diff --git a/sw/source/uibase/dbui/dbmgr.cxx b/sw/source/uibase/dbui/dbmgr.cxx
index d73bb63..529c3929 100644
--- a/sw/source/uibase/dbui/dbmgr.cxx
+++ b/sw/source/uibase/dbui/dbmgr.cxx
@@ -1005,17 +1005,8 @@ bool SwDBManager::MergeMailFiles(SwWrtShell* pSourceShell,
                             Application::Reschedule();
 
                         // The SfxObjectShell will be closed explicitly later but it is more safe to use SfxObjectShellLock here
-                        SfxObjectShellLock xWorkDocSh;
                         // copy the source document
-                        if( 1 == nDocNo && (bAsSingleFile || rMergeDescriptor.bCreateSingleFile) )
-                        {
-                            uno::Reference< util::XCloneable > xClone( pSourceDocSh->GetModel(), uno::UNO_QUERY);
-                            uno::Reference< lang::XUnoTunnel > xWorkDocShell( xClone->createClone(), uno::UNO_QUERY);
-                            SwXTextDocument* pWorkModel = reinterpret_cast<SwXTextDocument*>(xWorkDocShell->getSomething(SwXTextDocument::getUnoTunnelId()));
-                            xWorkDocSh = pWorkModel->GetDocShell();
-                        }
-                        else
-                            xWorkDocSh = pSourceDocSh->GetDoc()->CreateCopy( true );
+                        SfxObjectShellLock xWorkDocSh = pSourceDocSh->GetDoc()->CreateCopy( true );
 
                         {
                             //create a view frame for the document
@@ -2802,18 +2793,7 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
 
             // copy the source document
             // the copy will be closed later, but it is more safe to use SfxObjectShellLock here
-            SfxObjectShellLock xWorkDocSh;
-            if(nDocNo == 1 )
-            {
-                uno::Reference< util::XCloneable > xClone( rSourceView.GetDocShell()->GetModel(), uno::UNO_QUERY);
-                uno::Reference< lang::XUnoTunnel > xWorkDocShell( xClone->createClone(), uno::UNO_QUERY);
-                SwXTextDocument* pWorkModel = reinterpret_cast<SwXTextDocument*>(xWorkDocShell->getSomething(SwXTextDocument::getUnoTunnelId()));
-                xWorkDocSh = pWorkModel->GetDocShell();
-            }
-            else
-            {
-                xWorkDocSh = rSourceView.GetDocShell()->GetDoc()->CreateCopy(true);
-            }
+            SfxObjectShellLock xWorkDocSh = rSourceView.GetDocShell()->GetDoc()->CreateCopy(true);
 #ifdef DBG_UTIL
             if ( nDocNo <= MAX_DOC_DUMP )
                 lcl_SaveDoc( xWorkDocSh, "WorkDoc", nDocNo );
commit 7bee400dcfe7029460da456c7754965a640bf453
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Fri Jun 27 14:58:24 2014 +0200

    Some minor MM code cleanups
    
    Just makes the code in SwFEShell::Paste and
    SwDBManager::MergeDocuments more readable.
    
    Change-Id: Ifd78d6a44fa78eaf1f4fca63f4bbd3ee43ca129d

diff --git a/sw/source/core/frmedt/fecopy.cxx b/sw/source/core/frmedt/fecopy.cxx
index a09f923..628d9c1 100644
--- a/sw/source/core/frmedt/fecopy.cxx
+++ b/sw/source/core/frmedt/fecopy.cxx
@@ -680,7 +680,7 @@ bool SwFEShell::Paste( SwDoc* pClpDoc, bool bIncludingPageFrames, bool bIncludeF
     // If there are table formulas in the area, then display the table first
     // so that the table formula can calculate a new value first
     // (individual boxes in the area are retrieved via the layout)
-     SwFieldType* pTblFldTyp = GetDoc()->GetSysFldType( RES_TABLEFLD );
+    SwFieldType* pTblFldTyp = GetDoc()->GetSysFldType( RES_TABLEFLD );
 
     SwTableNode *pDestNd, *pSrcNd = aCpyPam.GetNode().GetTableNode();
     if( !pSrcNd )                               // TabellenNode ?
@@ -1071,19 +1071,12 @@ bool SwFEShell::Paste( SwDoc* pClpDoc, bool bIncludingPageFrames, bool bIncludeF
 
                 for ( sal_uInt16 i = 0; i < pClpDoc->GetSpzFrmFmts()->size(); ++i )
                 {
-                    bool bInsWithFmt = true;
                     const SwFrmFmt& rCpyFmt = *(*pClpDoc->GetSpzFrmFmts())[i];
-                    if( bInsWithFmt  )
-                    {
-                        SwFmtAnchor aAnchor( rCpyFmt.GetAnchor() );
-                        if ( FLY_AT_PAGE == aAnchor.GetAnchorId() )
-                        {
-                            aAnchor.SetPageNum( aAnchor.GetPageNum() + nStartPageNumber - 1 );
-                        }
-                        else
-                            continue;
-                        GetDoc()->CopyLayoutFmt( rCpyFmt, aAnchor, true, true );
-                    }
+                    SwFmtAnchor aAnchor( rCpyFmt.GetAnchor() );
+                    if ( FLY_AT_PAGE != aAnchor.GetAnchorId() )
+                        continue;
+                    aAnchor.SetPageNum( aAnchor.GetPageNum() + nStartPageNumber - 1 );
+                    GetDoc()->CopyLayoutFmt( rCpyFmt, aAnchor, true, true );
                 }
             }
         }
diff --git a/sw/source/uibase/dbui/dbmgr.cxx b/sw/source/uibase/dbui/dbmgr.cxx
index ef8d4df..d73bb63 100644
--- a/sw/source/uibase/dbui/dbmgr.cxx
+++ b/sw/source/uibase/dbui/dbmgr.cxx
@@ -2883,17 +2883,12 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
                 }
             }
             if(nDocNo == 1 || bPageStylesWithHeaderFooter)
-            {
                 pTargetView->GetDocShell()->_LoadStyles( *rSourceView.GetDocShell(), true );
-            }
             if(nDocNo > 1)
-            {
                 pTargetShell->InsertPageBreak( &sModifiedStartingPageDesc, nStartingPageNo );
-            }
             else
-            {
                 pTargetShell->SetPageStyle(sModifiedStartingPageDesc);
-            }
+
             sal_uInt16 nPageCountBefore = pTargetShell->GetPageCnt();
             OSL_ENSURE(!pTargetShell->GetTableFmt(),"target document ends with a table - paragraph should be appended");
             bool para_added = false;
@@ -2901,9 +2896,9 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
             //#i51359# add a second paragraph in case there's only one
             {
                 SwNodeIndex aIdx( pWorkDoc->GetNodes().GetEndOfExtras(), 2 );
-              SwPosition aTestPos( aIdx );
-              SwCursor aTestCrsr(aTestPos,0,false);
-                if(!aTestCrsr.MovePara(fnParaNext, fnParaStart))
+                SwPosition aTestPos( aIdx );
+                SwCursor aTestCrsr( aTestPos, 0, false );
+                if ( !aTestCrsr.MovePara(fnParaNext, fnParaStart) )
                 {
                     //append a paragraph
                     pWorkDoc->AppendTxtNode( aTestPos );
@@ -2955,7 +2950,7 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
                 lcl_SaveDoc( xTargetDocShell, "MergeDoc" );
 #endif
 
-            //add the document info to the config item
+            // add the document info to the config item
             SwDocMergeInfo aMergeInfo;
             aMergeInfo.nStartPageInTarget = nPageCountBefore;
             aMergeInfo.nEndPageInTarget = pTargetShell->GetPageCnt();
@@ -2967,17 +2962,17 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
             for( sal_uInt16 i = 0; i < 25; i++)
                 Application::Reschedule();
 
-            //restore the ole DBManager
+            // restore the old DBManager
             pWorkDoc->SetDBManager( pWorkDBManager );
-            //now the temporary document should be closed
-            SfxObjectShellRef xDocSh(pWorkView->GetDocShell());
-            xDocSh->DoClose();
+            // close the temporary document
+            xWorkDocSh->DoClose();
+
             nEndRow = pImpl->pMergeData->xResultSet->getRow();
             ++nDocNo;
         } while( !bCancel &&
                 (bSynchronizedDoc && (nStartRow != nEndRow)? ExistsNextRecord() : ToNextMergeRecord()));
 
-        //deselect all, go out of the frame and go to the beginning of the document
+        // deselect all, go out of the frame and go to the beginning of the document
         Point aPt(LONG_MIN, LONG_MIN);
         pTargetShell->SelectObj(aPt, SW_LEAVE_FRAME);
         if (pTargetShell->IsSelFrmMode())
commit dbc637c0ccf38ef4e725e13a7b30c96d297c14b4
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Fri Jun 27 11:46:00 2014 +0200

    MM: fix lost or broken paragraph anchored objects
    
    With the extended SwFEShell::Paste version, we can finally paste
    full documents without losing the paragraph anchored Flys of the
    first paragraph.
    
    Actually one should be able to drop the InsertPageBreak and the
    single paragraph delete, but my attempt resulted in problems with
    page anchored Flys and somehow reintroduced the problem seen in
    fdo#80395 with draw objects.
    
    Change-Id: I370fa89f432ba4dd95c1f02605f33f04dfbaad85

diff --git a/sw/source/uibase/dbui/dbmgr.cxx b/sw/source/uibase/dbui/dbmgr.cxx
index 646a0a6..ef8d4df 100644
--- a/sw/source/uibase/dbui/dbmgr.cxx
+++ b/sw/source/uibase/dbui/dbmgr.cxx
@@ -125,6 +125,8 @@
 #include <unomid.h>
 #include <section.hxx>
 #include <rootfrm.hxx>
+#include <fmtpdsc.hxx>
+#include <ndtxt.hxx>
 
 #include <boost/scoped_ptr.hpp>
 
@@ -2772,6 +2774,7 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
         const SwFrmFmt& rMaster = pSourcePageDesc->GetMaster();
         bool bPageStylesWithHeaderFooter = rMaster.GetHeader().IsActive()  ||
                                         rMaster.GetFooter().IsActive();
+        SwNodes *pTargetNodes = &pTargetShell->GetDoc()->GetNodes();
 
         // copy compatibility options
         lcl_CopyCompatibilityOptions( rSourceShell, *pTargetShell);
@@ -2860,6 +2863,7 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
 
             //#i63806# put the styles to the target document
             //if the source uses headers or footers each new copy need to copy a new page styles
+            SwPageDesc* pTargetPageDesc = NULL;
             if(bPageStylesWithHeaderFooter)
             {
                 //create a new pagestyle
@@ -2868,7 +2872,7 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
                 SwDoc* pTargetDoc = pTargetShell->GetDoc();
                 OUString sNewPageDescName = lcl_FindUniqueName(pTargetShell, sStartingPageDesc, nDocNo );
                 pTargetShell->GetDoc()->MakePageDesc( sNewPageDescName );
-                SwPageDesc* pTargetPageDesc = pTargetShell->FindPageDescByName( sNewPageDescName );
+                pTargetPageDesc = pTargetShell->FindPageDescByName( sNewPageDescName );
                 const SwPageDesc* pWorkPageDesc = rWorkShell.FindPageDescByName( sStartingPageDesc );
 
                 if(pWorkPageDesc && pTargetPageDesc)
@@ -2911,7 +2915,29 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
             if ( nDocNo <= MAX_DOC_DUMP )
                 lcl_SaveDoc( xWorkDocSh, "WorkDoc", nDocNo );
 #endif
-            pTargetShell->Paste( rWorkShell.GetDoc(), true );
+
+            SwNodeIndex fixupIdx( pTargetNodes->GetEndOfContent(), -1 );
+            pTargetShell->Paste( rWorkShell.GetDoc(), true, true );
+
+            if (bPageStylesWithHeaderFooter) {
+                // set the real page desc and update the number offset for the pasted document
+                fixupIdx += 2;
+                SwTxtNode *aTxtNd = fixupIdx.GetNode().GetTxtNode();
+                if ( aTxtNd ) {
+                    SfxPoolItem *pNewItem = aTxtNd->GetAttr( RES_PAGEDESC ).Clone();
+                    SwFmtPageDesc *aDesc = dynamic_cast< SwFmtPageDesc* >( pNewItem );
+                    if ( aDesc ) {
+                        aDesc->SetNumOffset( nStartingPageNo );
+                        aDesc->RegisterToPageDesc( *pTargetPageDesc );
+                        aTxtNd->SetAttr( *aDesc );
+                    }
+                    delete pNewItem;
+                }
+
+                // delete the leading empty page from InsertPageBreak
+                fixupIdx -= 2;
+                pTargetNodes->Delete( fixupIdx, 2 );
+            }
 
             if ( para_added ) {
                 // Move cursor to the start or Delete will assert because
@@ -2921,12 +2947,9 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
                 pTargetNodes->Delete( aTargetIdx, 1 );
             }
 
-            //convert fields in page styles (header/footer - has to be done after the first document has been pasted
-            if(1 == nDocNo)
-            {
-                pTargetShell->CalcLayout();
-                pTargetShell->ConvertFieldsToText();
-            }
+            // #i72820# calculate layout to be able to find the correct page index
+            pTargetShell->CalcLayout();
+
 #ifdef DBG_UTIL
             if ( nDocNo <= MAX_DOC_DUMP )
                 lcl_SaveDoc( xTargetDocShell, "MergeDoc" );
@@ -2935,8 +2958,6 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
             //add the document info to the config item
             SwDocMergeInfo aMergeInfo;
             aMergeInfo.nStartPageInTarget = nPageCountBefore;
-            //#i72820# calculate layout to be able to find the correct page index
-            pTargetShell->CalcLayout();
             aMergeInfo.nEndPageInTarget = pTargetShell->GetPageCnt();
             aMergeInfo.nDBRow = nStartRow;
             rMMConfig.AddMergedDocument( aMergeInfo );
commit 2a76b8ddc5e333613516cd5555cf13bee1a41758
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Fri Jun 27 11:28:02 2014 +0200

    MM: fix workaround for single paragraph docs
    
    There is already a workaround for pasting a document with a single
    paragraph by appending a dummy empty paragraph to the working copy.
    
    This patch removes the dummy paragraph from the target document.
    
    Change-Id: I288d35264bf6f1a5f92c50d6a309e3bdd4ab5836

diff --git a/sw/source/uibase/dbui/dbmgr.cxx b/sw/source/uibase/dbui/dbmgr.cxx
index 0ed706f..646a0a6 100644
--- a/sw/source/uibase/dbui/dbmgr.cxx
+++ b/sw/source/uibase/dbui/dbmgr.cxx
@@ -2892,6 +2892,8 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
             }
             sal_uInt16 nPageCountBefore = pTargetShell->GetPageCnt();
             OSL_ENSURE(!pTargetShell->GetTableFmt(),"target document ends with a table - paragraph should be appended");
+            bool para_added = false;
+
             //#i51359# add a second paragraph in case there's only one
             {
                 SwNodeIndex aIdx( pWorkDoc->GetNodes().GetEndOfExtras(), 2 );
@@ -2901,6 +2903,7 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
                 {
                     //append a paragraph
                     pWorkDoc->AppendTxtNode( aTestPos );
+                    para_added = true;
                 }
             }
 
@@ -2909,6 +2912,15 @@ sal_Int32 SwDBManager::MergeDocuments( SwMailMergeConfigItem& rMMConfig,
                 lcl_SaveDoc( xWorkDocSh, "WorkDoc", nDocNo );
 #endif
             pTargetShell->Paste( rWorkShell.GetDoc(), true );
+
+            if ( para_added ) {
+                // Move cursor to the start or Delete will assert because
+                // of the cursors SwIndex ref on the deleting node.
+                pTargetShell->SttEndDoc( true );
+                SwNodeIndex aTargetIdx( pTargetNodes->GetEndOfContent(), -1 );
+                pTargetNodes->Delete( aTargetIdx, 1 );
+            }
+
             //convert fields in page styles (header/footer - has to be done after the first document has been pasted
             if(1 == nDocNo)
             {
commit 5520b3884b8f3590259ca427e387421f242c48a3
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Fri Jun 27 11:21:47 2014 +0200

    Optionally paste the full document
    
    In the mail merge case we want to paste the full document including
    the SwTxtNode containing the SwFmtPageDesc node, which is always
    the first node of a document.
    
    For normal paste we want to merge the first paragraph into the
    paragraph at the cursor position. This currently loses all Flys
    anchored at the first paragraph.
    
    Change-Id: I2b1ce279743f559e700b47276012ad56d74a059c

diff --git a/sw/inc/fesh.hxx b/sw/inc/fesh.hxx
index 9c2e89d..2660c5a 100644
--- a/sw/inc/fesh.hxx
+++ b/sw/inc/fesh.hxx
@@ -219,7 +219,7 @@ public:
 
     /// Copy and Paste methods for internal clipboard.
     bool Copy( SwDoc* pClpDoc, const OUString* pNewClpTxt = 0 );
-    bool Paste( SwDoc* pClpDoc, bool bIncludingPageFrames = false);
+    bool Paste( SwDoc* pClpDoc, bool bIncludingPageFrames = false, bool bIncludeFullDocument = false);
 
     /// Paste some pages into another doc - used in mailmerge.
     bool PastePages( SwFEShell& rToFill, sal_uInt16 nStartPage, sal_uInt16 nEndPage);
diff --git a/sw/source/core/frmedt/fecopy.cxx b/sw/source/core/frmedt/fecopy.cxx
index c980082..a09f923 100644
--- a/sw/source/core/frmedt/fecopy.cxx
+++ b/sw/source/core/frmedt/fecopy.cxx
@@ -668,13 +668,13 @@ namespace {
     typedef std::pair< PaMPtr, PositionPtr > Insertion;
 }
 
-bool SwFEShell::Paste( SwDoc* pClpDoc, bool bIncludingPageFrames )
+bool SwFEShell::Paste( SwDoc* pClpDoc, bool bIncludingPageFrames, bool bIncludeFullDocument )
 {
     SET_CURR_SHELL( this );
     OSL_ENSURE( pClpDoc, "no clipboard document"  );
     const sal_uInt16 nStartPageNumber = GetPhyPageNum();
     // then till end of the nodes array
-    SwNodeIndex aIdx( pClpDoc->GetNodes().GetEndOfExtras(), 2 );
+    SwNodeIndex aIdx( pClpDoc->GetNodes().GetEndOfExtras(), (bIncludeFullDocument) ? 1 : 2 );
     SwPaM aCpyPam( aIdx ); //DocStart
 
     // If there are table formulas in the area, then display the table first
commit 6286b693af1d06a27ed14133c0f58b3a107c4a87
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Mon Jun 23 09:16:18 2014 +0200

    Replace the whole content for copied documents
    
    If the document is initialized in CreateCopy, it already contains
    the initial empty paragraph. So we have to delete the content from
    initial document, as we're going to replace the whole content with
    the pasted document.
    
    Change-Id: I33faed4de77919fb926d408e19af9c1ec3b0f7d3

diff --git a/sw/source/core/doc/docnew.cxx b/sw/source/core/doc/docnew.cxx
index cea0032..7d586ac 100644
--- a/sw/source/core/doc/docnew.cxx
+++ b/sw/source/core/doc/docnew.cxx
@@ -1018,10 +1018,10 @@ SfxObjectShell* SwDoc::CreateCopy(bool bCallInitNew ) const
     // Based on the simplified codepath from SwFEShell::Paste()
 
     // GetEndOfExtras + 1 = StartOfContent
-    SwNodeIndex aSourceIdx( GetNodes().GetEndOfExtras(), 2 );
+    SwNodeIndex aSourceIdx( GetNodes().GetEndOfExtras(), 1 );
     SwPaM aCpyPam( aSourceIdx ); // DocStart
 
-    SwNodeIndex aTargetIdx( pRet->GetNodes(), 2 );
+    SwNodeIndex aTargetIdx( pRet->GetNodes().GetEndOfContent() );
     SwPaM aInsertPam( aTargetIdx );
 
     aCpyPam.SetMark();
@@ -1066,6 +1066,12 @@ SfxObjectShell* SwDoc::CreateCopy(bool bCallInitNew ) const
 
     // End of SwFEShell::Paste() codepath
 
+    if ( bCallInitNew ) {
+        // delete leading page / initial content from target document
+        SwNodeIndex aDeleteIdx( pRet->GetNodes().GetEndOfExtras(), 2 );
+        pRet->GetNodes().Delete( aDeleteIdx, 1 );
+    }
+
     // remove the temporary shell if it is there as it was done before
     pRet->SetTmpDocShell( (SfxObjectShell*)NULL );
 
commit 41ffef22ca03c348f5f72d9fb2c9d9971ef5f84a
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Thu Jun 26 20:23:39 2014 +0200

    Merge SwDoc::Paste into SwDoc::CreateCopy
    
    Change-Id: I95686eb116e17b4da6662b4fbadcf08a0b92a6f4

diff --git a/sw/inc/doc.hxx b/sw/inc/doc.hxx
index 2f84c0d..ac31da1 100644
--- a/sw/inc/doc.hxx
+++ b/sw/inc/doc.hxx
@@ -531,7 +531,6 @@ private:
     OUString msDocAccTitle;
 
     void InitTOXTypes();
-    void Paste( const SwDoc& );
     bool DeleteAndJoinImpl(SwPaM&, const bool);
     bool DeleteAndJoinWithRedlineImpl(SwPaM&, const bool unused = false);
     bool DeleteRangeImpl(SwPaM&, const bool unused = false);
diff --git a/sw/source/core/doc/docnew.cxx b/sw/source/core/doc/docnew.cxx
index 9ebd797..cea0032 100644
--- a/sw/source/core/doc/docnew.cxx
+++ b/sw/source/core/doc/docnew.cxx
@@ -1015,37 +1015,22 @@ SfxObjectShell* SwDoc::CreateCopy(bool bCallInitNew ) const
 
     pRet->ReplaceStyles(*this);
 
-    // copy content
-    pRet->Paste( *this );
+    // Based on the simplified codepath from SwFEShell::Paste()
 
-    // remove the temporary shell if it is there as it was done before
-    pRet->SetTmpDocShell( (SfxObjectShell*)NULL );
-
-    pRet->release();
-
-    return pRetShell;
-}
+    // GetEndOfExtras + 1 = StartOfContent
+    SwNodeIndex aSourceIdx( GetNodes().GetEndOfExtras(), 2 );
+    SwPaM aCpyPam( aSourceIdx ); // DocStart
 
-// copy document content - code from SwFEShell::Paste( SwDoc* )
-void SwDoc::Paste( const SwDoc& rSource )
-{
-    // this has to be empty const sal_uInt16 nStartPageNumber = GetPhyPageNum();
-    // until the end of the NodesArray
-    SwNodeIndex aSourceIdx( rSource.GetNodes().GetEndOfExtras(), 2 );
-    SwPaM aCpyPam( aSourceIdx ); //DocStart
-    SwNodeIndex aTargetIdx( GetNodes().GetEndOfExtras(), 2 );
-    SwPaM aInsertPam( aTargetIdx ); //replaces PCURCRSR from SwFEShell::Paste()
+    SwNodeIndex aTargetIdx( pRet->GetNodes(), 2 );
+    SwPaM aInsertPam( aTargetIdx );
 
     aCpyPam.SetMark();
     aCpyPam.Move( fnMoveForward, fnGoDoc );
 
-    this->GetIDocumentUndoRedo().StartUndo( UNDO_INSGLOSSARY, NULL );
-    this->LockExpFlds();
+    pRet->LockExpFlds();
 
     {
         SwPosition& rInsPos = *aInsertPam.GetPoint();
-        //find out if the clipboard document starts with a table
-        bool bStartWithTable = 0 != aCpyPam.Start()->nNode.GetNode().FindTableNode();
         SwPosition aInsertPosition( rInsPos );
 
         {
@@ -1053,7 +1038,7 @@ void SwDoc::Paste( const SwDoc& rSource )
 
             aIndexBefore--;
 
-            rSource.CopyRange( aCpyPam, rInsPos, true );
+            CopyRange( aCpyPam, rInsPos, true );
             // Note: aCpyPam is invalid now
 
             ++aIndexBefore;
@@ -1062,38 +1047,31 @@ void SwDoc::Paste( const SwDoc& rSource )
 
             aPaM.GetDoc()->MakeUniqueNumRules(aPaM);
 
-            // No need to update the rsid, as this is an empty doc
+            // No need to update the rsid, as pRet is an empty doc
         }
 
-        //TODO: Is this necessary here? SaveTblBoxCntnt( &rInsPos );
-        if(/*bIncludingPageFrames && */bStartWithTable)
+        // additionally copy page bound frames
+        for ( sal_uInt16 i = 0; i < GetSpzFrmFmts()->size(); ++i )
         {
-            //remove the paragraph in front of the table
-            SwPaM aPara(aInsertPosition);
-            this->DelFullPara(aPara);
-        }
-        //additionally copy page bound frames
-        if( /*bIncludingPageFrames && */rSource.GetSpzFrmFmts()->size() )
-        {
-            for ( sal_uInt16 i = 0; i < rSource.GetSpzFrmFmts()->size(); ++i )
-            {
-                const SwFrmFmt& rCpyFmt = *(*rSource.GetSpzFrmFmts())[i];
-                    SwFmtAnchor aAnchor( rCpyFmt.GetAnchor() );
-                    if (FLY_AT_PAGE == aAnchor.GetAnchorId())
-                    {
-                        aAnchor.SetPageNum( aAnchor.GetPageNum() /*+ nStartPageNumber - */);
-                    }
-                    else
-                        continue;
-                    this->CopyLayoutFmt( rCpyFmt, aAnchor, true, true );
-            }
+            const SwFrmFmt& rCpyFmt = *(*GetSpzFrmFmts())[i];
+            SwFmtAnchor aAnchor( rCpyFmt.GetAnchor() );
+            if (FLY_AT_PAGE != aAnchor.GetAnchorId())
+                continue;
+            pRet->CopyLayoutFmt( rCpyFmt, aAnchor, true, true );
         }
     }
 
-    this->GetIDocumentUndoRedo().EndUndo( UNDO_INSGLOSSARY, NULL );
+    pRet->UnlockExpFlds();
+    pRet->UpdateFlds( NULL, false );
+
+    // End of SwFEShell::Paste() codepath
 
-    UnlockExpFlds();
-    UpdateFlds(NULL, false);
+    // remove the temporary shell if it is there as it was done before
+    pRet->SetTmpDocShell( (SfxObjectShell*)NULL );
+
+    pRet->release();
+
+    return pRetShell;
 }
 
 sal_uInt16 SwTxtFmtColls::GetPos(const SwTxtFmtColl* p) const
commit 12a76277aed05f55e6dc3110c5b8a0e500c6f49f
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Fri Jun 13 14:44:37 2014 +0200

    Revert "fdo#66145: do not check IsFirstShared() in SwPageDesc::GetLeftFmt()"
    
    This reverts commit 4df438c9a9d5e698c47c1e85903eb81880a5e6fa.
    
    Change-Id: I8f8d32c07f8706fad6c62fba2a9a373feed6cbed

diff --git a/sw/source/core/layout/pagedesc.cxx b/sw/source/core/layout/pagedesc.cxx
index e7641f2..42c7cc4 100644
--- a/sw/source/core/layout/pagedesc.cxx
+++ b/sw/source/core/layout/pagedesc.cxx
@@ -305,14 +305,14 @@ bool SwPageDesc::IsFollowNextPageOfNode( const SwNode& rNd ) const
 SwFrmFmt *SwPageDesc::GetLeftFmt(bool const bFirst)
 {
     return (nsUseOnPage::PD_LEFT & eUse)
-            ? ((bFirst) ? &m_FirstLeft : &aLeft)
+            ? ((bFirst && !IsFirstShared()) ? &m_FirstLeft : &aLeft)
             : 0;
 }
 
 SwFrmFmt *SwPageDesc::GetRightFmt(bool const bFirst)
 {
     return (nsUseOnPage::PD_RIGHT & eUse)
-            ? ((bFirst) ? &m_FirstMaster : &aMaster)
+            ? ((bFirst && !IsFirstShared()) ? &m_FirstMaster : &aMaster)
             : 0;
 }
 
commit dbf99dfb980f772250e8ec4792c1bf5a1458629b
Author: Stephan Bergmann <sbergman at redhat.com>
Date:   Wed Jul 2 08:42:58 2014 +0200

    mysqlc: sal_Bool -> bool
    
    Change-Id: Ie479e1671b03fbb958886d4c01ecff41b2ad1d23

diff --git a/mysqlc/source/mysqlc_connection.cxx b/mysqlc/source/mysqlc_connection.cxx
index f8274f4..9773703 100644
--- a/mysqlc/source/mysqlc_connection.cxx
+++ b/mysqlc/source/mysqlc_connection.cxx
@@ -67,9 +67,9 @@ OConnection::OConnection(MysqlCDriver& _rDriver, sql::Driver * _cppDriver)
     ,m_xMetaData(NULL)
     ,m_rDriver(_rDriver)
     ,cppDriver(_cppDriver)
-    ,m_bClosed(sal_False)
-    ,m_bUseCatalog(sal_False)
-    ,m_bUseOldDateFormat(sal_False)
+    ,m_bClosed(false)
+    ,m_bUseCatalog(false)
+    ,m_bUseOldDateFormat(false)
 {
     OSL_TRACE("OConnection::OConnection");
     m_rDriver.acquire();
@@ -106,7 +106,7 @@ void OConnection::construct(const OUString& url, const Sequence< PropertyValue >
     MutexGuard aGuard(m_aMutex);
 
     sal_Int32 nIndex;
-    sal_Bool  bEmbedded = sal_False;
+    bool  bEmbedded = false;
     OUString token;
     OUString aHostName("localhost");
     sal_Int32 nPort = 3306;

... etc. - the rest is truncated


More information about the Libreoffice-commits mailing list