summaryrefslogtreecommitdiffstats
path: root/PC/python34stub.def
Commit message (Expand)AuthorAgeFilesLines
* Issue #15422: get rid of PyCFunction_New macroAndrew Svetlov2012-12-251-0/+1
* Bump version to 3.4.0 alpha 0.Georg Brandl2012-09-291-0/+698
will + // have to shrink as the result of that. + // If any of these does not hold, we have a situation where the ParallelAnchor + // does not have enough information to calculate its equivalent prefSize. + prefSize = qMax(firstEdge->prefSize, secondPref); prefSize = qMin(prefSize, maxSize); // See comment in AnchorData::refreshSizeHints() about sizeAt* values diff --git a/src/gui/graphicsview/qgraphicsanchorlayout_p.h b/src/gui/graphicsview/qgraphicsanchorlayout_p.h index 1e11ee2..8d77b1a 100644 --- a/src/gui/graphicsview/qgraphicsanchorlayout_p.h +++ b/src/gui/graphicsview/qgraphicsanchorlayout_p.h @@ -256,10 +256,11 @@ struct ParallelAnchorData : public AnchorData type = AnchorData::Parallel; orientation = first->orientation; - // ### Those asserts force that both child anchors have the same direction, - // but can't we simplify a pair of anchors in opposite directions? - Q_ASSERT(first->from == second->from); - Q_ASSERT(first->to == second->to); + // This assert whether the child anchors share their vertices + Q_ASSERT(((first->from == second->from) && (first->to == second->to)) || + ((first->from == second->to) && (first->to == second->from))); + + // We arbitrarily choose the direction of the first child as "our" direction from = first->from; to = first->to; #ifdef QT_DEBUG -- cgit v0.12 From 720e04ac5f572c1ca0a32e1675fbda6e778d3e8c Mon Sep 17 00:00:00 2001 From: "Eduardo M. Fleury" Date: Thu, 5 Nov 2009 19:18:48 -0300 Subject: QGAL: Revamp the edge interpolation code Simplify the code of interpolateSequentialAnchor to use the distance values of the sequential anchor itself as base for the children distances. So the 'base' parameter was removed. This also allowed out-of-order parallel anchors to be interpolated, and the 'base' parameter also to be removed from interpolateParallelAnchor. Signed-off-by: Eduardo M. Fleury Reviewed-by: Caio Marcelo de Oliveira Filho --- src/gui/graphicsview/qgraphicsanchorlayout_p.cpp | 49 ++++++++++++------------ src/gui/graphicsview/qgraphicsanchorlayout_p.h | 6 +-- 2 files changed, 26 insertions(+), 29 deletions(-) diff --git a/src/gui/graphicsview/qgraphicsanchorlayout_p.cpp b/src/gui/graphicsview/qgraphicsanchorlayout_p.cpp index 95922ca..318ce20 100644 --- a/src/gui/graphicsview/qgraphicsanchorlayout_p.cpp +++ b/src/gui/graphicsview/qgraphicsanchorlayout_p.cpp @@ -2443,17 +2443,13 @@ void QGraphicsAnchorLayoutPrivate::interpolateEdge(AnchorVertex *base, // Process child anchors if (edge->type == AnchorData::Sequential) - interpolateSequentialEdges(edge->from, - static_cast(edge), - orientation); + interpolateSequentialEdges(static_cast(edge), orientation); else if (edge->type == AnchorData::Parallel) - interpolateParallelEdges(edge->from, - static_cast(edge), - orientation); + interpolateParallelEdges(static_cast(edge), orientation); } void QGraphicsAnchorLayoutPrivate::interpolateParallelEdges( - AnchorVertex *base, ParallelAnchorData *data, Orientation orientation) + ParallelAnchorData *data, Orientation orientation) { // In parallels the boundary vertices are already calculate, we // just need to look for sequential groups inside, because only @@ -2461,40 +2457,43 @@ void QGraphicsAnchorLayoutPrivate::interpolateParallelEdges( // First edge if (data->firstEdge->type == AnchorData::Sequential) - interpolateSequentialEdges(base, - static_cast(data->firstEdge), + interpolateSequentialEdges(static_cast(data->firstEdge), orientation); else if (data->firstEdge->type == AnchorData::Parallel) - interpolateParallelEdges(base, - static_cast(data->firstEdge), + interpolateParallelEdges(static_cast(data->firstEdge), orientation); // Second edge if (data->secondEdge->type == AnchorData::Sequential) - interpolateSequentialEdges(base, - static_cast(data->secondEdge), + interpolateSequentialEdges(static_cast(data->secondEdge), orientation); else if (data->secondEdge->type == AnchorData::Parallel) - interpolateParallelEdges(base, - static_cast(data->secondEdge), + interpolateParallelEdges(static_cast(data->secondEdge), orientation); } void QGraphicsAnchorLayoutPrivate::interpolateSequentialEdges( - AnchorVertex *base, SequentialAnchorData *data, Orientation orientation) + SequentialAnchorData *data, Orientation orientation) { - AnchorVertex *prev = base; + // This method is supposed to handle any sequential anchor, even out-of-order + // ones. However, in the current QGAL implementation we should get only the + // well behaved ones. + Q_ASSERT(data->m_edges.first()->from == data->from); + Q_ASSERT(data->m_edges.last()->to == data->to); - // ### I'm not sure whether this assumption is safe. If not, - // consider that m_edges.last() could be used instead (so - // at(0) would be the one to be treated specially). - Q_ASSERT(base == data->m_edges.at(0)->to || base == data->m_edges.at(0)->from); + // At this point, the two outter vertices already have their distance + // calculated. + // We use the first as the base to calculate the internal ones + + AnchorVertex *prev = data->from; - // Skip the last for (int i = 0; i < data->m_edges.count() - 1; ++i) { - AnchorData *child = data->m_edges.at(i); - interpolateEdge(prev, child, orientation); - prev = child->to; + AnchorData *edge = data->m_edges.at(i); + interpolateEdge(prev, edge, orientation); + + // Use the recently calculated vertex as the base for the next one + const bool edgeIsForward = (edge->from == prev); + prev = edgeIsForward ? edge->to : edge->from; } // Treat the last specially, since we already calculated it's end diff --git a/src/gui/graphicsview/qgraphicsanchorlayout_p.h b/src/gui/graphicsview/qgraphicsanchorlayout_p.h index 8d77b1a..d8e62b4 100644 --- a/src/gui/graphicsview/qgraphicsanchorlayout_p.h +++ b/src/gui/graphicsview/qgraphicsanchorlayout_p.h @@ -475,10 +475,8 @@ public: void calculateVertexPositions(Orientation orientation); void setupEdgesInterpolation(Orientation orientation); void interpolateEdge(AnchorVertex *base, AnchorData *edge, Orientation orientation); - void interpolateSequentialEdges(AnchorVertex *base, SequentialAnchorData *edge, - Orientation orientation); - void interpolateParallelEdges(AnchorVertex *base, ParallelAnchorData *edge, - Orientation orientation); + void interpolateSequentialEdges(SequentialAnchorData *edge, Orientation orientation); + void interpolateParallelEdges(ParallelAnchorData *edge, Orientation orientation); // Linear Programming solver methods bool solveMinMax(const QList &constraints, -- cgit v0.12 From f2f7ad1e0a73ef28aee406de358e1308f817bf6d Mon Sep 17 00:00:00 2001 From: "Eduardo M. Fleury" Date: Thu, 5 Nov 2009 14:44:04 -0300 Subject: QGAL (Test): Add test where center anchor is simplified by parallel We were not handling the case where a parallel anchor is created to simplify a central anchor. Unfortunately no tests had shown that case yet. Signed-off-by: Eduardo M. Fleury Reviewed-by: Caio Marcelo de Oliveira Filho --- .../tst_qgraphicsanchorlayout.cpp | 26 ++++++++++++++++++++++ 1 file changed, 26 insertions(+) diff --git a/tests/auto/qgraphicsanchorlayout/tst_qgraphicsanchorlayout.cpp b/tests/auto/qgraphicsanchorlayout/tst_qgraphicsanchorlayout.cpp index cc96edb..8b52674 100644 --- a/tests/auto/qgraphicsanchorlayout/tst_qgraphicsanchorlayout.cpp +++ b/tests/auto/qgraphicsanchorlayout/tst_qgraphicsanchorlayout.cpp @@ -83,6 +83,7 @@ private slots: void infiniteMaxSizes(); void simplifiableUnfeasible(); void simplificationVsOrder(); + void parallelSimplificationOfCenter(); }; class RectWidget : public QGraphicsWidget @@ -1801,5 +1802,30 @@ void tst_QGraphicsAnchorLayout::simplificationVsOrder() } } +void tst_QGraphicsAnchorLayout::parallelSimplificationOfCenter() +{ + QSizeF min(10, 10); + QSizeF pref(20, 10); + QSizeF max(50, 10); + + QGraphicsWidget *a = createItem(min, pref, max, "A"); + QGraphicsWidget *b = createItem(min, pref, max, "B"); + + QGraphicsWidget parent; + QGraphicsAnchorLayout *l = new QGraphicsAnchorLayout(&parent); + l->setContentsMargins(0, 0, 0, 0); + + l->addAnchor(l, Qt::AnchorLeft, a, Qt::AnchorLeft); + l->addAnchor(l, Qt::AnchorRight, a, Qt::AnchorRight); + + l->addAnchor(a, Qt::AnchorHorizontalCenter, b, Qt::AnchorLeft); + l->addAnchor(b, Qt::AnchorRight, a, Qt::AnchorRight); + + parent.resize(l->effectiveSizeHint(Qt::PreferredSize)); + + QCOMPARE(a->geometry(), QRectF(0, 0, 40, 10)); + QCOMPARE(b->geometry(), QRectF(20, 0, 20, 10)); +} + QTEST_MAIN(tst_QGraphicsAnchorLayout) #include "tst_qgraphicsanchorlayout.moc" -- cgit v0.12 From 92b51d119325adc7cef518c1260c71904fc68c40 Mon Sep 17 00:00:00 2001 From: "Eduardo M. Fleury" Date: Thu, 5 Nov 2009 20:11:37 -0300 Subject: QGAL (Test): Enable remaining tests in 'qgraphicsanchorlayout1' Some tests were still disabled because were not supported somewhere in the past. Signed-off-by: Eduardo M. Fleury Reviewed-by: Caio Marcelo de Oliveira Filho --- .../tst_qgraphicsanchorlayout1.cpp | 25 ++++++++-------------- 1 file changed, 9 insertions(+), 16 deletions(-) diff --git a/tests/auto/qgraphicsanchorlayout1/tst_qgraphicsanchorlayout1.cpp b/tests/auto/qgraphicsanchorlayout1/tst_qgraphicsanchorlayout1.cpp index 57e5c41..0fbd069 100644 --- a/tests/auto/qgraphicsanchorlayout1/tst_qgraphicsanchorlayout1.cpp +++ b/tests/auto/qgraphicsanchorlayout1/tst_qgraphicsanchorlayout1.cpp @@ -423,7 +423,6 @@ void tst_QGraphicsAnchorLayout1::testAddAndRemoveAnchor() layout->setAnchor(layout, Qt::AnchorLeft, widget5, Qt::AnchorTop, 10); QCOMPARE( layout->count(), 4 ); - // ###: NOT SUPPORTED // anchor two edges of a widget (to define width / height) QTest::ignoreMessage(QtWarningMsg, "QGraphicsAnchorLayout::addAnchor(): Cannot anchor the item to itself"); layout->setAnchor(widget5, Qt::AnchorLeft, widget5, Qt::AnchorRight, 10); @@ -520,8 +519,6 @@ void tst_QGraphicsAnchorLayout1::testIsValid() widget->setLayout(layout); widget->setGeometry(QRectF(0,0,100,100)); - // ###: this shall change once isValid() is ready - // QCOMPARE(layout->isValid(), false); QCOMPARE(layout->isValid(), true); delete widget; } @@ -698,9 +695,8 @@ void tst_QGraphicsAnchorLayout1::testSpecialCases() layout2->setAnchor(widget1, Qt::AnchorRight, layout2, Qt::AnchorRight, 1); layout2->setAnchor(widget1, Qt::AnchorBottom, layout2, Qt::AnchorBottom, 1); - // ###: uncomment when simplification bug is solved - //widget->setGeometry(QRectF(0,0,100,100)); - //QCOMPARE(widget1->geometry(), QRectF(51,2,47,96)); + widget->setGeometry(QRectF(0,0,100,100)); + QCOMPARE(widget1->geometry(), QRectF(51,2,47,96)); delete widget; } @@ -900,9 +896,6 @@ void tst_QGraphicsAnchorLayout1::testBasicLayout_data() << BasicData(-1, Qt::AnchorLeft, 1, Qt::AnchorRight, 20) ; - // ### SIMPLIFICATION BUG FOR ITEM 1 - // ### remove this when bug is solved - theResult << BasicResult(0, QRectF(10, 10, 180, 80) ) << BasicResult(1, QRectF(10, 80, 10, 10) ) @@ -1732,8 +1725,6 @@ void tst_QGraphicsAnchorLayout1::testBasicLayout() QCOMPARE(expected, actual); } - // ###: not supported yet -/* // Test mirrored mode widget->setLayoutDirection(Qt::RightToLeft); layout->activate(); @@ -1745,10 +1736,13 @@ void tst_QGraphicsAnchorLayout1::testBasicLayout() if (mirroredRect.isValid()){ mirroredRect.moveLeft(size.width()-item.rect.width()-item.rect.left()); } - QCOMPARE(widgets[item.index]->geometry(), mirroredRect); + QRectF expected = truncate(mirroredRect); + QRectF actual = truncate(widgets[item.index]->geometry()); + + QCOMPARE(expected, actual); delete widgets[item.index]; } -*/ + delete widget; } @@ -2447,6 +2441,8 @@ void tst_QGraphicsAnchorLayout1::testDoubleSizePolicy_data() QTest::newRow("double size policy: expanding-preferred") << sizePolicy1 << sizePolicy2 << width1 << width2; } + // QGAL handling of ignored flag is different + if (0) { QSizePolicy sizePolicy1( QSizePolicy::Ignored, QSizePolicy::Ignored ); QSizePolicy sizePolicy2( QSizePolicy::Preferred, QSizePolicy::Preferred ); @@ -2514,9 +2510,6 @@ void tst_QGraphicsAnchorLayout1::testDoubleSizePolicy_data() void tst_QGraphicsAnchorLayout1::testDoubleSizePolicy() { - // ### Size policy is not yet supported - return; - QFETCH(QSizePolicy, policy1); QFETCH(QSizePolicy, policy2); QFETCH(qreal, width1); -- cgit v0.12 From 2906522845d3ce9723b978b8b1490dfc9b9008f0 Mon Sep 17 00:00:00 2001 From: Caio Marcelo de Oliveira Filho Date: Wed, 4 Nov 2009 19:48:54 -0300 Subject: QGAL: fix leak when restoring anchors The restore algorithm had a leak, so we did not delete all the sequences and parallel anchors that were not part of the simplified graph, i.e. that were nested inside other anchors. This commit fix the leak and clean the restore function a little bit, so the recursive function is called even for Normal anchors (which are dealt accordingly). Note that the before/after information is exactly the ->from/->to information available in the anchor being looked on. Also added an assertion to document the fact that at this point (restoring anchor simplification), one of the two anchors inside a parallel anchor must be a sequence. The algorithm depends on that because you can't have two anchors with the same start and end points. Signed-off-by: Caio Marcelo de Oliveira Filho Reviewed-by: Eduardo M. Fleury --- src/gui/graphicsview/qgraphicsanchorlayout_p.cpp | 63 ++++++++++-------------- 1 file changed, 27 insertions(+), 36 deletions(-) diff --git a/src/gui/graphicsview/qgraphicsanchorlayout_p.cpp b/src/gui/graphicsview/qgraphicsanchorlayout_p.cpp index 318ce20..ff3fe69 100644 --- a/src/gui/graphicsview/qgraphicsanchorlayout_p.cpp +++ b/src/gui/graphicsview/qgraphicsanchorlayout_p.cpp @@ -880,48 +880,40 @@ bool QGraphicsAnchorLayoutPrivate::simplifyGraphIteration(QGraphicsAnchorLayoutP return false; } -static void restoreSimplifiedAnchor(Graph &g, - AnchorData *edge, - AnchorVertex *before, - AnchorVertex *after) +static void restoreSimplifiedAnchor(Graph &g, AnchorData *edge) { - Q_ASSERT(edge->type != AnchorData::Normal); #if 0 static const char *anchortypes[] = {"Normal", "Sequential", "Parallel"}; qDebug("Restoring %s edge.", anchortypes[int(edge->type)]); #endif - if (edge->type == AnchorData::Sequential) { - SequentialAnchorData* seqEdge = static_cast(edge); - // restore the sequential anchor - AnchorVertex *prev = before; - AnchorVertex *last = after; - if (edge->from != prev) - qSwap(last, prev); - - for (int i = 0; i < seqEdge->m_edges.count(); ++i) { - AnchorVertex *v1 = (i < seqEdge->m_children.count()) ? seqEdge->m_children.at(i) : last; - AnchorData *data = seqEdge->m_edges.at(i); - if (data->type != AnchorData::Normal) { - restoreSimplifiedAnchor(g, data, prev, v1); - } else { - g.createEdge(prev, v1, data); - } - prev = v1; + + if (edge->type == AnchorData::Normal) { + g.createEdge(edge->from, edge->to, edge); + + } else if (edge->type == AnchorData::Sequential) { + SequentialAnchorData *sequence = static_cast(edge); + + for (int i = 0; i < sequence->m_edges.count(); ++i) { + AnchorData *data = sequence->m_edges.at(i); + restoreSimplifiedAnchor(g, data); } + + delete sequence; + } else if (edge->type == AnchorData::Parallel) { - ParallelAnchorData* parallelEdge = static_cast(edge); - AnchorData *parallelEdges[2] = {parallelEdge->firstEdge, - parallelEdge->secondEdge}; - for (int i = 0; i < 2; ++i) { - AnchorData *data = parallelEdges[i]; - if (data->type == AnchorData::Normal) { - g.createEdge(before, after, data); - } else { - restoreSimplifiedAnchor(g, data, before, after); - } - } + ParallelAnchorData* parallel = static_cast(edge); + + // ### Because of the way parallel anchors are created in the anchor simplification + // algorithm, we know that one of these will be a sequence, so it'll be safe if the other + // anchor create an edge between the same vertices as the parallel. + Q_ASSERT(parallel->firstEdge->type == AnchorData::Sequential + || parallel->secondEdge->type == AnchorData::Sequential); + restoreSimplifiedAnchor(g, parallel->firstEdge); + restoreSimplifiedAnchor(g, parallel->secondEdge); + + delete parallel; } } @@ -944,9 +936,8 @@ void QGraphicsAnchorLayoutPrivate::restoreSimplifiedGraph(Orientation orientatio AnchorVertex *v2 = connections.at(i).second; AnchorData *edge = g.edgeData(v1, v2); if (edge->type != AnchorData::Normal) { - AnchorData *oldEdge = g.takeEdge(v1, v2); - restoreSimplifiedAnchor(g, edge, v1, v2); - delete oldEdge; + g.takeEdge(v1, v2); + restoreSimplifiedAnchor(g, edge); } } } -- cgit v0.12 From 9d89f0bd155b9eccc89eac6ff30b572795062baa Mon Sep 17 00:00:00 2001 From: Caio Marcelo de Oliveira Filho Date: Thu, 5 Nov 2009 15:19:23 -0300 Subject: QGAL: allow parallel anchors simplify center anchors This commit make possible to parallelize anchors that are center anchors, i.e. that have extra constraints (stored in itemCenterConstraints). This is trivial to support since the parallel anchor will have the same size as its children, so it can just "take the place" of its children in the constraints. Restore function was added as well. To manipulate internal structures, relevant static functions were promoted to methods. Signed-off-by: Caio Marcelo de Oliveira Filho Reviewed-by: Eduardo M. Fleury --- src/gui/graphicsview/qgraphicsanchorlayout_p.cpp | 80 ++++++++++++++++++++---- src/gui/graphicsview/qgraphicsanchorlayout_p.h | 18 ++++-- 2 files changed, 82 insertions(+), 16 deletions(-) diff --git a/src/gui/graphicsview/qgraphicsanchorlayout_p.cpp b/src/gui/graphicsview/qgraphicsanchorlayout_p.cpp index ff3fe69..ef89612 100644 --- a/src/gui/graphicsview/qgraphicsanchorlayout_p.cpp +++ b/src/gui/graphicsview/qgraphicsanchorlayout_p.cpp @@ -536,34 +536,67 @@ inline static qreal checkAdd(qreal a, qreal b) /*! \internal - Adds \a newAnchor to the graph \a g. + Adds \a newAnchor to the graph. Returns the newAnchor itself if it could be added without further changes to the graph. If a new parallel anchor had to be created, then returns the new parallel anchor. If a parallel anchor had to be created and it results in an unfeasible setup, \a feasible is set to false, otherwise true. + + Note that in the case a new parallel anchor is created, it might also take over some constraints + from its children anchors. */ -static AnchorData *addAnchorMaybeParallel(Graph *g, - AnchorData *newAnchor, bool *feasible) +AnchorData *QGraphicsAnchorLayoutPrivate::addAnchorMaybeParallel(AnchorData *newAnchor, bool *feasible) { + Orientation orientation = Orientation(newAnchor->orientation); + Graph &g = graph[orientation]; *feasible = true; // If already exists one anchor where newAnchor is supposed to be, we create a parallel // anchor. - if (AnchorData *oldAnchor = g->takeEdge(newAnchor->from, newAnchor->to)) { + if (AnchorData *oldAnchor = g.takeEdge(newAnchor->from, newAnchor->to)) { ParallelAnchorData *parallel = new ParallelAnchorData(oldAnchor, newAnchor); + // The parallel anchor will "replace" its children anchors in + // every center constraint that they appear. + + // ### If the dependent (center) anchors had reference(s) to their constraints, we + // could avoid traversing all the itemCenterConstraints. + QList &constraints = itemCenterConstraints[orientation]; + + AnchorData *children[2] = { oldAnchor, newAnchor }; + QList *childrenConstraints[2] = { ¶llel->m_firstConstraints, + ¶llel->m_secondConstraints }; + + for (int i = 0; i < 2; ++i) { + AnchorData *child = children[i]; + QList *childConstraints = childrenConstraints[i]; + + if (!child->isCenterAnchor) + continue; + + parallel->isCenterAnchor = true; + + for (int i = 0; i < constraints.count(); ++i) { + QSimplexConstraint *c = constraints[i]; + if (c->variables.contains(child)) { + childConstraints->append(c); + qreal v = c->variables.take(child); + c->variables.insert(parallel, v); + } + } + } + // At this point we can identify that the parallel anchor is not feasible, e.g. one // anchor minimum size is bigger than the other anchor maximum size. *feasible = parallel->refreshSizeHints_helper(0, false); newAnchor = parallel; } - g->createEdge(newAnchor->from, newAnchor->to, newAnchor); + g.createEdge(newAnchor->from, newAnchor->to, newAnchor); return newAnchor; } - /*! \internal @@ -858,7 +891,7 @@ bool QGraphicsAnchorLayoutPrivate::simplifyGraphIteration(QGraphicsAnchorLayoutP // If 'beforeSequence' and 'afterSequence' already had an anchor between them, we'll // create a parallel anchor between the new sequence and the old anchor. bool newFeasible; - AnchorData *newAnchor = addAnchorMaybeParallel(&g, sequence, &newFeasible); + AnchorData *newAnchor = addAnchorMaybeParallel(sequence, &newFeasible); if (!newFeasible) { *feasible = false; @@ -880,7 +913,7 @@ bool QGraphicsAnchorLayoutPrivate::simplifyGraphIteration(QGraphicsAnchorLayoutP return false; } -static void restoreSimplifiedAnchor(Graph &g, AnchorData *edge) +void QGraphicsAnchorLayoutPrivate::restoreSimplifiedAnchor(AnchorData *edge) { #if 0 static const char *anchortypes[] = {"Normal", @@ -889,6 +922,8 @@ static void restoreSimplifiedAnchor(Graph &g, AnchorDa qDebug("Restoring %s edge.", anchortypes[int(edge->type)]); #endif + Graph &g = graph[edge->orientation]; + if (edge->type == AnchorData::Normal) { g.createEdge(edge->from, edge->to, edge); @@ -897,26 +932,47 @@ static void restoreSimplifiedAnchor(Graph &g, AnchorDa for (int i = 0; i < sequence->m_edges.count(); ++i) { AnchorData *data = sequence->m_edges.at(i); - restoreSimplifiedAnchor(g, data); + restoreSimplifiedAnchor(data); } delete sequence; } else if (edge->type == AnchorData::Parallel) { ParallelAnchorData* parallel = static_cast(edge); + restoreSimplifiedConstraints(parallel); // ### Because of the way parallel anchors are created in the anchor simplification // algorithm, we know that one of these will be a sequence, so it'll be safe if the other // anchor create an edge between the same vertices as the parallel. Q_ASSERT(parallel->firstEdge->type == AnchorData::Sequential || parallel->secondEdge->type == AnchorData::Sequential); - restoreSimplifiedAnchor(g, parallel->firstEdge); - restoreSimplifiedAnchor(g, parallel->secondEdge); + restoreSimplifiedAnchor(parallel->firstEdge); + restoreSimplifiedAnchor(parallel->secondEdge); delete parallel; } } +void QGraphicsAnchorLayoutPrivate::restoreSimplifiedConstraints(ParallelAnchorData *parallel) +{ + if (!parallel->isCenterAnchor) + return; + + for (int i = 0; i < parallel->m_firstConstraints.count(); ++i) { + QSimplexConstraint *c = parallel->m_firstConstraints[i]; + qreal v = c->variables[parallel]; + c->variables.remove(parallel); + c->variables.insert(parallel->firstEdge, v); + } + + for (int i = 0; i < parallel->m_secondConstraints.count(); ++i) { + QSimplexConstraint *c = parallel->m_secondConstraints[i]; + qreal v = c->variables[parallel]; + c->variables.remove(parallel); + c->variables.insert(parallel->secondEdge, v); + } +} + void QGraphicsAnchorLayoutPrivate::restoreSimplifiedGraph(Orientation orientation) { if (!graphSimplified[orientation]) @@ -937,7 +993,7 @@ void QGraphicsAnchorLayoutPrivate::restoreSimplifiedGraph(Orientation orientatio AnchorData *edge = g.edgeData(v1, v2); if (edge->type != AnchorData::Normal) { g.takeEdge(v1, v2); - restoreSimplifiedAnchor(g, edge); + restoreSimplifiedAnchor(edge); } } } diff --git a/src/gui/graphicsview/qgraphicsanchorlayout_p.h b/src/gui/graphicsview/qgraphicsanchorlayout_p.h index d8e62b4..d7b3cfd 100644 --- a/src/gui/graphicsview/qgraphicsanchorlayout_p.h +++ b/src/gui/graphicsview/qgraphicsanchorlayout_p.h @@ -275,6 +275,9 @@ struct ParallelAnchorData : public AnchorData AnchorData* firstEdge; AnchorData* secondEdge; + + QList m_firstConstraints; + QList m_secondConstraints; }; /*! @@ -433,20 +436,27 @@ public: QLayoutStyleInfo &styleInfo() const; - // Activation methods - bool simplifyGraph(Orientation orientation); - bool simplifyGraphIteration(Orientation orientation, bool *feasible); - void restoreSimplifiedGraph(Orientation orientation); + AnchorData *addAnchorMaybeParallel(AnchorData *newAnchor, bool *feasible); + // Activation void calculateGraphs(); void calculateGraphs(Orientation orientation); + // Simplification + bool simplifyGraph(Orientation orientation); + bool simplifyGraphIteration(Orientation orientation, bool *feasible); + + void restoreSimplifiedGraph(Orientation orientation); + void restoreSimplifiedAnchor(AnchorData *edge); + void restoreSimplifiedConstraints(ParallelAnchorData *parallel); + bool calculateTrunk(Orientation orien