Accessing particle system startColor or colorOverLifetime during runtime in 5.4

Hi,

I was expecting 5.4 to expose more particle system properties for runtime modification, but I can’t find a way to change the startColor or colorOverLifetime colors.

Here’s my test regarding colorOverLifetime:

using UnityEngine;
using System.Collections;

public class particleSystemColorTest : MonoBehaviour {
   
    public ParticleSystem                localParticleSystem;
   
    Gradient newLifetimeColorKeys;
   
    [Range (0,1)]
    public float        saturation;
   
    // Use this for initialization
    void Start () {
        localParticleSystem = GetComponent<ParticleSystem>();
       
        newLifetimeColorKeys        = localParticleSystem.colorOverLifetime.color.gradient;
    }
   
    // Update is called once per frame
    void Update () {
        for(int i = 0; i < newLifetimeColorKeys.colorKeys.Length; i++)
        {
            newLifetimeColorKeys.colorKeys[i].color = Color.white * saturation;
        }
       
        var col = localParticleSystem.colorOverLifetime;
        col.enabled = true;
       
        col.color = newLifetimeColorKeys;
    }
}

The particle system has one color as the startColor and one gradient in the colorOverLifetime module.
If possible, I’d rather change the startColor gradients but I was going nowhere when I tried that.

Thanks.

You are modifying a copy of the curve. You need to reapply it.

localParticleSystem.colorOverLifetime.color = newLifetimeColorKeys;

http://blogs.unity3d.com/2016/04/20/particle-system-modules-faq/

Did it work for you? I get this error:
Assets/particleSystemColorTest.cs(27,37): error CS1612: Cannot modify a value type return value of `UnityEngine.ParticleSystem.colorOverLifetime’. Consider storing the value in a temporary variable

I also tried this:
localParticleSystem.colorOverLifetime.color.gradient = newLifetimeColorKeys;

And got the same error:
error CS1612: Cannot modify a value type return value of `UnityEngine.ParticleSystem.ColorOverLifetimeModule.color’. Consider storing the value in a temporary variable

The blog post does not mention colorOverLifetime or startColor specifically. Can you please test this? I’ve attached a minimal project.

2735204–194725–UNITY_ParticlesTest.zip (532 KB)

Sorry I was being lazy with my code. You need to get the module and then set it, you cant do it in one line. The blog post explains this, not specifically for colours but how particle system modules work.

var colOverLifetimeModule = localParticleSystem.colorOverLifetime;
colOverLifetimeModule.color = newLifetimeColorKeys;

Thanks. The errors are gone, but it still doesn’t work with this code:

using UnityEngine;
using System.Collections;

public class particleSystemColorTest : MonoBehaviour {
   
    public ParticleSystem                localParticleSystem;
   
    Gradient newLifetimeColorKeys;
   
    [Range (0,1)]
    public float        saturation;
   
    // Use this for initialization
    void Start () {
        localParticleSystem = GetComponent<ParticleSystem>();
       
        newLifetimeColorKeys        = localParticleSystem.colorOverLifetime.color.gradient;
    }
   
    // Update is called once per frame
    void Update () {
        for(int i = 0; i < newLifetimeColorKeys.colorKeys.Length; i++)
        {
            newLifetimeColorKeys.colorKeys[i].color = Color.white * saturation;
        }

        var colOverLifetimeModule = localParticleSystem.colorOverLifetime;
        colOverLifetimeModule.color = newLifetimeColorKeys;

        Color c = colOverLifetimeModule.color.gradient.colorKeys[0].color;

        Debug.Log("Color: " + c);
    }
}

While we’re at it, can you show me how to change the start color?

Looks like you are assigning the value to a copy.
Do this

using UnityEngine;
using System.Collections;

public class particleSystemColorTest : MonoBehaviour
{

    public ParticleSystem localParticleSystem;

    Gradient newLifetimeColorKeys;

    [Range(0, 1)]
    public float saturation;

    // Use this for initialization
    void Start()
    {
        localParticleSystem = GetComponent<ParticleSystem>();

        newLifetimeColorKeys = localParticleSystem.colorOverLifetime.color.gradient;
    }

    // Update is called once per frame
    void Update()
    {
        var keys = newLifetimeColorKeys.colorKeys;
        for (int i = 0; i < newLifetimeColorKeys.colorKeys.Length; i++)
        {
            keys[i].color = Color.red;
        }
        newLifetimeColorKeys.colorKeys = keys;
        var colOverLifetimeModule = localParticleSystem.colorOverLifetime;
        colOverLifetimeModule.color = newLifetimeColorKeys;
    }
}

The startColor gradient has not been exposed yet, should be in 5.5.

1 Like

Works great. Thank you very much!

2 Likes