~loic.molinari/+junk/qtdeclarative-shadereffectsource-changes

« back to all changes in this revision

Viewing changes to src/quick/items/qquickstateoperations.cpp

  • Committer: Loïc Molinari
  • Date: 2012-04-21 17:59:51 UTC
  • Revision ID: loic.molinari@canonical.com-20120421175951-bqx68caaf5zrp76l
Initial import

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/****************************************************************************
 
2
**
 
3
** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies).
 
4
** Contact: http://www.qt-project.org/
 
5
**
 
6
** This file is part of the QtQml module of the Qt Toolkit.
 
7
**
 
8
** $QT_BEGIN_LICENSE:LGPL$
 
9
** GNU Lesser General Public License Usage
 
10
** This file may be used under the terms of the GNU Lesser General Public
 
11
** License version 2.1 as published by the Free Software Foundation and
 
12
** appearing in the file LICENSE.LGPL included in the packaging of this
 
13
** file. Please review the following information to ensure the GNU Lesser
 
14
** General Public License version 2.1 requirements will be met:
 
15
** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
 
16
**
 
17
** In addition, as a special exception, Nokia gives you certain additional
 
18
** rights. These rights are described in the Nokia Qt LGPL Exception
 
19
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
 
20
**
 
21
** GNU General Public License Usage
 
22
** Alternatively, this file may be used under the terms of the GNU General
 
23
** Public License version 3.0 as published by the Free Software Foundation
 
24
** and appearing in the file LICENSE.GPL included in the packaging of this
 
25
** file. Please review the following information to ensure the GNU General
 
26
** Public License version 3.0 requirements will be met:
 
27
** http://www.gnu.org/copyleft/gpl.html.
 
28
**
 
29
** Other Usage
 
30
** Alternatively, this file may be used in accordance with the terms and
 
31
** conditions contained in a signed written agreement between you and Nokia.
 
32
**
 
33
**
 
34
**
 
35
**
 
36
**
 
37
**
 
38
** $QT_END_LICENSE$
 
39
**
 
40
****************************************************************************/
 
41
 
 
42
#include "qquickstateoperations_p.h"
 
43
#include "qquickitem_p.h"
 
44
 
 
45
#include <private/qquickstate_p_p.h>
 
46
 
 
47
#include <QtQml/qqmlinfo.h>
 
48
#include <QtCore/qmath.h>
 
49
 
 
50
QT_BEGIN_NAMESPACE
 
51
 
 
52
class QQuickParentChangePrivate : public QQuickStateOperationPrivate
 
53
{
 
54
    Q_DECLARE_PUBLIC(QQuickParentChange)
 
55
public:
 
56
    QQuickParentChangePrivate() : target(0), parent(0), origParent(0), origStackBefore(0),
 
57
        rewindParent(0), rewindStackBefore(0) {}
 
58
 
 
59
    QQuickItem *target;
 
60
    QQmlGuard<QQuickItem> parent;
 
61
    QQmlGuard<QQuickItem> origParent;
 
62
    QQmlGuard<QQuickItem> origStackBefore;
 
63
    QQuickItem *rewindParent;
 
64
    QQuickItem *rewindStackBefore;
 
65
 
 
66
    QQmlNullableValue<QQmlScriptString> xString;
 
67
    QQmlNullableValue<QQmlScriptString> yString;
 
68
    QQmlNullableValue<QQmlScriptString> widthString;
 
69
    QQmlNullableValue<QQmlScriptString> heightString;
 
70
    QQmlNullableValue<QQmlScriptString> scaleString;
 
71
    QQmlNullableValue<QQmlScriptString> rotationString;
 
72
 
 
73
    void doChange(QQuickItem *targetParent, QQuickItem *stackBefore = 0);
 
74
};
 
75
 
 
76
void QQuickParentChangePrivate::doChange(QQuickItem *targetParent, QQuickItem *stackBefore)
 
77
{
 
78
    if (targetParent && target && target->parentItem()) {
 
79
        Q_Q(QQuickParentChange);
 
80
        bool ok;
 
81
        const QTransform &transform = target->parentItem()->itemTransform(targetParent, &ok);
 
82
        if (transform.type() >= QTransform::TxShear || !ok) {
 
83
            qmlInfo(q) << QQuickParentChange::tr("Unable to preserve appearance under complex transform");
 
84
            ok = false;
 
85
        }
 
86
 
 
87
        qreal scale = 1;
 
88
        qreal rotation = 0;
 
89
        bool isRotate = (transform.type() == QTransform::TxRotate) || (transform.m11() < 0);
 
90
        if (ok && !isRotate) {
 
91
            if (transform.m11() == transform.m22())
 
92
                scale = transform.m11();
 
93
            else {
 
94
                qmlInfo(q) << QQuickParentChange::tr("Unable to preserve appearance under non-uniform scale");
 
95
                ok = false;
 
96
            }
 
97
        } else if (ok && isRotate) {
 
98
            if (transform.m11() == transform.m22())
 
99
                scale = qSqrt(transform.m11()*transform.m11() + transform.m12()*transform.m12());
 
100
            else {
 
101
                qmlInfo(q) << QQuickParentChange::tr("Unable to preserve appearance under non-uniform scale");
 
102
                ok = false;
 
103
            }
 
104
 
 
105
            if (scale != 0)
 
106
                rotation = atan2(transform.m12()/scale, transform.m11()/scale) * 180/M_PI;
 
107
            else {
 
108
                qmlInfo(q) << QQuickParentChange::tr("Unable to preserve appearance under scale of 0");
 
109
                ok = false;
 
110
            }
 
111
        }
 
112
 
 
113
        const QPointF &point = transform.map(QPointF(target->x(),target->y()));
 
114
        qreal x = point.x();
 
115
        qreal y = point.y();
 
116
 
 
117
        // setParentItem will update the transformOriginPoint if needed
 
118
        target->setParentItem(targetParent);
 
119
 
 
120
        if (ok && target->transformOrigin() != QQuickItem::TopLeft) {
 
121
            qreal tempxt = target->transformOriginPoint().x();
 
122
            qreal tempyt = target->transformOriginPoint().y();
 
123
            QTransform t;
 
124
            t.translate(-tempxt, -tempyt);
 
125
            t.rotate(rotation);
 
126
            t.scale(scale, scale);
 
127
            t.translate(tempxt, tempyt);
 
128
            const QPointF &offset = t.map(QPointF(0,0));
 
129
            x += offset.x();
 
130
            y += offset.y();
 
131
        }
 
132
 
 
133
        if (ok) {
 
134
            //qDebug() << x << y << rotation << scale;
 
135
            target->setPos(QPointF(x, y));
 
136
            target->setRotation(target->rotation() + rotation);
 
137
            target->setScale(target->scale() * scale);
 
138
        }
 
139
    } else if (target) {
 
140
        target->setParentItem(targetParent);
 
141
    }
 
142
 
 
143
    //restore the original stack position.
 
144
    //### if stackBefore has also been reparented this won't work
 
145
    if (stackBefore)
 
146
        target->stackBefore(stackBefore);
 
147
}
 
148
 
 
149
QQuickParentChange::QQuickParentChange(QObject *parent)
 
150
    : QQuickStateOperation(*(new QQuickParentChangePrivate), parent)
 
151
{
 
152
}
 
153
 
 
154
QQuickParentChange::~QQuickParentChange()
 
155
{
 
156
}
 
157
 
 
158
QQmlScriptString QQuickParentChange::x() const
 
159
{
 
160
    Q_D(const QQuickParentChange);
 
161
    return d->xString.value;
 
162
}
 
163
 
 
164
void QQuickParentChange::setX(QQmlScriptString x)
 
165
{
 
166
    Q_D(QQuickParentChange);
 
167
    d->xString = x;
 
168
}
 
169
 
 
170
bool QQuickParentChange::xIsSet() const
 
171
{
 
172
    Q_D(const QQuickParentChange);
 
173
    return d->xString.isValid();
 
174
}
 
175
 
 
176
QQmlScriptString QQuickParentChange::y() const
 
177
{
 
178
    Q_D(const QQuickParentChange);
 
179
    return d->yString.value;
 
180
}
 
181
 
 
182
void QQuickParentChange::setY(QQmlScriptString y)
 
183
{
 
184
    Q_D(QQuickParentChange);
 
185
    d->yString = y;
 
186
}
 
187
 
 
188
bool QQuickParentChange::yIsSet() const
 
189
{
 
190
    Q_D(const QQuickParentChange);
 
191
    return d->yString.isValid();
 
192
}
 
193
 
 
194
QQmlScriptString QQuickParentChange::width() const
 
195
{
 
196
    Q_D(const QQuickParentChange);
 
197
    return d->widthString.value;
 
198
}
 
199
 
 
200
void QQuickParentChange::setWidth(QQmlScriptString width)
 
201
{
 
202
    Q_D(QQuickParentChange);
 
203
    d->widthString = width;
 
204
}
 
205
 
 
206
bool QQuickParentChange::widthIsSet() const
 
207
{
 
208
    Q_D(const QQuickParentChange);
 
209
    return d->widthString.isValid();
 
210
}
 
211
 
 
212
QQmlScriptString QQuickParentChange::height() const
 
213
{
 
214
    Q_D(const QQuickParentChange);
 
215
    return d->heightString.value;
 
216
}
 
217
 
 
218
void QQuickParentChange::setHeight(QQmlScriptString height)
 
219
{
 
220
    Q_D(QQuickParentChange);
 
221
    d->heightString = height;
 
222
}
 
223
 
 
224
bool QQuickParentChange::heightIsSet() const
 
225
{
 
226
    Q_D(const QQuickParentChange);
 
227
    return d->heightString.isValid();
 
228
}
 
229
 
 
230
QQmlScriptString QQuickParentChange::scale() const
 
231
{
 
232
    Q_D(const QQuickParentChange);
 
233
    return d->scaleString.value;
 
234
}
 
235
 
 
236
void QQuickParentChange::setScale(QQmlScriptString scale)
 
237
{
 
238
    Q_D(QQuickParentChange);
 
239
    d->scaleString = scale;
 
240
}
 
241
 
 
242
bool QQuickParentChange::scaleIsSet() const
 
243
{
 
244
    Q_D(const QQuickParentChange);
 
245
    return d->scaleString.isValid();
 
246
}
 
247
 
 
248
QQmlScriptString QQuickParentChange::rotation() const
 
249
{
 
250
    Q_D(const QQuickParentChange);
 
251
    return d->rotationString.value;
 
252
}
 
253
 
 
254
void QQuickParentChange::setRotation(QQmlScriptString rotation)
 
255
{
 
256
    Q_D(QQuickParentChange);
 
257
    d->rotationString = rotation;
 
258
}
 
259
 
 
260
bool QQuickParentChange::rotationIsSet() const
 
261
{
 
262
    Q_D(const QQuickParentChange);
 
263
    return d->rotationString.isValid();
 
264
}
 
265
 
 
266
QQuickItem *QQuickParentChange::originalParent() const
 
267
{
 
268
    Q_D(const QQuickParentChange);
 
269
    return d->origParent;
 
270
}
 
271
 
 
272
QQuickItem *QQuickParentChange::object() const
 
273
{
 
274
    Q_D(const QQuickParentChange);
 
275
    return d->target;
 
276
}
 
277
 
 
278
void QQuickParentChange::setObject(QQuickItem *target)
 
279
{
 
280
    Q_D(QQuickParentChange);
 
281
    d->target = target;
 
282
}
 
283
 
 
284
QQuickItem *QQuickParentChange::parent() const
 
285
{
 
286
    Q_D(const QQuickParentChange);
 
287
    return d->parent;
 
288
}
 
289
 
 
290
void QQuickParentChange::setParent(QQuickItem *parent)
 
291
{
 
292
    Q_D(QQuickParentChange);
 
293
    d->parent = parent;
 
294
}
 
295
 
 
296
QQuickStateOperation::ActionList QQuickParentChange::actions()
 
297
{
 
298
    Q_D(QQuickParentChange);
 
299
    if (!d->target || !d->parent)
 
300
        return ActionList();
 
301
 
 
302
    ActionList actions;
 
303
 
 
304
    QQuickAction a;
 
305
    a.event = this;
 
306
    actions << a;
 
307
 
 
308
    if (d->xString.isValid()) {
 
309
        bool ok = false;
 
310
        QString script = d->xString.value.script();
 
311
        qreal x = script.toFloat(&ok);
 
312
        if (ok) {
 
313
            QQuickAction xa(d->target, QLatin1String("x"), x);
 
314
            actions << xa;
 
315
        } else {
 
316
            QQmlBinding *newBinding = new QQmlBinding(script, d->target, qmlContext(this));
 
317
            QQmlProperty property(d->target, QLatin1String("x"));
 
318
            newBinding->setTarget(property);
 
319
            QQuickAction xa;
 
320
            xa.property = property;
 
321
            xa.toBinding = QQmlAbstractBinding::getPointer(newBinding);
 
322
            xa.fromValue = xa.property.read();
 
323
            xa.deletableToBinding = true;
 
324
            actions << xa;
 
325
        }
 
326
    }
 
327
 
 
328
    if (d->yString.isValid()) {
 
329
        bool ok = false;
 
330
        QString script = d->yString.value.script();
 
331
        qreal y = script.toFloat(&ok);
 
332
        if (ok) {
 
333
            QQuickAction ya(d->target, QLatin1String("y"), y);
 
334
            actions << ya;
 
335
        } else {
 
336
            QQmlBinding *newBinding = new QQmlBinding(script, d->target, qmlContext(this));
 
337
            QQmlProperty property(d->target, QLatin1String("y"));
 
338
            newBinding->setTarget(property);
 
339
            QQuickAction ya;
 
340
            ya.property = property;
 
341
            ya.toBinding = QQmlAbstractBinding::getPointer(newBinding);
 
342
            ya.fromValue = ya.property.read();
 
343
            ya.deletableToBinding = true;
 
344
            actions << ya;
 
345
        }
 
346
    }
 
347
 
 
348
    if (d->scaleString.isValid()) {
 
349
        bool ok = false;
 
350
        QString script = d->scaleString.value.script();
 
351
        qreal scale = script.toFloat(&ok);
 
352
        if (ok) {
 
353
            QQuickAction sa(d->target, QLatin1String("scale"), scale);
 
354
            actions << sa;
 
355
        } else {
 
356
            QQmlBinding *newBinding = new QQmlBinding(script, d->target, qmlContext(this));
 
357
            QQmlProperty property(d->target, QLatin1String("scale"));
 
358
            newBinding->setTarget(property);
 
359
            QQuickAction sa;
 
360
            sa.property = property;
 
361
            sa.toBinding = QQmlAbstractBinding::getPointer(newBinding);
 
362
            sa.fromValue = sa.property.read();
 
363
            sa.deletableToBinding = true;
 
364
            actions << sa;
 
365
        }
 
366
    }
 
367
 
 
368
    if (d->rotationString.isValid()) {
 
369
        bool ok = false;
 
370
        QString script = d->rotationString.value.script();
 
371
        qreal rotation = script.toFloat(&ok);
 
372
        if (ok) {
 
373
            QQuickAction ra(d->target, QLatin1String("rotation"), rotation);
 
374
            actions << ra;
 
375
        } else {
 
376
            QQmlBinding *newBinding = new QQmlBinding(script, d->target, qmlContext(this));
 
377
            QQmlProperty property(d->target, QLatin1String("rotation"));
 
378
            newBinding->setTarget(property);
 
379
            QQuickAction ra;
 
380
            ra.property = property;
 
381
            ra.toBinding = QQmlAbstractBinding::getPointer(newBinding);
 
382
            ra.fromValue = ra.property.read();
 
383
            ra.deletableToBinding = true;
 
384
            actions << ra;
 
385
        }
 
386
    }
 
387
 
 
388
    if (d->widthString.isValid()) {
 
389
        bool ok = false;
 
390
        QString script = d->widthString.value.script();
 
391
        qreal width = script.toFloat(&ok);
 
392
        if (ok) {
 
393
            QQuickAction wa(d->target, QLatin1String("width"), width);
 
394
            actions << wa;
 
395
        } else {
 
396
            QQmlBinding *newBinding = new QQmlBinding(script, d->target, qmlContext(this));
 
397
            QQmlProperty property(d->target, QLatin1String("width"));
 
398
            newBinding->setTarget(property);
 
399
            QQuickAction wa;
 
400
            wa.property = property;
 
401
            wa.toBinding = QQmlAbstractBinding::getPointer(newBinding);
 
402
            wa.fromValue = wa.property.read();
 
403
            wa.deletableToBinding = true;
 
404
            actions << wa;
 
405
        }
 
406
    }
 
407
 
 
408
    if (d->heightString.isValid()) {
 
409
        bool ok = false;
 
410
        QString script = d->heightString.value.script();
 
411
        qreal height = script.toFloat(&ok);
 
412
        if (ok) {
 
413
            QQuickAction ha(d->target, QLatin1String("height"), height);
 
414
            actions << ha;
 
415
        } else {
 
416
            QQmlBinding *newBinding = new QQmlBinding(script, d->target, qmlContext(this));
 
417
            QQmlProperty property(d->target, QLatin1String("height"));
 
418
            newBinding->setTarget(property);
 
419
            QQuickAction ha;
 
420
            ha.property = property;
 
421
            ha.toBinding = QQmlAbstractBinding::getPointer(newBinding);
 
422
            ha.fromValue = ha.property.read();
 
423
            ha.deletableToBinding = true;
 
424
            actions << ha;
 
425
        }
 
426
    }
 
427
 
 
428
    return actions;
 
429
}
 
430
 
 
431
void QQuickParentChange::saveOriginals()
 
432
{
 
433
    Q_D(QQuickParentChange);
 
434
    saveCurrentValues();
 
435
    d->origParent = d->rewindParent;
 
436
    d->origStackBefore = d->rewindStackBefore;
 
437
}
 
438
 
 
439
/*void QQuickParentChange::copyOriginals(QQuickActionEvent *other)
 
440
{
 
441
    Q_D(QQuickParentChange);
 
442
    QQuickParentChange *pc = static_cast<QQuickParentChange*>(other);
 
443
 
 
444
    d->origParent = pc->d_func()->rewindParent;
 
445
    d->origStackBefore = pc->d_func()->rewindStackBefore;
 
446
 
 
447
    saveCurrentValues();
 
448
}*/
 
449
 
 
450
void QQuickParentChange::execute(Reason)
 
451
{
 
452
    Q_D(QQuickParentChange);
 
453
    d->doChange(d->parent);
 
454
}
 
455
 
 
456
bool QQuickParentChange::isReversable()
 
457
{
 
458
    return true;
 
459
}
 
460
 
 
461
void QQuickParentChange::reverse(Reason)
 
462
{
 
463
    Q_D(QQuickParentChange);
 
464
    d->doChange(d->origParent, d->origStackBefore);
 
465
}
 
466
 
 
467
QQuickActionEvent::EventType QQuickParentChange::type() const
 
468
{
 
469
    return ParentChange;
 
470
}
 
471
 
 
472
bool QQuickParentChange::override(QQuickActionEvent*other)
 
473
{
 
474
    Q_D(QQuickParentChange);
 
475
    if (other->type() != ParentChange)
 
476
        return false;
 
477
    if (QQuickParentChange *otherPC = static_cast<QQuickParentChange*>(other))
 
478
        return (d->target == otherPC->object());
 
479
    return false;
 
480
}
 
481
 
 
482
void QQuickParentChange::saveCurrentValues()
 
483
{
 
484
    Q_D(QQuickParentChange);
 
485
    if (!d->target) {
 
486
        d->rewindParent = 0;
 
487
        d->rewindStackBefore = 0;
 
488
        return;
 
489
    }
 
490
 
 
491
    d->rewindParent = d->target->parentItem();
 
492
    d->rewindStackBefore = 0;
 
493
 
 
494
    if (!d->rewindParent)
 
495
        return;
 
496
 
 
497
    QList<QQuickItem *> children = d->rewindParent->childItems();
 
498
    for (int ii = 0; ii < children.count() - 1; ++ii) {
 
499
        if (children.at(ii) == d->target) {
 
500
            d->rewindStackBefore = children.at(ii + 1);
 
501
            break;
 
502
        }
 
503
    }
 
504
}
 
505
 
 
506
void QQuickParentChange::rewind()
 
507
{
 
508
    Q_D(QQuickParentChange);
 
509
    d->doChange(d->rewindParent, d->rewindStackBefore);
 
510
}
 
511
 
 
512
class QQuickAnchorSetPrivate : public QObjectPrivate
 
513
{
 
514
    Q_DECLARE_PUBLIC(QQuickAnchorSet)
 
515
public:
 
516
    QQuickAnchorSetPrivate()
 
517
      : usedAnchors(0), resetAnchors(0), fill(0),
 
518
        centerIn(0)/*, leftMargin(0), rightMargin(0), topMargin(0), bottomMargin(0),
 
519
        margins(0), vCenterOffset(0), hCenterOffset(0), baselineOffset(0)*/
 
520
    {
 
521
    }
 
522
 
 
523
    QQuickAnchors::Anchors usedAnchors;
 
524
    QQuickAnchors::Anchors resetAnchors;
 
525
 
 
526
    QQuickItem *fill;
 
527
    QQuickItem *centerIn;
 
528
 
 
529
    QQmlScriptString leftScript;
 
530
    QQmlScriptString rightScript;
 
531
    QQmlScriptString topScript;
 
532
    QQmlScriptString bottomScript;
 
533
    QQmlScriptString hCenterScript;
 
534
    QQmlScriptString vCenterScript;
 
535
    QQmlScriptString baselineScript;
 
536
 
 
537
    /*qreal leftMargin;
 
538
    qreal rightMargin;
 
539
    qreal topMargin;
 
540
    qreal bottomMargin;
 
541
    qreal margins;
 
542
    qreal vCenterOffset;
 
543
    qreal hCenterOffset;
 
544
    qreal baselineOffset;*/
 
545
};
 
546
 
 
547
QQuickAnchorSet::QQuickAnchorSet(QObject *parent)
 
548
  : QObject(*new QQuickAnchorSetPrivate, parent)
 
549
{
 
550
}
 
551
 
 
552
QQuickAnchorSet::~QQuickAnchorSet()
 
553
{
 
554
}
 
555
 
 
556
QQmlScriptString QQuickAnchorSet::top() const
 
557
{
 
558
    Q_D(const QQuickAnchorSet);
 
559
    return d->topScript;
 
560
}
 
561
 
 
562
void QQuickAnchorSet::setTop(const QQmlScriptString &edge)
 
563
{
 
564
    Q_D(QQuickAnchorSet);
 
565
    d->usedAnchors |= QQuickAnchors::TopAnchor;
 
566
    d->topScript = edge;
 
567
    if (edge.script() == QLatin1String("undefined"))
 
568
        resetTop();
 
569
}
 
570
 
 
571
void QQuickAnchorSet::resetTop()
 
572
{
 
573
    Q_D(QQuickAnchorSet);
 
574
    d->usedAnchors &= ~QQuickAnchors::TopAnchor;
 
575
    d->resetAnchors |= QQuickAnchors::TopAnchor;
 
576
}
 
577
 
 
578
QQmlScriptString QQuickAnchorSet::bottom() const
 
579
{
 
580
    Q_D(const QQuickAnchorSet);
 
581
    return d->bottomScript;
 
582
}
 
583
 
 
584
void QQuickAnchorSet::setBottom(const QQmlScriptString &edge)
 
585
{
 
586
    Q_D(QQuickAnchorSet);
 
587
    d->usedAnchors |= QQuickAnchors::BottomAnchor;
 
588
    d->bottomScript = edge;
 
589
    if (edge.script() == QLatin1String("undefined"))
 
590
        resetBottom();
 
591
}
 
592
 
 
593
void QQuickAnchorSet::resetBottom()
 
594
{
 
595
    Q_D(QQuickAnchorSet);
 
596
    d->usedAnchors &= ~QQuickAnchors::BottomAnchor;
 
597
    d->resetAnchors |= QQuickAnchors::BottomAnchor;
 
598
}
 
599
 
 
600
QQmlScriptString QQuickAnchorSet::verticalCenter() const
 
601
{
 
602
    Q_D(const QQuickAnchorSet);
 
603
    return d->vCenterScript;
 
604
}
 
605
 
 
606
void QQuickAnchorSet::setVerticalCenter(const QQmlScriptString &edge)
 
607
{
 
608
    Q_D(QQuickAnchorSet);
 
609
    d->usedAnchors |= QQuickAnchors::VCenterAnchor;
 
610
    d->vCenterScript = edge;
 
611
    if (edge.script() == QLatin1String("undefined"))
 
612
        resetVerticalCenter();
 
613
}
 
614
 
 
615
void QQuickAnchorSet::resetVerticalCenter()
 
616
{
 
617
    Q_D(QQuickAnchorSet);
 
618
    d->usedAnchors &= ~QQuickAnchors::VCenterAnchor;
 
619
    d->resetAnchors |= QQuickAnchors::VCenterAnchor;
 
620
}
 
621
 
 
622
QQmlScriptString QQuickAnchorSet::baseline() const
 
623
{
 
624
    Q_D(const QQuickAnchorSet);
 
625
    return d->baselineScript;
 
626
}
 
627
 
 
628
void QQuickAnchorSet::setBaseline(const QQmlScriptString &edge)
 
629
{
 
630
    Q_D(QQuickAnchorSet);
 
631
    d->usedAnchors |= QQuickAnchors::BaselineAnchor;
 
632
    d->baselineScript = edge;
 
633
    if (edge.script() == QLatin1String("undefined"))
 
634
        resetBaseline();
 
635
}
 
636
 
 
637
void QQuickAnchorSet::resetBaseline()
 
638
{
 
639
    Q_D(QQuickAnchorSet);
 
640
    d->usedAnchors &= ~QQuickAnchors::BaselineAnchor;
 
641
    d->resetAnchors |= QQuickAnchors::BaselineAnchor;
 
642
}
 
643
 
 
644
QQmlScriptString QQuickAnchorSet::left() const
 
645
{
 
646
    Q_D(const QQuickAnchorSet);
 
647
    return d->leftScript;
 
648
}
 
649
 
 
650
void QQuickAnchorSet::setLeft(const QQmlScriptString &edge)
 
651
{
 
652
    Q_D(QQuickAnchorSet);
 
653
    d->usedAnchors |= QQuickAnchors::LeftAnchor;
 
654
    d->leftScript = edge;
 
655
    if (edge.script() == QLatin1String("undefined"))
 
656
        resetLeft();
 
657
}
 
658
 
 
659
void QQuickAnchorSet::resetLeft()
 
660
{
 
661
    Q_D(QQuickAnchorSet);
 
662
    d->usedAnchors &= ~QQuickAnchors::LeftAnchor;
 
663
    d->resetAnchors |= QQuickAnchors::LeftAnchor;
 
664
}
 
665
 
 
666
QQmlScriptString QQuickAnchorSet::right() const
 
667
{
 
668
    Q_D(const QQuickAnchorSet);
 
669
    return d->rightScript;
 
670
}
 
671
 
 
672
void QQuickAnchorSet::setRight(const QQmlScriptString &edge)
 
673
{
 
674
    Q_D(QQuickAnchorSet);
 
675
    d->usedAnchors |= QQuickAnchors::RightAnchor;
 
676
    d->rightScript = edge;
 
677
    if (edge.script() == QLatin1String("undefined"))
 
678
        resetRight();
 
679
}
 
680
 
 
681
void QQuickAnchorSet::resetRight()
 
682
{
 
683
    Q_D(QQuickAnchorSet);
 
684
    d->usedAnchors &= ~QQuickAnchors::RightAnchor;
 
685
    d->resetAnchors |= QQuickAnchors::RightAnchor;
 
686
}
 
687
 
 
688
QQmlScriptString QQuickAnchorSet::horizontalCenter() const
 
689
{
 
690
    Q_D(const QQuickAnchorSet);
 
691
    return d->hCenterScript;
 
692
}
 
693
 
 
694
void QQuickAnchorSet::setHorizontalCenter(const QQmlScriptString &edge)
 
695
{
 
696
    Q_D(QQuickAnchorSet);
 
697
    d->usedAnchors |= QQuickAnchors::HCenterAnchor;
 
698
    d->hCenterScript = edge;
 
699
    if (edge.script() == QLatin1String("undefined"))
 
700
        resetHorizontalCenter();
 
701
}
 
702
 
 
703
void QQuickAnchorSet::resetHorizontalCenter()
 
704
{
 
705
    Q_D(QQuickAnchorSet);
 
706
    d->usedAnchors &= ~QQuickAnchors::HCenterAnchor;
 
707
    d->resetAnchors |= QQuickAnchors::HCenterAnchor;
 
708
}
 
709
 
 
710
QQuickItem *QQuickAnchorSet::fill() const
 
711
{
 
712
    Q_D(const QQuickAnchorSet);
 
713
    return d->fill;
 
714
}
 
715
 
 
716
void QQuickAnchorSet::setFill(QQuickItem *f)
 
717
{
 
718
    Q_D(QQuickAnchorSet);
 
719
    d->fill = f;
 
720
}
 
721
 
 
722
void QQuickAnchorSet::resetFill()
 
723
{
 
724
    setFill(0);
 
725
}
 
726
 
 
727
QQuickItem *QQuickAnchorSet::centerIn() const
 
728
{
 
729
    Q_D(const QQuickAnchorSet);
 
730
    return d->centerIn;
 
731
}
 
732
 
 
733
void QQuickAnchorSet::setCenterIn(QQuickItem* c)
 
734
{
 
735
    Q_D(QQuickAnchorSet);
 
736
    d->centerIn = c;
 
737
}
 
738
 
 
739
void QQuickAnchorSet::resetCenterIn()
 
740
{
 
741
    setCenterIn(0);
 
742
}
 
743
 
 
744
 
 
745
class QQuickAnchorChangesPrivate : public QQuickStateOperationPrivate
 
746
{
 
747
public:
 
748
    QQuickAnchorChangesPrivate()
 
749
        : target(0), anchorSet(new QQuickAnchorSet),
 
750
          leftBinding(0), rightBinding(0), hCenterBinding(0),
 
751
          topBinding(0), bottomBinding(0), vCenterBinding(0), baselineBinding(0),
 
752
          origLeftBinding(0), origRightBinding(0), origHCenterBinding(0),
 
753
          origTopBinding(0), origBottomBinding(0), origVCenterBinding(0),
 
754
          origBaselineBinding(0)
 
755
    {
 
756
 
 
757
    }
 
758
    ~QQuickAnchorChangesPrivate() { delete anchorSet; }
 
759
 
 
760
    QQuickItem *target;
 
761
    QQuickAnchorSet *anchorSet;
 
762
 
 
763
    QQmlBinding *leftBinding;
 
764
    QQmlBinding *rightBinding;
 
765
    QQmlBinding *hCenterBinding;
 
766
    QQmlBinding *topBinding;
 
767
    QQmlBinding *bottomBinding;
 
768
    QQmlBinding *vCenterBinding;
 
769
    QQmlBinding *baselineBinding;
 
770
 
 
771
    QQmlAbstractBinding *origLeftBinding;
 
772
    QQmlAbstractBinding *origRightBinding;
 
773
    QQmlAbstractBinding *origHCenterBinding;
 
774
    QQmlAbstractBinding *origTopBinding;
 
775
    QQmlAbstractBinding *origBottomBinding;
 
776
    QQmlAbstractBinding *origVCenterBinding;
 
777
    QQmlAbstractBinding *origBaselineBinding;
 
778
 
 
779
    QQuickAnchorLine rewindLeft;
 
780
    QQuickAnchorLine rewindRight;
 
781
    QQuickAnchorLine rewindHCenter;
 
782
    QQuickAnchorLine rewindTop;
 
783
    QQuickAnchorLine rewindBottom;
 
784
    QQuickAnchorLine rewindVCenter;
 
785
    QQuickAnchorLine rewindBaseline;
 
786
 
 
787
    qreal fromX;
 
788
    qreal fromY;
 
789
    qreal fromWidth;
 
790
    qreal fromHeight;
 
791
 
 
792
    qreal toX;
 
793
    qreal toY;
 
794
    qreal toWidth;
 
795
    qreal toHeight;
 
796
 
 
797
    qreal rewindX;
 
798
    qreal rewindY;
 
799
    qreal rewindWidth;
 
800
    qreal rewindHeight;
 
801
 
 
802
    bool applyOrigLeft;
 
803
    bool applyOrigRight;
 
804
    bool applyOrigHCenter;
 
805
    bool applyOrigTop;
 
806
    bool applyOrigBottom;
 
807
    bool applyOrigVCenter;
 
808
    bool applyOrigBaseline;
 
809
 
 
810
    QQmlNullableValue<qreal> origWidth;
 
811
    QQmlNullableValue<qreal> origHeight;
 
812
    qreal origX;
 
813
    qreal origY;
 
814
 
 
815
    QList<QQmlAbstractBinding*> oldBindings;
 
816
 
 
817
    QQmlProperty leftProp;
 
818
    QQmlProperty rightProp;
 
819
    QQmlProperty hCenterProp;
 
820
    QQmlProperty topProp;
 
821
    QQmlProperty bottomProp;
 
822
    QQmlProperty vCenterProp;
 
823
    QQmlProperty baselineProp;
 
824
};
 
825
 
 
826
QQuickAnchorChanges::QQuickAnchorChanges(QObject *parent)
 
827
 : QQuickStateOperation(*(new QQuickAnchorChangesPrivate), parent)
 
828
{
 
829
}
 
830
 
 
831
QQuickAnchorChanges::~QQuickAnchorChanges()
 
832
{
 
833
}
 
834
 
 
835
QQuickAnchorChanges::ActionList QQuickAnchorChanges::actions()
 
836
{
 
837
    Q_D(QQuickAnchorChanges);
 
838
    d->leftBinding = d->rightBinding = d->hCenterBinding = d->topBinding
 
839
                   = d->bottomBinding = d->vCenterBinding = d->baselineBinding = 0;
 
840
 
 
841
    d->leftProp = QQmlProperty(d->target, QLatin1String("anchors.left"));
 
842
    d->rightProp = QQmlProperty(d->target, QLatin1String("anchors.right"));
 
843
    d->hCenterProp = QQmlProperty(d->target, QLatin1String("anchors.horizontalCenter"));
 
844
    d->topProp = QQmlProperty(d->target, QLatin1String("anchors.top"));
 
845
    d->bottomProp = QQmlProperty(d->target, QLatin1String("anchors.bottom"));
 
846
    d->vCenterProp = QQmlProperty(d->target, QLatin1String("anchors.verticalCenter"));
 
847
    d->baselineProp = QQmlProperty(d->target, QLatin1String("anchors.baseline"));
 
848
 
 
849
    if (d->anchorSet->d_func()->usedAnchors & QQuickAnchors::LeftAnchor) {
 
850
        d->leftBinding = new QQmlBinding(d->anchorSet->d_func()->leftScript.script(), d->target, qmlContext(this));
 
851
        d->leftBinding->setTarget(d->leftProp);
 
852
    }
 
853
    if (d->anchorSet->d_func()->usedAnchors & QQuickAnchors::RightAnchor) {
 
854
        d->rightBinding = new QQmlBinding(d->anchorSet->d_func()->rightScript.script(), d->target, qmlContext(this));
 
855
        d->rightBinding->setTarget(d->rightProp);
 
856
    }
 
857
    if (d->anchorSet->d_func()->usedAnchors & QQuickAnchors::HCenterAnchor) {
 
858
        d->hCenterBinding = new QQmlBinding(d->anchorSet->d_func()->hCenterScript.script(), d->target, qmlContext(this));
 
859
        d->hCenterBinding->setTarget(d->hCenterProp);
 
860
    }
 
861
    if (d->anchorSet->d_func()->usedAnchors & QQuickAnchors::TopAnchor) {
 
862
        d->topBinding = new QQmlBinding(d->anchorSet->d_func()->topScript.script(), d->target, qmlContext(this));
 
863
        d->topBinding->setTarget(d->topProp);
 
864
    }
 
865
    if (d->anchorSet->d_func()->usedAnchors & QQuickAnchors::BottomAnchor) {
 
866
        d->bottomBinding = new QQmlBinding(d->anchorSet->d_func()->bottomScript.script(), d->target, qmlContext(this));
 
867
        d->bottomBinding->setTarget(d->bottomProp);
 
868
    }
 
869
    if (d->anchorSet->d_func()->usedAnchors & QQuickAnchors::VCenterAnchor) {
 
870
        d->vCenterBinding = new QQmlBinding(d->anchorSet->d_func()->vCenterScript.script(), d->target, qmlContext(this));
 
871
        d->vCenterBinding->setTarget(d->vCenterProp);
 
872
    }
 
873
    if (d->anchorSet->d_func()->usedAnchors & QQuickAnchors::BaselineAnchor) {
 
874
        d->baselineBinding = new QQmlBinding(d->anchorSet->d_func()->baselineScript.script(), d->target, qmlContext(this));
 
875
        d->baselineBinding->setTarget(d->baselineProp);
 
876
    }
 
877
 
 
878
    QQuickAction a;
 
879
    a.event = this;
 
880
    return ActionList() << a;
 
881
}
 
882
 
 
883
QQuickAnchorSet *QQuickAnchorChanges::anchors()
 
884
{
 
885
    Q_D(QQuickAnchorChanges);
 
886
    return d->anchorSet;
 
887
}
 
888
 
 
889
QQuickItem *QQuickAnchorChanges::object() const
 
890
{
 
891
    Q_D(const QQuickAnchorChanges);
 
892
    return d->target;
 
893
}
 
894
 
 
895
void QQuickAnchorChanges::setObject(QQuickItem *target)
 
896
{
 
897
    Q_D(QQuickAnchorChanges);
 
898
    d->target = target;
 
899
}
 
900
 
 
901
void QQuickAnchorChanges::execute(Reason reason)
 
902
{
 
903
    Q_D(QQuickAnchorChanges);
 
904
    if (!d->target)
 
905
        return;
 
906
 
 
907
    QQuickItemPrivate *targetPrivate = QQuickItemPrivate::get(d->target);
 
908
    //incorporate any needed "reverts"
 
909
    if (d->applyOrigLeft) {
 
910
        if (!d->origLeftBinding)
 
911
            targetPrivate->anchors()->resetLeft();
 
912
        QQmlPropertyPrivate::setBinding(d->leftProp, d->origLeftBinding);
 
913
    }
 
914
    if (d->applyOrigRight) {
 
915
        if (!d->origRightBinding)
 
916
            targetPrivate->anchors()->resetRight();
 
917
        QQmlPropertyPrivate::setBinding(d->rightProp, d->origRightBinding);
 
918
    }
 
919
    if (d->applyOrigHCenter) {
 
920
        if (!d->origHCenterBinding)
 
921
            targetPrivate->anchors()->resetHorizontalCenter();
 
922
        QQmlPropertyPrivate::setBinding(d->hCenterProp, d->origHCenterBinding);
 
923
    }
 
924
    if (d->applyOrigTop) {
 
925
        if (!d->origTopBinding)
 
926
            targetPrivate->anchors()->resetTop();
 
927
        QQmlPropertyPrivate::setBinding(d->topProp, d->origTopBinding);
 
928
    }
 
929
    if (d->applyOrigBottom) {
 
930
        if (!d->origBottomBinding)
 
931
            targetPrivate->anchors()->resetBottom();
 
932
        QQmlPropertyPrivate::setBinding(d->bottomProp, d->origBottomBinding);
 
933
    }
 
934
    if (d->applyOrigVCenter) {
 
935
        if (!d->origVCenterBinding)
 
936
            targetPrivate->anchors()->resetVerticalCenter();
 
937
        QQmlPropertyPrivate::setBinding(d->vCenterProp, d->origVCenterBinding);
 
938
    }
 
939
    if (d->applyOrigBaseline) {
 
940
        if (!d->origBaselineBinding)
 
941
            targetPrivate->anchors()->resetBaseline();
 
942
        QQmlPropertyPrivate::setBinding(d->baselineProp, d->origBaselineBinding);
 
943
    }
 
944
 
 
945
    //destroy old bindings
 
946
    if (reason == ActualChange) {
 
947
        for (int i = 0; i < d->oldBindings.size(); ++i) {
 
948
            QQmlAbstractBinding *binding = d->oldBindings.at(i);
 
949
            if (binding)
 
950
                binding->destroy();
 
951
        }
 
952
        d->oldBindings.clear();
 
953
    }
 
954
 
 
955
    //reset any anchors that have been specified as "undefined"
 
956
    if (d->anchorSet->d_func()->resetAnchors & QQuickAnchors::LeftAnchor) {
 
957
        targetPrivate->anchors()->resetLeft();
 
958
        QQmlPropertyPrivate::setBinding(d->leftProp, 0);
 
959
    }
 
960
    if (d->anchorSet->d_func()->resetAnchors & QQuickAnchors::RightAnchor) {
 
961
        targetPrivate->anchors()->resetRight();
 
962
        QQmlPropertyPrivate::setBinding(d->rightProp, 0);
 
963
    }
 
964
    if (d->anchorSet->d_func()->resetAnchors & QQuickAnchors::HCenterAnchor) {
 
965
        targetPrivate->anchors()->resetHorizontalCenter();
 
966
        QQmlPropertyPrivate::setBinding(d->hCenterProp, 0);
 
967
    }
 
968
    if (d->anchorSet->d_func()->resetAnchors & QQuickAnchors::TopAnchor) {
 
969
        targetPrivate->anchors()->resetTop();
 
970
        QQmlPropertyPrivate::setBinding(d->topProp, 0);
 
971
    }
 
972
    if (d->anchorSet->d_func()->resetAnchors & QQuickAnchors::BottomAnchor) {
 
973
        targetPrivate->anchors()->resetBottom();
 
974
        QQmlPropertyPrivate::setBinding(d->bottomProp, 0);
 
975
    }
 
976
    if (d->anchorSet->d_func()->resetAnchors & QQuickAnchors::VCenterAnchor) {
 
977
        targetPrivate->anchors()->resetVerticalCenter();
 
978
        QQmlPropertyPrivate::setBinding(d->vCenterProp, 0);
 
979
    }
 
980
    if (d->anchorSet->d_func()->resetAnchors & QQuickAnchors::BaselineAnchor) {
 
981
        targetPrivate->anchors()->resetBaseline();
 
982
        QQmlPropertyPrivate::setBinding(d->baselineProp, 0);
 
983
    }
 
984
 
 
985
    //set any anchors that have been specified
 
986
    if (d->leftBinding)
 
987
        QQmlPropertyPrivate::setBinding(d->leftBinding->property(), d->leftBinding);
 
988
    if (d->rightBinding)
 
989
        QQmlPropertyPrivate::setBinding(d->rightBinding->property(), d->rightBinding);
 
990
    if (d->hCenterBinding)
 
991
        QQmlPropertyPrivate::setBinding(d->hCenterBinding->property(), d->hCenterBinding);
 
992
    if (d->topBinding)
 
993
        QQmlPropertyPrivate::setBinding(d->topBinding->property(), d->topBinding);
 
994
    if (d->bottomBinding)
 
995
        QQmlPropertyPrivate::setBinding(d->bottomBinding->property(), d->bottomBinding);
 
996
    if (d->vCenterBinding)
 
997
        QQmlPropertyPrivate::setBinding(d->vCenterBinding->property(), d->vCenterBinding);
 
998
    if (d->baselineBinding)
 
999
        QQmlPropertyPrivate::setBinding(d->baselineBinding->property(), d->baselineBinding);
 
1000
}
 
1001
 
 
1002
bool QQuickAnchorChanges::isReversable()
 
1003
{
 
1004
    return true;
 
1005
}
 
1006
 
 
1007
void QQuickAnchorChanges::reverse(Reason reason)
 
1008
{
 
1009
    Q_D(QQuickAnchorChanges);
 
1010
    if (!d->target)
 
1011
        return;
 
1012
 
 
1013
    QQuickItemPrivate *targetPrivate = QQuickItemPrivate::get(d->target);
 
1014
    //reset any anchors set by the state
 
1015
    if (d->leftBinding) {
 
1016
        targetPrivate->anchors()->resetLeft();
 
1017
        QQmlPropertyPrivate::setBinding(d->leftBinding->property(), 0);
 
1018
        if (reason == ActualChange) {
 
1019
            d->leftBinding->destroy(); d->leftBinding = 0;
 
1020
        }
 
1021
    }
 
1022
    if (d->rightBinding) {
 
1023
        targetPrivate->anchors()->resetRight();
 
1024
        QQmlPropertyPrivate::setBinding(d->rightBinding->property(), 0);
 
1025
        if (reason == ActualChange) {
 
1026
            d->rightBinding->destroy(); d->rightBinding = 0;
 
1027
        }
 
1028
    }
 
1029
    if (d->hCenterBinding) {
 
1030
        targetPrivate->anchors()->resetHorizontalCenter();
 
1031
        QQmlPropertyPrivate::setBinding(d->hCenterBinding->property(), 0);
 
1032
        if (reason == ActualChange) {
 
1033
            d->hCenterBinding->destroy(); d->hCenterBinding = 0;
 
1034
        }
 
1035
    }
 
1036
    if (d->topBinding) {
 
1037
        targetPrivate->anchors()->resetTop();
 
1038
        QQmlPropertyPrivate::setBinding(d->topBinding->property(), 0);
 
1039
        if (reason == ActualChange) {
 
1040
            d->topBinding->destroy(); d->topBinding = 0;
 
1041
        }
 
1042
    }
 
1043
    if (d->bottomBinding) {
 
1044
        targetPrivate->anchors()->resetBottom();
 
1045
        QQmlPropertyPrivate::setBinding(d->bottomBinding->property(), 0);
 
1046
        if (reason == ActualChange) {
 
1047
            d->bottomBinding->destroy(); d->bottomBinding = 0;
 
1048
        }
 
1049
    }
 
1050
    if (d->vCenterBinding) {
 
1051
        targetPrivate->anchors()->resetVerticalCenter();
 
1052
        QQmlPropertyPrivate::setBinding(d->vCenterBinding->property(), 0);
 
1053
        if (reason == ActualChange) {
 
1054
            d->vCenterBinding->destroy(); d->vCenterBinding = 0;
 
1055
        }
 
1056
    }
 
1057
    if (d->baselineBinding) {
 
1058
        targetPrivate->anchors()->resetBaseline();
 
1059
        QQmlPropertyPrivate::setBinding(d->baselineBinding->property(), 0);
 
1060
        if (reason == ActualChange) {
 
1061
            d->baselineBinding->destroy(); d->baselineBinding = 0;
 
1062
        }
 
1063
    }
 
1064
 
 
1065
    //restore previous anchors
 
1066
    if (d->origLeftBinding)
 
1067
        QQmlPropertyPrivate::setBinding(d->leftProp, d->origLeftBinding);
 
1068
    if (d->origRightBinding)
 
1069
        QQmlPropertyPrivate::setBinding(d->rightProp, d->origRightBinding);
 
1070
    if (d->origHCenterBinding)
 
1071
        QQmlPropertyPrivate::setBinding(d->hCenterProp, d->origHCenterBinding);
 
1072
    if (d->origTopBinding)
 
1073
        QQmlPropertyPrivate::setBinding(d->topProp, d->origTopBinding);
 
1074
    if (d->origBottomBinding)
 
1075
        QQmlPropertyPrivate::setBinding(d->bottomProp, d->origBottomBinding);
 
1076
    if (d->origVCenterBinding)
 
1077
        QQmlPropertyPrivate::setBinding(d->vCenterProp, d->origVCenterBinding);
 
1078
    if (d->origBaselineBinding)
 
1079
        QQmlPropertyPrivate::setBinding(d->baselineProp, d->origBaselineBinding);
 
1080
 
 
1081
    //restore any absolute geometry changed by the state's anchors
 
1082
    QQuickAnchors::Anchors stateVAnchors = d->anchorSet->d_func()->usedAnchors & QQuickAnchors::Vertical_Mask;
 
1083
    QQuickAnchors::Anchors origVAnchors = targetPrivate->anchors()->usedAnchors() & QQuickAnchors::Vertical_Mask;
 
1084
    QQuickAnchors::Anchors stateHAnchors = d->anchorSet->d_func()->usedAnchors & QQuickAnchors::Horizontal_Mask;
 
1085
    QQuickAnchors::Anchors origHAnchors = targetPrivate->anchors()->usedAnchors() & QQuickAnchors::Horizontal_Mask;
 
1086
 
 
1087
    bool stateSetWidth = (stateHAnchors &&
 
1088
                          stateHAnchors != QQuickAnchors::LeftAnchor &&
 
1089
                          stateHAnchors != QQuickAnchors::RightAnchor &&
 
1090
                          stateHAnchors != QQuickAnchors::HCenterAnchor);
 
1091
    bool origSetWidth = (origHAnchors &&
 
1092
                         origHAnchors != QQuickAnchors::LeftAnchor &&
 
1093
                         origHAnchors != QQuickAnchors::RightAnchor &&
 
1094
                         origHAnchors != QQuickAnchors::HCenterAnchor);
 
1095
    if (d->origWidth.isValid() && stateSetWidth && !origSetWidth)
 
1096
        d->target->setWidth(d->origWidth.value);
 
1097
 
 
1098
    bool stateSetHeight = (stateVAnchors &&
 
1099
                           stateVAnchors != QQuickAnchors::TopAnchor &&
 
1100
                           stateVAnchors != QQuickAnchors::BottomAnchor &&
 
1101
                           stateVAnchors != QQuickAnchors::VCenterAnchor &&
 
1102
                           stateVAnchors != QQuickAnchors::BaselineAnchor);
 
1103
    bool origSetHeight = (origVAnchors &&
 
1104
                          origVAnchors != QQuickAnchors::TopAnchor &&
 
1105
                          origVAnchors != QQuickAnchors::BottomAnchor &&
 
1106
                          origVAnchors != QQuickAnchors::VCenterAnchor &&
 
1107
                          origVAnchors != QQuickAnchors::BaselineAnchor);
 
1108
    if (d->origHeight.isValid() && stateSetHeight && !origSetHeight)
 
1109
        d->target->setHeight(d->origHeight.value);
 
1110
 
 
1111
    if (stateHAnchors && !origHAnchors)
 
1112
        d->target->setX(d->origX);
 
1113
 
 
1114
    if (stateVAnchors && !origVAnchors)
 
1115
        d->target->setY(d->origY);
 
1116
}
 
1117
 
 
1118
QQuickActionEvent::EventType QQuickAnchorChanges::type() const
 
1119
{
 
1120
    return AnchorChanges;
 
1121
}
 
1122
 
 
1123
QList<QQuickAction> QQuickAnchorChanges::additionalActions()
 
1124
{
 
1125
    Q_D(QQuickAnchorChanges);
 
1126
    QList<QQuickAction> extra;
 
1127
 
 
1128
    QQuickAnchors::Anchors combined = d->anchorSet->d_func()->usedAnchors | d->anchorSet->d_func()->resetAnchors;
 
1129
    bool hChange = combined & QQuickAnchors::Horizontal_Mask;
 
1130
    bool vChange = combined & QQuickAnchors::Vertical_Mask;
 
1131
 
 
1132
    if (d->target) {
 
1133
        QQuickAction a;
 
1134
        if (hChange && d->fromX != d->toX) {
 
1135
            a.property = QQmlProperty(d->target, QLatin1String("x"));
 
1136
            a.toValue = d->toX;
 
1137
            extra << a;
 
1138
        }
 
1139
        if (vChange && d->fromY != d->toY) {
 
1140
            a.property = QQmlProperty(d->target, QLatin1String("y"));
 
1141
            a.toValue = d->toY;
 
1142
            extra << a;
 
1143
        }
 
1144
        if (hChange && d->fromWidth != d->toWidth) {
 
1145
            a.property = QQmlProperty(d->target, QLatin1String("width"));
 
1146
            a.toValue = d->toWidth;
 
1147
            extra << a;
 
1148
        }
 
1149
        if (vChange && d->fromHeight != d->toHeight) {
 
1150
            a.property = QQmlProperty(d->target, QLatin1String("height"));
 
1151
            a.toValue = d->toHeight;
 
1152
            extra << a;
 
1153
        }
 
1154
    }
 
1155
 
 
1156
    return extra;
 
1157
}
 
1158
 
 
1159
bool QQuickAnchorChanges::changesBindings()
 
1160
{
 
1161
    return true;
 
1162
}
 
1163
 
 
1164
void QQuickAnchorChanges::saveOriginals()
 
1165
{
 
1166
    Q_D(QQuickAnchorChanges);
 
1167
    if (!d->target)
 
1168
        return;
 
1169
 
 
1170
    d->origLeftBinding = QQmlPropertyPrivate::binding(d->leftProp);
 
1171
    d->origRightBinding = QQmlPropertyPrivate::binding(d->rightProp);
 
1172
    d->origHCenterBinding = QQmlPropertyPrivate::binding(d->hCenterProp);
 
1173
    d->origTopBinding = QQmlPropertyPrivate::binding(d->topProp);
 
1174
    d->origBottomBinding = QQmlPropertyPrivate::binding(d->bottomProp);
 
1175
    d->origVCenterBinding = QQmlPropertyPrivate::binding(d->vCenterProp);
 
1176
    d->origBaselineBinding = QQmlPropertyPrivate::binding(d->baselineProp);
 
1177
 
 
1178
    QQuickItemPrivate *targetPrivate = QQuickItemPrivate::get(d->target);
 
1179
    if (targetPrivate->widthValid)
 
1180
        d->origWidth = d->target->width();
 
1181
    if (targetPrivate->heightValid)
 
1182
        d->origHeight = d->target->height();
 
1183
    d->origX = d->target->x();
 
1184
    d->origY = d->target->y();
 
1185
 
 
1186
    d->applyOrigLeft = d->applyOrigRight = d->applyOrigHCenter = d->applyOrigTop
 
1187
      = d->applyOrigBottom = d->applyOrigVCenter = d->applyOrigBaseline = false;
 
1188
 
 
1189
    saveCurrentValues();
 
1190
}
 
1191
 
 
1192
void QQuickAnchorChanges::copyOriginals(QQuickActionEvent *other)
 
1193
{
 
1194
    Q_D(QQuickAnchorChanges);
 
1195
    QQuickAnchorChanges *ac = static_cast<QQuickAnchorChanges*>(other);
 
1196
    QQuickAnchorChangesPrivate *acp = ac->d_func();
 
1197
 
 
1198
    QQuickAnchors::Anchors combined = acp->anchorSet->d_func()->usedAnchors |
 
1199
                                            acp->anchorSet->d_func()->resetAnchors;
 
1200
 
 
1201
    //probably also need to revert some things
 
1202
    d->applyOrigLeft = (combined & QQuickAnchors::LeftAnchor);
 
1203
    d->applyOrigRight = (combined & QQuickAnchors::RightAnchor);
 
1204
    d->applyOrigHCenter = (combined & QQuickAnchors::HCenterAnchor);
 
1205
    d->applyOrigTop = (combined & QQuickAnchors::TopAnchor);
 
1206
    d->applyOrigBottom = (combined & QQuickAnchors::BottomAnchor);
 
1207
    d->applyOrigVCenter = (combined & QQuickAnchors::VCenterAnchor);
 
1208
    d->applyOrigBaseline = (combined & QQuickAnchors::BaselineAnchor);
 
1209
 
 
1210
    d->origLeftBinding = acp->origLeftBinding;
 
1211
    d->origRightBinding = acp->origRightBinding;
 
1212
    d->origHCenterBinding = acp->origHCenterBinding;
 
1213
    d->origTopBinding = acp->origTopBinding;
 
1214
    d->origBottomBinding = acp->origBottomBinding;
 
1215
    d->origVCenterBinding = acp->origVCenterBinding;
 
1216
    d->origBaselineBinding = acp->origBaselineBinding;
 
1217
 
 
1218
    d->origWidth = acp->origWidth;
 
1219
    d->origHeight = acp->origHeight;
 
1220
    d->origX = acp->origX;
 
1221
    d->origY = acp->origY;
 
1222
 
 
1223
    d->oldBindings.clear();
 
1224
    d->oldBindings << acp->leftBinding << acp->rightBinding << acp->hCenterBinding
 
1225
                << acp->topBinding << acp->bottomBinding << acp->baselineBinding;
 
1226
 
 
1227
    saveCurrentValues();
 
1228
}
 
1229
 
 
1230
void QQuickAnchorChanges::clearBindings()
 
1231
{
 
1232
    Q_D(QQuickAnchorChanges);
 
1233
    if (!d->target)
 
1234
        return;
 
1235
 
 
1236
    //### should this (saving "from" values) be moved to saveCurrentValues()?
 
1237
    d->fromX = d->target->x();
 
1238
    d->fromY = d->target->y();
 
1239
    d->fromWidth = d->target->width();
 
1240
    d->fromHeight = d->target->height();
 
1241
 
 
1242
    QQuickItemPrivate *targetPrivate = QQuickItemPrivate::get(d->target);
 
1243
    //reset any anchors with corresponding reverts
 
1244
    //reset any anchors that have been specified as "undefined"
 
1245
    //reset any anchors that we'll be setting in the state
 
1246
    QQuickAnchors::Anchors combined = d->anchorSet->d_func()->resetAnchors |
 
1247
                                            d->anchorSet->d_func()->usedAnchors;
 
1248
    if (d->applyOrigLeft || (combined & QQuickAnchors::LeftAnchor)) {
 
1249
        targetPrivate->anchors()->resetLeft();
 
1250
        QQmlPropertyPrivate::setBinding(d->leftProp, 0);
 
1251
    }
 
1252
    if (d->applyOrigRight || (combined & QQuickAnchors::RightAnchor)) {
 
1253
        targetPrivate->anchors()->resetRight();
 
1254
        QQmlPropertyPrivate::setBinding(d->rightProp, 0);
 
1255
    }
 
1256
    if (d->applyOrigHCenter || (combined & QQuickAnchors::HCenterAnchor)) {
 
1257
        targetPrivate->anchors()->resetHorizontalCenter();
 
1258
        QQmlPropertyPrivate::setBinding(d->hCenterProp, 0);
 
1259
    }
 
1260
    if (d->applyOrigTop || (combined & QQuickAnchors::TopAnchor)) {
 
1261
        targetPrivate->anchors()->resetTop();
 
1262
        QQmlPropertyPrivate::setBinding(d->topProp, 0);
 
1263
    }
 
1264
    if (d->applyOrigBottom || (combined & QQuickAnchors::BottomAnchor)) {
 
1265
        targetPrivate->anchors()->resetBottom();
 
1266
        QQmlPropertyPrivate::setBinding(d->bottomProp, 0);
 
1267
    }
 
1268
    if (d->applyOrigVCenter || (combined & QQuickAnchors::VCenterAnchor)) {
 
1269
        targetPrivate->anchors()->resetVerticalCenter();
 
1270
        QQmlPropertyPrivate::setBinding(d->vCenterProp, 0);
 
1271
    }
 
1272
    if (d->applyOrigBaseline || (combined & QQuickAnchors::BaselineAnchor)) {
 
1273
        targetPrivate->anchors()->resetBaseline();
 
1274
        QQmlPropertyPrivate::setBinding(d->baselineProp, 0);
 
1275
    }
 
1276
}
 
1277
 
 
1278
bool QQuickAnchorChanges::override(QQuickActionEvent*other)
 
1279
{
 
1280
    if (other->type() != AnchorChanges)
 
1281
        return false;
 
1282
    if (static_cast<QQuickActionEvent*>(this) == other)
 
1283
        return true;
 
1284
    if (static_cast<QQuickAnchorChanges*>(other)->object() == object())
 
1285
        return true;
 
1286
    return false;
 
1287
}
 
1288
 
 
1289
void QQuickAnchorChanges::rewind()
 
1290
{
 
1291
    Q_D(QQuickAnchorChanges);
 
1292
    if (!d->target)
 
1293
        return;
 
1294
 
 
1295
    QQuickItemPrivate *targetPrivate = QQuickItemPrivate::get(d->target);
 
1296
 
 
1297
    //restore previous values (but not previous bindings, i.e. anchors)
 
1298
    d->target->setX(d->rewindX);
 
1299
    d->target->setY(d->rewindY);
 
1300
    if (targetPrivate->widthValid) {
 
1301
        d->target->setWidth(d->rewindWidth);
 
1302
    }
 
1303
    if (targetPrivate->heightValid) {
 
1304
        d->target->setHeight(d->rewindHeight);
 
1305
    }
 
1306
}
 
1307
 
 
1308
void QQuickAnchorChanges::saveCurrentValues()
 
1309
{
 
1310
    Q_D(QQuickAnchorChanges);
 
1311
    if (!d->target)
 
1312
        return;
 
1313
 
 
1314
    QQuickItemPrivate *targetPrivate = QQuickItemPrivate::get(d->target);
 
1315
    d->rewindLeft = targetPrivate->anchors()->left();
 
1316
    d->rewindRight = targetPrivate->anchors()->right();
 
1317
    d->rewindHCenter = targetPrivate->anchors()->horizontalCenter();
 
1318
    d->rewindTop = targetPrivate->anchors()->top();
 
1319
    d->rewindBottom = targetPrivate->anchors()->bottom();
 
1320
    d->rewindVCenter = targetPrivate->anchors()->verticalCenter();
 
1321
    d->rewindBaseline = targetPrivate->anchors()->baseline();
 
1322
 
 
1323
    d->rewindX = d->target->x();
 
1324
    d->rewindY = d->target->y();
 
1325
    d->rewindWidth = d->target->width();
 
1326
    d->rewindHeight = d->target->height();
 
1327
}
 
1328
 
 
1329
void QQuickAnchorChanges::saveTargetValues()
 
1330
{
 
1331
    Q_D(QQuickAnchorChanges);
 
1332
    if (!d->target)
 
1333
        return;
 
1334
 
 
1335
    d->toX = d->target->x();
 
1336
    d->toY = d->target->y();
 
1337
    d->toWidth = d->target->width();
 
1338
    d->toHeight = d->target->height();
 
1339
}
 
1340
 
 
1341
#include <moc_qquickstateoperations_p.cpp>
 
1342
 
 
1343
QT_END_NAMESPACE
 
1344