diff options
author | Armin Le Grand (Allotropia) <Armin.Le.Grand@me.com> | 2022-03-24 10:44:18 +0100 |
---|---|---|
committer | Armin Le Grand <Armin.Le.Grand@me.com> | 2022-03-24 16:31:42 +0100 |
commit | b658fdc33546f925a2a7406f8588a4aad160e4b8 (patch) | |
tree | 1a83265eb7a461aca3b80db1c001f734a50ba517 /oox | |
parent | 272a90c45af6ff8f6d5d80c024188b2959efdb93 (diff) |
Advanced Diagram support: Continue isolate oox-Shapes
As preparations to use the Diagram ModelData further isolate
it from the oox-library-only drawingML Shape used for import.
It is necessary to completely isolate the Diagram ModelData
from the Diagram import mechanism as a preparation to be
able to re-create that Shapes on-demand anytime if needed
for re-layout(s).
Also removed one unused loadDiagram implementation and
streamlined the AdvancedDiagramHelper some more.
Change-Id: I7a7c55389e0d00f70c02db73ce2c3ff9ce7a5b22
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/132058
Tested-by: Jenkins
Reviewed-by: Armin Le Grand <Armin.Le.Grand@me.com>
Diffstat (limited to 'oox')
-rw-r--r-- | oox/source/drawingml/diagram/datamodel.cxx | 54 | ||||
-rw-r--r-- | oox/source/drawingml/diagram/datamodel.hxx | 26 | ||||
-rw-r--r-- | oox/source/drawingml/diagram/datamodelcontext.cxx | 29 | ||||
-rw-r--r-- | oox/source/drawingml/diagram/diagram.cxx | 45 | ||||
-rw-r--r-- | oox/source/drawingml/diagram/diagramhelper.cxx | 6 | ||||
-rw-r--r-- | oox/source/drawingml/diagram/diagramhelper.hxx | 3 | ||||
-rw-r--r-- | oox/source/drawingml/diagram/diagramlayoutatoms.cxx | 36 | ||||
-rw-r--r-- | oox/source/drawingml/shape.cxx | 5 |
8 files changed, 104 insertions, 100 deletions
diff --git a/oox/source/drawingml/diagram/datamodel.cxx b/oox/source/drawingml/diagram/datamodel.cxx index 6185ee7acfb9..c68ee40cd71c 100644 --- a/oox/source/drawingml/diagram/datamodel.cxx +++ b/oox/source/drawingml/diagram/datamodel.cxx @@ -46,16 +46,33 @@ void Connection::dump() const << mnSourceOrder << ", dstOrd " << mnDestOrder); } -void Point::dump() const +void Point::dump(const Shape* pShape) const { SAL_INFO( "oox.drawingml", - "pt text " << mpShape.get() << ", cnxId " << msCnxId << ", modelId " + "pt text " << pShape << ", cnxId " << msCnxId << ", modelId " << msModelId << ", type " << mnType); } } // oox::drawingml::dgm namespace +Shape* DiagramData::getOrCreateAssociatedShape(const dgm::Point& rPoint, bool bCreateOnDemand) const +{ + if(maPointShapeMap.end() == maPointShapeMap.find(rPoint.msModelId)) + { + const_cast<DiagramData*>(this)->maPointShapeMap[rPoint.msModelId] = ShapePtr(); + } + + const ShapePtr& rShapePtr = maPointShapeMap.find(rPoint.msModelId)->second; + + if(!rShapePtr && bCreateOnDemand) + { + const_cast<ShapePtr&>(rShapePtr) = std::make_shared<Shape>(); + } + + return rShapePtr.get(); +} + DiagramData::DiagramData() : mpFillProperties( std::make_shared<FillProperties>() ) { @@ -79,7 +96,7 @@ void DiagramData::dump() const SAL_INFO("oox.drawingml", "Dgm: DiagramData # of pt: " << maPoints.size() ); for (const auto& rPoint : maPoints) - rPoint.dump(); + rPoint.dump(getOrCreateAssociatedShape(rPoint)); } void DiagramData::getChildrenString(OUStringBuffer& rBuf, const dgm::Point* pPoint, sal_Int32 nLevel) const @@ -87,13 +104,18 @@ void DiagramData::getChildrenString(OUStringBuffer& rBuf, const dgm::Point* pPoi if (!pPoint) return; + Shape* pShape(getOrCreateAssociatedShape(*pPoint)); + if(!pShape) + return; + if (nLevel > 0) { for (sal_Int32 i = 0; i < nLevel-1; i++) rBuf.append('\t'); rBuf.append('+'); rBuf.append(' '); - rBuf.append(pPoint->mpShape->getTextBody()->toString()); + if(pShape->getTextBody()) + rBuf.append(pShape->getTextBody()->toString()); rBuf.append('\n'); } @@ -131,9 +153,12 @@ std::vector<std::pair<OUString, OUString>> DiagramData::getChildren(const OUStri aChildren.resize(rCxn.mnSourceOrder + 1); const auto pChild = maPointNameMap.find(rCxn.msDestId); if (pChild != maPointNameMap.end()) + { + Shape* pShape(getOrCreateAssociatedShape(*(pChild->second))); aChildren[rCxn.mnSourceOrder] = std::make_pair( pChild->second->msModelId, - pChild->second->mpShape->getTextBody()->toString()); + nullptr != pShape && pShape->getTextBody() ? pShape->getTextBody()->toString() : OUString()); + } } // HACK: empty items shouldn't appear there @@ -174,11 +199,12 @@ OUString DiagramData::addNode(const OUString& rText) dgm::Point aDataPoint; aDataPoint.mnType = XML_node; aDataPoint.msModelId = sNewNodeId; - aDataPoint.mpShape = std::make_shared<Shape>(); - aDataPoint.mpShape->setTextBody(std::make_shared<TextBody>()); + + Shape* pShape(getOrCreateAssociatedShape(aDataPoint, true)); + pShape->setTextBody(std::make_shared<TextBody>()); TextRunPtr pTextRun = std::make_shared<TextRun>(); pTextRun->getText() = rText; - aDataPoint.mpShape->getTextBody()->addParagraph().addRun(pTextRun); + pShape->getTextBody()->addParagraph().addRun(pTextRun); OUString sDataSibling; for (const auto& aCxn : maConnections) @@ -193,7 +219,10 @@ OUString DiagramData::addNode(const OUString& rText) dgm::Point aPresPoint; aPresPoint.mnType = XML_pres; aPresPoint.msModelId = OStringToOUString(comphelper::xml::generateGUIDString(), RTL_TEXTENCODING_UTF8); - aPresPoint.mpShape = std::make_shared<Shape>(); + + // create pesPoint shape + getOrCreateAssociatedShape(aPresPoint, true); + aPresPoint.msPresentationAssociationId = aDataPoint.msModelId; if (!sPresSibling.isEmpty()) { @@ -356,9 +385,8 @@ void DiagramData::build() #endif // does currpoint have any text set? - if( point.mpShape && - point.mpShape->getTextBody() && - !point.mpShape->getTextBody()->isEmpty() ) + Shape* pShape(getOrCreateAssociatedShape(point)); + if( nullptr != pShape && pShape->getTextBody() && !pShape->getTextBody()->isEmpty() ) { #ifdef DEBUG_OOX_DIAGRAM static sal_Int32 nCount=0; @@ -367,7 +395,7 @@ void DiagramData::build() << " [" << "label=\"" << OUStringToOString( - point.mpShape->getTextBody()->toString(), + pShape->getTextBody()->toString(), RTL_TEXTENCODING_UTF8).getStr() << "\"" << "];" << std::endl; output << "\t" diff --git a/oox/source/drawingml/diagram/datamodel.hxx b/oox/source/drawingml/diagram/datamodel.hxx index b10287904c65..8da6ee9998e8 100644 --- a/oox/source/drawingml/diagram/datamodel.hxx +++ b/oox/source/drawingml/diagram/datamodel.hxx @@ -92,9 +92,8 @@ struct Point mbCustomText(false), mbIsPlaceholder(false) {} - void dump() const; - ShapePtr mpShape; + void dump(const Shape* pShape) const; OUString msCnxId; OUString msModelId; @@ -146,22 +145,26 @@ typedef std::vector< Point > Points; class DiagramData { public: + typedef std::map< OUString, ShapePtr > PointShapeMap; typedef std::map< OUString, dgm::Point* > PointNameMap; - typedef std::map< OUString, - std::vector<dgm::Point*> > PointsNameMap; + typedef std::map< OUString, std::vector<dgm::Point*> > PointsNameMap; typedef std::map< OUString, const dgm::Connection* > ConnectionNameMap; + struct SourceIdAndDepth { OUString msSourceId; sal_Int32 mnDepth = 0; }; + /// Tracks connections: destination id -> {destination order, details} map. - typedef std::map< OUString, - std::map<sal_Int32, SourceIdAndDepth > > StringMap; + typedef std::map< OUString, std::map<sal_Int32, SourceIdAndDepth > > StringMap; DiagramData(); virtual ~DiagramData() {} + + // creates temporary processing data from model data void build(); + FillPropertiesPtr & getFillProperties() { return mpFillProperties; } dgm::Connections & getConnections() @@ -184,14 +187,25 @@ public: OUString addNode(const OUString& rText); bool removeNode(const OUString& rNodeId); + Shape* getOrCreateAssociatedShape(const dgm::Point& rPoint, bool bCreateOnDemand = false) const; + private: void getChildrenString(OUStringBuffer& rBuf, const dgm::Point* pPoint, sal_Int32 nLevel) const; void addConnection(sal_Int32 nType, const OUString& sSourceId, const OUString& sDestId); + // evtl. existing alternative imported visualization identifier ::std::vector<OUString> maExtDrawings; + + // the model definition, + // - FillStyle + // - logic connections/assoziations + // - data point entries FillPropertiesPtr mpFillProperties; dgm::Connections maConnections; dgm::Points maPoints; + + // temporary processing data + PointShapeMap maPointShapeMap; PointNameMap maPointNameMap; PointsNameMap maPointsPresNameMap; ConnectionNameMap maConnectionNameMap; diff --git a/oox/source/drawingml/diagram/datamodelcontext.cxx b/oox/source/drawingml/diagram/datamodelcontext.cxx index 46324c183cab..4456e83f45d9 100644 --- a/oox/source/drawingml/diagram/datamodelcontext.cxx +++ b/oox/source/drawingml/diagram/datamodelcontext.cxx @@ -203,9 +203,11 @@ class PtContext public: PtContext( ContextHandler2Helper const & rParent, const AttributeList& rAttribs, - dgm::Point & rPoint): + dgm::Point & rPoint, + DiagramData& rDiagramData): ContextHandler2( rParent ), - mrPoint( rPoint ) + mrPoint( rPoint ), + mrDiagramData( rDiagramData ) { mrPoint.msModelId = rAttribs.getString( XML_modelId ).get(); @@ -229,15 +231,15 @@ public: case DGM_TOKEN( prSet ): return new PropertiesContext( *this, mrPoint, rAttribs ); case DGM_TOKEN( spPr ): - if( !mrPoint.mpShape ) - mrPoint.mpShape = std::make_shared<Shape>(); - return new ShapePropertiesContext( *this, *(mrPoint.mpShape) ); + { + Shape* pShape(mrDiagramData.getOrCreateAssociatedShape(mrPoint, true)); + return new ShapePropertiesContext( *this, *pShape ); + } case DGM_TOKEN( t ): { + Shape* pShape(mrDiagramData.getOrCreateAssociatedShape(mrPoint, true)); TextBodyPtr xTextBody = std::make_shared<TextBody>(); - if( !mrPoint.mpShape ) - mrPoint.mpShape = std::make_shared<Shape>(); - mrPoint.mpShape->setTextBody( xTextBody ); + pShape->setTextBody( xTextBody ); return new TextBodyContext( *this, *xTextBody ); } default: @@ -248,6 +250,7 @@ public: private: dgm::Point& mrPoint; + DiagramData& mrDiagramData; }; // CT_PtList @@ -255,9 +258,10 @@ class PtListContext : public ContextHandler2 { public: - PtListContext( ContextHandler2Helper const & rParent, dgm::Points& rPoints) : + PtListContext( ContextHandler2Helper const & rParent, dgm::Points& rPoints, DiagramData& rDiagramData) : ContextHandler2( rParent ), - mrPoints( rPoints ) + mrPoints( rPoints ), + mrDiagramData( rDiagramData ) {} virtual ContextHandlerRef onCreateContext( sal_Int32 aElementToken, @@ -269,7 +273,7 @@ public: { // CT_Pt mrPoints.emplace_back( ); - return new PtContext( *this, rAttribs, mrPoints.back() ); + return new PtContext( *this, rAttribs, mrPoints.back(), mrDiagramData ); } default: break; @@ -279,6 +283,7 @@ public: private: dgm::Points& mrPoints; + DiagramData& mrDiagramData; }; // CT_BackgroundFormatting @@ -349,7 +354,7 @@ DataModelContext::onCreateContext( ::sal_Int32 aElement, return new CxnListContext( *this, mpDataModel->getConnections() ); case DGM_TOKEN( ptLst ): // CT_PtList - return new PtListContext( *this, mpDataModel->getPoints() ); + return new PtListContext( *this, mpDataModel->getPoints(), *mpDataModel ); case DGM_TOKEN( bg ): // CT_BackgroundFormatting return new BackgroundFormattingContext( *this, mpDataModel ); diff --git a/oox/source/drawingml/diagram/diagram.cxx b/oox/source/drawingml/diagram/diagram.cxx index 481e56adec3c..c27c60b529ec 100644 --- a/oox/source/drawingml/diagram/diagram.cxx +++ b/oox/source/drawingml/diagram/diagram.cxx @@ -414,51 +414,6 @@ void loadDiagram( ShapePtr const & pShape, pShape->prepareDiagramHelper(pDiagram, rFilter.getCurrentThemePtr()); } -void loadDiagram(ShapePtr const& pShape, - DiagramDataPtr pDiagramData, - const uno::Reference<xml::dom::XDocument>& layoutDom, - const uno::Reference<xml::dom::XDocument>& styleDom, - const uno::Reference<xml::dom::XDocument>& colorDom, - core::XmlFilterBase& rFilter) -{ - DiagramPtr pDiagram = std::make_shared<Diagram>(); - - pDiagram->setData(pDiagramData); - - DiagramLayoutPtr pLayout = std::make_shared<DiagramLayout>(*pDiagram); - pDiagram->setLayout(pLayout); - - // layout - if (layoutDom.is()) - { - rtl::Reference<core::FragmentHandler> xRefLayout( - new DiagramLayoutFragmentHandler(rFilter, OUString(), pLayout)); - - importFragment(rFilter, layoutDom, "OOXLayout", pDiagram, xRefLayout); - } - - // style - if (styleDom.is()) - { - rtl::Reference<core::FragmentHandler> xRefQStyle( - new DiagramQStylesFragmentHandler(rFilter, OUString(), pDiagram->getStyles())); - - importFragment(rFilter, styleDom, "OOXStyle", pDiagram, xRefQStyle); - } - - // colors - if (colorDom.is()) - { - rtl::Reference<core::FragmentHandler> xRefColorStyle( - new ColorFragmentHandler(rFilter, OUString(), pDiagram->getColors())); - - importFragment(rFilter, colorDom, "OOXColor", pDiagram, xRefColorStyle); - } - - // diagram loaded. now lump together & attach to shape - pDiagram->addTo(pShape); -} - const oox::drawingml::Color& DiagramColor::getColorByIndex(const std::vector<oox::drawingml::Color>& rColors, sal_Int32 nIndex) { diff --git a/oox/source/drawingml/diagram/diagramhelper.cxx b/oox/source/drawingml/diagram/diagramhelper.cxx index b61c6b12994a..3d2491325722 100644 --- a/oox/source/drawingml/diagram/diagramhelper.cxx +++ b/oox/source/drawingml/diagram/diagramhelper.cxx @@ -39,12 +39,11 @@ bool AdvancedDiagramHelper::hasDiagramData() const AdvancedDiagramHelper::AdvancedDiagramHelper( const std::shared_ptr< Diagram >& rDiagramPtr, const std::shared_ptr<::oox::drawingml::Theme>& rTheme, - const Shape& rSourceShape) + css::awt::Size aImportSize) : IDiagramHelper() , mpDiagramPtr(rDiagramPtr) , mpThemePtr(rTheme) -, maImportSize(rSourceShape.getSize()) -, maImportPosition(rSourceShape.getPosition()) +, maImportSize(aImportSize) { } @@ -70,7 +69,6 @@ void AdvancedDiagramHelper::reLayout(SdrObjGroup& rTarget) oox::drawingml::ShapePtr pShapePtr = std::make_shared<Shape>( "com.sun.star.drawing.GroupShape" ); pShapePtr->setDiagramType(); pShapePtr->setSize(maImportSize); - pShapePtr->setPosition(maImportPosition); pShapePtr->getFillProperties() = *mpDiagramPtr->getData()->getFillProperties(); // Re-create the oox::Shapes for the diagram content diff --git a/oox/source/drawingml/diagram/diagramhelper.hxx b/oox/source/drawingml/diagram/diagramhelper.hxx index 0c1240bdd4ba..33fd2da9d7a1 100644 --- a/oox/source/drawingml/diagram/diagramhelper.hxx +++ b/oox/source/drawingml/diagram/diagramhelper.hxx @@ -47,7 +47,6 @@ class AdvancedDiagramHelper final : public IDiagramHelper const std::shared_ptr<::oox::drawingml::Theme> mpThemePtr; css::awt::Size maImportSize; - css::awt::Point maImportPosition; bool hasDiagramData() const; @@ -55,7 +54,7 @@ public: AdvancedDiagramHelper( const std::shared_ptr< Diagram >& rDiagramPtr, const std::shared_ptr<::oox::drawingml::Theme>& rTheme, - const Shape& rSourceShape); + css::awt::Size aImportSize); virtual ~AdvancedDiagramHelper(); // re-create XShapes diff --git a/oox/source/drawingml/diagram/diagramlayoutatoms.cxx b/oox/source/drawingml/diagram/diagramlayoutatoms.cxx index a91925b32376..b6b5d24da91b 100644 --- a/oox/source/drawingml/diagram/diagramlayoutatoms.cxx +++ b/oox/source/drawingml/diagram/diagramlayoutatoms.cxx @@ -1898,7 +1898,8 @@ bool LayoutNode::setupShape( const ShapePtr& rShape, const dgm::Point* pPresNode continue; } - if (!aDataNode2->second->mpShape) + Shape* pDataNode2Shape(mrDgm.getData()->getOrCreateAssociatedShape(*aDataNode2->second)); + if (nullptr == pDataNode2Shape) { //busted, skip it continue; @@ -1909,11 +1910,11 @@ bool LayoutNode::setupShape( const ShapePtr& rShape, const dgm::Point* pPresNode if (rItem.mnDepth == 0) { // grab shape attr from topmost element(s) - rShape->getShapeProperties() = aDataNode2->second->mpShape->getShapeProperties(); - rShape->getLineProperties() = aDataNode2->second->mpShape->getLineProperties(); - rShape->getFillProperties() = aDataNode2->second->mpShape->getFillProperties(); - rShape->getCustomShapeProperties() = aDataNode2->second->mpShape->getCustomShapeProperties(); - rShape->setMasterTextListStyle( aDataNode2->second->mpShape->getMasterTextListStyle() ); + rShape->getShapeProperties() = pDataNode2Shape->getShapeProperties(); + rShape->getLineProperties() = pDataNode2Shape->getLineProperties(); + rShape->getFillProperties() = pDataNode2Shape->getFillProperties(); + rShape->getCustomShapeProperties() = pDataNode2Shape->getCustomShapeProperties(); + rShape->setMasterTextListStyle( pDataNode2Shape->getMasterTextListStyle() ); SAL_INFO( "oox.drawingml", @@ -1927,14 +1928,14 @@ bool LayoutNode::setupShape( const ShapePtr& rShape, const dgm::Point* pPresNode { // If no real topmost element, then take properties from the one that's the closest // to topmost. - rShape->getLineProperties() = aDataNode2->second->mpShape->getLineProperties(); - rShape->getFillProperties() = aDataNode2->second->mpShape->getFillProperties(); + rShape->getLineProperties() = pDataNode2Shape->getLineProperties(); + rShape->getFillProperties() = pDataNode2Shape->getFillProperties(); } // append text with right outline level - if( aDataNode2->second->mpShape->getTextBody() && - !aDataNode2->second->mpShape->getTextBody()->getParagraphs().empty() && - !aDataNode2->second->mpShape->getTextBody()->getParagraphs().front()->getRuns().empty() ) + if( pDataNode2Shape->getTextBody() && + !pDataNode2Shape->getTextBody()->getParagraphs().empty() && + !pDataNode2Shape->getTextBody()->getParagraphs().front()->getRuns().empty() ) { TextBodyPtr pTextBody=rShape->getTextBody(); if( !pTextBody ) @@ -1943,15 +1944,15 @@ bool LayoutNode::setupShape( const ShapePtr& rShape, const dgm::Point* pPresNode // also copy text attrs pTextBody->getTextListStyle() = - aDataNode2->second->mpShape->getTextBody()->getTextListStyle(); + pDataNode2Shape->getTextBody()->getTextListStyle(); pTextBody->getTextProperties() = - aDataNode2->second->mpShape->getTextBody()->getTextProperties(); + pDataNode2Shape->getTextBody()->getTextProperties(); rShape->setTextBody(pTextBody); } const TextParagraphVector& rSourceParagraphs - = aDataNode2->second->mpShape->getTextBody()->getParagraphs(); + = pDataNode2Shape->getTextBody()->getParagraphs(); for (const auto& pSourceParagraph : rSourceParagraphs) { TextParagraph& rPara = pTextBody->addParagraph(); @@ -1960,7 +1961,7 @@ bool LayoutNode::setupShape( const ShapePtr& rShape, const dgm::Point* pPresNode for (const auto& pRun : pSourceParagraph->getRuns()) rPara.addRun(pRun); - const TextBodyPtr& rBody = aDataNode2->second->mpShape->getTextBody(); + const TextBodyPtr& rBody = pDataNode2Shape->getTextBody(); rPara.getProperties().apply(rBody->getParagraphs().front()->getProperties()); } } @@ -1974,8 +1975,9 @@ bool LayoutNode::setupShape( const ShapePtr& rShape, const dgm::Point* pPresNode " processing shape type " << rShape->getCustomShapeProperties()->getShapePresetType() << " for layout node named \"" << msName << "\""); - if (pPresNode->mpShape) - rShape->getFillProperties().assignUsed(pPresNode->mpShape->getFillProperties()); + Shape* pPresNodeShape(mrDgm.getData()->getOrCreateAssociatedShape(*pPresNode)); + if (nullptr != pPresNodeShape) + rShape->getFillProperties().assignUsed(pPresNodeShape->getFillProperties()); } // TODO(Q1): apply styling & coloring - take presentation diff --git a/oox/source/drawingml/shape.cxx b/oox/source/drawingml/shape.cxx index ac2ff8891add..9d05acb34faf 100644 --- a/oox/source/drawingml/shape.cxx +++ b/oox/source/drawingml/shape.cxx @@ -208,7 +208,10 @@ void Shape::prepareDiagramHelper( // Prepare Diagram data collecting for this Shape if( nullptr == mpDiagramHelper && FRAMETYPE_DIAGRAM == meFrameType ) { - mpDiagramHelper = new AdvancedDiagramHelper(rDiagramPtr, rTheme, *this); + mpDiagramHelper = new AdvancedDiagramHelper( + rDiagramPtr, + rTheme, + getSize()); } } |