include/oox/drawingml/diagram/diagram.hxx | 10 ++- include/oox/drawingml/shape.hxx | 5 + include/svx/DiagramDataInterface.hxx | 38 ++++++++++++++ include/svx/svdobj.hxx | 4 + oox/source/drawingml/diagram/diagram.cxx | 79 ++++++++++++++---------------- oox/source/drawingml/diagram/diagram.hxx | 8 ++- oox/source/drawingml/shape.cxx | 9 +++ sd/source/ui/view/drviews3.cxx | 3 - svx/source/svdraw/svdobj.cxx | 12 ++++ 9 files changed, 118 insertions(+), 50 deletions(-)
New commits: commit 8a029e4a39d9afda5334bc546338645241f656d6 Author: Grzegorz Araminowicz <grzegorz.araminow...@collabora.com> AuthorDate: Mon Jul 22 15:04:15 2019 +0200 Commit: Miklos Vajna <vmik...@collabora.com> CommitDate: Mon Aug 5 09:52:00 2019 +0200 SmartArt: store diagram data model in SdrObject It will allow modifying loaded diagram and exporting it. This data is used for regenerating diagram instead of parsing xml fragment every time. Also provided an interface for UI that can be extended to show, add and remove nodes from data model. It is stored as SdrObject field because diagram top-level shape is group shape. Item set doesn't exist for them and storing data in child shapes is not possible here because children are removed and recreated on every diagram reload. Change-Id: I84e5ec955f638b254fef9ef9d1731ca7938982b7 Reviewed-on: https://gerrit.libreoffice.org/76121 Tested-by: Jenkins Reviewed-by: Miklos Vajna <vmik...@collabora.com> diff --git a/include/oox/drawingml/diagram/diagram.hxx b/include/oox/drawingml/diagram/diagram.hxx index a449014e4be9..a5f69b4d56bd 100644 --- a/include/oox/drawingml/diagram/diagram.hxx +++ b/include/oox/drawingml/diagram/diagram.hxx @@ -23,13 +23,16 @@ #include <rtl/ustring.hxx> #include <oox/core/xmlfilterbase.hxx> #include <oox/drawingml/drawingmltypes.hxx> +#include <svx/svdobj.hxx> -#include <com/sun/star/drawing/XShape.hpp> #include <com/sun/star/uno/Reference.hxx> #include <com/sun/star/xml/dom/XDocument.hpp> namespace oox { namespace drawingml { +class DiagramData; +typedef std::shared_ptr<DiagramData> DiagramDataPtr; + /** load diagram data, and put resulting graphic into shape This method loads the diagram data fragments from the given paths, @@ -45,14 +48,13 @@ void loadDiagram( ShapePtr const & pShape, const oox::core::Relations& rRelations ); void loadDiagram(ShapePtr const& pShape, - const css::uno::Reference<css::xml::dom::XDocument>& dataDom, + DiagramDataPtr pDiagramData, const css::uno::Reference<css::xml::dom::XDocument>& layoutDom, const css::uno::Reference<css::xml::dom::XDocument>& styleDom, const css::uno::Reference<css::xml::dom::XDocument>& colorDom, core::XmlFilterBase& rFilter); -OOX_DLLPUBLIC void reloadDiagram(css::uno::Reference<css::drawing::XShape>& rXShape, - core::XmlFilterBase& rFilter); +OOX_DLLPUBLIC void reloadDiagram(SdrObject* pObj, core::XmlFilterBase& rFilter); } } diff --git a/include/oox/drawingml/shape.hxx b/include/oox/drawingml/shape.hxx index 5aa6f00318a8..d55e92ae5058 100644 --- a/include/oox/drawingml/shape.hxx +++ b/include/oox/drawingml/shape.hxx @@ -77,6 +77,9 @@ struct ShapeStyleRef typedef ::std::map< sal_Int32, ShapeStyleRef > ShapeStyleRefMap; +class DiagramData; +typedef std::shared_ptr<DiagramData> DiagramDataPtr; + /** Additional information for a chart embedded in a drawing shape. */ struct ChartShapeInfo { @@ -202,6 +205,7 @@ public: const css::uno::Sequence<css::beans::PropertyValue> & getDiagramDoms() { return maDiagramDoms; } void setDiagramDoms(const css::uno::Sequence<css::beans::PropertyValue>& rDiagramDoms) { maDiagramDoms = rDiagramDoms; } + void setDiagramData(const DiagramDataPtr& pDiagramData) { mpDiagramData = pDiagramData; } css::uno::Sequence< css::uno::Sequence< css::uno::Any > >resolveRelationshipsOfTypeFromOfficeDoc( core::XmlFilterBase& rFilter, const OUString& sFragment, const OUString& sType ); void setLinkedTxbxAttributes(const LinkedTxbxAttr& rhs){ maLinkedTxbxAttr = rhs; }; @@ -352,6 +356,7 @@ private: bool mbHasLinkedTxbx; // this text box has linked text box ? css::uno::Sequence<css::beans::PropertyValue> maDiagramDoms; + DiagramDataPtr mpDiagramData; /// Z-Order. sal_Int32 mnZOrder = 0; diff --git a/include/svx/DiagramDataInterface.hxx b/include/svx/DiagramDataInterface.hxx new file mode 100644 index 000000000000..439f2efeefdb --- /dev/null +++ b/include/svx/DiagramDataInterface.hxx @@ -0,0 +1,38 @@ +/* -*- 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 . + */ +#ifndef INCLUDED_SVX_DIAGRAMDATAINTERFACE_HXX +#define INCLUDED_SVX_DIAGRAMDATAINTERFACE_HXX + +#include <rtl/ustring.h> +#include <sal/types.h> + +/// Interface class to access diagram data for UI +class SAL_NO_VTABLE SAL_DLLPUBLIC_RTTI DiagramDataInterface +{ +public: + // get text representation of data tree + virtual OUString getString() const = 0; + +protected: + ~DiagramDataInterface() throw() {} +}; + +#endif // INCLUDED_SVX_DIAGRAMDATAINTERFACE_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/svx/svdobj.hxx b/include/svx/svdobj.hxx index 36f29f9d9fcf..0b1e5c3a832b 100644 --- a/include/svx/svdobj.hxx +++ b/include/svx/svdobj.hxx @@ -28,6 +28,7 @@ #include <svl/lstner.hxx> #include <svl/poolitem.hxx> #include <svl/typedwhich.hxx> +#include <svx/DiagramDataInterface.hxx> #include <svx/svdtypes.hxx> #include <svx/svxdllapi.h> #include <svx/shapeproperty.hxx> @@ -375,6 +376,9 @@ public: const double* GetRelativeHeight() const; sal_Int16 GetRelativeHeightRelation() const; + void SetDiagramData(std::shared_ptr<DiagramDataInterface> pDiagramData); + std::shared_ptr<DiagramDataInterface> GetDiagramData() const; + /// @param bNotMyself = true: set only ObjList to dirty, don't mark this object as dirty. /// /// This is needed for instance for NbcMove, because usually one moves SnapRect and aOutRect diff --git a/oox/source/drawingml/diagram/diagram.cxx b/oox/source/drawingml/diagram/diagram.cxx index 0edd94a874be..2c0c47899ffa 100644 --- a/oox/source/drawingml/diagram/diagram.cxx +++ b/oox/source/drawingml/diagram/diagram.cxx @@ -22,6 +22,7 @@ #include <com/sun/star/awt/Point.hpp> #include <com/sun/star/awt/Size.hpp> #include <com/sun/star/beans/XPropertySet.hpp> +#include <com/sun/star/drawing/XShape.hpp> #include <com/sun/star/drawing/XShapes.hpp> #include <com/sun/star/xml/dom/XDocument.hpp> #include <com/sun/star/xml/sax/XFastSAXSerializable.hpp> @@ -37,6 +38,8 @@ #include <oox/ppt/pptshape.hxx> #include <oox/token/namespaces.hxx> #include <basegfx/matrix/b2dhommatrix.hxx> +#include <svx/svdpage.hxx> +#include <svx/DiagramDataInterface.hxx> #include "diagramlayoutatoms.hxx" #include "layoutatomvisitors.hxx" @@ -177,7 +180,7 @@ static void sortChildrenByZOrder(const ShapePtr& pShape) sortChildrenByZOrder(rChild); } -void Diagram::build( ) +void DiagramData::build() { // build name-object maps #ifdef DEBUG_OOX_DIAGRAM @@ -185,7 +188,7 @@ void Diagram::build( ) output << "digraph datatree {" << std::endl; #endif - dgm::Points& rPoints = getData()->getPoints(); + dgm::Points& rPoints = getPoints(); for (auto & point : rPoints) { #ifdef DEBUG_OOX_DIAGRAM @@ -242,20 +245,20 @@ void Diagram::build( ) #endif } - const bool bInserted1=getData()->getPointNameMap().insert( + const bool bInserted1 = getPointNameMap().insert( std::make_pair(point.msModelId,&point)).second; - SAL_WARN_IF(!bInserted1, "oox.drawingml", "Diagram::build(): non-unique point model id"); + SAL_WARN_IF(!bInserted1, "oox.drawingml", "DiagramData::build(): non-unique point model id"); if( !point.msPresentationLayoutName.isEmpty() ) { DiagramData::PointsNameMap::value_type::second_type& rVec= - getData()->getPointsPresNameMap()[point.msPresentationLayoutName]; + getPointsPresNameMap()[point.msPresentationLayoutName]; rVec.push_back(&point); } } - const dgm::Connections& rConnections = getData()->getConnections(); + const dgm::Connections& rConnections = getConnections(); for (auto const& connection : rConnections) { #ifdef DEBUG_OOX_DIAGRAM @@ -307,25 +310,25 @@ void Diagram::build( ) << ";" << std::endl; #endif - const bool bInserted1=getData()->getConnectionNameMap().insert( + const bool bInserted1 = getConnectionNameMap().insert( std::make_pair(connection.msModelId,&connection)).second; - SAL_WARN_IF(!bInserted1, "oox.drawingml", "Diagram::build(): non-unique connection model id"); + SAL_WARN_IF(!bInserted1, "oox.drawingml", "DiagramData::build(): non-unique connection model id"); if( connection.mnType == XML_presOf ) { - DiagramData::StringMap::value_type::second_type& rVec=getData()->getPresOfNameMap()[connection.msDestId]; + DiagramData::StringMap::value_type::second_type& rVec = getPresOfNameMap()[connection.msDestId]; rVec[connection.mnDestOrder] = { connection.msSourceId, sal_Int32(0) }; } } // assign outline levels - DiagramData::StringMap& rStringMap = getData()->getPresOfNameMap(); + DiagramData::StringMap& rStringMap = getPresOfNameMap(); for (auto & elemPresOf : rStringMap) { for (auto & elem : elemPresOf.second) { - const sal_Int32 nDepth = calcDepth(elem.second.msSourceId, getData()->getConnections()); + const sal_Int32 nDepth = calcDepth(elem.second.msSourceId, getConnections()); elem.second.mnDepth = nDepth != 0 ? nDepth : -1; } } @@ -336,9 +339,6 @@ void Diagram::build( ) void Diagram::addTo( const ShapePtr & pParentShape ) { - // collect data, init maps - build( ); - if (pParentShape->getSize().Width == 0 || pParentShape->getSize().Height == 0) SAL_WARN("oox.drawingml", "Diagram cannot be correctly laid out. Size: " << pParentShape->getSize().Width << "x" << pParentShape->getSize().Height); @@ -368,8 +368,6 @@ void Diagram::addTo( const ShapePtr & pParentShape ) pBackground->setLocked(true); auto& aChildren = pParentShape->getChildren(); aChildren.insert(aChildren.begin(), pBackground); - - pParentShape->setDiagramDoms( getDomsAsPropertyValues() ); } uno::Sequence<beans::PropertyValue> Diagram::getDomsAsPropertyValues() const @@ -584,12 +582,17 @@ void loadDiagram( ShapePtr const & pShape, } } + // collect data, init maps + pData->build(); + // diagram loaded. now lump together & attach to shape pDiagram->addTo(pShape); + pShape->setDiagramData(pData); + pShape->setDiagramDoms(pDiagram->getDomsAsPropertyValues()); } void loadDiagram(ShapePtr const& pShape, - const uno::Reference<xml::dom::XDocument>& dataDom, + DiagramDataPtr pDiagramData, const uno::Reference<xml::dom::XDocument>& layoutDom, const uno::Reference<xml::dom::XDocument>& styleDom, const uno::Reference<xml::dom::XDocument>& colorDom, @@ -597,22 +600,11 @@ void loadDiagram(ShapePtr const& pShape, { DiagramPtr pDiagram(new Diagram); - DiagramDataPtr pData(new DiagramData()); - pDiagram->setData(pData); + pDiagram->setData(pDiagramData); DiagramLayoutPtr pLayout(new DiagramLayout(*pDiagram)); pDiagram->setLayout(pLayout); - - // data - if (dataDom.is()) - { - rtl::Reference<core::FragmentHandler> xRefDataModel( - new DiagramDataFragmentHandler(rFilter, OUString(), pData)); - - importFragment(rFilter, dataDom, "OOXData", pDiagram, xRefDataModel); - } - // layout if (layoutDom.is()) { @@ -644,12 +636,17 @@ void loadDiagram(ShapePtr const& pShape, pDiagram->addTo(pShape); } -void reloadDiagram(css::uno::Reference<css::drawing::XShape>& rXShape, - core::XmlFilterBase& rFilter) +void reloadDiagram(SdrObject* pObj, core::XmlFilterBase& rFilter) { - uno::Reference<beans::XPropertySet> xPropSet(rXShape, uno::UNO_QUERY_THROW); + DiagramDataPtr pDiagramData = std::dynamic_pointer_cast<DiagramData>(pObj->GetDiagramData()); + if (!pDiagramData) + return; + + pObj->getChildrenOfSdrObject()->ClearSdrObjList(); + + uno::Reference<css::drawing::XShape> xShape(pObj->getUnoShape(), uno::UNO_QUERY_THROW); + uno::Reference<beans::XPropertySet> xPropSet(xShape, uno::UNO_QUERY_THROW); - uno::Reference<xml::dom::XDocument> dataDom; uno::Reference<xml::dom::XDocument> layoutDom; uno::Reference<xml::dom::XDocument> styleDom; uno::Reference<xml::dom::XDocument> colorDom; @@ -660,9 +657,7 @@ void reloadDiagram(css::uno::Reference<css::drawing::XShape>& rXShape, for (sal_Int32 nProp = 0; nProp < propList.getLength(); ++nProp) { OUString propName = propList[nProp].Name; - if (propName == "OOXData") - propList[nProp].Value >>= dataDom; - else if (propName == "OOXLayout") + if (propName == "OOXLayout") propList[nProp].Value >>= layoutDom; else if (propName == "OOXStyle") propList[nProp].Value >>= styleDom; @@ -672,15 +667,15 @@ void reloadDiagram(css::uno::Reference<css::drawing::XShape>& rXShape, ShapePtr pShape(new Shape()); pShape->setDiagramType(); - pShape->setSize(awt::Size(rXShape->getSize().Width * EMU_PER_HMM, - rXShape->getSize().Height * EMU_PER_HMM)); + pShape->setSize(awt::Size(xShape->getSize().Width * EMU_PER_HMM, + xShape->getSize().Height * EMU_PER_HMM)); - loadDiagram(pShape, dataDom, layoutDom, styleDom, colorDom, rFilter); + loadDiagram(pShape, pDiagramData, layoutDom, styleDom, colorDom, rFilter); - uno::Reference<drawing::XShapes> xShapes(rXShape, uno::UNO_QUERY_THROW); + uno::Reference<drawing::XShapes> xShapes(xShape, uno::UNO_QUERY_THROW); basegfx::B2DHomMatrix aTransformation; - aTransformation.translate(rXShape->getPosition().X * EMU_PER_HMM, - rXShape->getPosition().Y * EMU_PER_HMM); + aTransformation.translate(xShape->getPosition().X * EMU_PER_HMM, + xShape->getPosition().Y * EMU_PER_HMM); for (auto const& child : pShape->getChildren()) child->addShape(rFilter, rFilter.getCurrentTheme(), xShapes, aTransformation, pShape->getFillProperties()); } diff --git a/oox/source/drawingml/diagram/diagram.hxx b/oox/source/drawingml/diagram/diagram.hxx index 8e615ea5fd24..656caacadb3a 100644 --- a/oox/source/drawingml/diagram/diagram.hxx +++ b/oox/source/drawingml/diagram/diagram.hxx @@ -29,6 +29,7 @@ #include <oox/drawingml/shape.hxx> #include <drawingml/fillproperties.hxx> #include <oox/token/tokens.hxx> +#include <svx/DiagramDataInterface.hxx> namespace com { namespace sun { namespace star { namespace xml { namespace dom { class XDocument; } } @@ -154,7 +155,7 @@ typedef std::shared_ptr<LayoutAtom> LayoutAtomPtr; typedef std::map< OUString, css::uno::Reference<css::xml::dom::XDocument> > DiagramDomMap; -class DiagramData +class DiagramData : public DiagramDataInterface { public: typedef std::map< OUString, dgm::Point* > PointNameMap; @@ -171,6 +172,8 @@ public: std::map<sal_Int32, SourceIdAndDepth > > StringMap; DiagramData(); + virtual ~DiagramData() {} + void build(); FillPropertiesPtr & getFillProperties() { return mpFillProperties; } dgm::Connections & getConnections() @@ -189,6 +192,8 @@ public: { return maExtDrawings; } const dgm::Point* getRootPoint() const; void dump() const; + OUString getString() const override { return OUString(); } + private: ::std::vector<OUString> maExtDrawings; FillPropertiesPtr mpFillProperties; @@ -303,7 +308,6 @@ public: css::uno::Sequence<css::beans::PropertyValue> getDomsAsPropertyValues() const; private: - void build( ); DiagramDataPtr mpData; DiagramLayoutPtr mpLayout; DiagramQStyleMap maStyles; diff --git a/oox/source/drawingml/shape.cxx b/oox/source/drawingml/shape.cxx index 41b264c16a8e..050a8884c151 100644 --- a/oox/source/drawingml/shape.cxx +++ b/oox/source/drawingml/shape.cxx @@ -46,6 +46,7 @@ #include <oox/mathml/importutils.hxx> #include <oox/mathml/import.hxx> #include <oox/token/properties.hxx> +#include "diagram/diagram.hxx" #include <comphelper/classids.hxx> #include <comphelper/propertysequence.hxx> @@ -95,9 +96,11 @@ #include <vcl/svapp.hxx> #include <vcl/wmfexternal.hxx> #include <sal/log.hxx> +#include <svx/unoapi.hxx> #include <svx/unoshape.hxx> #include <svx/xfillit0.hxx> #include <svx/sdtaitm.hxx> +#include <svx/DiagramDataInterface.hxx> #include <vcl/wmf.hxx> @@ -1484,6 +1487,12 @@ void Shape::keepDiagramCompatibilityInfo() if ( !xSetInfo.is() ) return; + if (mpDiagramData) + { + SdrObject* pObj = GetSdrObjectFromXShape(mxShape); + pObj->SetDiagramData(mpDiagramData); + } + const OUString aGrabBagPropName = UNO_NAME_MISC_OBJ_INTEROPGRABBAG; if( !xSetInfo->hasPropertyByName( aGrabBagPropName ) ) return; diff --git a/sd/source/ui/view/drviews3.cxx b/sd/source/ui/view/drviews3.cxx index a240890ab6f8..851e8997055c 100644 --- a/sd/source/ui/view/drviews3.cxx +++ b/sd/source/ui/view/drviews3.cxx @@ -491,7 +491,6 @@ void DrawViewShell::ExecCtrl(SfxRequest& rReq) if (oox::drawingml::DrawingML::IsDiagram(xShape)) { mpDrawView->UnmarkAll(); - pObj->getChildrenOfSdrObject()->ClearSdrObjList(); css::uno::Reference<css::uno::XComponentContext> xContext = comphelper::getProcessComponentContext(); @@ -499,7 +498,7 @@ void DrawViewShell::ExecCtrl(SfxRequest& rReq) new oox::shape::ShapeFilterBase(xContext)); xFilter->setTargetDocument(GetDocSh()->GetModel()); xFilter->importTheme(); - oox::drawingml::reloadDiagram(xShape, *xFilter); + oox::drawingml::reloadDiagram(pObj, *xFilter); mpDrawView->MarkObj(pObj, mpDrawView->GetSdrPageView()); } diff --git a/svx/source/svdraw/svdobj.cxx b/svx/source/svdraw/svdobj.cxx index 65e8492145fe..3439b50ac48e 100644 --- a/svx/source/svdraw/svdobj.cxx +++ b/svx/source/svdraw/svdobj.cxx @@ -210,6 +210,8 @@ struct SdrObject::Impl boost::optional<double> mnRelativeHeight; sal_Int16 meRelativeHeightRelation; + std::shared_ptr<DiagramDataInterface> mpDiagramData; + Impl() : meRelativeWidthRelation(text::RelOrientation::PAGE_FRAME), meRelativeHeightRelation(text::RelOrientation::PAGE_FRAME) {} @@ -558,6 +560,16 @@ sal_Int16 SdrObject::GetRelativeHeightRelation() const return mpImpl->meRelativeHeightRelation; } +void SdrObject::SetDiagramData(std::shared_ptr<DiagramDataInterface> pDiagramData) +{ + mpImpl->mpDiagramData = pDiagramData; +} + +std::shared_ptr<DiagramDataInterface> SdrObject::GetDiagramData() const +{ + return mpImpl->mpDiagramData; +} + SfxItemPool& SdrObject::GetObjectItemPool() const { return getSdrModelFromSdrObject().GetItemPool(); _______________________________________________ Libreoffice-commits mailing list libreoffice-comm...@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/libreoffice-commits