1 /****************************************************************************
3 ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies).
4 ** All rights reserved.
5 ** Contact: http://www.qt-project.org/
7 ** This file is part of the QtDeclarative module of the Qt Toolkit.
9 ** $QT_BEGIN_LICENSE:LGPL$
10 ** GNU Lesser General Public License Usage
11 ** This file may be used under the terms of the GNU Lesser General Public
12 ** License version 2.1 as published by the Free Software Foundation and
13 ** appearing in the file LICENSE.LGPL included in the packaging of this
14 ** file. Please review the following information to ensure the GNU Lesser
15 ** General Public License version 2.1 requirements will be met:
16 ** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
18 ** In addition, as a special exception, Nokia gives you certain additional
19 ** rights. These rights are described in the Nokia Qt LGPL Exception
20 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
22 ** GNU General Public License Usage
23 ** Alternatively, this file may be used under the terms of the GNU General
24 ** Public License version 3.0 as published by the Free Software Foundation
25 ** and appearing in the file LICENSE.GPL included in the packaging of this
26 ** file. Please review the following information to ensure the GNU General
27 ** Public License version 3.0 requirements will be met:
28 ** http://www.gnu.org/copyleft/gpl.html.
31 ** Alternatively, this file may be used in accordance with the terms and
32 ** conditions contained in a signed written agreement between you and Nokia.
40 ****************************************************************************/
42 #include "QtQuick1/private/qdeclarativepropertychanges_p.h"
44 #include "QtQuick1/private/qdeclarativeopenmetaobject_p.h"
45 #include "QtDeclarative/private/qdeclarativerewrite_p.h"
46 #include "QtDeclarative/private/qdeclarativeengine_p.h"
47 #include "QtDeclarative/private/qdeclarativecompiler_p.h"
49 #include <QtDeclarative/qdeclarativeinfo.h>
50 #include <QtDeclarative/private/qdeclarativecustomparser_p.h>
51 #include <QtDeclarative/private/qdeclarativescript_p.h>
52 #include <QtDeclarative/qdeclarativeexpression.h>
53 #include <QtDeclarative/private/qdeclarativebinding_p.h>
54 #include <QtDeclarative/qdeclarativecontext.h>
55 #include <QtDeclarative/private/qdeclarativeguard_p.h>
56 #include <QtDeclarative/private/qdeclarativeproperty_p.h>
57 #include <QtDeclarative/private/qdeclarativecontext_p.h>
58 #include <QtQuick1/private/qdeclarativestate_p_p.h>
60 #include <QtCore/qdebug.h>
62 #include <private/qobject_p.h>
69 \qmlclass PropertyChanges QDeclarative1PropertyChanges
70 \inqmlmodule QtQuick 1
71 \ingroup qml-state-elements
73 \brief The PropertyChanges element describes new property bindings or values for a state.
75 PropertyChanges is used to define the property values or bindings in a
76 \l State. This enables an item's property values to be changed when it
77 \l {QML States}{changes between states}.
79 To create a PropertyChanges object, specify the \l target item whose
80 properties are to be modified, and define the new property values or
81 bindings. For example:
83 \snippet doc/src/snippets/qtquick1/propertychanges.qml import
85 \snippet doc/src/snippets/qtquick1/propertychanges.qml 0
87 When the mouse is pressed, the \l Rectangle changes to the \e resized
88 state. In this state, the PropertyChanges object sets the rectangle's
89 color to blue and the \c height value to that of \c container.height.
91 Note this automatically binds \c rect.height to \c container.height
92 in the \e resized state. If a property binding should not be
93 established, and the height should just be set to the value of
94 \c container.height at the time of the state change, set the \l explicit
97 A PropertyChanges object can also override the default signal handler
98 for an object to implement a signal handler specific to the new state:
103 onClicked: doSomethingDifferent()
107 \note PropertyChanges can be used to change anchor margins, but not other anchor
108 values; use AnchorChanges for this instead. Similarly, to change an \l Item's
109 \l {Item::}{parent} value, use ParentChanges instead.
112 \section2 Resetting property values
114 The \c undefined value can be used to reset the property value for a state.
115 In the following example, when \c theText changes to the \e widerText
116 state, its \c width property is reset, giving the text its natural width
117 and displaying the whole string on a single line.
119 \snippet doc/src/snippets/qtquick1/propertychanges.qml reset
122 \section2 Immediate property changes in transitions
124 When \l{QML Animation and Transitions}{Transitions} are used to animate
125 state changes, they animate properties from their values in the current
126 state to those defined in the new state (as defined by PropertyChanges
127 objects). However, it is sometimes desirable to set a property value
128 \e immediately during a \l Transition, without animation; in these cases,
129 the PropertyAction element can be used to force an immediate property
132 See the PropertyAction documentation for more details.
134 \sa {declarative/animation/states}{states example}, {qmlstate}{States}, QtDeclarative
138 \qmlproperty Object QtQuick1::PropertyChanges::target
139 This property holds the object which contains the properties to be changed.
142 class QDeclarative1ReplaceSignalHandler : public QDeclarative1ActionEvent
145 QDeclarative1ReplaceSignalHandler() : expression(0), reverseExpression(0),
146 rewindExpression(0), ownedExpression(0) {}
147 ~QDeclarative1ReplaceSignalHandler() {
148 delete ownedExpression;
151 virtual QString typeName() const { return QLatin1String("ReplaceSignalHandler"); }
153 QDeclarativeProperty property;
154 QDeclarativeExpression *expression;
155 QDeclarativeExpression *reverseExpression;
156 QDeclarativeExpression *rewindExpression;
157 QDeclarativeGuard<QDeclarativeExpression> ownedExpression;
159 virtual void execute(Reason) {
160 ownedExpression = QDeclarativePropertyPrivate::setSignalExpression(property, expression);
161 if (ownedExpression == expression)
165 virtual bool isReversable() { return true; }
166 virtual void reverse(Reason) {
167 ownedExpression = QDeclarativePropertyPrivate::setSignalExpression(property, reverseExpression);
168 if (ownedExpression == reverseExpression)
172 virtual void saveOriginals() {
174 reverseExpression = rewindExpression;
177 virtual bool needsCopy() { return true; }
178 virtual void copyOriginals(QDeclarative1ActionEvent *other)
180 QDeclarative1ReplaceSignalHandler *rsh = static_cast<QDeclarative1ReplaceSignalHandler*>(other);
184 reverseExpression = rsh->reverseExpression;
185 if (rsh->ownedExpression == reverseExpression) {
186 ownedExpression = rsh->ownedExpression;
187 rsh->ownedExpression = 0;
191 virtual void rewind() {
192 ownedExpression = QDeclarativePropertyPrivate::setSignalExpression(property, rewindExpression);
193 if (ownedExpression == rewindExpression)
196 virtual void saveCurrentValues() {
197 rewindExpression = QDeclarativePropertyPrivate::signalExpression(property);
200 virtual bool override(QDeclarative1ActionEvent*other) {
203 if (other->typeName() != typeName())
205 if (static_cast<QDeclarative1ReplaceSignalHandler*>(other)->property == property)
212 class QDeclarative1PropertyChangesPrivate : public QDeclarative1StateOperationPrivate
214 Q_DECLARE_PUBLIC(QDeclarative1PropertyChanges)
216 QDeclarative1PropertyChangesPrivate() : decoded(true), restore(true),
219 QDeclarativeGuard<QObject> object;
228 class ExpressionChange {
230 ExpressionChange(const QString &_name,
231 QDeclarativeBinding::Identifier _id,
232 QDeclarativeExpression *_expr)
233 : name(_name), id(_id), expression(_expr) {}
235 QDeclarativeBinding::Identifier id;
236 QDeclarativeExpression *expression;
239 QList<QPair<QString, QVariant> > properties;
240 QList<ExpressionChange> expressions;
241 QList<QDeclarative1ReplaceSignalHandler*> signalReplacements;
243 QDeclarativeProperty property(const QString &);
247 QDeclarative1PropertyChangesParser::compileList(QList<QPair<QString, QVariant> > &list,
249 const QDeclarativeCustomParserProperty &prop)
251 QString propName = pre + prop.name();
253 QList<QVariant> values = prop.assignedValues();
254 for (int ii = 0; ii < values.count(); ++ii) {
255 const QVariant &value = values.at(ii);
257 if (value.userType() == qMetaTypeId<QDeclarativeCustomParserNode>()) {
258 error(qvariant_cast<QDeclarativeCustomParserNode>(value),
259 QDeclarative1PropertyChanges::tr("PropertyChanges does not support creating state-specific objects."));
261 } else if(value.userType() == qMetaTypeId<QDeclarativeCustomParserProperty>()) {
263 QDeclarativeCustomParserProperty prop =
264 qvariant_cast<QDeclarativeCustomParserProperty>(value);
265 QString pre = propName + QLatin1Char('.');
266 compileList(list, pre, prop);
269 list << qMakePair(propName, value);
275 QDeclarative1PropertyChangesParser::compile(const QList<QDeclarativeCustomParserProperty> &props)
277 QList<QPair<QString, QVariant> > data;
278 for(int ii = 0; ii < props.count(); ++ii)
279 compileList(data, QString(), props.at(ii));
282 QDataStream ds(&rv, QIODevice::WriteOnly);
285 for(int ii = 0; ii < data.count(); ++ii) {
286 QDeclarativeScript::Variant v = qvariant_cast<QDeclarativeScript::Variant>(data.at(ii).second);
288 bool isScript = v.isScript();
289 QDeclarativeBinding::Identifier id = 0;
291 case QDeclarativeScript::Variant::Boolean:
292 var = QVariant(v.asBoolean());
294 case QDeclarativeScript::Variant::Number:
295 var = QVariant(v.asNumber());
297 case QDeclarativeScript::Variant::String:
298 var = QVariant(v.asString());
300 case QDeclarativeScript::Variant::Invalid:
301 case QDeclarativeScript::Variant::Script:
302 var = QVariant(v.asScript());
304 id = rewriteBinding(v, data.at(ii).first);
309 ds << data.at(ii).first << isScript << var;
317 void QDeclarative1PropertyChangesPrivate::decode()
319 Q_Q(QDeclarative1PropertyChanges);
323 QDataStream ds(&data, QIODevice::ReadOnly);
327 for (int ii = 0; ii < count; ++ii) {
331 QDeclarativeBinding::Identifier id = QDeclarativeBinding::Invalid;
338 QDeclarativeProperty prop = property(name); //### better way to check for signal property?
339 if (prop.type() & QDeclarativeProperty::SignalProperty) {
340 QDeclarativeExpression *expression = new QDeclarativeExpression(qmlContext(q), object, data.toString());
341 QDeclarativeData *ddata = QDeclarativeData::get(q);
342 if (ddata && ddata->outerContext && !ddata->outerContext->url.isEmpty())
343 expression->setSourceLocation(ddata->outerContext->url.toString(), ddata->lineNumber, ddata->columnNumber);
344 QDeclarative1ReplaceSignalHandler *handler = new QDeclarative1ReplaceSignalHandler;
345 handler->property = prop;
346 handler->expression = expression;
347 signalReplacements << handler;
348 } else if (isScript) {
349 QDeclarativeExpression *expression = new QDeclarativeExpression(qmlContext(q), object, data.toString());
350 QDeclarativeData *ddata = QDeclarativeData::get(q);
351 if (ddata && ddata->outerContext && !ddata->outerContext->url.isEmpty())
352 expression->setSourceLocation(ddata->outerContext->url.toString(), ddata->lineNumber, ddata->columnNumber);
353 expressions << ExpressionChange(name, id, expression);
355 properties << qMakePair(name, data);
363 void QDeclarative1PropertyChangesParser::setCustomData(QObject *object,
364 const QByteArray &data)
366 QDeclarative1PropertyChangesPrivate *p =
367 static_cast<QDeclarative1PropertyChangesPrivate *>(QObjectPrivate::get(object));
372 QDeclarative1PropertyChanges::QDeclarative1PropertyChanges()
373 : QDeclarative1StateOperation(*(new QDeclarative1PropertyChangesPrivate))
377 QDeclarative1PropertyChanges::~QDeclarative1PropertyChanges()
379 Q_D(QDeclarative1PropertyChanges);
380 for(int ii = 0; ii < d->expressions.count(); ++ii)
381 delete d->expressions.at(ii).expression;
382 for(int ii = 0; ii < d->signalReplacements.count(); ++ii)
383 delete d->signalReplacements.at(ii);
386 QObject *QDeclarative1PropertyChanges::object() const
388 Q_D(const QDeclarative1PropertyChanges);
392 void QDeclarative1PropertyChanges::setObject(QObject *o)
394 Q_D(QDeclarative1PropertyChanges);
399 \qmlproperty bool QtQuick1::PropertyChanges::restoreEntryValues
401 This property holds whether the previous values should be restored when
404 The default value is \c true. Setting this value to \c false creates a
405 temporary state that has permanent effects on property values.
407 bool QDeclarative1PropertyChanges::restoreEntryValues() const
409 Q_D(const QDeclarative1PropertyChanges);
413 void QDeclarative1PropertyChanges::setRestoreEntryValues(bool v)
415 Q_D(QDeclarative1PropertyChanges);
420 QDeclarative1PropertyChangesPrivate::property(const QString &property)
422 Q_Q(QDeclarative1PropertyChanges);
423 QDeclarativeProperty prop(object, property, qmlContext(q));
424 if (!prop.isValid()) {
425 qmlInfo(q) << QDeclarative1PropertyChanges::tr("Cannot assign to non-existent property \"%1\"").arg(property);
426 return QDeclarativeProperty();
427 } else if (!(prop.type() & QDeclarativeProperty::SignalProperty) && !prop.isWritable()) {
428 qmlInfo(q) << QDeclarative1PropertyChanges::tr("Cannot assign to read-only property \"%1\"").arg(property);
429 return QDeclarativeProperty();
434 QDeclarative1PropertyChanges::ActionList QDeclarative1PropertyChanges::actions()
436 Q_D(QDeclarative1PropertyChanges);
442 for (int ii = 0; ii < d->properties.count(); ++ii) {
444 QDeclarative1Action a(d->object, d->properties.at(ii).first,
445 qmlContext(this), d->properties.at(ii).second);
447 if (a.property.isValid()) {
448 a.restore = restoreEntryValues();
453 for (int ii = 0; ii < d->signalReplacements.count(); ++ii) {
455 QDeclarative1ReplaceSignalHandler *handler = d->signalReplacements.at(ii);
457 if (handler->property.isValid()) {
458 QDeclarative1Action a;
464 for (int ii = 0; ii < d->expressions.count(); ++ii) {
466 const QString &property = d->expressions.at(ii).name;
467 QDeclarativeProperty prop = d->property(property);
469 if (prop.isValid()) {
470 QDeclarative1Action a;
471 a.restore = restoreEntryValues();
473 a.fromValue = a.property.read();
474 a.specifiedObject = d->object;
475 a.specifiedProperty = property;
478 a.toValue = d->expressions.at(ii).expression->evaluate();
480 QDeclarativeExpression *e = d->expressions.at(ii).expression;
482 QDeclarativeBinding::Identifier id = d->expressions.at(ii).id;
483 QDeclarativeBinding *newBinding = id != QDeclarativeBinding::Invalid ? QDeclarativeBinding::createBinding(id, object(), qmlContext(this), e->sourceFile(), e->lineNumber()) : 0;
485 newBinding = new QDeclarativeBinding(e->expression(), object(), qmlContext(this));
486 newBinding->setSourceLocation(e->sourceFile(), e->lineNumber(), e->columnNumber());
488 newBinding->setTarget(prop);
489 a.toBinding = newBinding;
490 a.deletableToBinding = true;
501 \qmlproperty bool QtQuick1::PropertyChanges::explicit
503 If explicit is set to true, any potential bindings will be interpreted as
504 once-off assignments that occur when the state is entered.
506 In the following example, the addition of explicit prevents \c myItem.width from
507 being bound to \c parent.width. Instead, it is assigned the value of \c parent.width
508 at the time of the state change.
517 By default, explicit is false.
519 bool QDeclarative1PropertyChanges::isExplicit() const
521 Q_D(const QDeclarative1PropertyChanges);
522 return d->isExplicit;
525 void QDeclarative1PropertyChanges::setIsExplicit(bool e)
527 Q_D(QDeclarative1PropertyChanges);
531 bool QDeclarative1PropertyChanges::containsValue(const QString &name) const
533 Q_D(const QDeclarative1PropertyChanges);
534 typedef QPair<QString, QVariant> PropertyEntry;
536 QListIterator<PropertyEntry> propertyIterator(d->properties);
537 while (propertyIterator.hasNext()) {
538 const PropertyEntry &entry = propertyIterator.next();
539 if (entry.first == name) {
547 bool QDeclarative1PropertyChanges::containsExpression(const QString &name) const
549 Q_D(const QDeclarative1PropertyChanges);
550 typedef QDeclarative1PropertyChangesPrivate::ExpressionChange ExpressionEntry;
552 QListIterator<ExpressionEntry> expressionIterator(d->expressions);
553 while (expressionIterator.hasNext()) {
554 const ExpressionEntry &entry = expressionIterator.next();
555 if (entry.name == name) {
563 bool QDeclarative1PropertyChanges::containsProperty(const QString &name) const
565 return containsValue(name) || containsExpression(name);
568 void QDeclarative1PropertyChanges::changeValue(const QString &name, const QVariant &value)
570 Q_D(QDeclarative1PropertyChanges);
571 typedef QPair<QString, QVariant> PropertyEntry;
572 typedef QDeclarative1PropertyChangesPrivate::ExpressionChange ExpressionEntry;
574 QMutableListIterator<ExpressionEntry> expressionIterator(d->expressions);
575 while (expressionIterator.hasNext()) {
576 const ExpressionEntry &entry = expressionIterator.next();
577 if (entry.name == name) {
578 expressionIterator.remove();
579 if (state() && state()->isStateActive()) {
580 QDeclarativeAbstractBinding *oldBinding = QDeclarativePropertyPrivate::binding(d->property(name));
582 QDeclarativePropertyPrivate::setBinding(d->property(name), 0);
583 oldBinding->destroy();
585 d->property(name).write(value);
588 d->properties.append(PropertyEntry(name, value));
593 QMutableListIterator<PropertyEntry> propertyIterator(d->properties);
594 while (propertyIterator.hasNext()) {
595 PropertyEntry &entry = propertyIterator.next();
596 if (entry.first == name) {
597 entry.second = value;
598 if (state() && state()->isStateActive())
599 d->property(name).write(value);
604 QDeclarative1Action action;
605 action.restore = restoreEntryValues();
606 action.property = d->property(name);
607 action.fromValue = action.property.read();
608 action.specifiedObject = object();
609 action.specifiedProperty = name;
610 action.toValue = value;
612 propertyIterator.insert(PropertyEntry(name, value));
613 if (state() && state()->isStateActive()) {
614 state()->addEntryToRevertList(action);
615 QDeclarativeAbstractBinding *oldBinding = QDeclarativePropertyPrivate::binding(action.property);
617 oldBinding->setEnabled(false, QDeclarativePropertyPrivate::DontRemoveBinding | QDeclarativePropertyPrivate::BypassInterceptor);
618 d->property(name).write(value);
622 void QDeclarative1PropertyChanges::changeExpression(const QString &name, const QString &expression)
624 Q_D(QDeclarative1PropertyChanges);
625 typedef QPair<QString, QVariant> PropertyEntry;
626 typedef QDeclarative1PropertyChangesPrivate::ExpressionChange ExpressionEntry;
628 bool hadValue = false;
630 QMutableListIterator<PropertyEntry> propertyIterator(d->properties);
631 while (propertyIterator.hasNext()) {
632 PropertyEntry &entry = propertyIterator.next();
633 if (entry.first == name) {
634 propertyIterator.remove();
640 QMutableListIterator<ExpressionEntry> expressionIterator(d->expressions);
641 while (expressionIterator.hasNext()) {
642 const ExpressionEntry &entry = expressionIterator.next();
643 if (entry.name == name) {
644 entry.expression->setExpression(expression);
645 if (state() && state()->isStateActive()) {
646 QDeclarativeAbstractBinding *oldBinding = QDeclarativePropertyPrivate::binding(d->property(name));
648 QDeclarativePropertyPrivate::setBinding(d->property(name), 0);
649 oldBinding->destroy();
652 QDeclarativeBinding *newBinding = new QDeclarativeBinding(expression, object(), qmlContext(this));
653 newBinding->setTarget(d->property(name));
654 QDeclarativePropertyPrivate::setBinding(d->property(name), newBinding, QDeclarativePropertyPrivate::DontRemoveBinding | QDeclarativePropertyPrivate::BypassInterceptor);
660 QDeclarativeExpression *newExpression = new QDeclarativeExpression(qmlContext(this), d->object, expression);
661 expressionIterator.insert(ExpressionEntry(name, QDeclarativeBinding::Invalid, newExpression));
663 if (state() && state()->isStateActive()) {
665 QDeclarativeAbstractBinding *oldBinding = QDeclarativePropertyPrivate::binding(d->property(name));
667 oldBinding->setEnabled(false, QDeclarativePropertyPrivate::DontRemoveBinding | QDeclarativePropertyPrivate::BypassInterceptor);
668 state()->changeBindingInRevertList(object(), name, oldBinding);
671 QDeclarativeBinding *newBinding = new QDeclarativeBinding(expression, object(), qmlContext(this));
672 newBinding->setTarget(d->property(name));
673 QDeclarativePropertyPrivate::setBinding(d->property(name), newBinding, QDeclarativePropertyPrivate::DontRemoveBinding | QDeclarativePropertyPrivate::BypassInterceptor);
675 QDeclarative1Action action;
676 action.restore = restoreEntryValues();
677 action.property = d->property(name);
678 action.fromValue = action.property.read();
679 action.specifiedObject = object();
680 action.specifiedProperty = name;
684 action.toValue = newExpression->evaluate();
686 QDeclarativeBinding *newBinding = new QDeclarativeBinding(newExpression->expression(), object(), qmlContext(this));
687 newBinding->setTarget(d->property(name));
688 action.toBinding = newBinding;
689 action.deletableToBinding = true;
691 state()->addEntryToRevertList(action);
692 QDeclarativeAbstractBinding *oldBinding = QDeclarativePropertyPrivate::binding(action.property);
694 oldBinding->setEnabled(false, QDeclarativePropertyPrivate::DontRemoveBinding | QDeclarativePropertyPrivate::BypassInterceptor);
696 QDeclarativePropertyPrivate::setBinding(action.property, newBinding, QDeclarativePropertyPrivate::DontRemoveBinding | QDeclarativePropertyPrivate::BypassInterceptor);
700 // what about the signal handler?
703 QVariant QDeclarative1PropertyChanges::property(const QString &name) const
705 Q_D(const QDeclarative1PropertyChanges);
706 typedef QPair<QString, QVariant> PropertyEntry;
707 typedef QDeclarative1PropertyChangesPrivate::ExpressionChange ExpressionEntry;
709 QListIterator<PropertyEntry> propertyIterator(d->properties);
710 while (propertyIterator.hasNext()) {
711 const PropertyEntry &entry = propertyIterator.next();
712 if (entry.first == name) {
717 QListIterator<ExpressionEntry> expressionIterator(d->expressions);
718 while (expressionIterator.hasNext()) {
719 const ExpressionEntry &entry = expressionIterator.next();
720 if (entry.name == name) {
721 return QVariant(entry.expression->expression());
728 void QDeclarative1PropertyChanges::removeProperty(const QString &name)
730 Q_D(QDeclarative1PropertyChanges);
731 typedef QPair<QString, QVariant> PropertyEntry;
732 typedef QDeclarative1PropertyChangesPrivate::ExpressionChange ExpressionEntry;
734 QMutableListIterator<ExpressionEntry> expressionIterator(d->expressions);
735 while (expressionIterator.hasNext()) {
736 const ExpressionEntry &entry = expressionIterator.next();
737 if (entry.name == name) {
738 expressionIterator.remove();
739 state()->removeEntryFromRevertList(object(), name);
744 QMutableListIterator<PropertyEntry> propertyIterator(d->properties);
745 while (propertyIterator.hasNext()) {
746 const PropertyEntry &entry = propertyIterator.next();
747 if (entry.first == name) {
748 propertyIterator.remove();
749 state()->removeEntryFromRevertList(object(), name);
755 QVariant QDeclarative1PropertyChanges::value(const QString &name) const
757 Q_D(const QDeclarative1PropertyChanges);
758 typedef QPair<QString, QVariant> PropertyEntry;
760 QListIterator<PropertyEntry> propertyIterator(d->properties);
761 while (propertyIterator.hasNext()) {
762 const PropertyEntry &entry = propertyIterator.next();
763 if (entry.first == name) {
771 QString QDeclarative1PropertyChanges::expression(const QString &name) const
773 Q_D(const QDeclarative1PropertyChanges);
774 typedef QDeclarative1PropertyChangesPrivate::ExpressionChange ExpressionEntry;
776 QListIterator<ExpressionEntry> expressionIterator(d->expressions);
777 while (expressionIterator.hasNext()) {
778 const ExpressionEntry &entry = expressionIterator.next();
779 if (entry.name == name) {
780 return entry.expression->expression();
787 void QDeclarative1PropertyChanges::detachFromState()
790 state()->removeAllEntriesFromRevertList(object());
793 void QDeclarative1PropertyChanges::attachToState()
796 state()->addEntriesToRevertList(actions());