Documentation
R_FFA

r_ffa Configuration

Every r_ffa config.lua option: framework and integrations, currencies and wagers, arena rules, the arena ped, attachments, UI and custom hooks.

All settings live in config.lua. Arenas, public lobbies and weapon sets have their own page: Creating Arenas.

Framework & integrations

R.Framework = 'auto'         -- 'auto' | 'esx' | 'qb' | 'qbox'
R.CoreName = 'es_extended'   -- only if you renamed es_extended
R.Inventory = 'ox_inventory' -- 'ox_inventory' | 'qs-inventory' | 'none' (ESX cash handling)
R.Target = 'ox_target'       -- 'ox_target' | 'qb-target' | 'none' (TextUI + E)
R.Notify = 'ox_lib'          -- 'ox_lib' | 'esx' | 'qb' | 'okok'
R.Ambulance = 'auto'         -- 'auto' | 'qbx_medical' | 'wasabi' | 'esx' | 'qb' | 'none'

General

R.Debug = false
R.EnableLogs = true        -- webhooks in server/sv_custom.lua
R.EnableAutoinsert = true  -- creates / migrates the r_ffa table on start
R.Names = 'player'         -- 'player' = FiveM name | 'character' = character name
R.Voice = true             -- pma-voice radio channel per lobby
R.HideTopHud = true        -- hides r_tophud while you are in an arena (the hub leaves it alone)
R.AdminGroup = 'group.admin'

R.Commands = {
    leave = 'ffaleave',
    admin = 'ffaadmin'
}

R.Keys = {
    menu = 'G',        -- arena menu
    scoreboard = 'TAB' -- hold to show the scoreboard
}

Keys are registered with ox_lib keybinds, so players can rebind them in Settings → Key Bindings → FiveM. R.Names decides what the killfeed, scoreboard and leaderboard show.

Currency & wagers

R.Currency = { symbol = '$', after = false, separator = ',' }

R.Payment = {
    cash = true,
    bank = true,
    credits = true -- r_store credits
}

R.Credits = { resource = 'r_store' }

R.Wager = {
    min = 100,
    max = 100000,
    minKills = 1,
    maxKills = 50,
    defaultKills = 5,
    countdown = 5,      -- seconds before every round
    responseTime = 30,  -- seconds the opponent has to answer
    range = 15.0        -- how close the opponent must be
}
OptionWhat it does
R.CurrencyHow money is shown everywhere ($1,000 or 1 000€).
R.PaymentWhich accounts can be wagered. credits only shows up when the r_store resource is running.
R.Wager.min/maxAllowed wager per player. Both stakes are taken when the challenge is accepted and the winner receives 2×.
R.Wager.minKills/maxKillsAllowed "first to X kills" range.
R.Wager.rangeThe opponent must be within this distance when the challenge is sent and accepted.
R.Wager.countdownFrozen countdown before every round of a duel.

Arena rules

R.Lobby = {
    leaveDelay = 5,          -- seconds before a player can leave after joining
    respawnDelay = 2,        -- seconds on the death screen before respawning
    spawnProtection = 1.5,   -- seconds of invincibility after (re)spawning
    outOfBounds = 5,         -- seconds to return after leaving the arena zone
    weaponSwapCooldown = 3,  -- seconds between weapon swaps in the menu
    infiniteAmmo = true,
    maxHealth = 200,
    customMaxPlayers = 32,   -- upper limit players can pick for a custom lobby
    bucketBase = 3000        -- routing buckets used by the arenas start from here
}

R.Streaks = { 3, 5, 10, 15, 20 } -- announced kill streaks

Arena ped & blip

R.Join = {
    {
        Ped = {
            Model = 'ig_joeminuteman',
            Scenario = 'WORLD_HUMAN_DRUG_DEALER',
            Coords = vec4(-257.2, -972.6, 31.2, 250.5)
        },
        Blip = { enabled = true, sprite = 110, colour = 27, scale = 0.7, label = 'FFA Arena' }
    }
}

Add more entries for more entrances. Players are always returned to the first entry when they leave an arena.

Attachments

R.Attachments = {
    { key = 'suppressor', label = 'Suppressor', image = 'nui://ox_inventory/web/images/at_suppressor.png', components = { 'COMPONENT_AT_PI_SUPP', ... } },
    ...
}

Each entry is one toggle in the arena menu. The first component in components that fits the current weapon is used, so one entry covers pistols, SMGs and rifles. image can be any URL or nui:// path.

UI

R.UI = {
    Accent = '#9a27ea',
    DefaultAvatar = 'nui://r_ffa/web/build/media/avatar.png' -- when MugShotBase64 is not running
}

R.WeaponImage = 'nui://ox_inventory/web/images/%s.png' -- %s = WEAPON_NAME in uppercase

Accent recolours the whole UI. Weapon images default to ox_inventory's; point R.WeaponImage at your own inventory's image folder if you use another one. Missing images fall back to an icon.

Hooks (cl_custom.lua / sv_custom.lua)

Both files are outside escrow so you can adapt integrations without touching the core:

FileFunctionWhen
client/cl_custom.luaNotify, GetAvatar, JoinVoice, LeaveVoice, RevivePlayerNotifications, mugshots, pma-voice, revives
client/cl_custom.luaOnHubOpened, OnHubClosed, OnArenaEntered, OnArenaLeftHide HUDs, disable inventory, weather/clock overrides
client/cl_custom.luaOnKillfeed, OnDuelResultCustom sounds or effects
server/sv_custom.luaLog + WebhooksDiscord logging
server/sv_custom.luaOnPlayerJoinedLobby, OnPlayerLeftLobby, OnKill, OnDuelFinishedYour own rewards, XP or achievements

Interface Colours

Every R-Scripts resource shares the same colour tokens, so you can match the UI to your server's branding without touching any code:

R.UI = {
    Accent = "#9a27ea",        -- icons, bars, badges and highlights
    Primary = "#ffffff",       -- main action buttons (buy / play / confirm)
    PrimaryText = "#000000",   -- text on those buttons
    NavActive = "",            -- selected tab background, "" keeps the neutral default
    NavActiveText = "#ffffff", -- selected tab text
}

Leave a value empty to keep the shipped look — the defaults above are exactly what you see out of the box. Accent stays a signal colour (icons, progress bars, badges); Primary is the solid button colour, so setting it to your brand colour turns every confirm button at once.