Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
Bug / Crash  Manual fluid emission throw exception with Compute backend
#1
Hi,

I received the latest ObiFluid 7 beta on 24/1/2024. I want to manually emit particle by setting emitter.speed = 0 and then call emitter.EmitParticle() instead. However, the emitter.EmitParticle() on Compute backend caused this exception:
Code:
ArgumentNullException: Value cannot be null.
Parameter name: buffer
UnityEngine.ComputeShader.SetBuffer (System.Int32 kernelIndex, System.Int32 nameID, UnityEngine.GraphicsBuffer buffer) (at <f7237cf7abef49bfbb552d7eb076e422>:0)
UnityEngine.ComputeShader.SetBuffer (System.Int32 kernelIndex, System.String name, UnityEngine.GraphicsBuffer buffer) (at <f7237cf7abef49bfbb552d7eb076e422>:0)
Obi.ComputeFluidMesherSystem.Render () (at Assets/Obi/Scripts/Common/Backends/Compute/Rendering/Fluid/ComputeFluidMesherSystem.cs:406)
Obi.ObiRenderSystemStack.Render () (at Assets/Obi/Scripts/Common/Solver/ObiRenderSystemStack.cs:41)
Obi.ObiSolver.Render (System.Single unsimulatedTime) (at Assets/Obi/Scripts/Common/Solver/ObiSolver.cs:1527)
Obi.ObiSolver.LateUpdate () (at Assets/Obi/Scripts/Common/Solver/ObiSolver.cs:970)

This does not happen on Burst backend.
Here is simple code to replicate the error:
Code:
public class EmitManually : MonoBehaviour
{
    [SerializeField] private ObiEmitter emitter;
    [Range(1, 100)]
    [SerializeField] private uint particlesPerEmission = 1;

    private void Awake()
    {
        emitter.speed = 0;
        emitter.minPoolSize = 0;
    }

    private void Update()
    {
        if (Input.GetKeyDown(KeyCode.Space))
        {
            for (uint i = 0; i < particlesPerEmission; i++)
                emitter.EmitParticle(0);
        }
    }
}
Reply
#2
Hi there,

The compute backend requires adding/destroying particles at a specific point in the solver's update cycle, can't be emitted at any time. EmitParticle() and KillParticle() can only be called in the solver's OnSimulate event.  This is because data on the CPU is sent to the GPU only once per frame, so modifying data on the CPU after it's been send to the GPU will result in both getting out of sync.

This isn't documented yet, so we'll make sure to mention it in the manual in the relevant places. We'll also look into adding a proper error message when attempting to do this.

thanks for reporting the issue!
Reply