Lua API v2Public reference

Script the overlay.

Events, menu elements, drawing, HUD windows, game data, files, network and memory: one API in every product. Everything on this page is the live reference, with an example you can paste as is.

modules
26
functions and fields
210
games documented
10

Getting started

  1. 01

    Write it

    A script is one .lua file. Every example below is a complete v2 script: copy it, or start from the one below.

  2. 02

    Load it

    Open the Lua tab of the in-game menu, or write it in the Editor tab. Signed in on the panel, Run in game sends a script straight to your loader.

  3. 03

    Iterate

    script.reload() picks up your edits. An error stays in the console with its line: it never takes the overlay or the other scripts down.

first_script.lua
local key = ui.create("Demo"):group("Keys"):hotkey("Aim key", 0x02, "hold")
events.render:set(function()
  if key:get() then render.text(nil, vector(20, 60), color(255, 200, 0), "s", "aiming") end
end)

How scripting works

A short mental model before the reference.

01

Events, not entry points

There is no OnDraw / OnMenu / OnThread any more. A script subscribes to events: events.render:set(fn) draws every frame, events.update:set(fn) runs before drawing, events.key_down, events.esp_player… Several callbacks per event, :unset(fn) removes one.

02

Menu elements are objects, made once

ui.create("My script") gives a tab, tab:group("Aimbot") a box, group:checkbox("Enabled", false) an element. Each one is a real menu setting: saved in configs, editable on /live, with :get(), :set(), :set_callback(), :depend()… No per-frame rebuilding.

03

vector and color everywhere

Positions and sizes are vectors (vector(x, y, z)), colors are colors (color(r, g, b, a)). render.rect(pos, size, col) - never packed integers or x, y, w, h lists.

04

The render thread never waits

Long calls (network, memory scans, device connects, os.execute…) take a callback as their last argument in a script and return at once. In a thread.spawn worker, call them without a callback: they block there, never the overlay.

05

One state per script, permissions per script

Each script has its own Lua state, memory cap (256 MB by default) and time budget (1 s per callback). Network, files outside its data folder, memory, devices, os and configs need a --@permissions header and the user's approval once; "Allow unsafe scripts" stays the master switch.

06

Everything is cleaned up on unload

Callbacks, timers, threads, menu elements, fonts, images, HUD windows, pending async calls and memory hooks belong to the script that made them and go away when it unloads. No callback of an unloaded script ever runs.

Per game

10 games

The API is the same in every product. What changes is the data: the players entity.* lists, the ESP elements, the hitbox names and the get_prop fields. A script can read elusive.product and game.name() to adapt.

Module 01

script · elusive · globals

10 entries

What a script knows about itself and the runtime. elusive.api_version is 2: no breaking change without a new number.

Module 02

events

11 entries

The entry points of a script. Each event object has :set(fn), :unset(fn); several callbacks per event run in the order they were set, each under its own script's time budget. Engine events cannot be fired by a script; events.custom(name) is the channel between scripts.

Module 03

timer

3 entries

Deferred and repeated callbacks on the render thread. At most 256 timers per script; a timer that runs out of its budget or raises 64 times in a row is cancelled.

Module 04

thread

6 entries

Background work in its own Lua state on its own OS thread. The function is self-contained: it sees none of the script's locals or globals (pass them as arguments; a function that captures a local is refused). Values cross as copies, like events.custom. At most 16 threads per script, 256 MB each; a loop that never calls thread.sleep / thread.recv is stopped after 300 million instructions; threads stop when the script unloads. A finished thread stays readable (recv) while it has unread messages, the last 16 of them only. A thread has its script's permissions; turning "Allow unsafe scripts" off or on reaches the running threads at once.

Module 05

ui

menu20 entries

The in-game menu. An element is made once (at the top level of the script) and becomes a real menu setting: drawn like the cheat's own under the Scripts category, saved in the configs, shown and editable on /live, listed in the keybinds HUD and the search. Stable ids: scripts.<script>.<tab>.<group>.<label>. Per script: 8 tabs, 64 groups, 1024 elements. Not available in a thread.

Module 06

vector

5 entries

The position / size / direction type. vector(x, y) is 2D (z = 0), vector(x, y, z) 3D. Fields x, y, z are writable. Operators: + - (vectors), * / (a number or a vector), unary -, ==, tostring.

Module 07

color

3 entries

The color type, 0..255 per channel. Fields r, g, b, a are writable (clamped when drawn). == and tostring work.

Module 08

render

events.render15 entries

Drawing over the game. The drawing calls work inside events.render and events.esp_player only; measure_text, screen_size, world_to_screen, load_font and load_image work anywhere in the script. Positions and sizes are vectors, colors are colors. At most 100,000 shapes per script per frame; a NaN or infinite coordinate draws nothing.

Module 09

hud

menu3 entries

The script's own HUD windows, in the style of the keybinds / spectators lists: draggable while the menu is open, magnetic, their placement saved with the configs. 16 windows per script; 256 items per window; not available in a thread.

Module 10

game · entity

varies by game11 entries

The game data, from the snapshot the product already fills every frame: these calls never read the game themselves. What each game exposes (players listed, ESP elements, hitbox names, get_prop fields, entity kinds, world axes) is in the "Per game" section above; a value a game does not have is nil. Not available in a thread.

Module 11

esp

varies by game10 entries

Take part in the cheat's own player ESP: hide players, recolor them, rewrite their labels, add texts, bars and flags laid out with the ESP's own elements (same sides, same stacking, same order as in the ESP preview). events.esp_player gives one (player, e) per player the ESP draws; esp.flag adds a real ESP element. Nothing is read from the game for this. Not available in a thread.

Module 12

input

4 entries

The game PC's keyboard and mouse, as the cheat reads them. Works in threads too. A vk outside 1..255 raises.

Module 13

common · configs

5 entries

Notifications, host information, and the configs (the cheat's saved settings). common works in threads; configs does not.

Module 14

radar

3 entries

The web radar (the Webradar tab: a live map of the game at elusive.is/r/<code>): its state, and marks your script puts on the viewers' map. Scripts only, not threads.

Module 15

string · table · math · bit · random

8 entries

Lua 5.4's standard library (base, coroutine, table, string, math, utf8, the safe part of os) with the functions that could loop in C replaced by bounded ones, plus these additions. Available in scripts and threads. Removed on every state: io, debug, package, dofile, loadfile, string.dump, bytecode loading (load takes text only), os.exit / remove / rename / tmpname / setlocale, warn, and __gc in setmetatable.

Module 16

json · base64 · crypto · regex

7 entries

Data libraries, available in scripts and threads, no permission needed.

Module 17

files

files permission (outside the data folder)5 entries

The script's files. A relative path is inside the script's own data folder, <scripts>\data\<slug>\ (made on first use; files.data_dir() gives it): no permission needed. Any other path (absolute, .., a drive) needs the files permission. Device names (CON, NUL, \\.\PhysicalDrive0…) are always refused. Works in threads too.

Module 18

network

network permission2 entries

HTTP and HTTPS requests. In a script they take a callback as the last argument and return at once; in a thread, call them without a callback and they return res | nil, err. 10 redirects, 64 MB body at most.

Module 19

clipboard · os

clipboard / os permissions3 entries

The host's clipboard and shell. os.time, os.clock, os.date and os.difftime are always there; os.getenv and os.execute need the os permission.

Module 20

memory

memory permission11 entries

Direct reads and writes in the game's memory over the DMA link. Prefer entity.*: it is read once per frame in one scatter, while every call here goes to the device. Quick calls answer at once; the long ones (scans, listings) take a callback in a script and block in a thread. Sizes per call: 1 MB in a script, 16 MB in a thread.

Module 21

shellcode

memory permission4 entries

Code hooks in the game. Every patch saves the bytes it overwrites and they are written back when the script unloads (unload, reload, shutdown), newest first, so a reload hooks a clean game. A range another script patched is refused; a hook whose write fails is undone.

Module 22

serial

device permission5 entries

MAKCU, KMBox B, Ferrum… over USB serial, on the same link as the Device settings. The long calls (open, connect, query) take a callback in a script and block in a thread. While a connect runs, the quick calls answer false / nil, "busy: the device is connecting" instead of blocking the overlay.

Module 23

kmbox

device permission7 entries

KMBox Net over UDP. In a script, commands are queued and sent in order by the device's own thread: a call returns true at once (or false, err when there is no box or 256 commands are waiting). In a thread they wait for the box. The release of a click / key, and key_up / button(b, false) / release_keys, are always sent, even if the script unloads in between.

Module 24

permissions · header

8 entries

What a script declares in its first 64 lines. "Allow unsafe scripts" (Configs & scripts > Lua) gives every script the permissions it declares, nothing to allow per script; when it is off, no permission applies. A call without its permission raises a message that says what to declare, or to turn the switch on.

Module 25

limits

8 entries

What keeps one script from taking the overlay or the other scripts down. Over a limit, the call raises a clean Lua error (or the script is unloaded with a clear message); nothing crashes.

Module 26

migrating from v1

old → new33 entries

API v2 is a clean break: OnDraw, OnMenu, OnThread and the immediate-mode menu are gone. Search the old name here to find its replacement. Behaviour that changed too: errors in a callback no longer stop other scripts; blocking calls (HTTP, serial queries, device connects, memory scans, os.execute) take a callback; memory hooks are undone when the script unloads; "Allow unsafe scripts" now gives a script only the permissions it declares (--@permissions).

elusive