sw/qa/extras/ww8export/data/clearing-break.doc |binary
 sw/qa/extras/ww8export/ww8export3.cxx          |   26 ++++++++++++++++
 sw/source/filter/ww8/ww8par.hxx                |    4 ++
 sw/source/filter/ww8/ww8par6.cxx               |   40 +++++++++++++++++++++++++
 4 files changed, 70 insertions(+)

New commits:
commit 31ac4edf2ec83c9f6ec475ad74e5fd94a0c8b1ca
Author:     Miklos Vajna <vmik...@collabora.com>
AuthorDate: Thu Mar 17 10:15:11 2022 +0100
Commit:     Miklos Vajna <vmik...@collabora.com>
CommitDate: Thu Mar 17 10:58:20 2022 +0100

    sw clearing breaks: add DOC import
    
    Map sprmCLbcCRJ's LBCOperand to SwLineBreakClear.
    
    Change-Id: Ie6a114bcd90a9442295815da68f6b0a9616c3210
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/131697
    Reviewed-by: Miklos Vajna <vmik...@collabora.com>
    Tested-by: Jenkins

diff --git a/sw/qa/extras/ww8export/data/clearing-break.doc 
b/sw/qa/extras/ww8export/data/clearing-break.doc
new file mode 100644
index 000000000000..87b51128db3f
Binary files /dev/null and b/sw/qa/extras/ww8export/data/clearing-break.doc 
differ
diff --git a/sw/qa/extras/ww8export/ww8export3.cxx 
b/sw/qa/extras/ww8export/ww8export3.cxx
index feb759312d15..e0eb32ee9f1b 100644
--- a/sw/qa/extras/ww8export/ww8export3.cxx
+++ b/sw/qa/extras/ww8export/ww8export3.cxx
@@ -995,6 +995,32 @@ DECLARE_WW8EXPORT_TEST(testTdf79186_noLayoutInCell, 
"tdf79186_noLayoutInCell.odt
     CPPUNIT_ASSERT(!getProperty<bool>(getShape(1), "IsFollowingTextFlow"));
 }
 
+CPPUNIT_TEST_FIXTURE(Test, testClearingBreak)
+{
+    // Given a document with a clearing break:
+    // When loading that file:
+    load(mpTestDocumentPath, "clearing-break.doc");
+
+    // Then make sure that the clear property of the break is not ignored:
+    uno::Reference<container::XEnumerationAccess> xParagraph(getParagraph(1), 
uno::UNO_QUERY);
+    uno::Reference<container::XEnumeration> xPortions = 
xParagraph->createEnumeration();
+    xPortions->nextElement();
+    xPortions->nextElement();
+    // Without the accompanying fix in place, this test would have failed with:
+    // An uncaught exception of type 
com.sun.star.container.NoSuchElementException
+    // i.e. the first para was just a fly + text portion, the clearing break 
was lost.
+    uno::Reference<beans::XPropertySet> xPortion(xPortions->nextElement(), 
uno::UNO_QUERY);
+    OUString aPortionType;
+    xPortion->getPropertyValue("TextPortionType") >>= aPortionType;
+    CPPUNIT_ASSERT_EQUAL(OUString("LineBreak"), aPortionType);
+    uno::Reference<text::XTextContent> xLineBreak;
+    xPortion->getPropertyValue("LineBreak") >>= xLineBreak;
+    sal_Int16 eClear{};
+    uno::Reference<beans::XPropertySet> xLineBreakProps(xLineBreak, 
uno::UNO_QUERY);
+    xLineBreakProps->getPropertyValue("Clear") >>= eClear;
+    // SwLineBreakClear::ALL
+    CPPUNIT_ASSERT_EQUAL(static_cast<sal_Int16>(3), eClear);
+}
 
 CPPUNIT_PLUGIN_IMPLEMENT();
 
diff --git a/sw/source/filter/ww8/ww8par.hxx b/sw/source/filter/ww8/ww8par.hxx
index 204a4de3efac..46198b105021 100644
--- a/sw/source/filter/ww8/ww8par.hxx
+++ b/sw/source/filter/ww8/ww8par.hxx
@@ -108,6 +108,7 @@ class GDIMetaFile;
 struct ESelection;
 class SfxItemSet;
 class OutlinerParaObject;
+enum class SwLineBreakClear;
 
 namespace com::sun::star{
     namespace beans{ class XPropertySet;}
@@ -1174,6 +1175,8 @@ private:
     */
     std::deque<FootnoteDescriptor> m_aFootnoteStack;
 
+    std::optional<SwLineBreakClear> m_oLineBreakClear;
+
     /*
     A queue of the ms sections in the document
     */
@@ -1775,6 +1778,7 @@ public:     // really private, but can only be done public
     void Read_ParaAutoBefore(sal_uInt16 , const sal_uInt8 *pData, short nLen);
     void Read_ParaAutoAfter(sal_uInt16 , const sal_uInt8 *pData, short nLen);
     void Read_ParaContextualSpacing( sal_uInt16 nId, const sal_uInt8* pData, 
short nLen );
+    void Read_LineBreakClear(sal_uInt16 nId, const sal_uInt8* pData, short 
nLen);
     void Read_LineSpace(        sal_uInt16, const sal_uInt8*, short nLen );
 
     void SetRelativeJustify( bool bRel );
diff --git a/sw/source/filter/ww8/ww8par6.cxx b/sw/source/filter/ww8/ww8par6.cxx
index 7f47d529656d..2352dfd1c12e 100644
--- a/sw/source/filter/ww8/ww8par6.cxx
+++ b/sw/source/filter/ww8/ww8par6.cxx
@@ -99,6 +99,7 @@
 #include "ww8graf.hxx"
 
 #include <fmtwrapinfluenceonobjpos.hxx>
+#include <textlinebreak.hxx>
 
 using namespace sw::util;
 using namespace sw::types;
@@ -4541,6 +4542,44 @@ void SwWW8ImplReader::Read_ParaContextualSpacing( 
sal_uInt16, const sal_uInt8* p
     NewAttr( aUL );
 }
 
+void SwWW8ImplReader::Read_LineBreakClear(sal_uInt16 /*nId*/, const sal_uInt8* 
pData, short nLen)
+{
+    if (nLen == -1 && m_oLineBreakClear.has_value())
+    {
+        SwTextNode* pText = m_pPaM->GetNode().GetTextNode();
+        sal_Int32 nPos = m_pPaM->GetPoint()->nContent.GetIndex();
+        if (!pText || !nPos)
+        {
+            // There should have been a linebreak char.
+            return;
+        }
+
+        // Replace the linebreak char with a clearing break.
+        --nPos;
+        m_pPaM->SetMark();
+        --m_pPaM->GetMark()->nContent;
+        m_rDoc.getIDocumentContentOperations().DeleteRange(*m_pPaM);
+        m_pPaM->DeleteMark();
+        SwFormatLineBreak aLineBreak(*m_oLineBreakClear);
+        m_oLineBreakClear.reset();
+        pText->InsertItem(aLineBreak, nPos, nPos);
+    }
+
+    if (nLen < 1)
+    {
+        return;
+    }
+
+    sal_uInt8 nClear = pData[0];
+    if (nClear > 3)
+    {
+        return;
+    }
+
+    auto eClear = static_cast<SwLineBreakClear>(nClear);
+    m_oLineBreakClear = eClear;
+}
+
 void SwWW8ImplReader::Read_IdctHint( sal_uInt16, const sal_uInt8* pData, short 
nLen )
 {
     // sprmcidcthint (opcode 0x286f) specifies a script bias for the text in 
the run.
@@ -6104,6 +6143,7 @@ static const wwSprmDispatcher *GetWW8SprmDispatcher()
         {NS_sprm::PFDyaBeforeAuto::val,   
&SwWW8ImplReader::Read_ParaAutoBefore},
         {NS_sprm::PFDyaAfterAuto::val,    
&SwWW8ImplReader::Read_ParaAutoAfter},
         {NS_sprm::PFContextualSpacing::val, 
&SwWW8ImplReader::Read_ParaContextualSpacing},
+        {NS_sprm::CLbcCRJ::val, &SwWW8ImplReader::Read_LineBreakClear},
     };
 
     static wwSprmDispatcher aSprmSrch(aSprms, SAL_N_ELEMENTS(aSprms));

Reply via email to