# Camera Dampers

V0.2.2 refactored the damping representation in this plugin. Before V0.2.2, all damping methods and their implementations are encapsulated in a single struct. V0.2.2 abstracts the damper representation so that each damper is relatively independent. This provides more flexibility and extensibility.&#x20;

## Using Pre-defined Dampers

Some components have already contained pre-defined dampers. For example, the ScreenFollow component contains an aggregate damper comprising three sub-dampers. Each sub-damper is responsible for damping a particular axis of current camera's positional movement.

<figure><img src="/files/2gqyDRiENIoVS3P3un81" alt=""><figcaption></figcaption></figure>

You can choose any of the pre-defined sub-damper to meet your needs. The default sub-damper is NaiveDamper. This is also the damper you're supposed to use for most of the time. It's simple and effecient, and generally lead to nice damping effects.

## Details of Pre-defined Dampers

There are six pre-defined dampers as shown below. The `Continuous Naive Damper,` `Lowpass Naive Damper`, `Restrict Naive Damper` and `Simulate Damper` are used to solve the camera jittering problem when the game's frames per second (FPS) is unstable. For most cases you should use the `Naive Damper` and for specific gameplay, you can use the `Spring Damper`.

<figure><img src="/files/c0H3uz2POGFoZySrcLnc" alt=""><figcaption></figcaption></figure>

* Naive Damper: Uses a simple residual-based damping algorithm. This is the damper you should choose for most of the time.
  * Damp Time: amount of time to finish damping.
  * Residual: damp residual after damp time (in percent).
* Simulate Damper: Splits the given deltaTime into multiple segments and simulates naive damping in order.
  * Damp Time: amount of time to finish damping.
  * Residual: damp residual after damp time (in percent).
  * Simulate Count: Number of simulations per damping.
* Continuous Naive Damper: Continuous optimization when FPS is unstable. [Reference](https://sulley.cc/2023/07/08/18/22/#solution-3-continuous-residual).
  * Damp Time: amount of time to finish damping.
  * Residual: damp residual after damp time (in percent).
  * Order: Orders of derivative you want to use for approximation. Larger means more accurate.
* Restrict Naive Damper: Restrict damp velocity when FPS in unstable. [Reference](https://sulley.cc/2023/07/08/18/22/#solution-1-imposing-an-invalid-range).
  * Damp Time: amount of time to finish damping.
  * Residual: damp residual after damp time (in percent).
  * Tolerance: Tolerance of restriction range.
  * Power: Controls how aggresively to compact the curve.
* Lowpass Naive Damper: Low-pass filtering optimization when FPS in unstable. [Reference](https://sulley.cc/2023/07/08/18/22/#solution-2-adding-low-pass-filter).
  * Damp Time: amount of time to finish damping.
  * Residual: damp residual after damp time (in percent).
  * Tolerance: Tolerance of restriction range.
  * Beta: Smaller means smoother.
* Spring Damper: Uses spring to damp. [Reference](https://sulley.cc/2024/06/18/20/06/).
  * Frequency: Controls the frequency of oscillation and the speed of decay.
  * Damp Ratio: Controls whether the spring is undamped (=0), underdamped (<1), critically damped (=1), or overdamped (>1).

## Customizing A Damper

A damper typically receives a single input value, damps it and returns the output damped value. There're six built-in dampers and you can customize your own damper.

1. Create a new blueprint class inheriting `ECameraDamper`.
2. Implement the `ApplyDamp` function and the `PostApplyDamp` function.\
   In the following figure, I create my custom damper `MyDamper`, and create two variables `DampTime` and `OtherParameters`. The `ApplyDamp` implements a simple linear damping algorithm and the `PostApplyDamp` is used to update any internal parameter.<br>

   <figure><img src="/files/egHfSWJ4dhT5RBmCTdXE" alt=""><figcaption></figcaption></figure>
3. Select `MyDamper` at wherever you would like to use your damper.<br>

   <figure><img src="/files/OFycLFaXUA4jdICOBR6k" alt=""><figcaption></figcaption></figure>
4. Play and see if it works correctly.<br>

   <figure><img src="/files/tdfucS1IslUicNVW950b" alt=""><figcaption></figcaption></figure>

## Customizing An Aggregate Damper

### Using Aggregate Damper for A Custom Component

An aggregate damper is a damper consisting of multiple sub-dampers, like the `ECamera Vector Damper` in ScreenFollow. It's highly related to the function and purpose of the component it resides in. For example, an `ECamera Vector Damper` aggregate damper is used for any Vector-like data, and an `ECamera Rotator Damper`, as in TargetingAim, is used for any Rotation-like data. That's to say, if you have a Vector2d data, you may prefer a `ECamera Pair Damper` aggregate damper.

To create your own `MyPairDamper` aggregate damper, create a new blueprint class inheriting `ECamera Aggregate Damper`, and create two variables of type `ECamera Damper`, designate their default damper types and parameters. That's it.

<figure><img src="/files/udtQlyEPO4HTyB4uOUQT" alt=""><figcaption></figcaption></figure>

It should be emphasized again that your new aggregate damper **can only be used in conjunction with your own customized components**. There is no place in the built-in components where you can use your aggregate damper.

For example, in the following customized follow component `MyFollowComponent`,  I add a variable `Damper` of type `MyPairDamper`, the one we just created. Then in the Class Defaults Details panel, select `My Pair Damper`.&#x20;

<figure><img src="/files/46wgKcVTG0f86a5MDUNK" alt=""><figcaption></figcaption></figure>

When you use this component, the default value for `Damper` will be `My Pair Damper`.

<figure><img src="/files/8gosm2iFmrGaYsaxZTnu" alt=""><figcaption></figcaption></figure>

So how do you update this custom damper inside your component? Two steps.

The first step is to define several update functions in your damper. In the example of `MyPairDamper`, you can define four functions:

* SetInput：Take a Vector2D data as input and feed the X/Y component to Damper X/Y. The input will be damped by a damper.
* SetOutput: Take a Vector2D data as input and feed the X/Y component to Damper X/Y. This is an interface to allow external modifications on the output derived by a damper. The modified output is then propagated into the damper internally.
* ApplyDamp: Each damper applies damping.
* PostApplyDamp: An interface allowing each damper to update its internal parameters. For example, the `Spring Damper` has velocity as its internal mutable parameter and is updated each frame.

<figure><img src="/files/0atlsNYfjwj1rZ08sPZj" alt=""><figcaption></figcaption></figure>

A typical workflow of an aggregate damper is to sequentially call SetInput->ApplyDamp->SetOutput (Optional)->PostApplyDamp.

In the following example of `MyFollowComponent`, you can see how the `Damper` processes the `Position` variable.

<figure><img src="/files/97bJsw4yvnsYxoTi0Mr1" alt=""><figcaption></figcaption></figure>

### Using Aggregate Damper As Template

You can also comprehen an aggregate damper as a template. For example, in some cases you may want all the three sub-dampers in `ECamera Damper Vector` to be `Spring Damper`, and in other cases, you want the `Damper X` to be `Spring Damper` and `Damper Y/Z` to be `Naive Damper`. To this end, you can inherit `ECamera Damper Vector` and specify the concrete type for each sub-damper. Then, in the component, say ScreenFollow, you can directly use your customized version of `ECamera Damper Vector`  without specifying the type of each sub-damper.

As an example, I create my own aggregate damper named `MyDamperVector` inheriting from `ECamera Damper Vector`  and have all sub-dampers be `Spring Damper`.

<figure><img src="/files/WoKjZFXfC3mdW3JcFwD1" alt=""><figcaption></figcaption></figure>

In the ScreenFollow component, all I need to do is choose `My Damper Vector`. This will save much time tuning the types and parameters of sub-dampers for each component of each camera by customizing some commonly-used damper templates.

<figure><img src="/files/vHIfpWKDsi9kYRkDc0xn" alt=""><figcaption></figcaption></figure>


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://sulleyyys-organization.gitbook.io/manuals-of-ccs/advanced-uses/camera-dampers.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
