Search Unity

How do I get a ParticleSystem to pool itself when it finishes WITHOUT checking OnUpdate?

Discussion in 'General Graphics' started by bunp, Oct 25, 2021.

  1. bunp

    bunp

    Joined:
    Feb 21, 2019
    Posts:
    70
    Problem:

    I have a particleSystem and a pooling system. When the particle is done, I want it to go to the pool.
    I can't use Stop Callback because it never gets called because the system never stops.
    I run IsAlive() on Update (to debug ONLY) and it returns true every frame, even when the system and all child systems have zero particles in them, and none of them are set to loop.

    I can't get it to call the callback function unless I manually fire Stop() on the system, but I can't know when to manually fire Stop() without checking Update, which I do not want to do.

    How do I solve this?
     
  2. bunp

    bunp

    Joined:
    Feb 21, 2019
    Posts:
    70
    Here is my code, the Callback method never gets called because it never stops itself.

    Code (CSharp):
    1. using System.Collections;
    2. using System.Collections.Generic;
    3. using UnityEngine;
    4.  
    5. public class ParticleInstance : MonoBehaviour
    6. {
    7.     // THIS IS: The component on the actual effect itself.
    8.  
    9.     public ParticlePool parentPool;
    10.     [Space]
    11.     [SerializeField] private ParticleSystem pSystem;
    12.     [SerializeField] private Transform followTarget;
    13.     //[SerializeField] private float timeTilTerminate = -1;
    14.  
    15.     //[SerializeField] private bool selfTerminate = true;
    16.  
    17.  
    18.     //private IEnumerator coroutine; // Coroutine reference if required.
    19.  
    20.     /*
    21.     private void OnEnable()
    22.     {
    23.         Initialize(true, 1f);
    24.     }
    25.     */
    26.  
    27.     public void Start()
    28.     {
    29.         //this.timeTilTerminate = timeTillSelfTerminate;
    30.         InitializeCallback();
    31.         if (pSystem == null)
    32.         {
    33.             pSystem = GetComponent<ParticleSystem>();
    34.         }
    35.         //Debug.Log("Particle instance ID on Enabke: " + gameObject.GetInstanceID());
    36.         //if (timeTillSelfTerminate >= 0)
    37.         //{
    38.         //    StartCoroutine(TerminateTime(timeTilTerminate));
    39.         //}
    40.     }
    41.  
    42.     public void Update()
    43.     {
    44.         Debug.Log(pSystem.IsAlive());
    45.         if (followTarget != null)
    46.         {
    47.             transform.position = followTarget.position;
    48.         }
    49.     }
    50.  
    51.     public void Initialize(Actor target)
    52.     {
    53.         followTarget = target.VisualCenter.transform;
    54.     }
    55.  
    56.     private void InitializeCallback()
    57.     {
    58.         var main = pSystem.main;
    59.         main.stopAction = ParticleSystemStopAction.Callback;
    60.     }
    61.  
    62.  
    63.     public void End()
    64.     {
    65.         if (parentPool != null)
    66.         {
    67.             pSystem.Stop(true);
    68.         }
    69.         else
    70.         {
    71.             Debug.LogWarning("Orphan detected! " + this + " tried to return to it's parent's objectPool but it has no parent.");
    72.         }
    73.     }
    74.  
    75.     private void OnParticleSystemStopped()
    76.     {
    77.         parentPool.ReturnToParticlePool(this);
    78.     }
    79.  
    80.     /*
    81.     IEnumerator TerminateTime(float time)
    82.     {
    83.         yield return new WaitForSeconds(time);
    84.         End();
    85.     }
    86.     */
    87.  
    88.     /*
    89.     private void Start()
    90.     {
    91.         Debug.Log("Particle instance ID on Startup: " + gameObject.GetInstanceID());
    92.     }
    93.  
    94.     private void Awake()
    95.     {
    96.         Debug.Log("Particle instance ID on Awake: " + gameObject.GetInstanceID());
    97.     }
    98.  
    99.     private void OnDisable()
    100.     {
    101.         Debug.Log("Particle instance ID on Disable: " + gameObject.GetInstanceID());
    102.     }
    103.     */
     
  3. richardkettlewell

    richardkettlewell

    Unity Technologies

    Joined:
    Sep 9, 2015
    Posts:
    2,285
    Why does the system never stop?

    I'm trying to understand the states of the system. you want it to return to the pool when it is "done", but you also say the system never stops. So it would be good to understand your criteria for knowing that the system is finished.