diff options
author | Grzegorz Araminowicz <g.araminowicz@gmail.com> | 2017-08-08 10:57:24 +0200 |
---|---|---|
committer | Jan Holesovsky <kendy@collabora.com> | 2017-08-10 16:51:49 +0200 |
commit | 93a3739bf47ada4549b3c139c55a9b039c1db1ee (patch) | |
tree | 9cc3fa7aad805df1d21a4881fe30a80d9fb57f5f /oox | |
parent | 0bb18896ad593bed31cc231c7779045ee907a43e (diff) |
SmartArt: add nested shapes only if they are node's children
Change-Id: I6527fc4166001ffc1e1e170b179cd4eadf55305c
Reviewed-on: https://gerrit.libreoffice.org/40870
Reviewed-by: Jan Holesovsky <kendy@collabora.com>
Tested-by: Jan Holesovsky <kendy@collabora.com>
Tested-by: Jenkins <ci@libreoffice.org>
Diffstat (limited to 'oox')
-rw-r--r-- | oox/source/drawingml/diagram/diagram.cxx | 10 | ||||
-rw-r--r-- | oox/source/drawingml/diagram/diagram.hxx | 1 | ||||
-rw-r--r-- | oox/source/drawingml/diagram/diagramlayoutatoms.cxx | 226 | ||||
-rw-r--r-- | oox/source/drawingml/diagram/diagramlayoutatoms.hxx | 2 | ||||
-rwxr-xr-x | oox/source/drawingml/diagram/layoutatomvisitors.cxx | 26 | ||||
-rwxr-xr-x | oox/source/drawingml/diagram/layoutatomvisitors.hxx | 4 |
6 files changed, 143 insertions, 126 deletions
diff --git a/oox/source/drawingml/diagram/diagram.cxx b/oox/source/drawingml/diagram/diagram.cxx index ec396ceed9d3..4185dd01f15b 100644 --- a/oox/source/drawingml/diagram/diagram.cxx +++ b/oox/source/drawingml/diagram/diagram.cxx @@ -72,6 +72,16 @@ DiagramData::DiagramData() { } +const dgm::Point* DiagramData::getRootPoint() const +{ + for (const auto & aCurrPoint : maPoints) + if (aCurrPoint.mnType == XML_doc) + return &aCurrPoint; + + SAL_WARN("oox.drawingml", "No root point"); + return nullptr; +} + void DiagramData::dump() { SAL_INFO("oox.drawingml", "Dgm: DiagramData # of cnx: " << maConnections.size() ); diff --git a/oox/source/drawingml/diagram/diagram.hxx b/oox/source/drawingml/diagram/diagram.hxx index 2e1429da37b0..914c421e1a6d 100644 --- a/oox/source/drawingml/diagram/diagram.hxx +++ b/oox/source/drawingml/diagram/diagram.hxx @@ -180,6 +180,7 @@ public: { return maPointsPresNameMap; } ::std::vector<OUString> &getExtDrawings() { return maExtDrawings; } + const dgm::Point* getRootPoint() const; void dump(); private: FillPropertiesPtr mpFillProperties; diff --git a/oox/source/drawingml/diagram/diagramlayoutatoms.cxx b/oox/source/drawingml/diagram/diagramlayoutatoms.cxx index 2c3c8cf6749a..79390b1a3792 100644 --- a/oox/source/drawingml/diagram/diagramlayoutatoms.cxx +++ b/oox/source/drawingml/diagram/diagramlayoutatoms.cxx @@ -353,150 +353,132 @@ void LayoutNode::accept( LayoutAtomVisitor& rVisitor ) rVisitor.visit(*this); } -bool LayoutNode::setupShape( const ShapePtr& rShape, const Diagram& rDgm, sal_uInt32 nIdx ) const +bool LayoutNode::setupShape( const ShapePtr& rShape, const Diagram& rDgm, const dgm::Point* pPresNode ) const { - // find the data node to grab text from - DiagramData::PointsNameMap::const_iterator aDataNode=rDgm.getData()->getPointsPresNameMap().find(msName); - if( aDataNode != rDgm.getData()->getPointsPresNameMap().end() && - aDataNode->second.size() > nIdx ) + SAL_INFO( + "oox.drawingml", + "Filling content from layout node named \"" << msName + << "\", modelId \"" << pPresNode->msModelId << "\""); + + // have the presentation node - now, need the actual data node: + const DiagramData::StringMap::const_iterator aNodeName = rDgm.getData()->getPresOfNameMap().find( + pPresNode->msModelId); + if( aNodeName != rDgm.getData()->getPresOfNameMap().end() ) { - const dgm::Point* aPresNode = aDataNode->second.at(nIdx); - SAL_INFO( - "oox.drawingml", - "Filling content from " << nIdx << "th layout node named \"" - << msName << "\", modelId \"" - << aPresNode->msModelId << "\""); - - // got the presentation node - now, need the actual data node: - const DiagramData::StringMap::const_iterator aNodeName=rDgm.getData()->getPresOfNameMap().find( - aPresNode->msModelId); - if( aNodeName != rDgm.getData()->getPresOfNameMap().end() ) + DiagramData::StringMap::value_type::second_type::const_iterator aVecIter=aNodeName->second.begin(); + const DiagramData::StringMap::value_type::second_type::const_iterator aVecEnd=aNodeName->second.end(); + while( aVecIter != aVecEnd ) { - DiagramData::StringMap::value_type::second_type::const_iterator aVecIter=aNodeName->second.begin(); - const DiagramData::StringMap::value_type::second_type::const_iterator aVecEnd=aNodeName->second.end(); - while( aVecIter != aVecEnd ) + DiagramData::PointNameMap& rMap = rDgm.getData()->getPointNameMap(); + DiagramData::PointNameMap::const_iterator aDataNode2 = rMap.find(aVecIter->first); + if (aDataNode2 == rMap.end()) { - DiagramData::PointNameMap& rMap = rDgm.getData()->getPointNameMap(); - DiagramData::PointNameMap::const_iterator aDataNode2 = rMap.find(aVecIter->first); - if (aDataNode2 == rMap.end()) - { - //busted, skip it - ++aVecIter; - continue; - } - - if( aVecIter->second == 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() ); - - SAL_INFO( - "oox.drawingml", - "Custom shape with preset type " - << (rShape->getCustomShapeProperties() - ->getShapePresetType()) - << " added for layout node named \"" << msName - << "\""); - } - - // 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() ) - { - TextBodyPtr pTextBody=rShape->getTextBody(); - if( !pTextBody ) - { - pTextBody.reset( new TextBody() ); - - // also copy text attrs - pTextBody->getTextListStyle() = - aDataNode2->second->mpShape->getTextBody()->getTextListStyle(); - pTextBody->getTextProperties() = - aDataNode2->second->mpShape->getTextBody()->getTextProperties(); - - rShape->setTextBody(pTextBody); - } - - TextParagraph& rPara=pTextBody->addParagraph(); - if( aVecIter->second != -1 ) - rPara.getProperties().setLevel(aVecIter->second); - - rPara.addRun( - aDataNode2->second->mpShape->getTextBody()->getParagraphs().front()->getRuns().front()); - rPara.getProperties().apply( - aDataNode2->second->mpShape->getTextBody()->getParagraphs().front()->getProperties()); - } - + //busted, skip it ++aVecIter; + continue; } - } - else - { - SAL_INFO( - "oox.drawingml", - "ShapeCreationVisitor::visit: no data node name found while" - " processing shape type " - << rShape->getCustomShapeProperties()->getShapePresetType() - << " for layout node named \"" << msName << "\""); - } - // TODO(Q1): apply styling & coloring - take presentation - // point's presStyleLbl for both style & color - // if not found use layout node's styleLbl - // however, docs are a bit unclear on this - OUString aStyleLabel = aPresNode->msPresentationLayoutStyleLabel; - if (aStyleLabel.isEmpty()) - aStyleLabel = msStyleLabel; - if( !aStyleLabel.isEmpty() ) - { - const DiagramQStyleMap::const_iterator aStyle = rDgm.getStyles().find(aStyleLabel); - if( aStyle != rDgm.getStyles().end() ) - { - const DiagramStyle& rStyle = aStyle->second; - rShape->getShapeStyleRefs()[XML_fillRef] = rStyle.maFillStyle; - rShape->getShapeStyleRefs()[XML_lnRef] = rStyle.maLineStyle; - rShape->getShapeStyleRefs()[XML_effectRef] = rStyle.maEffectStyle; - rShape->getShapeStyleRefs()[XML_fontRef] = rStyle.maTextStyle; - } - else + if( aVecIter->second == 0 ) { - SAL_WARN("oox.drawingml", "Style " << aStyleLabel << " not found"); + // 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() ); + + SAL_INFO( + "oox.drawingml", + "Custom shape with preset type " + << (rShape->getCustomShapeProperties() + ->getShapePresetType()) + << " added for layout node named \"" << msName + << "\""); } - const DiagramColorMap::const_iterator aColor = rDgm.getColors().find(aStyleLabel); - if( aColor != rDgm.getColors().end() ) + // 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() ) { - const DiagramColor& rColor=aColor->second; - if( rColor.maFillColor.isUsed() ) - rShape->getShapeStyleRefs()[XML_fillRef].maPhClr = rColor.maFillColor; - if( rColor.maLineColor.isUsed() ) - rShape->getShapeStyleRefs()[XML_lnRef].maPhClr = rColor.maLineColor; - if( rColor.maEffectColor.isUsed() ) - rShape->getShapeStyleRefs()[XML_effectRef].maPhClr = rColor.maEffectColor; - if( rColor.maTextFillColor.isUsed() ) - rShape->getShapeStyleRefs()[XML_fontRef].maPhClr = rColor.maTextFillColor; + TextBodyPtr pTextBody=rShape->getTextBody(); + if( !pTextBody ) + { + pTextBody.reset( new TextBody() ); + + // also copy text attrs + pTextBody->getTextListStyle() = + aDataNode2->second->mpShape->getTextBody()->getTextListStyle(); + pTextBody->getTextProperties() = + aDataNode2->second->mpShape->getTextBody()->getTextProperties(); + + rShape->setTextBody(pTextBody); + } + + TextParagraph& rPara=pTextBody->addParagraph(); + if( aVecIter->second != -1 ) + rPara.getProperties().setLevel(aVecIter->second); + + rPara.addRun( + aDataNode2->second->mpShape->getTextBody()->getParagraphs().front()->getRuns().front()); + rPara.getProperties().apply( + aDataNode2->second->mpShape->getTextBody()->getParagraphs().front()->getProperties()); } - } - // even if no data node found, successful anyway. it's - // contained at the layoutnode - return true; + ++aVecIter; + } } else { SAL_INFO( "oox.drawingml", - "no text found while processing shape type " + "ShapeCreationVisitor::visit: no data node name found while" + " processing shape type " << rShape->getCustomShapeProperties()->getShapePresetType() << " for layout node named \"" << msName << "\""); } - return false; + // TODO(Q1): apply styling & coloring - take presentation + // point's presStyleLbl for both style & color + // if not found use layout node's styleLbl + // however, docs are a bit unclear on this + OUString aStyleLabel = pPresNode->msPresentationLayoutStyleLabel; + if (aStyleLabel.isEmpty()) + aStyleLabel = msStyleLabel; + if( !aStyleLabel.isEmpty() ) + { + const DiagramQStyleMap::const_iterator aStyle = rDgm.getStyles().find(aStyleLabel); + if( aStyle != rDgm.getStyles().end() ) + { + const DiagramStyle& rStyle = aStyle->second; + rShape->getShapeStyleRefs()[XML_fillRef] = rStyle.maFillStyle; + rShape->getShapeStyleRefs()[XML_lnRef] = rStyle.maLineStyle; + rShape->getShapeStyleRefs()[XML_effectRef] = rStyle.maEffectStyle; + rShape->getShapeStyleRefs()[XML_fontRef] = rStyle.maTextStyle; + } + else + { + SAL_WARN("oox.drawingml", "Style " << aStyleLabel << " not found"); + } + + const DiagramColorMap::const_iterator aColor = rDgm.getColors().find(aStyleLabel); + if( aColor != rDgm.getColors().end() ) + { + const DiagramColor& rColor=aColor->second; + if( rColor.maFillColor.isUsed() ) + rShape->getShapeStyleRefs()[XML_fillRef].maPhClr = rColor.maFillColor; + if( rColor.maLineColor.isUsed() ) + rShape->getShapeStyleRefs()[XML_lnRef].maPhClr = rColor.maLineColor; + if( rColor.maEffectColor.isUsed() ) + rShape->getShapeStyleRefs()[XML_effectRef].maPhClr = rColor.maEffectColor; + if( rColor.maTextFillColor.isUsed() ) + rShape->getShapeStyleRefs()[XML_fontRef].maPhClr = rColor.maTextFillColor; + } + } + + // even if no data node found, successful anyway. it's + // contained at the layoutnode + return true; } void ShapeAtom::accept( LayoutAtomVisitor& rVisitor ) diff --git a/oox/source/drawingml/diagram/diagramlayoutatoms.hxx b/oox/source/drawingml/diagram/diagramlayoutatoms.hxx index a6123ccbd62c..7414303bbdb1 100644 --- a/oox/source/drawingml/diagram/diagramlayoutatoms.hxx +++ b/oox/source/drawingml/diagram/diagramlayoutatoms.hxx @@ -247,7 +247,7 @@ public: bool setupShape( const ShapePtr& rShape, const Diagram& rDgm, - sal_uInt32 nIdx ) const; + const dgm::Point* pPresNode ) const; private: VarMap mVariables; diff --git a/oox/source/drawingml/diagram/layoutatomvisitors.cxx b/oox/source/drawingml/diagram/layoutatomvisitors.cxx index f661d48389d2..c0b019a9019b 100755 --- a/oox/source/drawingml/diagram/layoutatomvisitors.cxx +++ b/oox/source/drawingml/diagram/layoutatomvisitors.cxx @@ -93,12 +93,30 @@ void ShapeCreationVisitor::visit(ChooseAtom& rAtom) void ShapeCreationVisitor::visit(LayoutNode& rAtom) { + // stop processing if it's not a child of previous LayoutNode + + const DiagramData::PointsNameMap::const_iterator aDataNode = mrDgm.getData()->getPointsPresNameMap().find(rAtom.getName()); + if (aDataNode == mrDgm.getData()->getPointsPresNameMap().end() || mnCurrIdx >= (sal_Int32)aDataNode->second.size()) + return; + + const dgm::Point* pNewNode = aDataNode->second.at(mnCurrIdx); + if (!mpCurrentNode || !pNewNode) + return; + + bool bIsChild = false; + for (const auto & aConnection : mrDgm.getData()->getConnections()) + if (aConnection.msSourceId == mpCurrentNode->msModelId && aConnection.msDestId == pNewNode->msModelId) + bIsChild = true; + + if (!bIsChild) + return; + ShapePtr pCurrParent(mpParentShape); if (rAtom.getExistingShape()) { // reuse existing shape - if (rAtom.setupShape(rAtom.getExistingShape(), mrDgm, mnCurrIdx)) + if (rAtom.setupShape(rAtom.getExistingShape(), mrDgm, pNewNode)) rAtom.getNodeShapes().push_back(rAtom.getExistingShape()); } else @@ -115,7 +133,7 @@ void ShapeCreationVisitor::visit(LayoutNode& rAtom) << (pShape->getCustomShapeProperties() ->getShapePresetType())); - if (rAtom.setupShape(pShape, mrDgm, mnCurrIdx)) + if (rAtom.setupShape(pShape, mrDgm, pNewNode)) { pCurrParent->addChild(pShape); pCurrParent = pShape; @@ -128,6 +146,9 @@ void ShapeCreationVisitor::visit(LayoutNode& rAtom) } } + const dgm::Point* pPreviousNode = mpCurrentNode; + mpCurrentNode = pNewNode; + // set new parent for children ShapePtr pPreviousParent(mpParentShape); mpParentShape=pCurrParent; @@ -137,6 +158,7 @@ void ShapeCreationVisitor::visit(LayoutNode& rAtom) // restore parent mpParentShape=pPreviousParent; + mpCurrentNode = pPreviousNode; // remove unneeded empty group shapes pCurrParent->getChildren().erase( diff --git a/oox/source/drawingml/diagram/layoutatomvisitors.hxx b/oox/source/drawingml/diagram/layoutatomvisitors.hxx index 86432a8a4376..28bdf7d855e6 100755 --- a/oox/source/drawingml/diagram/layoutatomvisitors.hxx +++ b/oox/source/drawingml/diagram/layoutatomvisitors.hxx @@ -33,6 +33,7 @@ class ShapeCreationVisitor : public LayoutAtomVisitor ShapePtr mpParentShape; const Diagram& mrDgm; sal_Int32 mnCurrIdx; + const dgm::Point* mpCurrentNode; void defaultVisit(LayoutAtom const & rAtom); virtual void visit(ConstraintAtom& rAtom) override; @@ -48,7 +49,8 @@ public: const Diagram& rDgm) : mpParentShape(rParentShape), mrDgm(rDgm), - mnCurrIdx(0) + mnCurrIdx(0), + mpCurrentNode(rDgm.getData()->getRootPoint()) {} }; |