> For the complete documentation index, see [llms.txt](https://docs.twgamesdev.com/uhfps/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.twgamesdev.com/uhfps/guides/dynamic-objects.md).

# Dynamic Objects

### Adding New Dynamic Objects

1. To make an object dynamic (such as a door, drawer, lever, or valve), add a **Dynamic Object** component to the object.

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

2. Select the object dynamic type by clicking on the icons located at the top of the component.
3. Choose the **Interact Type** for the dynamic object, which can be either **Dynamic**, **Mouse**, or **Animation** type. Once you've selected the **Interact Type**, the **References** section will change, requiring you to assign all the necessary references to ensure the dynamic object works properly.

{% hint style="info" %}
The **Target** field refers to the object where all interactions will be applied. This can either be the current object where the **Dynamic Object** component is added or a parent object.
{% endhint %}

### Dynamic Door

{% hint style="danger" %}
Make sure that the **Pivot Mode** is set to **Pivot** and **Pivot Rotation** to **Local**. If this will be set incorrectly, a prompt will appear.
{% endhint %}

1. To configure a dynamic door, begin by setting the Open Limits, Hinge, and Forward Axis.

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

{% hint style="info" %}
By using curves, you can specify the speed change when opening or closing the dynamic object. The curve should be defined between 0 to 1 values.
{% endhint %}

2. **Open Limits** is actually an angle how the door should open. Rotate the door to its open position, note the hinge value, and update the **Open Limits -> Max** limit accordingly.

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

3. Rotate the door back to the closed position. Adjust the **Target Hinge** (the axis where the door pivots) and **Target Forward** (the axis along which the door mesh extends).

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

{% hint style="success" %}
Make sure you have gizmos enabled, it will help you set up the dynamic object correctly.
{% endhint %}

{% hint style="success" %}
In certain situations, if a door or custom openable model has a different pivot rotation, you can use axis mirroring to maintain positive axes. For instance, if an axis is set to X, toggling the mirror option will switch it to X\_Negative, and vice versa.&#x20;

The same principle applies to the **Starting Angle**, if the open position is reversed (e.g., -90 is open and 0 is closed), enabling mirroring will invert that angle as well.
{% endhint %}

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

### Dynamic Drawer

If you select the **Drawer** dynamic type, you can determine the min/max open limits by copying the position from the corresponding axis, as demonstrated in the image below.

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

{% hint style="warning" %}
The process of configuring a switchable or rotatable dynamic type is similar to the previous steps.
{% endhint %}

### Setting Unlock Dynamic Script&#x20;

To use a custom unlock dynamic script, create a script that implements the **IDynamicUnlock** interface. By doing so, you will be prompted to implement the <mark style="color:blue;">**OnTryUnlock()**</mark> method, which will be called when you interact with the locked dynamic object. Here is a code snippet for a simple dynamic unlock script:

```csharp
using UnityEngine;
using UHFPS.Runtime;

public class TestUnlock : MonoBehaviour, IDynamicUnlock, IInventorySelector
{
    public ItemGuid UnlockItem;
    private DynamicObject dynamicObject;

    public void OnTryUnlock(DynamicObject dynamicObject)
    {
        Inventory.Instance.OpenItemSelector(this);
        this.dynamicObject = dynamicObject;
    }

    public void OnInventoryItemSelect(Inventory inventory, InventoryItem selectedItem)
    {
        if (selectedItem.ItemGuid != UnlockItem)
            return;

        // unlock dynamic object
        dynamicObject.TryUnlockResult(true);
    }
}
```

{% hint style="info" %}
If you interact with the locked dynamic object using this code, you will be prompted to use an item from your inventory. When you choose the item, **OnInventoryItemSelect()** will be triggered, which will unlock the dynamic object if the item is correct.
{% endhint %}

To use the dynamic unlock script, simply assign the reference to the script that implements **IDynamicUnlock** interface in the **Unlock Script** field.

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

{% hint style="info" %}
A good example of using a custom unlock script is the lockpicking puzzle.
{% endhint %}
