# CodeRanch - UI System

Lightweight and modern UI helpers for RedM resources: show in-game toast notifications and run a cancellable progress bar with optional animations and props.

## Features

* Simple, fast, modern notifications (success, info, warning, error)
* Configurable progress bar with text and timeout
* ESC cancel support (key configurable in `config.lua`)
* Optional animation and prop handling while progress is active
* Built-in NUI preview/editor command (`/ui`)

## Requirements

* RedM (cerulean)

## Installation

{% stepper %}
{% step %}

### Place the resource

Put the resource in your server resources:

* `resources/[coderanch]/coderanch-ui`
  {% endstep %}

{% step %}

### Add to server.cfg

Add the following to your `server.cfg`:

```
ensure coderanch-ui
```

{% endstep %}

{% step %}

### (Optional) Adjust keys

Edit `config.lua` as needed:

* `Config.UICommand = 'ui'` (NUI preview/editor command)
* `Config.escapeKey = 0x24978A28` (ESC key hash for cancel)
  {% endstep %}
  {% endstepper %}

## Exports

From `fxmanifest.lua`:

```lua
exports {
    'startProgress',
    'SendNotification',
}
```

* Notification:
  * `exports['coderanch-ui']:SendNotification(type, message, timeout)`
* Progress Bar:
  * `exports['coderanch-ui']:startProgress(action, onProcessStart, onProcessTick, onProcessComplete, onProcessCancel)`

Additionally, there is an event for notifications:

* `TriggerEvent('coderanch-ui:createNotification', type, message, timeout)`

***

## Usage — Notifications

Signature:

```lua
SendNotification(type, message, timeout)
```

Parameters:

* `type`: one of `"success" | "info" | "warning" | "error"` (default: `"info"`)
* `message`: string (default: `"No message provided"`)
* `timeout`: number in ms (default: `5000`)

Examples:

```lua
-- Basic success toast
exports['coderanch-ui']:SendNotification('success', 'Operation completed!', 3000)

-- Warning
exports['coderanch-ui']:SendNotification('warning', 'Be careful!', 5000)

-- Error via event
TriggerEvent('coderanch-ui:createNotification', 'error', 'Something went wrong!', 4000)
```

***

## Usage — Progress Bar

Signature:

```lua
startProgress(action, onProcessStart, onProcessTick, onProcessComplete, onProcessCancel)
```

Action table fields:

* `text` (string): Text displayed on the bar
* `timeout` (number): Duration in ms
* `useWhileDead` (boolean): Allow when player is dead
* `cancelable` (boolean): Allow cancel with ESC
* `disablemovement` (boolean): Intended movement restriction (client-only flag)
* `disablecombat` (boolean): Intended combat restriction (client-only flag)
* `setunarmed` (boolean): Intended to set unarmed (client-only flag)
* `animation` (table):
  * `animDict` (string)
  * `anim` (string)
  * `flags` (number)
  * `task` (string) — alternative scenario task
* `prop` (table):
  * `model` (string): model name/hash
  * `bone` (number|string): bone index or name (default: `SKEL_R_HAND`)
  * `coords` (vec3): attachment offset
  * `rotation` (vec3): attachment rotation

Callbacks (all optional):

* `onProcessStart()` — called once at the beginning
* `onProcessTick()` — called every frame while running
* `onProcessComplete()` — called when finished without cancel
* `onProcessCancel()` — called if canceled (ESC or invalid state)

Cancel key:

* Defined in `config.lua` → `Config.escapeKey` (default: ESC)

{% stepper %}
{% step %}

### Simple 3s progress

```lua
exports['coderanch-ui']:startProgress({
  text = 'Preparing item...',
  timeout = 3000,
  cancelable = true
},
function() -- onProcessStart
  print('Started')
end,
function() -- onProcessTick
  -- runs every frame
end,
function() -- onProcessComplete
  print('Completed')
end,
function() -- onProcessCancel
  print('Canceled')
end)
```

{% endstep %}

{% step %}

### With animation

```lua
exports['coderanch-ui']:startProgress({
  text = 'Working...',
  timeout = 5000,
  cancelable = true,
  animation = {
    animDict = 'amb_craft@world_camp_fire_cook@male_a@wip_base',
    anim = 'wip_base',
    flags = 31
    -- or: task = 'WORLD_HUMAN_HAMMER'
  }
})
```

{% endstep %}

{% step %}

### With prop attached to hand

```lua
exports['coderanch-ui']:startProgress({
  text = 'Eating...',
  timeout = 4000,
  cancelable = false,
  prop = {
    model = 'p_bread05x',
    bone = 'SKEL_R_HAND',
    coords = vec3(0.05, 0.02, 0.0),
    rotation = vec3(0.0, 0.0, 0.0)
  }
})
```

{% endstep %}

{% step %}

### Allow while dead

```lua
exports['coderanch-ui']:startProgress({
  text = 'Waiting...',
  timeout = 2000,
  useWhileDead = true,
  cancelable = true
})
```

{% endstep %}
{% endstepper %}

### Callback Functions — Named Usage

You can define named functions and pass them into `startProgress` for clarity and reuse:

```lua
local function onProcessStart()
  print('Progress started (named)')
end

local function onProcessTick()
  -- Avoid heavy logic; this runs every frame
end

local function onProcessComplete()
  print('Progress completed (named)')
end

local function onProcessCancel()
  print('Progress canceled (named)')
end

exports['coderanch-ui']:startProgress({
  text = 'Crafting...',
  timeout = 6000,
  cancelable = true
}, onProcessStart, onProcessTick, onProcessComplete, onProcessCancel)
```

Notes:

* `onProcessTick` is called very frequently; avoid heavy logic inside.
* `prop.bone` accepts a bone name or index; defaults to `SKEL_R_HAND` if omitted.
* If progress is canceled (ESC or player death without `useWhileDead`), `onProcessCancel` runs and `onProcessComplete` will not.

***

## NUI Preview/Editor

* Command: `/ui`
  * Opens a simple UI to preview notifications and progress bar.
  * Close using the UI’s close button.

***

## Configuration

Edit `config.lua`:

```lua
Config = {}
Config.UICommand = 'ui'              -- command to open the UI preview/editor
Config.escapeKey = 0x24978A28        -- ESC key hash for canceling progress
```

Key hash reference is included in `config.lua` comments for convenience.

***

## License

This resource is developed by CodeRanch. Commercial usage requires permission.


---

# 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://coderanch-redm-store.gitbook.io/coderanch-redm-store-docs/coderanch-ui-system.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.
