editeng/source/items/frmitems.cxx              |   12 ----
 include/editeng/boxitem.hxx                    |    2 
 sw/CppunitTest_sw_filter_ww8.mk                |   75 +++++++++++++++++++++++++
 sw/Module_sw.mk                                |    1 
 sw/qa/filter/ww8/data/negative-page-border.doc |binary
 sw/qa/filter/ww8/ww8.cxx                       |   55 ++++++++++++++++++
 writerfilter/source/dmapper/PropertyMap.cxx    |    2 
 7 files changed, 135 insertions(+), 12 deletions(-)

New commits:
commit 51942eafdb4439559b6d59f3becd4afab45277f0
Author:     Miklos Vajna <vmik...@collabora.com>
AuthorDate: Wed Jun 8 09:08:27 2022 +0200
Commit:     Miklos Vajna <vmik...@collabora.com>
CommitDate: Wed Jun 8 12:07:48 2022 +0200

    DOC import: allow negative page border distances
    
    In case the margin (distance between body frame and page frame) is
    smaller than the border spacing (distance between border and page
    frame), then we can map that to a negative border distance during the
    import of DOCX files since commit
    1f127a2b9e1c1daab0972f98fc8708ecb7afa299 (sw layout: allow negative page
    border distances, 2022-06-07), but DOC import had the same problem.
    
    The above commit intentionally kept the default behavior of
    BorderDistanceFromWord() unchanged to avoid side effects in other
    clients of that function (not DOCX import), but means that DOC import
    was still broken.
    
    Given that it turns out there are only 2 callers of
    BorderDistanceFromWord(), fix the problem by allowing negative border
    distances unconditionally: this simplifies code & SetBorderDistance() in
    the DOC import will now get the correct border distance out of the box.
    
    DOC export works out of the box without any additional work.
    
    Change-Id: I6bf15b3c73823c9265218b7b3a7b869e131818db
    Reviewed-on: https://gerrit.libreoffice.org/c/core/+/135484
    Tested-by: Jenkins
    Reviewed-by: Miklos Vajna <vmik...@collabora.com>

diff --git a/editeng/source/items/frmitems.cxx 
b/editeng/source/items/frmitems.cxx
index 9780af4904c0..c1b9e66de5a7 100644
--- a/editeng/source/items/frmitems.cxx
+++ b/editeng/source/items/frmitems.cxx
@@ -2452,7 +2452,7 @@ namespace editeng
 {
 
 void BorderDistanceFromWord(bool bFromEdge, sal_Int32& nMargin, sal_Int32& 
nBorderDistance,
-    sal_Int32 nBorderWidth, bool bAllowNegativeBorderDistance)
+    sal_Int32 nBorderWidth)
 {
     // See 
https://wiki.openoffice.org/wiki/Writer/MSInteroperability/PageBorder
 
@@ -2479,15 +2479,7 @@ void BorderDistanceFromWord(bool bFromEdge, sal_Int32& 
nMargin, sal_Int32& nBord
     }
     else if (nNewBorderDistance < 0)
     {
-        if (bAllowNegativeBorderDistance)
-        {
-            nNewMargin = nMargin;
-        }
-        else
-        {
-            nNewMargin = std::max<sal_Int32>(nMargin - nBorderWidth, 0);
-            nNewBorderDistance = 0;
-        }
+        nNewMargin = nMargin;
     }
 
     nMargin = nNewMargin;
diff --git a/include/editeng/boxitem.hxx b/include/editeng/boxitem.hxx
index 750993c91f7d..786821c02ff0 100644
--- a/include/editeng/boxitem.hxx
+++ b/include/editeng/boxitem.hxx
@@ -241,7 +241,7 @@ namespace editeng
 {
 
 void EDITENG_DLLPUBLIC BorderDistanceFromWord(bool bFromEdge, sal_Int32& 
nMargin,
-    sal_Int32& nBorderDistance, sal_Int32 nBorderWidth, bool 
bAllowNegativeBorderDistance = false);
+    sal_Int32& nBorderDistance, sal_Int32 nBorderWidth);
 
 struct EDITENG_DLLPUBLIC WordPageMargins final
 {
diff --git a/sw/CppunitTest_sw_filter_ww8.mk b/sw/CppunitTest_sw_filter_ww8.mk
new file mode 100644
index 000000000000..0452776478df
--- /dev/null
+++ b/sw/CppunitTest_sw_filter_ww8.mk
@@ -0,0 +1,75 @@
+# -*- Mode: makefile-gmake; tab-width: 4; indent-tabs-mode: t -*-
+#*************************************************************************
+#
+# This file is part of the LibreOffice project.
+#
+# This Source Code Form is subject to the terms of the Mozilla Public
+# License, v. 2.0. If a copy of the MPL was not distributed with this
+# file, You can obtain one at http://mozilla.org/MPL/2.0/.
+#
+#*************************************************************************
+
+$(eval $(call gb_CppunitTest_CppunitTest,sw_filter_ww8))
+
+$(eval $(call gb_CppunitTest_use_common_precompiled_header,sw_filter_ww8))
+
+$(eval $(call gb_CppunitTest_add_exception_objects,sw_filter_ww8, \
+    sw/qa/filter/ww8/ww8 \
+))
+
+$(eval $(call gb_CppunitTest_use_libraries,sw_filter_ww8, \
+    comphelper \
+    cppu \
+    cppuhelper \
+    editeng \
+    sal \
+    sfx \
+    svl \
+    svx \
+    svxcore \
+    sw \
+    swqahelper \
+    test \
+    unotest \
+    utl \
+    vcl \
+    tl \
+))
+
+$(eval $(call gb_CppunitTest_use_externals,sw_filter_ww8,\
+    boost_headers \
+    libxml2 \
+))
+
+$(eval $(call gb_CppunitTest_set_include,sw_filter_ww8,\
+    -I$(SRCDIR)/sw/inc \
+    -I$(SRCDIR)/sw/source/core/inc \
+    -I$(SRCDIR)/sw/source/uibase/inc \
+    -I$(SRCDIR)/sw/qa/inc \
+    $$(INCLUDE) \
+))
+
+$(eval $(call gb_CppunitTest_use_api,sw_filter_ww8,\
+       udkapi \
+       offapi \
+       oovbaapi \
+))
+
+$(eval $(call gb_CppunitTest_use_ure,sw_filter_ww8))
+$(eval $(call gb_CppunitTest_use_vcl,sw_filter_ww8))
+
+$(eval $(call gb_CppunitTest_use_rdb,sw_filter_ww8,services))
+
+$(eval $(call gb_CppunitTest_use_custom_headers,sw_filter_ww8,\
+    officecfg/registry \
+))
+
+$(eval $(call gb_CppunitTest_use_configuration,sw_filter_ww8))
+
+$(eval $(call gb_CppunitTest_use_uiconfigs,sw_filter_ww8, \
+    modules/swriter \
+))
+
+$(eval $(call gb_CppunitTest_use_more_fonts,sw_filter_ww8))
+
+# vim: set noet sw=4 ts=4:
diff --git a/sw/Module_sw.mk b/sw/Module_sw.mk
index a543a57b0f55..8ef269a3f412 100644
--- a/sw/Module_sw.mk
+++ b/sw/Module_sw.mk
@@ -146,6 +146,7 @@ $(eval $(call gb_Module_add_slowcheck_targets,sw,\
     CppunitTest_sw_uibase_fldui \
     CppunitTest_sw_core_view \
     CppunitTest_sw_core_attr \
+    CppunitTest_sw_filter_ww8 \
 ))
 
 ifneq ($(DISABLE_GUI),TRUE)
diff --git a/sw/qa/filter/ww8/data/negative-page-border.doc 
b/sw/qa/filter/ww8/data/negative-page-border.doc
new file mode 100644
index 000000000000..6ea5e9030fa3
Binary files /dev/null and b/sw/qa/filter/ww8/data/negative-page-border.doc 
differ
diff --git a/sw/qa/filter/ww8/ww8.cxx b/sw/qa/filter/ww8/ww8.cxx
new file mode 100644
index 000000000000..eb735b16a746
--- /dev/null
+++ b/sw/qa/filter/ww8/ww8.cxx
@@ -0,0 +1,55 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+#include <swmodeltestbase.hxx>
+
+namespace
+{
+constexpr OUStringLiteral DATA_DIRECTORY = u"/sw/qa/filter/ww8/data/";
+
+/**
+ * Covers sw/source/filter/ww8/ fixes.
+ *
+ * Note that these tests are meant to be simple: either load a file and assert 
some result or build
+ * a document model with code, export and assert that result.
+ *
+ * Keep using the various sw_<format>import/export suites for multiple filter 
calls inside a single
+ * test.
+ */
+class Test : public SwModelTestBase
+{
+};
+
+CPPUNIT_TEST_FIXTURE(Test, testSwAttrSet)
+{
+    // Given a document with a border distance that is larger than the margin, 
when loading that
+    // document:
+    createSwDoc(DATA_DIRECTORY, "negative-page-border.doc");
+
+    // Then make sure we map that to a negative border distance (move border 
from the edge of body
+    // frame towards the center of the page, not towards the edge of the page):
+    uno::Reference<container::XNameAccess> xStyleFamily = 
getStyles("PageStyles");
+    uno::Reference<beans::XPropertySet> 
xStyle(xStyleFamily->getByName("Standard"), uno::UNO_QUERY);
+    auto nTopMargin = xStyle->getPropertyValue("TopMargin").get<sal_Int32>();
+    // Without the accompanying fix in place, this test would have failed with:
+    // - Expected: 501
+    // - Actual  : 342
+    // i.e. the border properties influenced the margin, which was 284 twips 
in the sprmSDyaTop
+    // SPRM.
+    CPPUNIT_ASSERT_EQUAL(static_cast<sal_Int32>(501), nTopMargin);
+    auto aTopBorder = 
xStyle->getPropertyValue("TopBorder").get<table::BorderLine2>();
+    CPPUNIT_ASSERT_EQUAL(static_cast<sal_uInt32>(159), aTopBorder.LineWidth);
+    auto nTopBorderDistance = 
xStyle->getPropertyValue("TopBorderDistance").get<sal_Int32>();
+    CPPUNIT_ASSERT_EQUAL(static_cast<sal_Int32>(-646), nTopBorderDistance);
+}
+}
+
+CPPUNIT_PLUGIN_IMPLEMENT();
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/writerfilter/source/dmapper/PropertyMap.cxx 
b/writerfilter/source/dmapper/PropertyMap.cxx
index 645cc8c00c86..e1814a8ce1d5 100644
--- a/writerfilter/source/dmapper/PropertyMap.cxx
+++ b/writerfilter/source/dmapper/PropertyMap.cxx
@@ -670,7 +670,7 @@ void SectionPropertyMap::SetBorderDistance( const 
uno::Reference< beans::XProper
     sal_Int32 nMargin = 0;
     aMargin >>= nMargin;
     editeng::BorderDistanceFromWord(eOffsetFrom == BorderOffsetFrom::Edge, 
nMargin, nDistance,
-                                    nLineWidth, 
/*bAllowNegativeBorderDistance=*/true);
+                                    nLineWidth);
 
     if (eOffsetFrom == BorderOffsetFrom::Edge)
     {

Reply via email to