8#include <QtQuick/qsgnode.h>
10#include <QQmlComponent>
16
17
18
19
20
21
22
26
27
28
29
30
33
34
35
36
37
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
66
67
68
69
70
71
74
75
76
77
78
79
80
81
83
84
85
86
87
88
89
90
91
92
94QQuickItemParticle::QQuickItemParticle(QQuickItem *parent) :
95 QQuickParticlePainter(parent), m_fade(
true), m_lastT(0), m_activeCount(0), m_delegate(
nullptr)
97 setFlag(QQuickItem::ItemHasContents);
98 clock =
new Clock(
this);
99 connect(
this, &QQuickItemParticle::systemChanged,
this, &QQuickItemParticle::reconnectSystem);
100 connect(
this, &QQuickItemParticle::parentChanged,
this, &QQuickItemParticle::reconnectParent);
101 connect(
this, &QQuickItemParticle::enabledChanged,
this, &QQuickItemParticle::updateClock);
102 reconnectSystem(m_system);
103 reconnectParent(parent);
106QQuickItemParticle::~QQuickItemParticle()
109 qDeleteAll(m_managed);
112void QQuickItemParticle::freeze(QQuickItem* item)
118void QQuickItemParticle::unfreeze(QQuickItem* item)
120 m_stasis.remove(item);
123void QQuickItemParticle::take(QQuickItem *item,
bool prioritize)
126 m_pendingItems.push_front(item);
128 m_pendingItems.push_back(item);
131void QQuickItemParticle::give(QQuickItem *item)
133 for (
auto groupId : groupIds()) {
134 for (QQuickParticleData* data : std::as_const(m_system->groupData[groupId]->data)) {
135 if (data->delegate == item){
136 m_deletables << item;
137 data->delegate =
nullptr;
138 m_system->groupData[groupId]->kill(data);
145void QQuickItemParticle::initialize(
int gIdx,
int pIdx)
151void QQuickItemParticle::commit(
int,
int)
155void QQuickItemParticle::processDeletables()
157 foreach (QQuickItem* item, m_deletables){
159 item->setOpacity(0.);
160 item->setVisible(
false);
161 QQuickItemParticleAttached* mpa;
162 if ((mpa = qobject_cast<QQuickItemParticleAttached*>(qmlAttachedPropertiesObject<QQuickItemParticle>(item)))) {
163 if (mpa->m_parentItem !=
nullptr)
164 item->setParentItem(mpa->m_parentItem);
168 if ((idx = m_managed.indexOf(item)) != -1) {
169 m_managed.takeAt(idx);
174 m_deletables.clear();
177void QQuickItemParticle::tick(
int time)
181 for (
auto groupId : groupIds()) {
182 for (QQuickParticleData* d : std::as_const(m_system->groupData[groupId]->data)) {
183 if (!d->delegate && d->t != -1 && d->stillAlive(m_system)) {
184 QQuickItem* parentItem =
nullptr;
185 if (!m_pendingItems.isEmpty()){
186 QQuickItem *item = m_pendingItems.front();
187 m_pendingItems.pop_front();
188 parentItem = item->parentItem();
190 }
else if (m_delegate){
191 d->delegate = qobject_cast<QQuickItem*>(m_delegate->create(qmlContext(
this)));
193 m_managed << d->delegate;
195 if (d && d->delegate){
196 d->delegate->setX(d->curX(m_system) - d->delegate->width() / 2);
197 d->delegate->setY(d->curY(m_system) - d->delegate->height() / 2);
198 QQuickItemParticleAttached* mpa = qobject_cast<QQuickItemParticleAttached*>(qmlAttachedPropertiesObject<QQuickItemParticle>(d->delegate));
200 mpa->m_parentItem = parentItem;
204 d->delegate->setParentItem(
this);
206 d->delegate->setOpacity(0.);
207 d->delegate->setVisible(
false);
215void QQuickItemParticle::reset()
217 QQuickParticlePainter::reset();
221 QSet<QQuickItem*> lost = QSet<QQuickItem*>(m_managed.cbegin(), m_managed.cend());
222 for (
auto groupId : groupIds()) {
223 for (QQuickParticleData* d : std::as_const(m_system->groupData[groupId]->data)) {
224 lost.remove(d->delegate);
227 m_deletables.unite(lost);
233QSGNode* QQuickItemParticle::updatePaintNode(QSGNode* n, UpdatePaintNodeData* d)
237 m_pleaseReset =
false;
239 if (clockShouldUpdate()) {
244 n->markDirty(QSGNode::DirtyMaterial);
245 return QQuickItem::updatePaintNode(n,d);
248void QQuickItemParticle::prepareNextFrame()
252 qint64 timeStamp = m_system->systemSync(
this);
253 qreal curT = timeStamp/1000.0;
254 qreal dt = curT - m_lastT;
260 for (
auto groupId : groupIds()) {
261 for (QQuickParticleData* data : std::as_const(m_system->groupData[groupId]->data)) {
262 QQuickItem* item = data->delegate;
265 float t = ((timeStamp / 1000.0f) - data->t) / data->lifeSpan;
266 if (m_stasis.contains(item)) {
271 m_deletables << item;
272 data->delegate =
nullptr;
274 data->delegate->setVisible(
true);
284 item->setX(data->curX(m_system) - item->width() / 2 - m_systemOffset.x());
285 item->setY(data->curY(m_system) - item->height() / 2 - m_systemOffset.y());
290QQuickItemParticleAttached *QQuickItemParticle::qmlAttachedProperties(QObject *object)
292 return new QQuickItemParticleAttached(object);
295bool QQuickItemParticle::clockShouldUpdate()
const
301 QQuickParticleEmitter *parentEmitter = qobject_cast<QQuickParticleEmitter *>(parent());
302 bool parentEmitterDisabled = parentEmitter && !parentEmitter->isEnabled();
303 bool systemRunning = m_system && (m_system->isRunning() || m_system->isPaused());
304 return systemRunning && !parentEmitterDisabled;
307void QQuickItemParticle::reconnectParent(QQuickItem *parentItem)
310 disconnect(m_parentEnabledStateConnection);
312 m_parentEnabledStateConnection = connect(parentItem, &QQuickParticleSystem::enabledChanged,
313 this, &QQuickItemParticle::updateClock);
317void QQuickItemParticle::reconnectSystem(QQuickParticleSystem *system)
320 disconnect(m_systemRunStateConnection);
321 disconnect(m_systemPauseStateConnection);
322 disconnect(m_systemEnabledStateConnection);
324 m_systemRunStateConnection = connect(m_system, &QQuickParticleSystem::runningChanged,
this, [
this](){
325 QQuickItemParticle::updateClock();
327 m_systemPauseStateConnection = connect(m_system, &QQuickParticleSystem::pausedChanged,
this, [
this](){
328 QQuickItemParticle::updateClock();
330 m_systemEnabledStateConnection = connect(m_system, &QQuickParticleSystem::enabledChanged,
this,
331 &QQuickItemParticle::updateClock);
335void QQuickItemParticle::updateClock()
337 if (clockShouldUpdate()) {
338 if (!clock->isRunning())
341 if (clock->isRunning())
348#include "moc_qquickitemparticle_p.cpp"
Combined button and popup list for selecting options.