---
description: v1.0
---

# Observers, Global Observers, and Observer Objects

Observers are passive watchers of lifecycle events, and can act depending on what they see. [**Observer Objects**](#observer-object-example) are `Monobehaviours` which can watch a Projectile.

## Observer Scriptable Object

The `Observer` class derives from `ProjectileBehavior`, as do all of the other [**Behavior**](behaviors) classes, giving it access to lifecycle events on Projectiles. While behaviors aim to act upon the Projectile itself, an Observer is intended to act upon something external to the Projectile.

The _Demo Actor Observer_ in the demo scene is used to recognize when a projetile fired by the "Player" `Actor` collides with a "Target" `Actor` in order to compute and transfer damage to the target.

The _Turn Off On Collision Observer_ is used to turn off a `GameObject` whenever a specific Projectile collides with something.

{% hint style="info" %}
Observers are a great way to hook into the Projectile Factory system, and connect your game to the lifecycle events. This means you'll likely want to create your own Observers. Check out the [**Create Custom Behaviors**](create-custom-behaviors) page for more details on how (easy it is) to create custom behaviors and observers.
{% endhint %}

There are two ways to attach an Observer `ScriptableObject` to a `Projectile`.

### Attach via the ProjectileSpawner

The [**Projectile Spawner**](projectile-spawner) has an Observers `List<Observer>`. Each Projectile that is created by this Spawner will be given an instance of each Observer in the list. This is how the _Demo Actor Observer_ is added to all Projectiles the player spawns.

## Global Observer

A **Global Observer** is an object that intends to be interested in Projectiles spawned by more than just one `ProjectileSpawner`. In the demo scenes, the `Camera` has a `GlobalObserver` class on it, which shakes the camera anytime a projectile collides.

**Global Observers** subscribe to the [**Factory Manager**](factory-manager), which repeats events from the Projectiles registered to it.

## Observer Example

The **Projectile Spawner** also has one **Observer** assigned to the `Observers` list.

<figure><img src="https://2431624982-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2F-MY3N_li2jPq7az6mYfq%2Fuploads%2FXw5HVGBacJmfMVBeOay3%2FScreenshot%202024-03-30%20at%2011.40.54%E2%80%AFPM.png?alt=media&#x26;token=881d70e1-4f4d-4a1e-9cb3-bd4158bff77d" alt=""><figcaption></figcaption></figure>

<figure><img src="https://2431624982-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2F-MY3N_li2jPq7az6mYfq%2Fuploads%2FrxgVREEIrxw1ooLJmZjw%2FScreenshot%202024-03-30%20at%2011.42.18%E2%80%AFPM.png?alt=media&#x26;token=3238ba84-8b59-4abf-bce9-9112e97db989" alt=""><figcaption></figcaption></figure>

This observer has no exposed parameters. As an `ProjectileObserver`, it automatically subscribes to all lifecycle events on each Projectile spawned -- this class inherits from `ProjectileBehavior`, as do all of the [**Behaviors**](behaviors).

Whenever `CollisionEnter` or `TriggerEnter` is called by a Projectile, the `HitObject` method on this observer is called. If the `HitObject` has a `ProjectileDemoActor` component, then the `Actor` who spawned the projectile will run the `RegisterHit` method, which computes damage and passes it to the hit `Actor`.&#x20;

{% hint style="info" %}
This **Projectile Observer** is a demo class, intended to showcase one way of connecting your project to the **Projectile Factory** events. Each project is unique, and you can choose for yourself the most efficient way to get the information you need to process data for your game.
{% endhint %}

## Global Observer Example

The [**Factory Manager**](factory-manager) exists in all scenes, as it is a `Static Scriptable Object`. This manager maintains a `List` of all `ProjectileSpawner` and `Projectile` objects in the scene, along with [**global observers**](observers-global-observers-and-observer-objects), which are `ProjectileObserver` objects.

In the demo scene, the `Camera` has a `CameraShakeOnProjectileCollision` component on it. This class inherits from `GlobalObserver`. This means it automatically subscribes to the `FactoryManager` lifecycle events.

The class overrides the `CollisionEnter` method, which is called whenever ANY projectile that is registered with the `FactoryManager` collides.

```csharp
protected override void CollisionEnter(Projectile basicProjectile, Collision collision, GameObject objectHit = null, Vector3 contactPoint = default)
{
     var valueOnCurve = DistanceValueOnCurve(contactPoint);
     ShakeCamera(shakeDuration * valueOnCurve, shakeMagnitude * valueOnCurve, shakeFrequency * valueOnCurve);
}
```

Whenever this occurs, the method will shake the camera, with the shake impact determined by the distance the collision is from the camera itself.

## Observer Object Example

**Observer Objects** are `MonoBehaviours` which connect to an external **Projectile**, and have access to all the lifecycle events on that **Projectile**. Each one will derive from `ObserverObject`.

<figure><img src="https://2431624982-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2F-MY3N_li2jPq7az6mYfq%2Fuploads%2F3ysMw6DVl65WRVn8CP5t%2FScreenshot%202024-04-09%20at%205.34.43%E2%80%AFPM.png?alt=media&#x26;token=8584d8eb-211b-4831-849c-c251ad827a2f" alt=""><figcaption></figcaption></figure>

In the example above, the [**`ToggleObjectAtEventsObserverObject`**](observers-global-observers-and-observer-objects/toggle-objects-at-events-observer-object) will turn the list of objects on and off at the defined events.

{% hint style="success" %}
I prefer to include "ObserverObject" in the class name. It's easier to find, and more clear what kind of class it is.
{% endhint %}

## Spawner Observer Object Example

**Spawner Observer Objects** are `MonoBehaviours` which connect to a `ProjectileSpawner`, and have access to all the lifecycle events on that spawner. Each one will derive from `SpawnerObserverObject`.

<figure><img src="https://2431624982-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2F-MY3N_li2jPq7az6mYfq%2Fuploads%2FAQ3jC89EFup3Feb8z3HM%2FScreenshot%202024-04-14%20at%205.28.14%E2%80%AFPM.png?alt=media&#x26;token=f2ca4690-cc47-419f-af0d-17b170624134" alt=""><figcaption></figcaption></figure>

The SpawnOnSpawnPointsSpawnerObserverObject will spawn objects onto one or all of the Spawn Points at the events you select. In the example above, the objects will be spawned when the projecitles start shooting, and will be destroyed when they stop shooting. We use it in one of the Integraitons to show a "charging" particle, along with a Projectile that has a 0.5 second delay.

<figure><img src="https://2431624982-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2F-MY3N_li2jPq7az6mYfq%2Fuploads%2FPGOEQUjPnksTxsq2KE9l%2FScreen%20Recording%202024-04-14%20at%205.25.22%E2%80%AFPM.gif?alt=media&#x26;token=6f7fa3e5-7a58-46f5-9690-c08dbc50d7a9" alt=""><figcaption></figcaption></figure>
