[Libreoffice-commits] core.git: Branch 'distro/collabora/cp-5.3' - sw/qa sw/source writerfilter/source
Mike Kaganski
mike.kaganski at collabora.com
Tue Sep 12 17:08:45 UTC 2017
sw/qa/extras/ww8import/data/tdf112346.doc |binary
sw/qa/extras/ww8import/ww8import.cxx | 8 ++
sw/source/filter/ww8/ww8par.cxx | 103 +++++++++++++++++++++-------
sw/source/filter/ww8/ww8par.hxx | 1
sw/source/filter/ww8/ww8par6.cxx | 14 ---
writerfilter/source/dmapper/PropertyMap.cxx | 11 ++
6 files changed, 97 insertions(+), 40 deletions(-)
New commits:
commit 21f73d47e949ef2732b778bd1ebe123473edf231
Author: Mike Kaganski <mike.kaganski at collabora.com>
Date: Tue Sep 12 13:54:26 2017 +0300
tdf#112346: take Word no-wrap limit into account also for ww8
This also makes ww8 floating-table conversion decision heuristics
somewhat closer to OOXML code.
Change-Id: I29ca2ebabd1758ad98e02aaf560cf2f44daec3a8
Reviewed-on: https://gerrit.libreoffice.org/42196
Tested-by: Jenkins <ci at libreoffice.org>
Reviewed-by: Miklos Vajna <vmiklos at collabora.co.uk>
Reviewed-on: https://gerrit.libreoffice.org/42216
Reviewed-by: Mike Kaganski <mike.kaganski at collabora.com>
Tested-by: Mike Kaganski <mike.kaganski at collabora.com>
diff --git a/sw/qa/extras/ww8import/data/tdf112346.doc b/sw/qa/extras/ww8import/data/tdf112346.doc
new file mode 100644
index 000000000000..af0cca219acf
Binary files /dev/null and b/sw/qa/extras/ww8import/data/tdf112346.doc differ
diff --git a/sw/qa/extras/ww8import/ww8import.cxx b/sw/qa/extras/ww8import/ww8import.cxx
index 751006a4a553..eb45c8172e36 100644
--- a/sw/qa/extras/ww8import/ww8import.cxx
+++ b/sw/qa/extras/ww8import/ww8import.cxx
@@ -88,6 +88,14 @@ DECLARE_WW8IMPORT_TEST(testTdf106799, "tdf106799.doc")
}
}
+DECLARE_WW8IMPORT_TEST(testTdf112346, "tdf112346.doc")
+{
+ uno::Reference<drawing::XDrawPageSupplier> xDrawPageSupplier(mxComponent, uno::UNO_QUERY);
+ uno::Reference<drawing::XDrawPage> xDrawPage = xDrawPageSupplier->getDrawPage();
+ // This was 1, multi-page table was imported as a floating one.
+ CPPUNIT_ASSERT_EQUAL(static_cast<sal_Int32>(0), xDrawPage->getCount());
+}
+
// tests should only be added to ww8IMPORT *if* they fail round-tripping in ww8EXPORT
CPPUNIT_PLUGIN_IMPLEMENT();
diff --git a/sw/source/filter/ww8/ww8par.cxx b/sw/source/filter/ww8/ww8par.cxx
index 88f4f4f3d22c..45c22d149874 100644
--- a/sw/source/filter/ww8/ww8par.cxx
+++ b/sw/source/filter/ww8/ww8par.cxx
@@ -91,6 +91,7 @@
#include <charfmt.hxx>
#include <unocrsr.hxx>
#include <IDocumentSettingAccess.hxx>
+#include <sprmids.hxx>
#include <fltini.hxx>
@@ -2592,6 +2593,83 @@ void SwWW8ImplReader::EndSpecial()
OSL_ENSURE(!m_nInTable, "unclosed table!");
}
+bool SwWW8ImplReader::FloatingTableConversion(WW8PLCFx_Cp_FKP* pPap)
+{
+ // This is ww8 version of the code deciding if the table needs to be
+ // in a floating frame.
+ // For OOXML code, see SectionPropertyMap::FloatingTableConversion in
+ // writerfilter/source/dmapper/PropertyMap.cxx
+ // The two should do ~same, so if you make changes here, please check
+ // that the other is in sync.
+
+ // Note that this is just a list of heuristics till sw core can have a
+ // table that is floating and can span over multiple pages at the same
+ // time.
+
+ bool bResult = true;
+
+ const sal_uInt8 *pRes = pPap->HasSprm(NS_sprm::LN_TDefTable);
+ if (nullptr != pRes)
+ {
+ bResult = false;
+ WW8TabBandDesc aDesc;
+ aDesc.ReadDef(false, pRes);
+ int nTextAreaWidth = m_aSectionManager.GetTextAreaWidth();
+ int nTableWidth = aDesc.nCenter[aDesc.nWwCols] - aDesc.nCenter[0];
+
+ // It seems Word has a limit here, so that in case the table width is quite
+ // close to the text area width, then it won't perform a wrapping, even in
+ // case the content (e.g. an empty paragraph) would fit. The magic constant
+ // here represents this limit.
+ const int nMagicNumber = 469;
+
+ // If the table is wider than the text area, then don't create a fly
+ // for the table: no wrapping will be performed anyway, but multi-page
+ // tables will be broken.
+ if ((nTableWidth + nMagicNumber) < nTextAreaWidth)
+ bResult = true;
+
+ // If there are columns, do create a fly, as the flow of the columns
+ // would otherwise restrict the table.
+ if (!bResult && (m_aSectionManager.CurrentSectionColCount() >= 2))
+ bResult = true;
+ }
+
+ if (bResult)
+ {
+ WW8PLCFxSave1 aSave;
+ pPap->Save(aSave);
+ if (SearchTableEnd(pPap))
+ {
+ // Table is considered to be imported into a fly frame and we
+ // know where the end of the table is.
+ bool bIsUnicode;
+ WW8_FC nFc = m_pSBase->WW8Cp2Fc(pPap->Where(), &bIsUnicode);
+ sal_uInt64 nPos = m_pStrm->Tell();
+ m_pStrm->Seek(nFc);
+ sal_uInt16 nUChar = 0;
+ if (bIsUnicode)
+ m_pStrm->ReadUInt16(nUChar);
+ else
+ {
+ sal_uInt8 nChar = 0;
+ m_pStrm->ReadUChar(nChar);
+ nUChar = nChar;
+ }
+ m_pStrm->Seek(nPos);
+ if (nUChar == 0xc)
+ // The pap after the table starts with a page break, so
+ // there will be no wrapping around the float-table.
+ // Request no fly in this case, so the table can properly
+ // be a multi-page one if necessary.
+ bResult = false;
+ }
+ pPap->Restore(aSave);
+ }
+
+ return bResult;
+}
+
bool SwWW8ImplReader::ProcessSpecial(bool &rbReSync, WW8_CP nStartCp)
{
// Frame/Table/Anl
@@ -2665,31 +2743,6 @@ bool SwWW8ImplReader::ProcessSpecial(bool &rbReSync, WW8_CP nStartCp)
if (bHasRowEnd && ParseTabPos(&aTabPos,pPap))
pTabPos = &aTabPos;
- if (pTabPos && !pTabPos->bNoFly && SearchTableEnd(pPap))
- {
- // Table is considered to be imported into a fly frame and we
- // know where the end of the table is.
- bool bIsUnicode;
- WW8_FC nFc = m_pSBase->WW8Cp2Fc(pPap->Where(), &bIsUnicode);
- sal_uInt64 nPos = m_pStrm->Tell();
- m_pStrm->Seek(nFc);
- sal_uInt16 nUChar = 0;
- if (bIsUnicode)
- m_pStrm->ReadUInt16(nUChar);
- else
- {
- sal_uInt8 nChar = 0;
- m_pStrm->ReadUChar(nChar);
- nUChar = nChar;
- }
- m_pStrm->Seek(nPos);
- if (nUChar == 0xc)
- // The pap after the table starts with a page break, so
- // there will be no wrapping around the float-table.
- // Request no fly in this case, so the table can properly
- // be a multi-page one if necessary.
- pTabPos->bNoFly = true;
- }
m_pPlcxMan->GetPap()->Restore( aSave );
}
diff --git a/sw/source/filter/ww8/ww8par.hxx b/sw/source/filter/ww8/ww8par.hxx
index 600cb409b263..3de77f914409 100644
--- a/sw/source/filter/ww8/ww8par.hxx
+++ b/sw/source/filter/ww8/ww8par.hxx
@@ -1851,6 +1851,7 @@ public: // really private, but can only be done public
bool SearchRowEnd(WW8PLCFx_Cp_FKP* pPap,WW8_CP &rStartCp, int nLevel) const;
/// Seek to the end of the table with pPap, returns true on success.
bool SearchTableEnd(WW8PLCFx_Cp_FKP* pPap) const;
+ bool FloatingTableConversion(WW8PLCFx_Cp_FKP* pPap);
const WW8Fib& GetFib() const { return *m_pWwFib; }
SwDoc& GetDoc() const { return m_rDoc; }
diff --git a/sw/source/filter/ww8/ww8par6.cxx b/sw/source/filter/ww8/ww8par6.cxx
index f86eb4c80819..bfe724c2f8ca 100644
--- a/sw/source/filter/ww8/ww8par6.cxx
+++ b/sw/source/filter/ww8/ww8par6.cxx
@@ -5067,21 +5067,9 @@ bool SwWW8ImplReader::ParseTabPos(WW8_TablePos *pTabPos, WW8PLCFx_Cp_FKP* pPap)
pTabPos->nUpMgn = SVBT16ToShort(pRes);
if (nullptr != (pRes = pPap->HasSprm(0x941F)))
pTabPos->nLoMgn = SVBT16ToShort(pRes);
+ pTabPos->bNoFly = !FloatingTableConversion(pPap);
bRet = true;
}
- if (nullptr != (pRes = pPap->HasSprm(NS_sprm::LN_TDefTable)))
- {
- WW8TabBandDesc aDesc;
- aDesc.ReadDef(false, pRes);
- int nTableWidth = aDesc.nCenter[aDesc.nWwCols] - aDesc.nCenter[0];
- int nTextAreaWidth = m_aSectionManager.GetTextAreaWidth();
- // If the table is wider than the text area, then don't create a fly
- // for the table: no wrapping will be performed anyway, but multi-page
- // tables will be broken.
- // If there are columns, do create a fly, as the flow of the columns
- // would otherwise restrict the table.
- pTabPos->bNoFly = nTableWidth >= nTextAreaWidth && m_aSectionManager.CurrentSectionColCount() < 2;
- }
return bRet;
}
diff --git a/writerfilter/source/dmapper/PropertyMap.cxx b/writerfilter/source/dmapper/PropertyMap.cxx
index 8b84e318bc67..6ff4d05c1476 100644
--- a/writerfilter/source/dmapper/PropertyMap.cxx
+++ b/writerfilter/source/dmapper/PropertyMap.cxx
@@ -1054,6 +1054,13 @@ void SectionPropertyMap::HandleMarginsHeaderFooter(bool bFirstPage, DomainMapper
bool SectionPropertyMap::FloatingTableConversion(DomainMapper_Impl& rDM_Impl, FloatingTableInfo& rInfo)
{
+ // This is OOXML version of the code deciding if the table needs to be
+ // in a floating frame.
+ // For ww8 code, see SwWW8ImplReader::FloatingTableConversion in
+ // sw/source/filter/ww8/ww8par.cxx
+ // The two should do the same, so if you make changes here, please check
+ // that the other is in sync.
+
// Note that this is just a list of heuristics till sw core can have a
// table that is floating and can span over multiple pages at the same
// time.
@@ -1107,9 +1114,9 @@ bool SectionPropertyMap::FloatingTableConversion(DomainMapper_Impl& rDM_Impl, Fl
// If the position is relative to the edge of the page, then we need to check the whole
// page width to see whether text can fit next to the table.
- if ( rInfo.getPropertyValue( "HoriOrientRelation" ) == text::RelOrientation::PAGE_FRAME )
+ if ( nHoriOrientRelation == text::RelOrientation::PAGE_FRAME )
{
- // If the table is wide enough to that no text fits next to it, then don't create a fly
+ // If the table is wide enough so that no text fits next to it, then don't create a fly
// for the table: no wrapping will be performed anyway, but multi-page
// tables will be broken.
if ((nTableWidth + nMagicNumber) < (nPageWidth - std::min(GetLeftMargin(), GetRightMargin())))
More information about the Libreoffice-commits
mailing list