// Copyright (C) 2021 The Qt Company Ltd. // SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only #ifndef QQUICK3DPARTICLEEMITTER_H #define QQUICK3DPARTICLEEMITTER_H // // W A R N I N G // ------------- // // This file is not part of the Qt API. It exists purely as an // implementation detail. This header file may change from version to // version without notice, or even be removed. // // We mean it. // #include #include #include #include #include #include #include QT_BEGIN_NAMESPACE class Q_QUICK3DPARTICLES_EXPORT QQuick3DParticleEmitter : public QQuick3DNode { Q_OBJECT Q_PROPERTY(QQuick3DParticleSystem *system READ system WRITE setSystem NOTIFY systemChanged) Q_PROPERTY(QQmlListProperty emitBursts READ emitBursts) Q_PROPERTY(QQuick3DParticleDirection *velocity READ velocity WRITE setVelocity NOTIFY velocityChanged) Q_PROPERTY(QQuick3DParticle *particle READ particle WRITE setParticle NOTIFY particleChanged) Q_PROPERTY(bool enabled READ enabled WRITE setEnabled NOTIFY enabledChanged) Q_PROPERTY(QQuick3DParticleAbstractShape *shape READ shape WRITE setShape NOTIFY shapeChanged) Q_PROPERTY(float emitRate READ emitRate WRITE setEmitRate NOTIFY emitRateChanged) Q_PROPERTY(int lifeSpan READ lifeSpan WRITE setLifeSpan NOTIFY lifeSpanChanged) Q_PROPERTY(int lifeSpanVariation READ lifeSpanVariation WRITE setLifeSpanVariation NOTIFY lifeSpanVariationChanged) Q_PROPERTY(float particleScale READ particleScale WRITE setParticleScale NOTIFY particleScaleChanged) Q_PROPERTY(float particleEndScale READ particleEndScale WRITE setParticleEndScale NOTIFY particleEndScaleChanged) Q_PROPERTY(float particleScaleVariation READ particleScaleVariation WRITE setParticleScaleVariation NOTIFY particleScaleVariationChanged) Q_PROPERTY(float particleEndScaleVariation READ particleEndScaleVariation WRITE setParticleEndScaleVariation NOTIFY particleEndScaleVariationChanged) Q_PROPERTY(QVector3D particleRotation READ particleRotation WRITE setParticleRotation NOTIFY particleRotationChanged) Q_PROPERTY(QVector3D particleRotationVariation READ particleRotationVariation WRITE setParticleRotationVariation NOTIFY particleRotationVariationChanged) Q_PROPERTY(QVector3D particleRotationVelocity READ particleRotationVelocity WRITE setParticleRotationVelocity NOTIFY particleRotationVelocityChanged) Q_PROPERTY(QVector3D particleRotationVelocityVariation READ particleRotationVelocityVariation WRITE setParticleRotationVelocityVariation NOTIFY particleRotationVariationVelocityChanged) Q_PROPERTY(float depthBias READ depthBias WRITE setDepthBias NOTIFY depthBiasChanged) Q_PROPERTY(bool reversed READ reversed WRITE setReversed NOTIFY reversedChanged REVISION(6, 10)) Q_PROPERTY(EmitMode emitMode READ emitMode WRITE setEmitMode NOTIFY emitModeChanged REVISION(6, 10)) QML_NAMED_ELEMENT(ParticleEmitter3D) QML_ADDED_IN_VERSION(6, 2) public: enum EmitMode { Default = 0, SurfaceNormal, SurfaceReflected }; Q_ENUM(EmitMode) QQuick3DParticleEmitter(QQuick3DNode *parent = nullptr); ~QQuick3DParticleEmitter() override; bool enabled() const; QQuick3DParticleDirection *velocity() const; QQuick3DParticleSystem *system() const; float emitRate() const; float particleScale() const; float particleEndScale() const; float particleScaleVariation() const; float particleEndScaleVariation() const; int lifeSpan() const; int lifeSpanVariation() const; QQuick3DParticle *particle() const; QQuick3DParticleAbstractShape *shape() const; QVector3D particleRotation() const; QVector3D particleRotationVariation() const; QVector3D particleRotationVelocity() const; QVector3D particleRotationVelocityVariation() const; float depthBias() const; Q_REVISION(6, 10) bool reversed() const; Q_REVISION(6, 10) EmitMode emitMode() const; QQmlListProperty emitBursts(); Q_INVOKABLE virtual void burst(int count); Q_INVOKABLE virtual void burst(int count, int duration); Q_INVOKABLE virtual void burst(int count, int duration, const QVector3D &position); public Q_SLOTS: void setEnabled(bool enabled); void setVelocity(QQuick3DParticleDirection *velocity); void setSystem(QQuick3DParticleSystem *system); void setEmitRate(float emitRate); void setParticleScale(float particleScale); void setParticleEndScale(float particleEndScale); void setParticleScaleVariation(float particleScaleVariation); void setParticleEndScaleVariation(float particleEndScaleVariation); void setLifeSpan(int lifeSpan); void setLifeSpanVariation(int lifeSpanVariation); void setParticle(QQuick3DParticle *particle); void setShape(QQuick3DParticleAbstractShape *shape); void setParticleRotation(const QVector3D &particleRotation); void setParticleRotationVariation(const QVector3D &particleRotationVariation); void setParticleRotationVelocity(const QVector3D &particleRotationVelocity); void setParticleRotationVelocityVariation(const QVector3D &particleRotationVelocityVariation); void setDepthBias(float bias); Q_REVISION(6, 10) void setReversed(bool reversed); Q_REVISION(6, 10) void setEmitMode(EmitMode mode); Q_SIGNALS: void velocityChanged(); void systemChanged(); void emitRateChanged(); void particleScaleChanged(); void particleEndScaleChanged(); void particleScaleVariationChanged(); void particleEndScaleVariationChanged(); void lifeSpanChanged(); void lifeSpanVariationChanged(); void particleChanged(); void shapeChanged(); void particleRotationChanged(); void particleRotationVariationChanged(); void particleRotationVelocityChanged(); void particleRotationVariationVelocityChanged(); void enabledChanged(); void depthBiasChanged(); Q_REVISION(6, 10) void reversedChanged(); Q_REVISION(6, 10) void emitModeChanged(); protected: friend class QQuick3DParticleSystem; friend class QQuick3DParticleEmitBurst; friend class QQuick3DParticleTrailEmitter; void componentComplete() override; void registerEmitBurst(QQuick3DParticleEmitBurst *emitBurst); void unRegisterEmitBurst(QQuick3DParticleEmitBurst *emitBurst); void generateEmitBursts(); void emitParticle(QQuick3DParticle *particle, float startTime, const QMatrix4x4 &transform, const QQuaternion &parentRotation, const QVector3D ¢erPos, int index = -1, const QVector3D &velocity = QVector3D(), const QVector3D &normal = QVector3D()); void emitParticles(); void emitActivationNodeParticles(QQuick3DParticleModelBlendParticle *particle); void emitParticlesBurst(const QQuick3DParticleEmitBurstData &burst); int getEmitAmount(); int getEmitAmountFromDynamicBursts(int triggerType = 0); void reset(); // EmitBursts - list handling void appendEmitBurst(QQuick3DParticleEmitBurst *); qsizetype emitBurstCount() const; QQuick3DParticleEmitBurst *emitBurst(qsizetype) const; void clearEmitBursts(); void replaceEmitBurst(qsizetype, QQuick3DParticleEmitBurst *); void removeLastEmitBurst(); // EmitBursts - static static void appendEmitBurst(QQmlListProperty *, QQuick3DParticleEmitBurst *); static qsizetype emitBurstCount(QQmlListProperty *); static QQuick3DParticleEmitBurst *emitBurst(QQmlListProperty *, qsizetype); static void clearEmitBursts(QQmlListProperty *); static void replaceEmitBurst(QQmlListProperty *, qsizetype, QQuick3DParticleEmitBurst *); static void removeLastEmitBurst(QQmlListProperty *); private: struct BurstEmitData { int startTime; int endTime; int emitAmount; int emitCounter = 0; int prevBurstTime; }; QQuick3DParticleDirection *m_velocity = nullptr; QQuick3DParticleSystem *m_system = nullptr; float m_emitRate = 0.0f; // Time in ms when emitting last time happened int m_prevEmitTime = 0; // Time in ms when dynamic burst last time happened int m_prevBurstTime = 0; float m_particleScale = 1.0f; float m_particleEndScale = -1.0f; float m_particleScaleVariation = 0.0f; float m_particleEndScaleVariation = -1.0f; int m_lifeSpan = 1000; int m_lifeSpanVariation = 0; float m_unemittedF = 0.0f; float m_depthBias = 0.0f; QQuick3DParticle *m_particle = nullptr; QQuick3DParticleAbstractShape *m_shape = nullptr; QVector3D m_particleRotation; QVector3D m_particleRotationVariation; QVector3D m_particleRotationVelocity; QVector3D m_particleRotationVelocityVariation; bool m_enabled = true; const QQuick3DParticleData m_clearData = {}; bool m_burstGenerated = false; QQuick3DNode *m_systemSharedParent = nullptr; // This list contains all emit bursts (both QQuick3DParticleEmitBurst and QQuick3DParticleDynamicBurst) QList m_emitBursts; QList m_burstEmitData; bool m_reversed = false; EmitMode m_emitMode = EmitMode::Default; }; QT_END_NAMESPACE #endif // QQUICK3DPARTICLEEMITTER_H