Dynamically add animation to dynamically created QML component from C++
-
I have a rectangle in rect.qml
import QtQuick 2.0 Rectangle{ id: myRect; width: 100 height: 100 color: "red" }and animation in anim.qml:
import QtQuick 2.12 ScaleAnimator { id: rotationAnim target: myRect from: 0 to: 1 duration: 2000 }I load the rectangle from c++:
QQmlComponent component(qmlEngine, QUrl::fromLocalFile("rect.qml")); QQmlContext* rootItemContext = QQmlEngine::contextForObject(rootWindow); QQuickItem *object = qobject_cast<QQuickItem*>(component.beginCreate(rootItemContext)); if(object != nullptr) { QQmlEngine::setObjectOwnership(object, QQmlEngine::CppOwnership); object->setParentItem(rootWindow->contentItem()); object->setParent(qmlEngine); } } component.completeCreate();I can load the animation the same way, but obviously, I get the error:
ReferenceError: myRect is not definedI want to keep a rectangle and animation in different files. I have a set of animations and depending on my need I want to append selected animation to a rectangle.
Is there any way to refer to this rectangle from the animation or any way to append an animation to an existing object? -
You can define
ScaleAnimatorinside your rectacgle, like in documentation. -
Hi @ChrisTof , you can do like this:-
Rectangle { id: myRect width: 100 height: 100 color: "red" Anim { target: myRect } }Note:- Remove target inside ScaleAnimator in anim.qml
-
Of course, I can define ScaleAnimator inside the rectangle. I did not express myself clearly. I have animation and rectangle in separate files, because:
- I have a rectangle.
- I have a set of animations.
I create a rectangle and sometimes I want to append animation and sometimes I don't. Sometimes I append animation 1, and other time animation 2. I want to this dynamically.
-
Remove
targetproperty then and setrunningtofalsefor yourScaleAnimator. Create Animator at C++ like Rectangle and do a bit magic like in example below:QQmlComponent rect(&engine, QUrl(QStringLiteral("qrc:/MyRect.qml"))); QQuickItem* rectangle = qobject_cast<QQuickItem*>(rect.beginCreate(context)); if (rectangle != nullptr) { auto rootItem = engine.rootObjects()[0]->property("contentItem").value<QQuickItem*>(); rectangle->setParentItem(rootItem); QQmlComponent a1(&engine, QUrl(QStringLiteral("qrc:/Anim1.qml"))); auto animation = a1.beginCreate(context); rect.completeCreate(); animation->setParent(rectangle); animation->setProperty("target", QVariant::fromValue(rectangle)); a1.completeCreate(); animation->setProperty("running", true); } -
Remove
targetproperty then and setrunningtofalsefor yourScaleAnimator. Create Animator at C++ like Rectangle and do a bit magic like in example below:QQmlComponent rect(&engine, QUrl(QStringLiteral("qrc:/MyRect.qml"))); QQuickItem* rectangle = qobject_cast<QQuickItem*>(rect.beginCreate(context)); if (rectangle != nullptr) { auto rootItem = engine.rootObjects()[0]->property("contentItem").value<QQuickItem*>(); rectangle->setParentItem(rootItem); QQmlComponent a1(&engine, QUrl(QStringLiteral("qrc:/Anim1.qml"))); auto animation = a1.beginCreate(context); rect.completeCreate(); animation->setParent(rectangle); animation->setProperty("target", QVariant::fromValue(rectangle)); a1.completeCreate(); animation->setProperty("running", true); }@IntruderExcluder exactly what I needed. Thank you very much.