tdf#131537 DOCX export: fix OLE "Display as icon"
for example to avoid converting OLE icons of an ODF document
to an icon-size embedded spreadsheet.
When creating a new OLE object in Writer the user has an option called
"Display as icon" which causes the actual contents of the OLE to be
hidden when rendered in the document. This setting, referred to
internally as the DrawAspect of the object, was imported fine, but when
exported to a .docx it always had the value "Content" (corresponding to
"Display as icon" being unchecked). Now OLE objects with "Display as
icon" checked are saved with DrawAspect="Icon".
A grab bag entry was previously used to let the DrawAspect setting flow
through Writer from OOXML import to export. Now this workaround is no
longer needed and is removed by the present commit.
Change-Id: I46ea4fc95a26bcd1f85e19a506c0965f73d4257a
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/101711
Tested-by: László Németh <nemeth@numbertext.org>
Reviewed-by: László Németh <nemeth@numbertext.org>
diff --git a/include/oox/ole/oleobjecthelper.hxx b/include/oox/ole/oleobjecthelper.hxx
index a9d6bfe..d2506f3 100644
--- a/include/oox/ole/oleobjecthelper.hxx
+++ b/include/oox/ole/oleobjecthelper.hxx
@@ -76,7 +76,7 @@ private:
OOX_DLLPUBLIC void SaveInteropProperties(
css::uno::Reference<css::frame::XModel> const& xModel,
OUString const& rObjectName, OUString const* pOldObjectName,
OUString const& rProgId, OUString const& rDrawAspect);
OUString const& rProgId);
} // namespace oox::ole
diff --git a/oox/source/ole/oleobjecthelper.cxx b/oox/source/ole/oleobjecthelper.cxx
index b6c4edb..6716ac1 100644
--- a/oox/source/ole/oleobjecthelper.cxx
+++ b/oox/source/ole/oleobjecthelper.cxx
@@ -87,7 +87,7 @@ OleObjectHelper::~OleObjectHelper()
// just "application/vnd.sun.star.oleobject"
void SaveInteropProperties(uno::Reference<frame::XModel> const& xModel,
OUString const& rObjectName, OUString const*const pOldObjectName,
OUString const& rProgId, OUString const& rDrawAspect)
OUString const& rProgId)
{
static const char sEmbeddingsPropName[] = "EmbeddedObjects";
@@ -100,11 +100,9 @@ void SaveInteropProperties(uno::Reference<frame::XModel> const& xModel,
if (aGrabBag.find(sEmbeddingsPropName) != aGrabBag.end())
objectsList << aGrabBag[sEmbeddingsPropName];
uno::Sequence< beans::PropertyValue > aGrabBagAttribute(2);
uno::Sequence< beans::PropertyValue > aGrabBagAttribute(1);
aGrabBagAttribute[0].Name = "ProgID";
aGrabBagAttribute[0].Value <<= rProgId;
aGrabBagAttribute[1].Name = "DrawAspect";
aGrabBagAttribute[1].Value <<= rDrawAspect;
// If we got an "old name", erase that first.
if (pOldObjectName)
@@ -148,9 +146,7 @@ bool OleObjectHelper::importOleObject( PropertyMap& rPropMap, const OleObjectInf
xOutStrm->writeBytes( rOleObject.maEmbeddedData );
xOutStrm->closeOutput();
SaveInteropProperties(m_xModel, aObjectId, nullptr,
rOleObject.maProgId,
rOleObject.mbShowAsIcon ? OUString("Icon") : OUString("Content"));
SaveInteropProperties(m_xModel, aObjectId, nullptr, rOleObject.maProgId);
OUString aUrl = mxResolver->resolveEmbeddedObjectURL( aObjectId );
OSL_ENSURE( aUrl.match( g_aEmbeddedObjScheme ), "OleObjectHelper::importOleObject - unexpected URL scheme" );
diff --git a/sw/qa/extras/ooxmlexport/data/tdf131537.odt b/sw/qa/extras/ooxmlexport/data/tdf131537.odt
new file mode 100644
index 0000000..21f3963
--- /dev/null
+++ b/sw/qa/extras/ooxmlexport/data/tdf131537.odt
Binary files differ
diff --git a/sw/qa/extras/ooxmlexport/ooxmlexport5.cxx b/sw/qa/extras/ooxmlexport/ooxmlexport5.cxx
index 6c07f45..af9cd5c 100644
--- a/sw/qa/extras/ooxmlexport/ooxmlexport5.cxx
+++ b/sw/qa/extras/ooxmlexport/ooxmlexport5.cxx
@@ -909,6 +909,13 @@ DECLARE_OOXMLEXPORT_EXPORTONLY_TEST(testfdo80898, "fdo80898.docx")
"Word.Document.8");
}
DECLARE_OOXMLEXPORT_EXPORTONLY_TEST(testOleIconDrawAspect, "tdf131537.odt")
{
xmlDocUniquePtr pXmlDoc = parseExport("word/document.xml");
assertXPath(pXmlDoc, "/w:document/w:body/w:p[2]/w:r/w:object/o:OLEObject",
"DrawAspect", "Icon");
}
DECLARE_OOXMLEXPORT_EXPORTONLY_TEST(testTableCellWithDirectFormatting, "fdo80800.docx")
{
// Issue was Direct Formatting for non-first Table cells was not getting preserved.
diff --git a/sw/source/filter/ww8/docxattributeoutput.cxx b/sw/source/filter/ww8/docxattributeoutput.cxx
index 1dabca1..947a7f3 100644
--- a/sw/source/filter/ww8/docxattributeoutput.cxx
+++ b/sw/source/filter/ww8/docxattributeoutput.cxx
@@ -142,6 +142,7 @@
#include <com/sun/star/drawing/ShadingPattern.hpp>
#include <com/sun/star/text/GraphicCrop.hpp>
#include <com/sun/star/embed/EmbedStates.hpp>
#include <com/sun/star/embed/Aspects.hpp>
#include <algorithm>
#include <stdarg.h>
@@ -5541,7 +5542,16 @@ void DocxAttributeOutput::WriteOLE( SwOLENode& rNode, const Size& rSize, const S
OUString sObjectName = aContainer->GetEmbeddedObjectName( xObj );
// set some attributes according to the type of the embedded object
OUString sProgID, sDrawAspect = "Content";
OUString sProgID, sDrawAspect;
switch (rNode.GetAspect())
{
case embed::Aspects::MSOLE_CONTENT: sDrawAspect = "Content"; break;
case embed::Aspects::MSOLE_DOCPRINT: sDrawAspect = "DocPrint"; break;
case embed::Aspects::MSOLE_ICON: sDrawAspect = "Icon"; break;
case embed::Aspects::MSOLE_THUMBNAIL: sDrawAspect = "Thumbnail"; break;
default:
SAL_WARN("sw.ww8", "DocxAttributeOutput::WriteOLE: invalid aspect value");
}
auto pObjectsInterop = std::find_if(aObjectsInteropList.begin(), aObjectsInteropList.end(),
[&sObjectName](const beans::PropertyValue& rProp) { return rProp.Name == sObjectName; });
if (pObjectsInterop != aObjectsInteropList.end())
@@ -5553,10 +5563,6 @@ void DocxAttributeOutput::WriteOLE( SwOLENode& rNode, const Size& rSize, const S
{
rObjectInteropAttribute.Value >>= sProgID;
}
else if ( rObjectInteropAttribute.Name == "DrawAspect" )
{
rObjectInteropAttribute.Value >>= sDrawAspect;
}
}
// write embedded file
diff --git a/writerfilter/source/dmapper/OLEHandler.cxx b/writerfilter/source/dmapper/OLEHandler.cxx
index dd7b131..ae1967a 100644
--- a/writerfilter/source/dmapper/OLEHandler.cxx
+++ b/writerfilter/source/dmapper/OLEHandler.cxx
@@ -218,7 +218,7 @@ void OLEHandler::importStream(const uno::Reference<uno::XComponentContext>& xCom
uno::Reference<beans::XPropertySet> xPropertySet(xOLE, uno::UNO_QUERY);
::oox::ole::SaveInteropProperties(xTextDocument,
xPropertySet->getPropertyValue("StreamName").get<OUString>(), &m_aURL,
m_sProgId, m_sDrawAspect);
m_sProgId);
}
OUString OLEHandler::getCLSID(const uno::Reference<uno::XComponentContext>& xComponentContext) const
@@ -294,7 +294,7 @@ OUString OLEHandler::copyOLEOStream(
}
}
::oox::ole::SaveInteropProperties(xTextDocument, aURL, nullptr, m_sProgId, m_sDrawAspect);
::oox::ole::SaveInteropProperties(xTextDocument, aURL, nullptr, m_sProgId);
OUString aPersistName( xEmbeddedResolver->resolveEmbeddedObjectURL( aURL ) );
sRet = aPersistName.copy( strlen("vnd.sun.star.EmbeddedObject:") );