Inherit velocity of a moving object for VFX graph particles

Hi. I am trying to create flares for a spaceship but I have a trouble applying velocity of the spaceship to the particles themselves. If I use block “Inherit Source Velocity” , it does nothing. Flares then look really unnatural, spawning behind the spaceship.
Sorry for asking a trivial question, I just could not find any documentation for VFX graph that could help me.
Thanks for the help.


1 Like

Hey Adam! A bit late but here’s my input:

I’ve encountered the same problem and have been experimenting with it. As far as I understood “Inherit Source Velocity” is for spawning particles from other particles (and inheriting their velocity).

I’ve tried adding exposed Vector3 variable and updating it to object velocity on each particles emission, it kind of works but result is a really stuttery moving particles when object is moving alongside them with attached camera. My guess is that it has something to do with the fact that they run on GPU and there’s some desync between GPU and CPU simulation.

Anyway here’s a graph:

And in c# you do

using UnityEngine.VFX;
...

public VisualEffect lasorBurstVFX;
...
Vector3 locVel = transform.InverseTransformDirection(rBody.velocity); // This transforms velocity vector from world to local, which needs to be done if emitter is a child of that rigidBody

lasorBurstVFX.SetVector3("startVelocity",locVel);

Think the idea should be pretty clear, will be curious to see if it works out in your case.

My stuttery result (was strafing left here):

Here’s a solution that uses a custom block, just drop it anywhere and use the new “Calculate Object Velocity” block.

using Unity.Mathematics;
using UnityEngine;
using UnityEngine.VFX;

class CalculateObjectVelocity : VFXSpawnerCallbacks
{
    private static readonly int PositionPropertyId = Shader.PropertyToID("ObjectPositionWS");

    private static readonly int PositionAttributeId = Shader.PropertyToID("position");
    private static readonly int OldPositionAttributeId = Shader.PropertyToID("oldPosition");
    private static readonly int VelocityAttributeId = Shader.PropertyToID("velocity");

    public class InputProperties
    {
        public Vector3 ObjectPositionWS = Vector3.zero;
    }

    private float3 _lastPosition;

    public override void OnPlay(VFXSpawnerState state, VFXExpressionValues vfxValues, VisualEffect vfxComponent)
    {
        _lastPosition = vfxValues.GetVector3(PositionPropertyId);
    }

    public override void OnUpdate(VFXSpawnerState state, VFXExpressionValues vfxValues, VisualEffect vfxComponent)
    {
        if (!state.playing || state.deltaTime == 0) return;

        float3 position = vfxValues.GetVector3(PositionPropertyId);

        state.vfxEventAttribute.SetVector3(OldPositionAttributeId, _lastPosition);
        state.vfxEventAttribute.SetVector3(PositionAttributeId, position);

        state.vfxEventAttribute.SetVector3(VelocityAttributeId, (position - _lastPosition) / state.deltaTime);

        _lastPosition = position;
    }

    public override void OnStop(VFXSpawnerState state, VFXExpressionValues vfxValues, VisualEffect vfxComponent)
    {

    }
}

I had to offset the particle position because the system adds the velocity in this frame itself, causing it to jump ahead of the intended position.