summaryrefslogtreecommitdiff
path: root/oox/source/drawingml/diagram/layoutatomvisitors.cxx
diff options
context:
space:
mode:
Diffstat (limited to 'oox/source/drawingml/diagram/layoutatomvisitors.cxx')
-rw-r--r--oox/source/drawingml/diagram/layoutatomvisitors.cxx48
1 files changed, 47 insertions, 1 deletions
diff --git a/oox/source/drawingml/diagram/layoutatomvisitors.cxx b/oox/source/drawingml/diagram/layoutatomvisitors.cxx
index ce8e6ab72b9e..49a664c1e821 100644
--- a/oox/source/drawingml/diagram/layoutatomvisitors.cxx
+++ b/oox/source/drawingml/diagram/layoutatomvisitors.cxx
@@ -46,6 +46,14 @@ void ShapeCreationVisitor::visit(AlgAtom& rAtom)
void ShapeCreationVisitor::visit(ForEachAtom& rAtom)
{
+ if (rAtom.iterator().mnAxis == XML_followSib)
+ {
+ // If the axis is the follow sibling, then the last atom should not be
+ // visited.
+ if (mnCurrIdx + mnCurrStep >= mnCurrCnt)
+ return;
+ }
+
const std::vector<LayoutAtomPtr>& rChildren=rAtom.getChildren();
sal_Int32 nChildren=1;
@@ -65,7 +73,11 @@ void ShapeCreationVisitor::visit(ForEachAtom& rAtom)
rAtom.iterator().mnCnt==-1 ? nChildren : rAtom.iterator().mnCnt);
const sal_Int32 nOldIdx=mnCurrIdx;
+ const sal_Int32 nOldStep = mnCurrStep;
+ const sal_Int32 nOldCnt = mnCurrCnt;
const sal_Int32 nStep=rAtom.iterator().mnStep;
+ mnCurrStep = nStep;
+ mnCurrCnt = nCnt;
for( mnCurrIdx=0; mnCurrIdx<nCnt && nStep>0; mnCurrIdx+=nStep )
{
// TODO there is likely some conditions
@@ -75,6 +87,8 @@ void ShapeCreationVisitor::visit(ForEachAtom& rAtom)
// and restore idx
mnCurrIdx = nOldIdx;
+ mnCurrStep = nOldStep;
+ mnCurrCnt = nOldCnt;
}
void ShapeCreationVisitor::visit(ConditionAtom& rAtom)
@@ -166,6 +180,38 @@ void ShapeCreationVisitor::visit(LayoutNode& rAtom)
std::remove_if(pCurrParent->getChildren().begin(), pCurrParent->getChildren().end(),
[] (const ShapePtr & aChild) { return aChild->getServiceName() == "com.sun.star.drawing.GroupShape" && aChild->getChildren().empty(); }),
pCurrParent->getChildren().end());
+
+ // Offset the children from their default z-order stacking, if necessary.
+ std::vector<ShapePtr>& rChildren = pCurrParent->getChildren();
+ for (size_t i = 0; i < rChildren.size(); ++i)
+ rChildren[i]->setZOrder(i);
+
+ for (size_t i = 0; i < rChildren.size(); ++i)
+ {
+ const ShapePtr& pChild = rChildren[i];
+ sal_Int32 nZOrderOff = pChild->getZOrderOff();
+ if (nZOrderOff <= 0)
+ continue;
+
+ // Increase my ZOrder by nZOrderOff.
+ pChild->setZOrder(pChild->getZOrder() + nZOrderOff);
+ pChild->setZOrderOff(0);
+
+ for (sal_Int32 j = 0; j < nZOrderOff; ++j)
+ {
+ size_t nIndex = i + j + 1;
+ if (nIndex >= rChildren.size())
+ break;
+
+ // Decrease the ZOrder of the next nZOrderOff elements by one.
+ const ShapePtr& pNext = rChildren[nIndex];
+ pNext->setZOrder(pNext->getZOrder() - 1);
+ }
+ }
+
+ // Now that the ZOrders are adjusted, sort the children.
+ std::sort(rChildren.begin(), rChildren.end(),
+ [](const ShapePtr& a, const ShapePtr& b) { return a->getZOrder() < b->getZOrder(); });
}
void ShapeCreationVisitor::visit(ShapeAtom& /*rAtom*/)
@@ -235,7 +281,7 @@ void ShapeLayoutingVisitor::defaultVisit(LayoutAtom const & rAtom)
void ShapeLayoutingVisitor::visit(ConstraintAtom& rAtom)
{
if (meLookFor == CONSTRAINT)
- rAtom.parseConstraint(maConstraints);
+ rAtom.parseConstraint(maConstraints, /*bRequireForName=*/true);
}
void ShapeLayoutingVisitor::visit(AlgAtom& rAtom)