Projectile Factory
v1.0
This is an integration with Projectile Factory, a behavior-based projectile system.
Integrating Projectile Factory with Juicy Actions adds additional actions that specifically work with Projectile Factory.
Installation
Install Projectile Factory from Package Manager. Please also import the "Demo" folder since the integration demo is a variant of that, and the demo objects are used.
Find the "ProjectileFactoryIntegration" .unitypackage in Juicy Actions/Integrations. Extract that into your project.
The demo scene objects require layers "Actor" and "Projectile". If you add those in index 6 and 7 respectively, things *should* just work and remap to those layers.
In later Unity 6.x versions, you may also need to update the "Include Layers" in the Layer Overrides optoin on the collider of the objects.
Calling Juicy Actions from Projectile Spawner
The ProjectileSpawner has many events built-in. These can be used to Execute() actions on ActionExecutors, or on components like the ActionRunner.
The Demo Player Actor in the scene is a variant, and has the ProjectileDemoActorJuicy on it β this inherits from the original ProjectileDemoActor. This adds ActionExecutors and properties to Execute() them.
// ProjectileDemoActorJuicy.cs
public void ExecuteLaunchActions() => onLaunchActions.Execute(this);
public ActionExecutor onLaunchActions;We can then call the Execute() method using the OnLaunch event in the Projectile Events on the ProjectileSpawner.

With that, we can add a bunch of juice, including transform and material effects plus post processing effects.



Actors Getting Hit
The original Projectile Factory demo had DemoTarget objects with a ProjectileDemoActorGotHitReaction script. This script does one thing with code: make the material flash pink. We can use Juicy Actions to do this and more.
Instead, we can use ProjectileDemoActorActions, which will subscribe to the GotHit event on the ProjectileDemoActor, same as the original, but instead of a boiler plate reaction, we'll use an ActionExecutor to drive the response β something far more customizable, quick, and easily changed later.
To recreate the original effect, we can use the ColorChangeAction, and set it to flash pink for 0.5 seconds, with a fade via AnimationCurve.
Objets Getting Hit
The spheres and cubes in the scene can be juicy as well. However, Projectile Factory projectiles have many ways of causing a collision, and in many cases, they handle all the behavior effects directly.
In this demo, we want our spheres and cubes to perform actions when they get hit by projectiles.
Each of these obejcts has an ActionOnPhysicsEvent component, which handles both triggers and collisions β essentially it's a combination of ActionOnTrigger and ActionOnCollision. That takes care of many projectile behaviors, but some don't perform a phyics event.
We will make use of the IProjectileFactoryCollisionReceiver interface. Check the docs here for more complete details.
The custom script ProjectileFactoryColliionHandler connects with the ActionOnPhysicsEvent component and triggers the OnEnterActions without requiring a physics event.
It is possible to write a custom handler that works with your custom actions and utilizes the ProjectileCollisionMessage data that is passed to the interface. In this example, we pass in a null collider since not all projectiles of this nature have a collider, but you can make use of the data if you'd like.
See the docs for full details on this struct.
Time Control
We can easily ensure that the Juicy Action Clock is used by ensuring we Sync UnityTime to Juicy Actions Clock. This way, any change to the Juicy Action Clock timescale value will be set on the Unity.Time timescale.

Actions from Projectile Events
There are a number of ActionOnEvent classes that hook directly into the Projectile class, subscribing to the events the class provides. Generally these would be added to a specific Projectile object, but they could be added to other classes, so long as the Projectile field is populated.
If you do assign a projectile at runtime, use the public AssignProjectile(Projectile newProjectile) method. This will automatically unsubscribe from the existing projectile (if applicable), and subscribe to the new one as well.

Other classes like ActionRunner can also be used on Projectiles to perform actions.
Actions from Projectile Spawner Events
There are also a number of ActionOnEvent classes that hook directly into the ProjectileSpawner class, just as the ones that hook into the Projectile class.

The same pattern is used for assigning a new ProjectileSpawner at runtime as the Projectile event classes.
Projectile Factory Actions
New Actions are provided that interact specifically with Projectile Factory.
Projectile Spawner Actions
These actions are specific to the ProjectileSpawner class. By default they target the ProjectileSpawner on the Target object, but you can specify one or more ProjectileSpawner components, and choose to target all, a random one, or sequentially β iterated each time the action is looped or executed again.
Change Projectile Action
ChangeProjectileAction will change the active Projectile on the ProjectileSpawner. If the Projectile is not already in the spawners list, it will be added.
Launch Projectile Action
This will launch the current projectile, or if you'd like, a new projectile (or one from a List<Projectile>).
Stop Projectile Spawner
Simply stops the ProjectileSpawner that is selected.
Destroy Active Projectiles Action
This will destroy (or pool) all active projectiles that have been spawned by the ProjectileSpawner.
Projectile Actions
These actions are specific to the Projectile class.
Projectile Data to Blackboard
This action will store data about the projectile on the Blackboard, either the global blackboard or the local ActionExecutor blackboard. You can choose to include or exclude specific values such as the GameObject itself, the velocity (Vector3, magnitude & direction), position, rotation, and speed.
The key for each value is based on the UID of the Action, which is visible, and customizable, at the top of the Action in the Inspector. For example, if the UID is "MyProjectile", then the GameObject key would be "MyProjectile_GameObject". You can customize the suffix if you'd like, in which case it would be "MyProjectile_CustomSuffix", etc.
This works great with the Conditionals, as you can then check the values of these data points before executing specific groups of actions.
By default, the blackboard entries will be automatically removed when the projectile is destroyed or disabled.
Projectile Target
SetProjectileTarget will set a new target GameObject on the projectile. Keep in mind you can set the override GameObject via code before executing.
ClearProjectileTarget will remove the current target GameObject from the projectile.
Behavior Management
The ToggleProjectileBehaviorAction will enable or disable (or toggle) a specific behavior. If the behavior is not present on the projectile, it is ignored.
The AddProjectileBehaviorAction and RemoveProjectileBehaviorAction will add or remove specific behavior objects from the selected projectiles.
Observer Mangement
Observers can be added and removed with AddProjectileObserverAction and RemoveProjectileObserverAction.
Collision Maks Handling
Projectile collision masks can be managed with SetProjectileCollisionMaskAction, which sets the exact values, or AddToProjectileCollisionMaskAction and RemoveFromProjectileCollisionMaskAction.
Lifecycle Management
TriggerProjectileColliionAction will immediately trigger the collision at a specific point.
TriggerProjectileDestroyAction will call the Destroy() behavior. ResetProjectileAction will call the Reset() methods, and ReturnProjectileToPoolAction will return the projectile to the Object Pool without calling Destroy().
Last updated