diff options
-rw-r--r-- | include/oox/ole/vbaproject.hxx | 4 | ||||
-rw-r--r-- | oox/source/core/filterdetect.cxx | 9 | ||||
-rw-r--r-- | oox/source/ole/vbaproject.cxx | 14 | ||||
-rw-r--r-- | sw/source/filter/ww8/docxexport.cxx | 61 | ||||
-rw-r--r-- | writerfilter/inc/ooxml/OOXMLDocument.hxx | 3 | ||||
-rw-r--r-- | writerfilter/source/filter/WriterFilter.cxx | 11 | ||||
-rw-r--r-- | writerfilter/source/ooxml/OOXMLDocumentImpl.cxx | 74 | ||||
-rw-r--r-- | writerfilter/source/ooxml/OOXMLDocumentImpl.hxx | 4 | ||||
-rw-r--r-- | writerfilter/source/ooxml/OOXMLStreamImpl.cxx | 23 | ||||
-rw-r--r-- | writerfilter/source/ooxml/OOXMLStreamImpl.hxx | 3 |
10 files changed, 69 insertions, 137 deletions
diff --git a/include/oox/ole/vbaproject.hxx b/include/oox/ole/vbaproject.hxx index 3f0e2b0fccfc..4e6aacf24ad6 100644 --- a/include/oox/ole/vbaproject.hxx +++ b/include/oox/ole/vbaproject.hxx @@ -37,6 +37,7 @@ namespace com { namespace sun { namespace star { namespace script { namespace vba { class XVBAMacroResolver; } } namespace uno { class XComponentContext; } namespace uno { class XInterface; } + namespace io { class XInputStream; } } } } namespace oox { @@ -130,6 +131,9 @@ public: bool importVbaProject( StorageBase& rVbaPrjStrg ); + /// Imports VBA data for a VBA project, e.g. word/vbaData.xml. + void importVbaData(const css::uno::Reference<css::io::XInputStream>& xInputStream); + /** Reads vba module related information from the project streams */ void readVbaModules( StorageBase& rVbaPrjStrg ); /** Imports (and creates) vba modules and user forms from the vba project records previously read. diff --git a/oox/source/core/filterdetect.cxx b/oox/source/core/filterdetect.cxx index ed94ca5a5770..991b3d86a585 100644 --- a/oox/source/core/filterdetect.cxx +++ b/oox/source/core/filterdetect.cxx @@ -163,14 +163,7 @@ void FilterDetectDocHandler::parseRelationship( const AttributeList& rAttribs ) OUString FilterDetectDocHandler::getFilterNameFromContentType( const OUString& rContentType, const OUString& rFileName ) { - bool bDocm = false; - OUString aDocmExtension = ".docm"; - if (rFileName.getLength() >= aDocmExtension.getLength()) - { - OUString aExtension = rFileName.copy(rFileName.getLength() - aDocmExtension.getLength()); - // The file name ends with .docm, ignoring case. - bDocm = aExtension.equalsIgnoreAsciiCase(aDocmExtension); - } + bool bDocm = rFileName.endsWithIgnoreAsciiCase(".docm"); if( rContentType == "application/vnd.openxmlformats-officedocument.wordprocessingml.document.main+xml" && !bDocm ) return OUString( "writer_MS_Word_2007" ); diff --git a/oox/source/ole/vbaproject.cxx b/oox/source/ole/vbaproject.cxx index e915ba78ea10..c38adc9c3777 100644 --- a/oox/source/ole/vbaproject.cxx +++ b/oox/source/ole/vbaproject.cxx @@ -32,6 +32,7 @@ #include <com/sun/star/uno/XComponentContext.hpp> #include <comphelper/configurationhelper.hxx> #include <comphelper/string.hxx> +#include <comphelper/storagehelper.hxx> #include <osl/diagnose.h> #include <rtl/tencinfo.h> #include <rtl/ustrbuf.h> @@ -49,6 +50,7 @@ namespace oox { namespace ole { +using namespace ::com::sun::star; using namespace ::com::sun::star::container; using namespace ::com::sun::star::document; using namespace ::com::sun::star::embed; @@ -182,6 +184,18 @@ void VbaProject::importVbaProject( StorageBase& rVbaPrjStrg, const GraphicHelper } } +void VbaProject::importVbaData(const uno::Reference<io::XInputStream>& xInputStream) +{ + uno::Reference<document::XStorageBasedDocument> xStorageBasedDoc(mxDocModel, uno::UNO_QUERY); + uno::Reference<embed::XStorage> xDocStorage(xStorageBasedDoc->getDocumentStorage(), uno::UNO_QUERY); + { + const sal_Int32 nOpenMode = ElementModes::SEEKABLE | ElementModes::WRITE | ElementModes::TRUNCATE; + uno::Reference<io::XOutputStream> xDocStream(xDocStorage->openStreamElement("_MS_VBA_Macros_XML", nOpenMode), uno::UNO_QUERY); + comphelper::OStorageHelper::CopyInputToOutput(xInputStream, xDocStream); + } + uno::Reference<embed::XTransactedObject>(xDocStorage, uno::UNO_QUERY)->commit(); +} + void VbaProject::registerMacroAttacher( const VbaMacroAttacherRef& rxAttacher ) { OSL_ENSURE( rxAttacher.get(), "VbaProject::registerMacroAttacher - unexpected empty reference" ); diff --git a/sw/source/filter/ww8/docxexport.cxx b/sw/source/filter/ww8/docxexport.cxx index f95aa0cb3a82..24a388ec1ab6 100644 --- a/sw/source/filter/ww8/docxexport.cxx +++ b/sw/source/filter/ww8/docxexport.cxx @@ -1287,51 +1287,30 @@ void DocxExport::WriteVBA() m_pFilter->addRelation(m_pDocumentFS->getOutputStream(), "http://schemas.microsoft.com/office/2006/relationships/vbaProject", "vbaProject.bin"); } - uno::Reference<beans::XPropertySet> xPropertySet(m_pDoc->GetDocShell()->GetBaseModel(), uno::UNO_QUERY); - if (!xPropertySet.is()) + OUString aDataName("_MS_VBA_Macros_XML"); + if (!xDocumentStorage.is() || !xDocumentStorage->hasByName(aDataName)) return; - uno::Reference<beans::XPropertySetInfo> xPropertySetInfo = xPropertySet->getPropertySetInfo(); - if (!xPropertySetInfo->hasPropertyByName(UNO_NAME_MISC_OBJ_INTEROPGRABBAG)) - return; - - uno::Sequence<beans::PropertyValue> aGrabBag; - xPropertySet->getPropertyValue(UNO_NAME_MISC_OBJ_INTEROPGRABBAG) >>= aGrabBag; - uno::Sequence<beans::PropertyValue> aVBA; - for (const auto& rProperty : aGrabBag) + uno::Reference<io::XStream> xDataStream(xDocumentStorage->openStreamElement(aDataName, nOpenMode), uno::UNO_QUERY); + if (xDataStream.is()) { - if (rProperty.Name == "OOXVBA") - rProperty.Value >>= aVBA; - } - if (!aVBA.hasElements()) - return; + // Then the data stream, which wants to work with an already set + // xProjectStream. + std::unique_ptr<SvStream> pIn(utl::UcbStreamHelper::CreateStream(xDataStream)); - for (const auto& rProperty : aVBA) - { - if (rProperty.Name == "DataStream") - { - // Then the data stream, which wants to work with an already set - // xProjectStream. - uno::Reference<io::XStream> xInputStream; - rProperty.Value >>= xInputStream; - if (!xInputStream.is()) - return; - std::unique_ptr<SvStream> pIn(utl::UcbStreamHelper::CreateStream(xInputStream)); - - uno::Reference<io::XStream> xOutputStream(GetFilter().openFragmentStream("word/vbaData.xml", "application/vnd.ms-word.vbaData+xml"), uno::UNO_QUERY); - if (!xOutputStream.is()) - return; - std::unique_ptr<SvStream> pOut(utl::UcbStreamHelper::CreateStream(xOutputStream)); - - // Write the stream. - pOut->WriteStream(*pIn); - - // Write the relationship. - if (!xProjectStream.is()) - return; - - m_pFilter->addRelation(xProjectStream, "http://schemas.microsoft.com/office/2006/relationships/wordVbaData", "vbaData.xml"); - } + uno::Reference<io::XStream> xOutputStream(GetFilter().openFragmentStream("word/vbaData.xml", "application/vnd.ms-word.vbaData+xml"), uno::UNO_QUERY); + if (!xOutputStream.is()) + return; + std::unique_ptr<SvStream> pOut(utl::UcbStreamHelper::CreateStream(xOutputStream)); + + // Write the stream. + pOut->WriteStream(*pIn); + + // Write the relationship. + if (!xProjectStream.is()) + return; + + m_pFilter->addRelation(xProjectStream, "http://schemas.microsoft.com/office/2006/relationships/wordVbaData", "vbaData.xml"); } } diff --git a/writerfilter/inc/ooxml/OOXMLDocument.hxx b/writerfilter/inc/ooxml/OOXMLDocument.hxx index 009aeba949cc..c7241f946311 100644 --- a/writerfilter/inc/ooxml/OOXMLDocument.hxx +++ b/writerfilter/inc/ooxml/OOXMLDocument.hxx @@ -75,7 +75,7 @@ class OOXMLStream { public: enum StreamType_t { UNKNOWN, DOCUMENT, STYLES, WEBSETTINGS, FONTTABLE, NUMBERING, - FOOTNOTES, ENDNOTES, COMMENTS, THEME, CUSTOMXML, CUSTOMXMLPROPS, ACTIVEX, ACTIVEXBIN, GLOSSARY, CHARTS, EMBEDDINGS, SETTINGS, VBAPROJECT, FOOTER, HEADER }; + FOOTNOTES, ENDNOTES, COMMENTS, THEME, CUSTOMXML, CUSTOMXMLPROPS, ACTIVEX, ACTIVEXBIN, GLOSSARY, CHARTS, EMBEDDINGS, SETTINGS, VBAPROJECT, FOOTER, HEADER, VBADATA }; typedef std::shared_ptr<OOXMLStream> Pointer_t; virtual ~OOXMLStream() {} @@ -229,7 +229,6 @@ public: virtual css::uno::Sequence<css::uno::Reference<css::xml::dom::XDocument> > getActiveXDomList( ) = 0; virtual css::uno::Sequence<css::uno::Reference<css::io::XInputStream> > getActiveXBinList() = 0; virtual css::uno::Sequence<css::beans::PropertyValue > getEmbeddingsList() = 0; - virtual css::uno::Sequence<css::beans::PropertyValue > getVBA() = 0; }; diff --git a/writerfilter/source/filter/WriterFilter.cxx b/writerfilter/source/filter/WriterFilter.cxx index 55c70e11eabc..df23ef38bb0c 100644 --- a/writerfilter/source/filter/WriterFilter.cxx +++ b/writerfilter/source/filter/WriterFilter.cxx @@ -236,9 +236,6 @@ sal_Bool WriterFilter::filter(const uno::Sequence< beans::PropertyValue >& aDesc // Adding the saved embedding document to document's grab bag aGrabBagProperties["OOXEmbeddings"] <<= pDocument->getEmbeddingsList(); - if (pDocument->getVBA().hasElements()) - aGrabBagProperties["OOXVBA"] <<= pDocument->getVBA(); - putPropertiesToDocumentGrabBag(aGrabBagProperties); writerfilter::ooxml::OOXMLStream::Pointer_t pVBAProjectStream(writerfilter::ooxml::OOXMLDocumentFactory::createStream(pDocStream, writerfilter::ooxml::OOXMLStream::VBAPROJECT)); @@ -257,6 +254,14 @@ sal_Bool WriterFilter::filter(const uno::Sequence< beans::PropertyValue >& aDesc oox::GraphicHelper gHelper(m_xContext, xFrame, xVbaPrjStrg); aVbaProject.importVbaProject(*xVbaPrjStrg, gHelper); + + writerfilter::ooxml::OOXMLStream::Pointer_t pVBADataStream(writerfilter::ooxml::OOXMLDocumentFactory::createStream(pDocStream, writerfilter::ooxml::OOXMLStream::VBADATA)); + if (pVBADataStream) + { + uno::Reference<io::XInputStream> xDataStream = pVBADataStream->getDocumentStream(); + if (xDataStream.is()) + aVbaProject.importVbaData(xDataStream); + } } pStream.reset(); diff --git a/writerfilter/source/ooxml/OOXMLDocumentImpl.cxx b/writerfilter/source/ooxml/OOXMLDocumentImpl.cxx index c6095737d6ba..3213d690dce8 100644 --- a/writerfilter/source/ooxml/OOXMLDocumentImpl.cxx +++ b/writerfilter/source/ooxml/OOXMLDocumentImpl.cxx @@ -39,7 +39,6 @@ #include <svx/dialogs.hrc> #include <comphelper/sequence.hxx> #include <unotools/mediadescriptor.hxx> -#include <comphelper/propertysequence.hxx> #include <iostream> #include "sfx2/objsh.hxx" @@ -497,9 +496,6 @@ void OOXMLDocumentImpl::resolve(Stream & rStream) resolveActiveXStream(rStream); - if (!mbIsSubstream) - preserveVBA(); - resolveFastSubStream(rStream, OOXMLStream::FONTTABLE); resolveFastSubStream(rStream, OOXMLStream::STYLES); resolveFastSubStream(rStream, OOXMLStream::NUMBERING); @@ -811,71 +807,6 @@ void OOXMLDocumentImpl::resolveEmbeddingsStream(const OOXMLStream::Pointer_t& pS mxEmbeddingsList = comphelper::containerToSequence(aEmbeddings); } -namespace -{ -/// Returns the target string for rType in xRelationshipAccess. -OUString getTypeTarget(const uno::Reference<embed::XRelationshipAccess>& xRelationshipAccess, const OUString& rType) -{ - uno::Sequence< uno::Sequence<beans::StringPair> > aRelations = xRelationshipAccess->getAllRelationships(); - for (const auto& rRelation : aRelations) - { - OUString aType; - OUString aTarget; - for (const auto& rPair : rRelation) - { - if (rPair.First == "Type") - aType = rPair.Second; - else if (rPair.First == "Target") - aTarget = rPair.Second; - } - - if (aType == rType) - return aTarget; - } - - return OUString(); -} -} - -void OOXMLDocumentImpl::preserveVBA() -{ - auto pOOXMLStream = dynamic_cast<OOXMLStreamImpl*>(mpStream.get()); - if (!pOOXMLStream) - return; - - uno::Reference<embed::XRelationshipAccess> xRelationshipAccess(pOOXMLStream->accessDocumentStream(), uno::UNO_QUERY); - if (!xRelationshipAccess.is()) - return; - - OUString aVBAStreamName = getTypeTarget(xRelationshipAccess, "http://schemas.microsoft.com/office/2006/relationships/vbaProject"); - if (aVBAStreamName.isEmpty()) - return; - - uno::Reference<embed::XHierarchicalStorageAccess> xStorage(pOOXMLStream->getStorage(), uno::UNO_QUERY); - if (!xStorage.is()) - return; - - OUString aPath = pOOXMLStream->getPath(); - uno::Reference<io::XStream> xStream(xStorage->openStreamElementByHierarchicalName(aPath + aVBAStreamName, embed::ElementModes::SEEKABLEREAD), uno::UNO_QUERY); - if (!xStream.is()) - return; - - xRelationshipAccess.set(xStream, uno::UNO_QUERY); - uno::Reference<io::XStream> xDataStream; - if (xRelationshipAccess.is()) - { - // Check if there is a vbaData.xml for the vbaProject.bin. - OUString aVBAData = getTypeTarget(xRelationshipAccess, "http://schemas.microsoft.com/office/2006/relationships/wordVbaData"); - if (!aVBAData.isEmpty()) - xDataStream.set(xStorage->openStreamElementByHierarchicalName(aPath + aVBAData, embed::ElementModes::SEEKABLEREAD), uno::UNO_QUERY); - } - - maVBA = comphelper::InitPropertySequence( - { - {"DataStream", uno::makeAny(xDataStream)} - }); -} - void OOXMLDocumentImpl::resolveActiveXStream(Stream & rStream) { // Resolving all ActiveX[n].xml files from ActiveX folder. @@ -1015,11 +946,6 @@ uno::Sequence<beans::PropertyValue > OOXMLDocumentImpl::getEmbeddingsList( ) return mxEmbeddingsList; } -uno::Sequence<beans::PropertyValue> OOXMLDocumentImpl::getVBA() -{ - return maVBA; -} - OOXMLDocument * OOXMLDocumentFactory::createDocument (const OOXMLStream::Pointer_t& pStream, diff --git a/writerfilter/source/ooxml/OOXMLDocumentImpl.hxx b/writerfilter/source/ooxml/OOXMLDocumentImpl.hxx index 1922e225e168..e8bca30237ce 100644 --- a/writerfilter/source/ooxml/OOXMLDocumentImpl.hxx +++ b/writerfilter/source/ooxml/OOXMLDocumentImpl.hxx @@ -54,8 +54,6 @@ class OOXMLDocumentImpl : public OOXMLDocument css::uno::Reference<css::io::XInputStream> mxEmbeddings; css::uno::Sequence < css::beans::PropertyValue > mxEmbeddingsList; std::vector<css::beans::PropertyValue> aEmbeddings; - /// List of VBA-related streams. - css::uno::Sequence<css::beans::PropertyValue> maVBA; bool mbIsSubstream; bool mbSkipImages; /// How many paragraphs equal to 1 percent? @@ -94,7 +92,6 @@ protected: void resolveActiveXStream(Stream & rStream); void resolveGlossaryStream(Stream & rStream); void resolveEmbeddingsStream(const OOXMLStream::Pointer_t& pStream); - void preserveVBA(); public: OOXMLDocumentImpl(OOXMLStream::Pointer_t const & pStream, const css::uno::Reference<css::task::XStatusIndicator>& xStatusIndicator, bool bSkipImages, const css::uno::Sequence<css::beans::PropertyValue>& rDescriptor); virtual ~OOXMLDocumentImpl() override; @@ -140,7 +137,6 @@ public: virtual css::uno::Reference<css::xml::dom::XDocument> getGlossaryDocDom() override; virtual css::uno::Sequence<css::uno::Sequence< css::uno::Any> > getGlossaryDomList() override; virtual css::uno::Sequence<css::beans::PropertyValue > getEmbeddingsList() override; - virtual css::uno::Sequence<css::beans::PropertyValue> getVBA() override; void incrementProgress(); bool IsSkipImages() { return mbSkipImages; }; diff --git a/writerfilter/source/ooxml/OOXMLStreamImpl.cxx b/writerfilter/source/ooxml/OOXMLStreamImpl.cxx index 9530654dcf3c..ddb89f17b528 100644 --- a/writerfilter/source/ooxml/OOXMLStreamImpl.cxx +++ b/writerfilter/source/ooxml/OOXMLStreamImpl.cxx @@ -172,6 +172,7 @@ bool OOXMLStreamImpl::lcl_getTarget(const uno::Reference<embed::XRelationshipAcc static const char sHeaderTypeStrict[] = "http://purl.oclc.org/ooxml/officeDocument/relationships/header"; static const char sOleObjectTypeStrict[] = "http://purl.oclc.org/ooxml/officeDocument/relationships/oleObject"; static const char sVBAProjectType[] = "http://schemas.microsoft.com/office/2006/relationships/vbaProject"; + static const char sVBADataType[] = "http://schemas.microsoft.com/office/2006/relationships/wordVbaData"; OUString sStreamType; OUString sStreamTypeStrict; @@ -182,6 +183,10 @@ bool OOXMLStreamImpl::lcl_getTarget(const uno::Reference<embed::XRelationshipAcc sStreamType = sVBAProjectType; sStreamTypeStrict = sVBAProjectType; break; + case VBADATA: + sStreamType = sVBADataType; + sStreamTypeStrict = sVBADataType; + break; case DOCUMENT: sStreamType = sDocumentType; sStreamTypeStrict = sDocumentTypeStrict; @@ -416,8 +421,22 @@ OOXMLDocumentFactory::createStream (const OOXMLStream::Pointer_t& pStream, OOXMLStream::StreamType_t nStreamType) { OOXMLStream::Pointer_t pRet; - if (OOXMLStreamImpl* pImpl = dynamic_cast<OOXMLStreamImpl *>(pStream.get())) - pRet.reset(new OOXMLStreamImpl(*pImpl, nStreamType)); + + if (nStreamType != OOXMLStream::VBADATA) + { + if (OOXMLStreamImpl* pImpl = dynamic_cast<OOXMLStreamImpl *>(pStream.get())) + pRet.reset(new OOXMLStreamImpl(*pImpl, nStreamType)); + } + else + { + // VBADATA is not a relation of the document, but of the VBAPROJECT stream. + if (OOXMLStreamImpl* pImpl = dynamic_cast<OOXMLStreamImpl *>(pStream.get())) + { + std::unique_ptr<OOXMLStreamImpl> pProject(new OOXMLStreamImpl(*pImpl, OOXMLStream::VBAPROJECT)); + pRet.reset(new OOXMLStreamImpl(*pProject, OOXMLStream::VBADATA)); + } + } + return pRet; } diff --git a/writerfilter/source/ooxml/OOXMLStreamImpl.hxx b/writerfilter/source/ooxml/OOXMLStreamImpl.hxx index cb0276d84649..aff8189b7396 100644 --- a/writerfilter/source/ooxml/OOXMLStreamImpl.hxx +++ b/writerfilter/source/ooxml/OOXMLStreamImpl.hxx @@ -80,9 +80,6 @@ public: // Giving access to mxDocumentStream. It is needed by resolving custom xml to get list of customxml's used in document. const css::uno::Reference<css::io::XStream>& accessDocumentStream() { return mxDocumentStream;} - - const css::uno::Reference<css::embed::XStorage>& getStorage() { return mxStorage; } - const OUString& getPath() { return msPath; } }; }} #endif // INCLUDED_WRITERFILTER_SOURCE_OOXML_OOXMLSTREAMIMPL_HXX |