Writing a New Action Task
An Action changes game state and returns Running while its work continues. This
example consumes the target produced by the
Within Sight Conditional and moves toward
it.
Create the task
using BehaviorDesigner.Runtime;
using BehaviorDesigner.Runtime.Tasks;
using UnityEngine;
[TaskCategory("Tutorial")]
[TaskDescription("Moves the owner toward a target Transform.")]
public class MoveTowards : Action
{
public SharedFloat Speed = 2f;
public SharedFloat ArrivedDistance = 0.1f;
public SharedTransform Target;
public override TaskStatus OnUpdate()
{
if (Target.Value == null) {
return TaskStatus.Failure;
}
var offset = Target.Value.position - transform.position;
if (offset.sqrMagnitude <= ArrivedDistance.Value * ArrivedDistance.Value) {
return TaskStatus.Success;
}
transform.position = Vector3.MoveTowards(
transform.position,
Target.Value.position,
Speed.Value * Time.deltaTime);
return TaskStatus.Running;
}
public override void OnReset()
{
Speed = 2f;
ArrivedDistance = 0.1f;
Target = null;
}
}
The null check prevents an invalid output from becoming an exception. Squared
distance avoids a square root each update. A production character should
usually delegate movement to its navigation or character controller instead of
setting the Transform directly.
Build the branch
- Add a Sequence.
- Add Tutorial > Within Sight as its first child.
- Add Tutorial > Move Towards as its second child.
- Bind both Target fields to the same local
Transformvariable. - Set movement values appropriate for the scene.
The Sequence reaches Move Towards only when sensing succeeds. The Action
returns Running while moving and Success after entering Arrived Distance.
Verify interruption
Run the tree and confirm the graph remains on Move Towards until arrival.
Then interrupt the branch with a conditional abort.
The task should stop cleanly. Add OnEnd cleanup to custom Actions that start an
Animator parameter, ability, audio source, or navigation request that otherwise
survives interruption.