diff options
author | Oliver Specht <oliver.specht@cib.de> | 2024-10-14 14:50:06 +0200 |
---|---|---|
committer | Thorsten Behrens <thorsten.behrens@allotropia.de> | 2024-12-10 17:18:10 +0100 |
commit | 5fb8e29926a5c0dd1ae027f05d48826399cc31a1 (patch) | |
tree | 92b333f15f3a399c8312810c2c7d3009263caf16 /sw | |
parent | 9877694e27f7e52ab8ac69c3729677cd8090e41f (diff) |
tdf#164065 load vml textbox in a group shape
Store (vml) textbox elements to determine whether to load shape text or
Writer frame. Replay elements in second step and process depending
on the outcome.
- result flag not yet available while processing
- The text shape in docx bugdoc of tdf#152878 can now be loaded as Writer frame
but with wrong size/position.
- should also be applied to drawing ml shapes currently always loaded as Writer
frame
Change-Id: I0778057f9985f5523d91a9d757e00f2968aba350
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/174902
Tested-by: Jenkins
Reviewed-by: Thorsten Behrens <thorsten.behrens@allotropia.de>
Tested-by: Gabor Kelemen <gabor.kelemen.extern@allotropia.de>
Diffstat (limited to 'sw')
-rw-r--r-- | sw/Library_sw_writerfilter.mk | 1 | ||||
-rw-r--r-- | sw/qa/extras/ooxmlexport/data/tdf164065.docx | bin | 0 -> 14817 bytes | |||
-rw-r--r-- | sw/qa/extras/ooxmlexport/ooxmlexport21.cxx | 15 | ||||
-rw-r--r-- | sw/source/writerfilter/ooxml/OOXMLFastContextHandler.cxx | 199 | ||||
-rw-r--r-- | sw/source/writerfilter/ooxml/OOXMLFastContextHandler.hxx | 12 | ||||
-rw-r--r-- | sw/source/writerfilter/ooxml/ShadowContext.cxx | 96 | ||||
-rw-r--r-- | sw/source/writerfilter/ooxml/ShadowContext.hxx | 156 |
7 files changed, 462 insertions, 17 deletions
diff --git a/sw/Library_sw_writerfilter.mk b/sw/Library_sw_writerfilter.mk index a51650ce9bf2..224b73de5cc7 100644 --- a/sw/Library_sw_writerfilter.mk +++ b/sw/Library_sw_writerfilter.mk @@ -134,6 +134,7 @@ $(eval $(call gb_Library_add_exception_objects,sw_writerfilter,\ sw/source/writerfilter/ooxml/OOXMLParserState \ sw/source/writerfilter/ooxml/OOXMLPropertySet \ sw/source/writerfilter/ooxml/OOXMLStreamImpl \ + sw/source/writerfilter/ooxml/ShadowContext \ )) $(eval $(call gb_Library_add_generated_exception_objects,sw_writerfilter,\ diff --git a/sw/qa/extras/ooxmlexport/data/tdf164065.docx b/sw/qa/extras/ooxmlexport/data/tdf164065.docx Binary files differnew file mode 100644 index 000000000000..b66a6cdb2da4 --- /dev/null +++ b/sw/qa/extras/ooxmlexport/data/tdf164065.docx diff --git a/sw/qa/extras/ooxmlexport/ooxmlexport21.cxx b/sw/qa/extras/ooxmlexport/ooxmlexport21.cxx index 207568ee8b76..0447f0b78f12 100644 --- a/sw/qa/extras/ooxmlexport/ooxmlexport21.cxx +++ b/sw/qa/extras/ooxmlexport/ooxmlexport21.cxx @@ -17,6 +17,7 @@ #include <com/sun/star/text/XDocumentIndex.hpp> #include <com/sun/star/text/XTextTable.hpp> #include <com/sun/star/text/XTextField.hpp> +#include <com/sun/star/table/XCellRange.hpp> #include <com/sun/star/style/LineSpacing.hpp> #include <com/sun/star/style/LineSpacingMode.hpp> #include <com/sun/star/packages/zip/ZipFileAccess.hpp> @@ -1189,6 +1190,20 @@ CPPUNIT_TEST_FIXTURE(Test, testTdf146269) } } +CPPUNIT_TEST_FIXTURE(Test, testTdf164065) +{ + loadAndSave("tdf164065.docx"); + CPPUNIT_ASSERT_EQUAL(1, getShapes()); + + uno::Reference<text::XTextTablesSupplier> xTextTablesSupplier(mxComponent, uno::UNO_QUERY); + uno::Reference<container::XIndexAccess> xTables(xTextTablesSupplier->getTextTables(), + uno::UNO_QUERY); + CPPUNIT_ASSERT_EQUAL(sal_Int32(1), xTables->getCount()); + uno::Reference<table::XCellRange> xTable(xTables->getByIndex(0), uno::UNO_QUERY); + uno::Reference<text::XText> xCell(xTable->getCellByPosition(0, 0), uno::UNO_QUERY); + CPPUNIT_ASSERT_EQUAL(u"a"_ustr, xCell->getString()); +} + } // end of anonymous namespace CPPUNIT_PLUGIN_IMPLEMENT(); diff --git a/sw/source/writerfilter/ooxml/OOXMLFastContextHandler.cxx b/sw/source/writerfilter/ooxml/OOXMLFastContextHandler.cxx index 046d8c6aacb0..ab01166040fe 100644 --- a/sw/source/writerfilter/ooxml/OOXMLFastContextHandler.cxx +++ b/sw/source/writerfilter/ooxml/OOXMLFastContextHandler.cxx @@ -25,6 +25,7 @@ #include <oox/mathml/imexport.hxx> #include <oox/token/namespaces.hxx> #include <oox/shape/ShapeFilterBase.hxx> +#include <oox/vml/vmlshapecontext.hxx> #include <sal/log.hxx> #include <comphelper/embeddedobjectcontainer.hxx> #include <comphelper/propertyvalue.hxx> @@ -42,6 +43,7 @@ #include "OOXMLPropertySet.hxx" #include <dmapper/GraphicHelpers.hxx> #include <unodraw.hxx> +#include "ShadowContext.hxx" const sal_Unicode uCR = 0xd; const sal_Unicode uFtnEdnRef = 0x2; @@ -1973,7 +1975,26 @@ OOXMLFastContextHandlerWrapper::OOXMLFastContextHandlerWrapper rtl::Reference<OOXMLFastContextHandlerShape> const & xShapeHandler) : OOXMLFastContextHandler(pParent), mxWrappedContext(xContext), - mxShapeHandler(xShapeHandler) + mxShapeHandler(xShapeHandler), + mbIsWriterFrameDetected(false), + mbIsReplayTextBox(false) +{ + setId(pParent->getId()); + setToken(pParent->getToken()); + setPropertySet(pParent->getPropertySet()); +} + +OOXMLFastContextHandlerWrapper::OOXMLFastContextHandlerWrapper(OOXMLFastContextHandler * pParent, + rtl::Reference<ShadowContext> const & xShadowContext, + uno::Reference<XFastContextHandler> const& xParentContext, + rtl::Reference<OOXMLFastContextHandlerShape> const & xShapeHandler) + : OOXMLFastContextHandler(pParent), + mxWrappedContext(xShadowContext), + mxShapeHandler(xShapeHandler), + mxShadowContext(xShadowContext), + mxReplayParentContext(xParentContext), + mbIsWriterFrameDetected(false), + mbIsReplayTextBox(false) { setId(pParent->getId()); setToken(pParent->getToken()); @@ -2001,6 +2022,114 @@ void SAL_CALL OOXMLFastContextHandlerWrapper::endUnknownElement mxWrappedContext->endUnknownElement(Namespace, Name); } +void SAL_CALL OOXMLFastContextHandlerWrapper::endFastElement(::sal_Int32 Element) +{ + OOXMLFastContextHandler::endFastElement(Element); + if (mxShadowContext.is()) + { + mxWrappedContext = mxReplayParentContext; + mbIsReplayTextBox = true; + mbIsWriterFrameDetected = mxShadowContext->isWriterFrame(); + sal_uInt16 nLevel = mxShadowContext->getElementLevel(); + if (!nLevel) + { + std::deque<CallData>& callDataDeque = mxShadowContext->getCallData(); + std::deque<uno::Reference<xml::sax::XFastContextHandler>> aLocalHandlers; + for (auto callDataIt = callDataDeque.begin(); callDataIt != callDataDeque.end(); ++callDataIt) + { + switch (callDataIt->getType()) + { + case Init: + { + sal_Int32 nElement = callDataIt->getElement(); + css::uno::Reference<css::xml::sax::XFastAttributeList> rAttribs + = callDataIt->getAttributes(); + if (mbIsWriterFrameDetected) + { + oox::vml::ShapeContext* pShapeContext = dynamic_cast<oox::vml::ShapeContext*>(mxWrappedContext.get()); + if (pShapeContext) + pShapeContext->setWriterShape(); + } + uno::Reference< xml::sax::XFastContextHandler > newWrapper = lcl_createFastChildContext(nElement, rAttribs); + static_cast<OOXMLFastContextHandlerWrapper*>(newWrapper.get())->mbIsWriterFrameDetected = mbIsWriterFrameDetected; + aLocalHandlers.push_back(newWrapper); + } + break; + case ElementAttr: + { + sal_Int32 nElement = callDataIt->getElement(); + css::uno::Reference<css::xml::sax::XFastAttributeList> rAttrs + = callDataIt->getAttributes(); + auto xHandler = aLocalHandlers.back(); + if (xHandler) + xHandler->startFastElement(nElement, rAttrs); + } + break; + case Char: + { + const ::rtl::OUString& chars = callDataIt->getChars(); + auto xHandler = aLocalHandlers.back(); + if (xHandler) + xHandler->characters(chars); + } + break; + case EndElementAttr: + { + sal_Int32 nElement = callDataIt->getElement(); + auto xHandler = aLocalHandlers.back(); + if (xHandler) + xHandler->endFastElement(nElement); + aLocalHandlers.pop_back(); + } + break; + case Unknown: + { + const ::rtl::OUString& rNameSpace = callDataIt->getUnknownNameSpace(); + const ::rtl::OUString& rElement = callDataIt->getUnknownElement(); + css::uno::Reference<css::xml::sax::XFastAttributeList> rAttrs + = callDataIt->getAttributes(); + auto xHandler = aLocalHandlers.back(); + if (xHandler) + xHandler->startUnknownElement(rNameSpace, rElement, rAttrs); + } + break; + case EndUnknown: + { + const ::rtl::OUString& rNameSpace = callDataIt->getUnknownNameSpace(); + const ::rtl::OUString& rElement = callDataIt->getUnknownElement(); + auto xHandler = aLocalHandlers.back(); + if (xHandler) + xHandler->endUnknownElement(rNameSpace, rElement); + aLocalHandlers.pop_back(); + } + break; + case ElementContext: + { + sal_Int32 nElement = callDataIt->getElement(); + css::uno::Reference<css::xml::sax::XFastAttributeList> rAttrs + = callDataIt->getAttributes(); + uno::Reference< xml::sax::XFastContextHandler > newContext = aLocalHandlers.back()->createFastChildContext(nElement, rAttrs); + if (nElement == Token_t(NMSP_vml | XML_textbox)) + static_cast<OOXMLFastContextHandlerWrapper*>(newContext.get())->mbIsWriterFrameDetected = mbIsWriterFrameDetected; + aLocalHandlers.push_back(newContext); + } + break; + case UnknownContext: + { + const ::rtl::OUString& rNameSpace = callDataIt->getUnknownNameSpace(); + const ::rtl::OUString& rElement = callDataIt->getUnknownElement(); + css::uno::Reference<css::xml::sax::XFastAttributeList> rAttrs + = callDataIt->getAttributes(); + uno::Reference< xml::sax::XFastContextHandler > newContext = aLocalHandlers.back()->createUnknownChildContext(rNameSpace, rElement, rAttrs); + aLocalHandlers.push_back(newContext); + } + break; + } + } + } + } +} + uno::Reference< xml::sax::XFastContextHandler > SAL_CALL OOXMLFastContextHandlerWrapper::createUnknownChildContext (const OUString & Namespace, @@ -2051,12 +2180,17 @@ void OOXMLFastContextHandlerWrapper::lcl_startFastElement { if (mxWrappedContext.is()) mxWrappedContext->startFastElement(Element, Attribs); - - if (mxShapeHandler->isDMLGroupShape() - && (Element == Token_t(NMSP_wps | XML_txbx) - || Element == Token_t(NMSP_wps | XML_linkedTxbx))) - { - mpStream->startTextBoxContent(); + if (!mxShadowContext.is()) + { + bool bInTokens = mMyTokens.find(Element) != mMyTokens.end(); + if ((mxShapeHandler->isDMLGroupShape() + && (Element == Token_t(NMSP_wps | XML_txbx) + || Element == Token_t(NMSP_wps | XML_linkedTxbx))) + //TODO: why check for bInTokens + || (!bInTokens && mbIsWriterFrameDetected && Element == Token_t(NMSP_vml | XML_textbox))) + { + mpStream->startTextBoxContent(); + } } } @@ -2066,11 +2200,16 @@ void OOXMLFastContextHandlerWrapper::lcl_endFastElement if (mxWrappedContext.is()) mxWrappedContext->endFastElement(Element); - if (mxShapeHandler->isDMLGroupShape() - && (Element == Token_t(NMSP_wps | XML_txbx) - || Element == Token_t(NMSP_wps | XML_linkedTxbx))) + if (!mxShadowContext.is()) { - mpStream->endTextBoxContent(); + bool bInTokens = mMyTokens.find(Element) != mMyTokens.end(); + if ((mxShapeHandler->isDMLGroupShape() + && (Element == Token_t(NMSP_wps | XML_txbx) + || Element == Token_t(NMSP_wps | XML_linkedTxbx))) + || (!bInTokens && mbIsWriterFrameDetected && Element == Token_t(NMSP_vml | XML_textbox))) + { + mpStream->endTextBoxContent(); + } } } @@ -2080,6 +2219,10 @@ OOXMLFastContextHandlerWrapper::lcl_createFastChildContext const uno::Reference< xml::sax::XFastAttributeList > & Attribs) { uno::Reference< xml::sax::XFastContextHandler > xResult; + if (mxShadowContext.is() && !mbIsReplayTextBox) + { + return mxShadowContext->createFastChildContext(Element, Attribs); + } bool bInNamespaces = mMyNamespaces.find(oox::getNamespace(Element)) != mMyNamespaces.end(); bool bInTokens = mMyTokens.find( Element ) != mMyTokens.end( ); @@ -2100,11 +2243,34 @@ OOXMLFastContextHandlerWrapper::lcl_createFastChildContext } else if (mxWrappedContext.is() && !bSkipImages) { - rtl::Reference<OOXMLFastContextHandlerWrapper> pWrapper = - new OOXMLFastContextHandlerWrapper - (this, mxWrappedContext->createFastChildContext(Element, Attribs), - mxShapeHandler); - pWrapper->mMyNamespaces = mMyNamespaces; + rtl::Reference<OOXMLFastContextHandlerWrapper> pWrapper; + if (Element == (NMSP_vml | XML_textbox) && !mbIsReplayTextBox) + { + //TODO: change handling of drawingml, currently Writer frame only + rtl::Reference<ShadowContext> xShadowContext + = new ShadowContext(Element, Attribs); + pWrapper = new OOXMLFastContextHandlerWrapper(this, xShadowContext, mxWrappedContext, mxShapeHandler); + pWrapper->mMyNamespaces = mMyNamespaces; + //don't send shape here + bInTokens = false; + } + else + { + pWrapper = + new OOXMLFastContextHandlerWrapper + (this, mxWrappedContext->createFastChildContext(Element, Attribs), + mxShapeHandler); + if (mbIsWriterFrameDetected) + { + pWrapper->addNamespace(NMSP_doc); + pWrapper->addNamespace(NMSP_vmlWord); + pWrapper->addNamespace(NMSP_vmlOffice); + } + else + { + pWrapper->mMyNamespaces = mMyNamespaces; + } + } pWrapper->mMyTokens = mMyTokens; pWrapper->setPropertySet(getPropertySet()); xResult.set(pWrapper); @@ -2243,7 +2409,6 @@ Token_t OOXMLFastContextHandlerWrapper::getToken() const return nResult; } - /* class OOXMLFastContextHandlerLinear */ diff --git a/sw/source/writerfilter/ooxml/OOXMLFastContextHandler.hxx b/sw/source/writerfilter/ooxml/OOXMLFastContextHandler.hxx index 03a4d40e5c2f..49abfde529ce 100644 --- a/sw/source/writerfilter/ooxml/OOXMLFastContextHandler.hxx +++ b/sw/source/writerfilter/ooxml/OOXMLFastContextHandler.hxx @@ -27,6 +27,7 @@ #include <rtl/ref.hxx> #include "OOXMLParserState.hxx" #include "OOXMLPropertySet.hxx" +#include "ShadowContext.hxx" namespace writerfilter::ooxml { @@ -494,9 +495,14 @@ public: OOXMLFastContextHandlerWrapper(OOXMLFastContextHandler * pParent, css::uno::Reference<css::xml::sax::XFastContextHandler> const & xContext, rtl::Reference<OOXMLFastContextHandlerShape> const & xShapeHandler); + OOXMLFastContextHandlerWrapper(OOXMLFastContextHandler * pParent, + rtl::Reference<ShadowContext> const & xContext, + css::uno::Reference<css::xml::sax::XFastContextHandler> const & xParentContext, + rtl::Reference<OOXMLFastContextHandlerShape> const & xShapeHandler); virtual ~OOXMLFastContextHandlerWrapper() override; // css::xml::sax::XFastContextHandler: + virtual void SAL_CALL endFastElement( ::sal_Int32 Element ) override; virtual void SAL_CALL startUnknownElement(const OUString & Namespace, const OUString & Name, const css::uno::Reference< css::xml::sax::XFastAttributeList > & Attribs) override; virtual void SAL_CALL endUnknownElement(const OUString & Namespace, const OUString & Name) override; @@ -532,12 +538,18 @@ protected: virtual void setToken(Token_t nToken) override; virtual Token_t getToken() const override; + bool isWriterFrameDetected() const { return mbIsWriterFrameDetected;} + private: css::uno::Reference<css::xml::sax::XFastContextHandler> mxWrappedContext; rtl::Reference<OOXMLFastContextHandlerShape> mxShapeHandler; std::set<Id> mMyNamespaces; std::set<Token_t> mMyTokens; OOXMLPropertySet::Pointer_t mpPropertySet; + rtl::Reference<ShadowContext> const mxShadowContext; + css::uno::Reference<css::xml::sax::XFastContextHandler> mxReplayParentContext; + bool mbIsWriterFrameDetected; + bool mbIsReplayTextBox; OOXMLFastContextHandler * getFastContextHandler() const; }; diff --git a/sw/source/writerfilter/ooxml/ShadowContext.cxx b/sw/source/writerfilter/ooxml/ShadowContext.cxx new file mode 100644 index 000000000000..d850092c9adc --- /dev/null +++ b/sw/source/writerfilter/ooxml/ShadowContext.cxx @@ -0,0 +1,96 @@ +/* -*- 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/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#include "ShadowContext.hxx" +#include <ooxml/resourceids.hxx> +#include <oox/token/namespaces.hxx> + +namespace writerfilter::ooxml +{ +using namespace ::com::sun::star; +using namespace oox; +using namespace ::com::sun::star::xml::sax; + +ShadowContext::ShadowContext(::sal_Int32 nElement, + const uno::Reference<XFastAttributeList>& rAttribs) + : m_nElementLevel(0) + , m_bImportAsWriterFrame(false) +{ + CallData callData(m_nElementLevel, nElement, rAttribs, CallDataType::Init); + m_aCallDataDeque.push_back(callData); +} +ShadowContext::~ShadowContext() {} + +void ShadowContext::startFastElement( + ::sal_Int32 nElement, + const ::css::uno::Reference<::css::xml::sax::XFastAttributeList>& rAttribs) +{ + ++m_nElementLevel; + CallData callData(m_nElementLevel, nElement, rAttribs, CallDataType::ElementAttr); + m_aCallDataDeque.push_back(callData); + if (nElement == (oox::NMSP_doc | oox::XML_tbl)) + { + m_bImportAsWriterFrame = true; + } +} + +void ShadowContext::startUnknownElement( + const ::rtl::OUString& rNamespace, const ::rtl::OUString& rElement, + const ::css::uno::Reference<::css::xml::sax::XFastAttributeList>& rAttribs) +{ + ++m_nElementLevel; + CallData callData(m_nElementLevel, rNamespace, rElement, rAttribs, CallDataType::Unknown); + m_aCallDataDeque.push_back(callData); +} +void ShadowContext::endFastElement(::sal_Int32 nElement) +{ + --m_nElementLevel; + CallData callData(m_nElementLevel, nElement); + m_aCallDataDeque.push_back(callData); +} +void ShadowContext::endUnknownElement(const ::rtl::OUString& rNamespace, + const ::rtl::OUString& rElement) +{ + --m_nElementLevel; + CallData callData(m_nElementLevel, rNamespace, rElement); + m_aCallDataDeque.push_back(callData); +} +::css::uno::Reference<::css::xml::sax::XFastContextHandler> ShadowContext::createFastChildContext( + ::sal_Int32 nElement, + const ::css::uno::Reference<::css::xml::sax::XFastAttributeList>& rAttribs) +{ + CallData callData(m_nElementLevel, nElement, rAttribs, CallDataType::ElementContext); + m_aCallDataDeque.push_back(callData); + return this; +} +::css::uno::Reference<::css::xml::sax::XFastContextHandler> +ShadowContext::createUnknownChildContext( + const ::rtl::OUString& rNamespace, const ::rtl::OUString& rElement, + const ::css::uno::Reference<::css::xml::sax::XFastAttributeList>& rAttribs) +{ + CallData callData(m_nElementLevel, rNamespace, rElement, rAttribs, + CallDataType::UnknownContext); + m_aCallDataDeque.push_back(callData); + return this; +} +void ShadowContext::characters(const ::rtl::OUString& aChars) +{ + CallData callData(m_nElementLevel, aChars); + m_aCallDataDeque.push_back(callData); +} +} //namespace diff --git a/sw/source/writerfilter/ooxml/ShadowContext.hxx b/sw/source/writerfilter/ooxml/ShadowContext.hxx new file mode 100644 index 000000000000..d7e389d10abd --- /dev/null +++ b/sw/source/writerfilter/ooxml/ShadowContext.hxx @@ -0,0 +1,156 @@ +/* -*- 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/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#pragma once + +#include <cppuhelper/implbase.hxx> +#include <com/sun/star/xml/sax/XFastContextHandler.hpp> +#include <sax/fastattribs.hxx> +#include <oox/helper/attributelist.hxx> +#include <oox/core/contexthandler.hxx> +#include <queue> + +namespace writerfilter::ooxml +{ +enum CallDataType +{ + Init, + ElementAttr, + Char, + EndElementAttr, + Unknown, + EndUnknown, + ElementContext, + UnknownContext +}; + +class CallData +{ + sal_uInt32 m_nLevel; + CallDataType m_eType; + sal_Int32 m_nElement; + css::uno::Reference<css::xml::sax::XFastAttributeList> m_aAttributes; + + //char + ::rtl::OUString m_aChars; + + //unknwon + ::rtl::OUString m_sNameSpace; + ::rtl::OUString m_sElement; + +public: + //Start unknown element or context + CallData(sal_uInt32 nLevel, const ::rtl::OUString& rNameSpace, const ::rtl::OUString& rElement, + const css::uno::Reference<css::xml::sax::XFastAttributeList>& rAttributes, + CallDataType eType) + : m_nLevel(nLevel) + , m_eType(eType) + , m_aAttributes(new sax_fastparser::FastAttributeList(rAttributes)) + , m_sNameSpace(rNameSpace) + , m_sElement(rElement) + { + } + + //end unknown element + CallData(sal_uInt32 nLevel, const ::rtl::OUString& rNameSpace, const ::rtl::OUString& rElement) + : m_nLevel(nLevel) + , m_eType(CallDataType::EndUnknown) + , m_sNameSpace(rNameSpace) + , m_sElement(rElement) + { + } + + // start fast element + CallData(sal_uInt32 nLevel, sal_Int32 nElement, + const css::uno::Reference<css::xml::sax::XFastAttributeList>& rAttributes, + CallDataType eType) + : m_nLevel(nLevel) + , m_eType(eType) + , m_nElement(nElement) + , m_aAttributes(new sax_fastparser::FastAttributeList(rAttributes)) + { + } + + // end fast element + CallData(sal_uInt32 nLevel, sal_Int32 nElement) + : m_nLevel(nLevel) + , m_eType(CallDataType::EndElementAttr) + , m_nElement(nElement) + { + } + + //chars + CallData(sal_uInt32 nLevel, const ::rtl::OUString& rChars) + : m_nLevel(nLevel) + , m_eType(CallDataType::Char) + , m_aChars(rChars) + { + } + + CallData(CallData const&) = default; + + sal_uInt32 getLevel() const { return m_nLevel; } + CallDataType getType() const { return m_eType; } + sal_Int32 getElement() const { return m_nElement; } + const ::rtl::OUString& getChars() { return m_aChars; } + css::uno::Reference<css::xml::sax::XFastAttributeList> getAttributes() const + { + return m_aAttributes; + } + const ::rtl::OUString& getUnknownNameSpace() const { return m_sNameSpace; } + const ::rtl::OUString& getUnknownElement() const { return m_sElement; } +}; +class ShadowContext : public ::oox::core::ContextHandler_BASE +{ +public: + explicit ShadowContext(::sal_Int32 Element, + const css::uno::Reference<css::xml::sax::XFastAttributeList>& rAttribs); + virtual ~ShadowContext() override; + + //XFastContextHandler + virtual void SAL_CALL startFastElement( + ::sal_Int32 Element, + const ::css::uno::Reference<::css::xml::sax::XFastAttributeList>& Attribs) override; + virtual void SAL_CALL startUnknownElement( + const ::rtl::OUString& Namespace, const ::rtl::OUString& Name, + const ::css::uno::Reference<::css::xml::sax::XFastAttributeList>& Attribs) override; + virtual void SAL_CALL endFastElement(::sal_Int32 Element) override; + virtual void SAL_CALL endUnknownElement(const ::rtl::OUString& Namespace, + const ::rtl::OUString& Name) override; + virtual ::css::uno::Reference<::css::xml::sax::XFastContextHandler> + SAL_CALL createFastChildContext( + ::sal_Int32 Element, + const ::css::uno::Reference<::css::xml::sax::XFastAttributeList>& Attribs) override; + virtual ::css::uno::Reference<::css::xml::sax::XFastContextHandler> + SAL_CALL createUnknownChildContext( + const ::rtl::OUString& Namespace, const ::rtl::OUString& Name, + const ::css::uno::Reference<::css::xml::sax::XFastAttributeList>& Attribs) override; + virtual void SAL_CALL characters(const ::rtl::OUString& aChars) override; + + sal_uInt16 getElementLevel() const { return m_nElementLevel; } + bool isWriterFrame() const { return m_bImportAsWriterFrame; } + + std::deque<CallData>& getCallData() { return m_aCallDataDeque; } + +private: + std::deque<CallData> m_aCallDataDeque; + sal_uInt16 m_nElementLevel; + bool m_bImportAsWriterFrame; +}; +} |