sw/CppunitTest_sw_writerfilter_dmapper.mk | 12 ++++ sw/qa/writerfilter/dmapper/DomainMapperTableHandler.cxx | 31 ++++++++++-- sw/qa/writerfilter/dmapper/data/floattable-redline.docx |binary sw/source/writerfilter/dmapper/DomainMapperTableHandler.cxx | 5 + 4 files changed, 44 insertions(+), 4 deletions(-)
New commits: commit f124b25380a8ae9f5bbae7ca04772124a6572926 Author: Miklos Vajna <vmik...@collabora.com> AuthorDate: Tue Jul 8 09:50:08 2025 +0200 Commit: Miklos Vajna <vmik...@collabora.com> CommitDate: Tue Jul 8 15:00:20 2025 +0200 tdf#167229 sw floattable: fix missing cell background with redlines Open the DOCX file, the 3rd table should have a gray background in its B2 cell, but its background is white. It seems this happens because there are 2 floating tables before the table and the first floating table has a redline. Commit 288db6eb47fbbd2b3ca34ffea0686d8ed8ed9be9 (tdf#132271 DOCX: import change tracking in floating tables, 2020-09-07) added special handling of redlines inside floating tables, and I moved that code around for SwFormatFlySplit in c50bf5a5daaae3d40f89ea0784a75a8a571c208d (sw floattable: remove no longer needed DOCX import heuristics, 2023-04-12). The trouble is that once these pending redlines are processed, nobody clears rFramedRedlines, so it gets processed also for a next floating table, which pollutes the state of the importer, which leads to missing cell properties for later tables. Fix the problem by clearing the redline list in DomainMapperTableHandler::endTable(), which restores the invariant that once the redline list is processed, it's cleared -- that was there in the old SectionPropertyMap::CloseSectionGroup() code before the SwFormatFlySplit work. An alternative I've considered is to just catch exceptions in BeforeConvertToTextFrame() when getting the TextTable and Cell properties, but that would still result in this unwanted behavior that a floattable-with-redlines has an influance on the next floattable. Change-Id: I9998a46d72a72172dffcf85bf96b3478d63c9269 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/187535 Reviewed-by: Miklos Vajna <vmik...@collabora.com> Tested-by: Jenkins diff --git a/sw/CppunitTest_sw_writerfilter_dmapper.mk b/sw/CppunitTest_sw_writerfilter_dmapper.mk index 366cca5dd239..260c8d9b37f9 100644 --- a/sw/CppunitTest_sw_writerfilter_dmapper.mk +++ b/sw/CppunitTest_sw_writerfilter_dmapper.mk @@ -37,6 +37,7 @@ $(eval $(call gb_CppunitTest_use_libraries,sw_writerfilter_dmapper, \ comphelper \ cppu \ cppuhelper \ + editeng \ oox \ sal \ subsequenttest \ @@ -45,6 +46,17 @@ $(eval $(call gb_CppunitTest_use_libraries,sw_writerfilter_dmapper, \ utl \ tl \ vcl \ + svl \ + sw \ + swqahelper \ +)) + +$(eval $(call gb_CppunitTest_set_include,sw_writerfilter_dmapper,\ + -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_sdk_api,sw_writerfilter_dmapper)) diff --git a/sw/qa/writerfilter/dmapper/DomainMapperTableHandler.cxx b/sw/qa/writerfilter/dmapper/DomainMapperTableHandler.cxx index 03c4727737b7..e36ae88a7728 100644 --- a/sw/qa/writerfilter/dmapper/DomainMapperTableHandler.cxx +++ b/sw/qa/writerfilter/dmapper/DomainMapperTableHandler.cxx @@ -7,7 +7,7 @@ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ -#include <test/unoapixml_test.hxx> +#include <swmodeltestbase.hxx> #include <com/sun/star/beans/XPropertySet.hpp> #include <com/sun/star/table/BorderLine2.hpp> @@ -21,16 +21,19 @@ #include <com/sun/star/text/XPageCursor.hpp> #include <com/sun/star/qa/XDumper.hpp> +#include <frmatr.hxx> +#include <swtable.hxx> + using namespace ::com::sun::star; namespace { /// Tests for sw/source/writerfilter/dmapper/DomainMapperTableHandler.cxx. -class Test : public UnoApiXmlTest +class Test : public SwModelTestBase { public: Test() - : UnoApiXmlTest(u"/sw/qa/writerfilter/dmapper/data/"_ustr) + : SwModelTestBase(u"/sw/qa/writerfilter/dmapper/data/"_ustr) { } }; @@ -277,6 +280,28 @@ CPPUNIT_TEST_FIXTURE(Test, testDOCXFloatingTableNestedLayout) CPPUNIT_ASSERT_GREATER(nTableTop, nFlyTop); CPPUNIT_ASSERT_LESS(nTableBottom, nFlyBottom); } + +CPPUNIT_TEST_FIXTURE(Test, testDOCXFloatingTableRedline) +{ + // Given a document with 3 floating tables, the last table has a last cell with a custom cell + // background: + // When importing that document from DOCX: + createSwDoc("floattable-redline.docx"); + + // Then make sure that the cell background is not lost: + SwDoc* pDoc = getSwDoc(); + sw::TableFrameFormats& rTableFormats = *pDoc->GetTableFrameFormats(); + SwTableFormat* pTableFormat = rTableFormats[2]; + SwTable* pTable = SwTable::FindTable(pTableFormat); + const SwTableBox* pCell = pTable->GetTableBox(u"B2"_ustr); + const SwAttrSet& rCellSet = pCell->GetFrameFormat()->GetAttrSet(); + const SvxBrushItem& rCellBackground = rCellSet.GetBackground(); + // Without the accompanying fix in place, this test would have failed with: + // - Expected: rgba[d0d8e8ff] + // - Actual : rgba[ffffff00] + // i.e. the cell background was white, should be gray. + CPPUNIT_ASSERT_EQUAL(Color(0xD0D8E8), rCellBackground.GetColor()); +} } CPPUNIT_PLUGIN_IMPLEMENT(); diff --git a/sw/qa/writerfilter/dmapper/data/floattable-redline.docx b/sw/qa/writerfilter/dmapper/data/floattable-redline.docx new file mode 100644 index 000000000000..9b45768ca9d2 Binary files /dev/null and b/sw/qa/writerfilter/dmapper/data/floattable-redline.docx differ diff --git a/sw/source/writerfilter/dmapper/DomainMapperTableHandler.cxx b/sw/source/writerfilter/dmapper/DomainMapperTableHandler.cxx index a98cd7f56403..74c25f9ad9ea 100644 --- a/sw/source/writerfilter/dmapper/DomainMapperTableHandler.cxx +++ b/sw/source/writerfilter/dmapper/DomainMapperTableHandler.cxx @@ -1668,7 +1668,7 @@ void DomainMapperTableHandler::endTable(unsigned int nestedTableLevel) bool bRecordChanges = m_rDMapper_Impl.GetSettingsTable()->GetRecordChanges(); if (xTextAppendAndConvert.is() && !(bInFootnote && bRecordChanges)) { - const std::deque<StoredRedline>& rFramedRedlines = m_rDMapper_Impl.m_aStoredRedlines[StoredRedlines::FRAME]; + std::deque<StoredRedline>& rFramedRedlines = m_rDMapper_Impl.m_aStoredRedlines[StoredRedlines::FRAME]; std::vector<sal_Int32> redPos, redLen; std::vector<OUString> redCell; std::vector<OUString> redTable; @@ -1722,6 +1722,9 @@ void DomainMapperTableHandler::endTable(unsigned int nestedTableLevel) } AfterConvertToTextFrame(m_rDMapper_Impl, rFramedRedlines, redPos, redLen, redCell, redTable); + + // These redlines are not relevant for the next floating table, clear them. + rFramedRedlines.clear(); } if (xFrameAnchor.is() && eBreakType != style::BreakType_NONE)