> For the complete documentation index, see [llms.txt](https://docs.cuxial.com/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.cuxial.com/scripts/core/cuxial-interactions/developers.md).

# Exports & events

Public API of Cuxial Interactions: register NPCs, dialogues and shops from your own resources.

Register your own NPCs from any resource, attach a dialogue to a ped you already created, or open a dialogue or a shop directly. Points are registered on the client; the prices of a shop are registered on the server.

## Quick reference

| Side   | Export                             | Returns                            |
| ------ | ---------------------------------- | ---------------------------------- |
| Client | `Register(id, def)`                | `boolean`                          |
| Client | `Update(id, patch)`                | `boolean`                          |
| Client | `Remove(id)`                       | `boolean`                          |
| Client | `Exists(id)`                       | `boolean`                          |
| Client | `GetEntity(id)`                    | `integer` or `nil`                 |
| Client | `Interact(id)`                     | `boolean`                          |
| Client | `ShowDialog(data)`                 | id of the closing button, or `nil` |
| Client | `SwitchDialog(dialogId)`           | `boolean`                          |
| Client | `ShowShop(data)`                   | `boolean` or `nil`                 |
| Client | `Close()`                          | `boolean`                          |
| Client | `IsOpen()`                         | `boolean`                          |
| Server | `RegisterShop(id, items, options)` | `boolean`                          |
| Server | `RemoveShop(id)`                   | `boolean`                          |
| Server | `GetShop(id)`                      | `table` or `nil`                   |

## Full example: an NPC with dialogue and shop

A buyer NPC registered from a resource called `my_resource`. The client registers the point; the server registers what the shop buys and at which price.

{% stepper %}
{% step %}

### Declare the dependency

{% code title="my\_resource/fxmanifest.lua" %}

```lua
dependency 'cuxial_interactions'
```

{% endcode %}
{% endstep %}

{% step %}

### Register the shop on the server

{% code title="my\_resource/server.lua" %}

```lua
local SHOP_ID = 'my_resource:scrap_buyer'

local function registerShop()
    if GetResourceState('cuxial_interactions') ~= 'started' then return end

    exports.cuxial_interactions:RegisterShop(SHOP_ID, {
        { name = 'scrapmetal', price = 12 },
        { name = 'copper', price = 20, label = 'Copper wire' },
    }, {
        coords = vec3(25.7, -1347.3, 29.49),
        distance = 6.0,
        account = 'cash',
    })
end

CreateThread(registerShop)

AddEventHandler('onResourceStart', function(resource)
    if resource == 'cuxial_interactions' then registerShop() end
end)

RegisterNetEvent('my_resource:server:AskForWork', function(args, info)
    local src = source
    -- args and info come from the client: check the player, the distance and the state here.
    print(('player %s asked for work at point %s'):format(src, info.id))
end)
```

{% endcode %}
{% endstep %}

{% step %}

### Register the NPC on the client

{% code title="my\_resource/client.lua" %}

```lua
local POINT_ID = 'my_resource:scrap_buyer'

local function registerNpc()
    if GetResourceState('cuxial_interactions') ~= 'started' then return end

    exports.cuxial_interactions:Register(POINT_ID, {
        coords = vec4(25.7, -1347.3, 29.49, 271.0),
        model = 's_m_y_dealer_01',
        scenario = 'WORLD_HUMAN_STAND_IMPATIENT',
        behavior = { invincible = true, noTemporaryEvents = true, freeze = true },

        label = 'Talk to the buyer',
        targetIcon = 'fas fa-comment-dots',
        activeDistance = 2.5,
        blip = { id = 52, scale = 0.6, colour = 5, name = 'Scrap buyer' },

        -- shop.id defaults to the id of the point, so it matches RegisterShop.
        shop = { name = 'Sam', job = 'Buyer', icon = 'store' },

        dialog = {
            {
                id = 'start',
                name = 'Sam',
                job = 'Buyer',
                icon = 'store',
                text = 'Got anything for me?',
                buttons = {
                    { id = 'sell', label = 'Show what I have', icon = 'hand-coins', shop = true },
                    { id = 'work', label = 'Do you have work?', icon = 'briefcase', nextDialog = 'work' },
                    { id = 'bye', label = 'Not today', icon = 'x', close = true },
                },
            },
            {
                id = 'work',
                name = 'Sam',
                job = 'Buyer',
                text = 'Maybe. Bring me a lockpick and we talk.',
                buttons = {
                    {
                        id = 'accept',
                        label = 'I have one',
                        icon = 'key',
                        item = 'lockpick',
                        close = true,
                        serverEvent = 'my_resource:server:AskForWork',
                        args = { job = 'scrap' },
                    },
                    {
                        id = 'wave',
                        label = 'Say goodbye',
                        icon = 'hand',
                        close = true,
                        onSelect = function(ctx)
                            PlayAmbientSpeech1(ctx.entity, 'GENERIC_BYE', 'SPEECH_PARAMS_FORCE')
                        end,
                    },
                    { id = 'back', label = 'Back', icon = 'undo-2', nextDialog = 'start' },
                },
            },
        },
    })
end

CreateThread(registerNpc)

AddEventHandler('onClientResourceStart', function(resource)
    if resource == 'cuxial_interactions' then registerNpc() end
end)
```

{% endcode %}
{% endstep %}
{% endstepper %}

{% hint style="warning" %}
Restarting `cuxial_interactions` wipes every point and shop registered by other resources. Keep the `onClientResourceStart` and `onResourceStart` handlers of the example so yours are registered again.
{% endhint %}

## Ownership and cleanup

* Every point and shop belongs to the resource that registered it.
* Registering an id you already own replaces it. An id owned by another resource is rejected with a console warning.
* Only the owner can update or remove a point or a shop.
* When a resource stops, its points are removed, its open dialogue is closed and its shops are deleted.
* Ids are shared by the whole server. Prefix them with the name of your resource: `'my_resource:scrap_buyer'`.

## Client exports

### Register

Registers a point: an NPC, or a spot without a ped, that opens a dialogue or a shop.

```lua
exports.cuxial_interactions:Register(id, def)
```

| Parameter | Type   | Description                                                         |
| --------- | ------ | ------------------------------------------------------------------- |
| `id`      | string | Unique id of the point. Not empty.                                  |
| `def`     | table  | Definition of the point. See [Point definition](#point-definition). |

**Returns:** `boolean`. `false` when `id` or `def` is not valid, when the id belongs to another resource, when `def.enabled == false`, or when `def` has none of `coords`, `entity` and `netId`.

```lua
-- Attach a dialogue to a ped your resource already created.
exports.cuxial_interactions:Register('my_resource:doctor', {
    entity = doctorPed,
    label = 'Talk',
    dialog = {
        {
            id = 'start',
            name = 'Dr. Lee',
            text = 'How can I help?',
            buttons = { { id = 'bye', label = 'Nothing, thanks', close = true } },
        },
    },
})
```

### Update

Merges `patch` into the definition of a point you own and rebuilds it.

```lua
exports.cuxial_interactions:Update(id, patch)
```

| Parameter | Type   | Description                                                                                                      |
| --------- | ------ | ---------------------------------------------------------------------------------------------------------------- |
| `id`      | string | Id of the point.                                                                                                 |
| `patch`   | table  | Fields to replace. Only the first level is merged: a `dialog` or a `blip` in the patch replaces the whole table. |

**Returns:** `boolean`. `false` when the point does not exist or belongs to another resource.

```lua
exports.cuxial_interactions:Update('my_resource:scrap_buyer', { label = 'Closed for today', dialog = closedDialog })
```

{% hint style="info" %}
`Update` cannot delete a field, because a `nil` value does not travel in the patch. Call `Register` again with the full definition instead.
{% endhint %}

### Remove

Removes a point you own: its ped, its blip and its target option. If its dialogue is open, it closes.

```lua
exports.cuxial_interactions:Remove(id)
```

**Returns:** `boolean`. `false` when the point does not exist or belongs to another resource.

```lua
exports.cuxial_interactions:Remove('my_resource:scrap_buyer')
```

### Exists

Tells whether a point is registered, whoever owns it.

```lua
local registered = exports.cuxial_interactions:Exists(id)
```

**Returns:** `boolean`.

### GetEntity

Returns the ped of a point.

```lua
local ped = exports.cuxial_interactions:GetEntity(id)
```

**Returns:** `integer` or `nil`. `nil` when the point does not exist, has no ped, or the player is too far and the ped is not created.

```lua
local ped = exports.cuxial_interactions:GetEntity('my_resource:scrap_buyer')
if ped then PlayAmbientSpeech1(ped, 'GENERIC_HI', 'SPEECH_PARAMS_FORCE') end
```

### Interact

Opens a point as if the player had selected it. It applies the same conditions (`job`, `item`, `canInteract`). Use it for points with `interaction = 'none'`, which you open from your own marker, key or menu.

```lua
exports.cuxial_interactions:Interact(id)
```

**Returns:** `boolean`. `false` when the point does not exist, a dialogue or shop is already open, the conditions fail, or the point has no `dialog`, `shop` or `onInteract`.

```lua
if not exports.cuxial_interactions:Interact('my_resource:scrap_buyer') then
    lib.notify({ description = 'He does not want to talk to you.', type = 'error' })
end
```

### ShowDialog

Opens a dialogue that is not tied to a registered point. The call waits until the dialogue closes.

```lua
local result = exports.cuxial_interactions:ShowDialog(data)
```

| Parameter        | Type    | Description                                                       |
| ---------------- | ------- | ----------------------------------------------------------------- |
| `data.dialog`    | table   | List of pages. Required. See [Dialogue page](#dialogue-page).     |
| `data.entity`    | integer | Ped the camera focuses on. Optional.                              |
| `data.shop`      | table   | Shop opened by the buttons with `shop = true`. See [Shop](#shop). |
| `data.extraData` | table   | Your own data, delivered in `ctx.extraData`.                      |
| `data.camera`    | boolean | `false` opens without moving the camera.                          |
| `data.id`        | string  | Id reported in `ctx.id` and in the events. Optional.              |

**Returns:** the `id` of the button with `close = true` that closed the dialogue, or its position when it has no `id`. `nil` when it was closed with <kbd>Esc</kbd> or by `Close()`, when the data is not valid, or at once when something is already open.

```lua
local answer = exports.cuxial_interactions:ShowDialog({
    entity = guardPed,
    dialog = {
        {
            id = 'ask',
            name = 'Guard',
            text = 'This area is closed. Do you want to pay the fee?',
            buttons = {
                { id = 'yes', label = 'Pay', icon = 'dollar-sign', close = true },
                { id = 'no', label = 'Leave', icon = 'x', close = true },
            },
        },
    },
})

if answer == 'yes' then
    TriggerServerEvent('my_resource:server:PayFee')
end
```

{% hint style="info" %}
`ShowDialog` blocks the thread that calls it. Call it inside `CreateThread` or an event handler, never in a loop that runs every frame.
{% endhint %}

### SwitchDialog

Changes the page of the open dialogue.

```lua
exports.cuxial_interactions:SwitchDialog(dialogId)
```

| Parameter  | Type             | Description                          |
| ---------- | ---------------- | ------------------------------------ |
| `dialogId` | string \| number | `id` of a page of the open dialogue. |

**Returns:** `boolean`. `false` when no dialogue is open or the page does not exist or is disabled.

```lua
onSelect = function()
    local hasLicense = lib.callback.await('my_resource:server:HasLicense', false)
    exports.cuxial_interactions:SwitchDialog(hasLicense and 'approved' or 'denied')
end,
```

### ShowShop

Opens a shop. With a dialogue open it switches to the shop and adds a button to go back. With nothing open it opens the shop directly and waits until it closes.

```lua
exports.cuxial_interactions:ShowShop(data)
```

| Parameter | Type  | Description                                                                                              |
| --------- | ----- | -------------------------------------------------------------------------------------------------------- |
| `data`    | table | A shop table, or `{ shop = shopTable, entity = ped, camera = boolean, id = string }`. See [Shop](#shop). |

**Returns:** `boolean` when it switched from an open dialogue. `nil` when it opened directly, once the shop is closed.

```lua
exports.cuxial_interactions:ShowShop({
    entity = buyerPed,
    shop = { id = 'my_resource:scrap_buyer', name = 'Sam', job = 'Buyer' },
})
```

{% hint style="warning" %}
Opened this way, the shop needs its own `id`, and that id must be registered on the server with `RegisterShop`. Otherwise it is shown as unavailable.
{% endhint %}

### Close

Closes the dialogue or the shop that is open.

```lua
exports.cuxial_interactions:Close()
```

**Returns:** `boolean`. `false` when nothing was open.

### IsOpen

Tells whether a dialogue or a shop is open.

```lua
local open = exports.cuxial_interactions:IsOpen()
```

**Returns:** `boolean`.

```lua
if exports.cuxial_interactions:IsOpen() then return end
```

{% hint style="info" %}
The same value is in `LocalPlayer.state.isDialogOpen`. It is local to the player's client and is not sent to the server.
{% endhint %}

### Compatibility aliases

Older lowercase names are kept so existing code keeps working. Use the names above in new code.

| Alias                           | Equivalent                                                 |
| ------------------------------- | ---------------------------------------------------------- |
| `showDialog(data)`              | `ShowDialog(data)`. Also accepts `data.ped` as the entity. |
| `switchDialog(id)`              | `SwitchDialog(id)`                                         |
| `showShop(shop)`                | Switches to the shop from an open dialogue.                |
| `showShopDirect({ ped, shop })` | Opens the shop directly.                                   |

## Server exports

### RegisterShop

Registers what a shop buys and at which price. The server only accepts sales to registered shops, and it always pays the price registered here.

```lua
exports.cuxial_interactions:RegisterShop(id, items, options)
```

| Parameter          | Type                        | Description                                                                                                                                                                                                          |
| ------------------ | --------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `id`               | string                      | Id of the shop. The same as `shop.id` on the client; for a point registered with `Register`, the id of the point unless you set another.                                                                             |
| `items`            | table                       | List of `{ name, price, label, image }`. `name` is the item name and `price` a number from 0 up; both are required. `label` defaults to the label of the inventory. `image` is a URL. A repeated item is taken once. |
| `options.coords`   | vector3 \| vector4 \| table | Position of the shop, or a list of positions.                                                                                                                                                                        |
| `options.netId`    | integer                     | Network id of a networked ped; the distance is measured to it.                                                                                                                                                       |
| `options.anywhere` | boolean                     | `true` accepts sales from any distance.                                                                                                                                                                              |
| `options.distance` | number                      | Maximum metres to `coords` or to the ped. Defaults to `shop.maxDistance` of the config.                                                                                                                              |
| `options.account`  | string                      | Account the sale is paid into. Defaults to `shop.account` of the config.                                                                                                                                             |

One of `coords`, `netId` or `anywhere = true` is required.

**Returns:** `boolean`. `false` when the id is not valid or belongs to another resource, when the list is empty or any item lacks a name or a valid price, or when no location is given.

```lua
exports.cuxial_interactions:RegisterShop('my_resource:scrap_buyer', {
    { name = 'scrapmetal', price = 12 },
}, { coords = vec3(25.7, -1347.3, 29.49) })
```

What the server checks on every sale, in this order:

1. The shop is registered and buys that item.
2. The quantity is a whole number between 1 and `shop.maxQuantity`.
3. The player waited `shop.cooldown` since their last sale.
4. The player is within the distance of the shop.
5. The player carries the units.

Then it removes the items and pays `price × quantity`, rounded to a whole number. If the payment fails the items are returned.

{% hint style="info" %}
Once the shop is registered, the player sees the list and the prices of the server. The `items` of the client shop table are only shown when the shop is not registered, and then nothing can be sold.
{% endhint %}

### RemoveShop

Removes a shop you own.

```lua
exports.cuxial_interactions:RemoveShop(id)
```

**Returns:** `boolean`. `false` when the shop does not exist or belongs to another resource.

### GetShop

Returns a registered shop.

```lua
local shop = exports.cuxial_interactions:GetShop(id)
```

**Returns:** `{ id, account, items }` or `nil`. Each item has `name`, `label`, `price` and `image`.

```lua
local shop = exports.cuxial_interactions:GetShop('my_resource:scrap_buyer')
if shop then
    for _, item in ipairs(shop.items) do
        print(item.name, item.price)
    end
end
```

## Data reference

### Point definition

The table passed to `Register`, and the value of each NPC in a `data/` file.

**Where.** One of the three is required.

| Field    | Type               | Description                                                                                                                                                    |
| -------- | ------------------ | -------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `coords` | vector3 \| vector4 | Position of the point. With `model` or `usePlayerSkin` a ped is created there; without them it is a spot without a ped. The `w` of a `vector4` is the heading. |
| `entity` | integer            | A ped or object that already exists on this client. It is not created or deleted by the point.                                                                 |
| `netId`  | integer            | The same, by network id. The point attaches when the entity comes into range.                                                                                  |

**Ped.** Only for points with `coords` that create their own ped.

| Field           | Type             | Description                                                                                                            |
| --------------- | ---------------- | ---------------------------------------------------------------------------------------------------------------------- |
| `model`         | string \| number | Ped model. If it does not exist, `npc.fallbackModel` is used.                                                          |
| `usePlayerSkin` | boolean          | `true` gives the ped the look of a random active character. Falls back to `model` when no look is available.           |
| `heading`       | number           | Heading, when `coords` is a `vector3`.                                                                                 |
| `scenario`      | string           | Scenario the ped plays, such as `'WORLD_HUMAN_CLIPBOARD'`.                                                             |
| `animation`     | table            | `{ dict, clip, speed, blendOut, duration, flag }`. `dict` and `clip` are required. Defaults: `8.0`, `-8.0`, `-1`, `1`. |
| `clothing`      | table            | List of `{ componentIndex, variation, texture }`. Not applied when the ped got a player look.                          |
| `behavior`      | table            | `{ invincible, noTemporaryEvents, freeze }`, each a boolean.                                                           |
| `spawnDistance` | number           | Metres at which the ped is created. Defaults to `npc.spawnDistance`.                                                   |

**Interaction.**

| Field            | Type    | Description                                                                                                                                                                                       |
| ---------------- | ------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `label`          | string  | Text of the target option. Defaults to "Talk".                                                                                                                                                    |
| `targetIcon`     | string  | Font Awesome class of the target option. Defaults to `target.icon`.                                                                                                                               |
| `activeDistance` | number  | Metres from which the player can interact. Defaults to `target.distance`.                                                                                                                         |
| `interaction`    | string  | `'target'`, `'sprite'` or `'none'`. Defaults to `interaction` of the config.                                                                                                                      |
| `camera`         | boolean | `false` opens without moving the camera.                                                                                                                                                          |
| `blip`           | table   | `{ id, scale, colour, name }`. `id` is the blip sprite. Defaults: scale `0.6`, colour `0`. Needs `coords`. The blip is created when the point is registered, whatever the distance to the player. |

**Conditions.** All of them must pass for the option to appear.

| Field         | Type            | Description                                                                           |
| ------------- | --------------- | ------------------------------------------------------------------------------------- |
| `job`         | string \| table | `'police'`, `{ 'police', 'ambulance' }` (any), or `{ police = 2 }` (minimum grade).   |
| `item`        | string \| table | `'lockpick'`, `{ 'lockpick', 'phone' }` (all), or `{ lockpick = 3 }` (minimum units). |
| `canInteract` | function        | `function(ctx)`. Must return `true`.                                                  |
| `enabled`     | boolean         | `false` leaves the point unregistered.                                                |

**Content.**

| Field        | Type     | Description                                                                                                                 |
| ------------ | -------- | --------------------------------------------------------------------------------------------------------------------------- |
| `dialog`     | table    | List of pages. The first enabled page is the one shown.                                                                     |
| `shop`       | table    | Shop of the point. Without `dialog` the point opens the shop directly; with `dialog`, a button with `shop = true` opens it. |
| `onInteract` | function | `function(ctx)`. Runs instead of opening the dialogue or the shop.                                                          |
| `extraData`  | table    | Your own data, delivered in `ctx.extraData`.                                                                                |

### Dialogue page

| Field       | Type             | Description                                                          |
| ----------- | ---------------- | -------------------------------------------------------------------- |
| `id`        | string \| number | Unique within the dialogue. Used by `nextDialog` and `SwitchDialog`. |
| `name`      | string           | Who speaks.                                                          |
| `job`       | string           | Role shown in the header. Text only, not a condition.                |
| `text`      | string           | What the NPC says.                                                   |
| `textSpeed` | number           | Milliseconds per character. Defaults to `dialog.textSpeed`.          |
| `icon`      | string           | Icon of the header. See [Icons](#icons).                             |
| `enabled`   | boolean          | `false` skips the page.                                              |
| `buttons`   | table            | List of buttons.                                                     |

### Dialogue button

| Field                        | Type             | Description                                                                                      |
| ---------------------------- | ---------------- | ------------------------------------------------------------------------------------------------ |
| `id`                         | string \| number | Id of the button. It is what `ShowDialog` returns when the button closes.                        |
| `label`                      | string           | Text of the button.                                                                              |
| `icon`                       | string           | Icon of the button. See [Icons](#icons).                                                         |
| `enabled`                    | boolean          | `false` hides the button.                                                                        |
| `job`, `item`, `canInteract` |                  | Conditions, as in the point. A button that fails is not sent to the interface and cannot be run. |
| `close`                      | boolean          | Closes the dialogue.                                                                             |
| `onSelect`                   | function         | `function(ctx)`.                                                                                 |
| `event`                      | string           | Client event: `TriggerEvent(event, args, info)`.                                                 |
| `serverEvent`                | string           | Server event: `TriggerServerEvent(serverEvent, args, info)`.                                     |
| `args`                       | any              | Value sent as the first argument of `event` and `serverEvent`.                                   |
| `shop`                       | boolean          | Opens the shop of the point.                                                                     |
| `nextDialog`                 | string \| number | `id` of the page to show next.                                                                   |

A button runs its actions in this order: `close`, `onSelect`, `event`, `serverEvent`, and then `shop` or `nextDialog`. With `close = true` the last step is skipped. `shop` wins over `nextDialog`.

### Shop

| Field   | Type   | Description                                                                                                                                                                                    |
| ------- | ------ | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `id`    | string | Id registered with `RegisterShop`. In a point it defaults to the id of the point.                                                                                                              |
| `name`  | string | Name of the buyer. Defaults to "Seller".                                                                                                                                                       |
| `job`   | string | Role shown in the header. Defaults to "Merchant".                                                                                                                                              |
| `icon`  | string | Icon of the header. See [Icons](#icons).                                                                                                                                                       |
| `items` | table  | List of `{ name, label, price, image }`. Required in `data/` files, where it is also the list registered on the server. From another resource it is optional: the server list is the one used. |

### The `ctx` table

Received by `onSelect`, `canInteract` and `onInteract`.

| Field       | Type             | Description                                                                      |
| ----------- | ---------------- | -------------------------------------------------------------------------------- |
| `id`        | string           | Id of the point. `nil` in a dialogue opened with `ShowDialog` without `data.id`. |
| `entity`    | integer          | Ped of the point, if any. `ctx.ped` holds the same value.                        |
| `dialogId`  | string \| number | `id` of the current page. Only in buttons.                                       |
| `buttonId`  | string \| number | `id` of the button. Only in buttons.                                             |
| `index`     | integer          | Position of the button in the page. Only in buttons.                             |
| `extraData` | table            | The `extraData` of the point or of `ShowDialog`.                                 |

### The `info` table

Second argument of `event` and `serverEvent`.

| Field      | Type             | Description                                                                                                 |
| ---------- | ---------------- | ----------------------------------------------------------------------------------------------------------- |
| `id`       | string           | Id of the point.                                                                                            |
| `dialogId` | string \| number | `id` of the page.                                                                                           |
| `buttonId` | string \| number | `id` of the button.                                                                                         |
| `entity`   | integer          | Ped handle on the client that sent it.                                                                      |
| `netId`    | integer          | Network id of the ped. Only when the ped is networked; the peds created by a point are local and have none. |

{% hint style="danger" %}
A server event can be triggered by any client at any time. In its handler, check the player (`source`), the distance to the NPC and whatever the action requires. Never trust `args` or `info`.
{% endhint %}

### Functions sent through exports

`onSelect`, `canInteract` and `onInteract` are functions of your resource called from Cuxial Interactions. Keep in mind:

* `canInteract` of a point is evaluated while the player aims at it, with the result reused for `dialog.conditionInterval` milliseconds, and once more on selection. Keep it cheap.
* An error inside any of them does not break the dialogue. It leaves a warning in the client console.
* Do not keep `ctx` after the call returns.
* When an event is enough, prefer `event` or `serverEvent`: they do not depend on function references.

### Icons

`targetIcon` takes a Font Awesome class, because it is drawn by your target resource.

The `icon` of pages, buttons and shops takes one of these names:

`arrow-left`, `arrow-right`, `bed`, `book`, `book-open`, `briefcase`, `car`, `check`, `circle-alert`, `circle-check`, `circle-play`, `circle-question-mark`, `circle-x`, `clipboard`, `clipboard-plus`, `dollar-sign`, `door-open`, `fish`, `folder-open`, `gamepad-2`, `hand`, `hand-coins`, `hand-heart`, `heart`, `hospital`, `house`, `id-card`, `info`, `key`, `log-out`, `message-circle`, `message-circle-more`, `messages-square`, `package`, `phone`, `pill`, `shield`, `shopping-cart`, `skull`, `stethoscope`, `store`, `thumbs-up`, `undo-2`, `user`, `user-pen`, `venetian-mask`, `wrench`, `x`.

Any other name shows a speech bubble. In the header of a shop it shows a store.

## Events

Cuxial Interactions has no events of its own for other resources. Use the `event` and `serverEvent` fields of a button to receive your own.


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

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

Perform an HTTP GET request on the following URL with the `ask` and `goal` query parameters:

```
GET https://docs.cuxial.com/scripts/core/cuxial-interactions/developers.md?ask=<question>&goal=<user_goal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is what the user is ultimately trying to achieve, the reason they need the answer. Sharing it helps GitBook give you a better, more relevant answer. A goal is most helpful when it describes the outcome the user wants rather than restating the question. For example, with `ask=how do I create an API token`, a goal like `automate deployments from our CI pipeline` lets GitBook tailor the answer to that use case.

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.
