Overview
About nCore Inventory
You press F2 and the panel opens on a grid. Every item takes the cells it needs. R turns it while you drag, and the cells show whether it fits before you let go.
It runs standalone or on top of ESX, QBCore, QBox, ND_Core or ox_core, and it saves to oxmysql or to the server's own storage. The panel only asks, the server decides every move.
What you carry
Backpacks are worn on your character and carry their own inventory. Take one off and it drops with everything in it. Duffels and the plate carrier hold things as well, and vests show on the body.
Clothing pieces are items, so a jacket can be handed over or kept in a stash. Outfits save at the wardrobes of 8 clothing stores. This only works on freemode characters, and you need an appearance resource such as ncore_character, illenium-appearance, fivem-appearance, qb-clothing or esx_skin.
Drop a gun and it lies on the ground as that gun. A pile shows the model of what's in it, and you can also throw an item or place it where you want. Weapons and evidence can only be destroyed at a disposal point, like the Los Santos Foundry.
Food goes one bite at a time. Pull out a burger, left click takes a bite and right click puts it away. What's left stays in the item and it gets lighter as you eat. If someone is standing next to you, you can offer them a bite and they get a Y/U prompt.
Food also goes off over time. A cooler bag or a fridge slows it down, a freezer stops it.
Weapons
106 weapons ship as items. They wear and can jam, and every firearm has a serial number. Guns you carry show on your body, and parts go on at a 3D gun bench.
Other players and cars
/trade opens a window for items and cash. Both players see both offers and confirm after a short countdown. I added the countdown so nobody gets rushed into a bad trade.
/search and /rob work on other players. X puts your hands up.
Keys are items for cars, doors, houses, businesses and safes, so handing someone a key gives them access. L locks the nearest car you have a key for and opens it again. Trunks and gloveboxes have their own space, set per vehicle class and per model, and the ones of owned cars are only saved if you run oxmysql.
Around the map
Eight shops are already placed on 44 counters: 24/7, LTD, Robs Liquor, hardware stores, Ammu-Nation, Binco, a fence and a pawn shop. Each counter has its own stock that sells out and comes back, and a shop or a single row can be locked to a job. A row can also need a license. There are also 256 vending machines, about 7,800 bins and dumpsters players can dig through, and mailboxes and newspaper boxes where someone can hide a thing for someone else to find.
Crafting has a workbench, a gunsmith bench and a mechanic bench. You can queue a few jobs and walk off, the finished items wait for you in a tray.
Moving from another inventory
Scripts written for the QBCore inventory exports (AddItem, RemoveItem, HasItem, OpenInventory, CreateShop and the rest) keep working on any framework, and AddItem and RemoveItem take either common argument order. On QBox and ESX Legacy, the small compatibility folder in the package answers for the frameworks and scripts that ask for an inventory by name. A script that checks whether another inventory is running before it calls won't work unchanged.
Your players' saved items come across with invmigrate in the server console, from four common saved-data layouts. It only reports until you add apply, which runs only with nobody online, and it only reads your old tables. Stashes, trunks and gloveboxes come along too, except from ESX, which has no stash tables. This part needs oxmysql.
For you as the owner
/invadmin opens the admin panel, where you can open a player's inventory even when they're offline, give items and kits, and read the logs.
In the item editor you change an item's label, weight, stack size, value, rarity and rules, and the change reaches every player at once. It's stored by the server, so data/items.lua isn't touched. You can also add simple items there that have no use of their own. In the Config tab every setting shows whether a change applies live or at the next restart, and the ones that can only be changed in the file are marked as such.
The Economy tab counts every item on the server and shows which resource created how many per hour. When a resource suddenly makes far more than its usual hour, admins online get a notice. You can see who holds an item, and pull the whole history of one gun or unique item by its serial or id.
There's a testing guide that walks your staff through every feature, and a demo mode I use to record videos like the one above.
Other resources can watch or refuse moves, uses, buys, crafts and trades with RegisterHook, add items at runtime with RegisterItem, and add stashes with RegisterStash. Every export and event is listed in DOCUMENTATION.md.
The interface comes in 8 languages: English, Hungarian, German, French, Spanish, Brazilian Portuguese, Polish and Turkish.
This page is the short version. FEATURES.md comes with the script and lists everything.
Requirements
- OneSync
- Optional: oxmysql for database storage,
invmigrateand saved trunks of owned cars, ox_target or qb-target, an appearance resource for clothing - No ox_lib and no build step (QBox still needs ox_lib for itself)
- On QBox and ESX Legacy, the small ox_inventory compatibility folder that comes in the package
- ESX Legacy 1.14 and 1.15 need
setr inventory:accounts "[]"in server.cfg - Game build 3407 or newer is recommended so every weapon works
Editions
There are two editions. In Escrow the Lua code is protected by Cfx.re escrow, while config.lua, the item and data files, languages, shops, benches, framework bridges and the web panel stay open to edit. Full source has every file readable. Both get the same features and the same updates.
Updates don't install themselves. You download the new version again (escrow from your Cfx.re account, full source from Tebex), keep your config.lua and copy the new shared/defaults.lua over the old one. The changelog says what else to copy for each version.
Support
Support is on intelnpc.com and I reply within 72 hours. Refunds are handled by Tebex under their terms.
nCore Inventory is made by nCore Development, intelnpc.com.
Not approved, sponsored or endorsed by Rockstar Games.
What you get
Config open, core escrowed
Docs
Read it before you buy
The same docs that ship with the script, updated with every release.
This is the reference for server owners and script authors. README.md is the short overview, FEATURES.md the full feature list and INSTALLATION.md the setup guide.
Most settings live in config.lua. Items, stashes, shops and benches have their own files: data/items.lua, data/stashes.lua, modules/shop/shops.lua, modules/craft/benches.lua and modules/gunbench/benches.lua, plus the language packs in locales/. shared/defaults.lua fills in any key your own config.lua does not have, so keep your config.lua when you update and copy the new shared/defaults.lua over the old one. The admin panel's Config tab shows for each setting whether it takes effect at once or after a restart.
1. Where each feature is#
"Target eye" means ox_target or qb-target. Where a row names the target eye and neither of them runs, the same thing is an E prompt. Exceptions: "Give an item" and "Offer a bite / sip" are target eye options only (use drag, the right-click menu or /give instead), ground piles always open with E, and world stashes keep their marker and E prompt next to the target eye.
All built-in E prompts share one key: only the nearest one shows, one press does one thing, and they wait while a request prompt is up, while you place or throw, or while another resource shows its own GTA help text (ncore_character's counter prompts excepted, they run through the inventory's own hints). When another resource's help text makes an E prompt step aside, the client console says so once (info).
Panel and hotbar#
| Feature | How a player reaches it | Default | Switch |
|---|---|---|---|
| Open the inventory | F2 or /inventory |
on | Config.Player.keybind, Config.Player.command |
| Help sheet | "?" in the panel header and in the character header; opens by itself on a player's first open | on | Config.Panel.help |
| Turn and zoom the character | Drag and scroll on the character | on | Config.Character.rotate, Config.Character.zoom |
| Hotbar | Keys 1-5 (up to 9); drag an item onto a cell to bind it. A separate key that only shows the row can be set (no default) | on | Config.Hotbar, Config.Hotbar.peekKey |
| Item keys | Right-click > Bind to a key, then set the key in FiveM's key bindings (4 keys) | on, no default keys | Config.Binds |
| Rotate an item | R while dragging it, or R over an item on the grid | on | Config.Grid.enabled, Config.Grid.rotateKey |
| Open a container item | Right-click a wallet, pouch or other container > Open container; it opens inside the panel with a back button. A container cannot hold another container | on | Config.Containers.enabled, Config.Containers.maxDepth |
| Notes and labels | Right-click > Write a note (up to 120 characters); right-click > Add label, or double-click an item that has no use, for a label (up to 14 characters) | on | Config.Panel.notes (notes, also checked by the server); per item notes = false, rename = false |
| Multi-select | Ctrl-click several stacks | on | Config.Panel.modifiers |
| Sort, filter and stack | Sort menu, filter chips and the Auto-stack button in the toolbar | on | Config.Panel.sorts, Config.Panel.filters |
| Player settings | Gear button in the panel | on | Config.Panel.settings |
| Key hints | Key caps at the bottom of the screen for the stop key, E prompts, requests, the item in your hand and tips; they show the key each player bound, a rebind included | on | Config.Hints |
| Recover a stuck screen | /invunstuck |
always | - |
Items and the ground#
| Feature | How a player reaches it | Default | Switch |
|---|---|---|---|
| Drop | Drag the item off the panel and let go (Shift drops half, Alt one, Ctrl places it precisely), or right-click > Drop on the ground. A pile nobody touches for 30 minutes is removed, unless it holds a weapon or evidence | on | Config.Drops.enabled, Config.Drops.expireMs |
| Pick up | E at a pile; hold E to take the whole nearest pile (not in a vehicle) | on | Config.Drops.quickPickup |
| Everything on the ground | F2 or E at a pile lists the items of every pile within 2.5 m (up to 8 piles) in the ground bar, nearest first; Take all empties them all | on | Config.Drops.gatherRadius, Config.Drops.gatherMax |
| Throw | Right-click > Throw (grayed out while a weapon is drawn). Switched off, Throw drops the item at your feet | on | Config.Drops.throw.enabled |
| Place | Right-click > Place precisely (grayed out while a weapon is drawn) | on | Config.Drops.place.enabled |
| Storage crates | Place a crate item; E opens it, hold E picks it back up with its contents. Only the player who placed it (or an admin) can pick it up | on | Config.Drops.place.storage; item placeStash |
| Combine | Drag an item onto another | on | Config.Combine |
| Destroy | Right-click > Destroy…. Weapons and evidence only at a disposal point; elsewhere the sheet names the nearest point with a Set GPS button | on | Config.Disposal |
| Bags | Use a bag item or pick one up to wear it; Take off sets it down in front of you with everything inside. One bag at a time | on | Config.Bags |
| Clothing as items | Clothes tab; use or drag a clothing item to put it on, click a worn slot on the character to take it off | on | Config.Clothing.asItems |
| Vests and plates | Use a vest to put it on; use a plate with a vest on to raise its armor | on | Config.Armour |
| Bites, sips and smoking | Use the item, then left mouse; right mouse puts it away; Finish it takes every portion in turn. A cigarette or joint is lit with a lighter or a match, plays a light-up clip and burns down after its puffs | on | Config.Use.hand, Config.Use.light, Config.Use.butt, Config.Use.preferPortions |
| Item reactions | Use binoculars, documents, the vehicle kits, diving gear, fireworks and other reacting items. Each steps aside when the framework already has a usable callback of the same name | on | Config.Use.reactions |
| Parachute | Use the parachute item to strap it on; it shows on the back | on | Config.Use.parachute |
| Stop the current action | Backspace (the rebindable "Stop the current action" key), right click, or walking where the action holds you still. Stops kits, bandages and pills, Finish it, vehicle kits, towel and soap, the tank refill, gun and serial work, vest clips, pump filling and bench crafting. Ignored while the inventory or another screen is open | on | Config.Use.cancel |
| Drunk, wired and high | Alcohol, coffee, energy drinks, drugs and pills change the walk, screen and sprint of the player who took them | on | Config.Use.alcohol, Config.Use.buff, Config.Use.drugs |
Players#
| Feature | How a player reaches it | Default | Switch |
|---|---|---|---|
| Give | Drag onto a player chip, right-click > Give…, /give, target eye "Give an item" |
on | Config.Give |
| Trade | /trade, E when facing a player, the Trade button on a player chip while dragging, target eye "Trade". Cash can be added on ESX, QBCore, QBox and ND_Core |
on | Config.Trade, Config.Trade.money |
| Search or rob | /search or /rob, E at a player who is down, cuffed or has their hands up, target eye "Search". Anyone else is asked first. On-duty police and sheriff can search anyone |
on | Config.Search, Config.Search.jobs |
| Hands up | X or /handsup (not while crafting, in a vehicle or with the panel open). Steps aside for an emote resource that has its own |
on | Config.HandsUp, Config.HandsUp.standDownFor |
| Accept or decline a request | Y or U | on | Config.Search.acceptKey, Config.Search.declineKey |
| Offer a bite or sip | Right-click > Offer…, or the target eye ("Offer a bite", "Offer a sip") while holding food or a drink | on | Config.Offer |
Vehicles and keys#
| Feature | How a player reaches it | Default | Switch |
|---|---|---|---|
| Trunk | Inventory key at an unlocked boot; target eye "Open the trunk" | on | Config.Vehicles, Config.Vehicles.target |
| Glovebox | Inventory key in the driver or front passenger seat | on | Config.Vehicles, Config.Vehicles.gloveboxFrontOnly |
| Loot in unowned cars | The trunk and glovebox of a car nobody owns roll a few items the first time they are opened | off | Config.Vehicles.loot.enabled |
| Car keys | Use the key item, or press L (the rebindable "Lock or unlock the nearest car you hold a key for" key). While a vehicle key resource with its own lock key runs, L is left to it | on | Config.Keys, Config.Keys.vehicle.key |
| Door, property and safe keys | Use the key item. Door keys work through a supported door lock resource or the doors listed in Config.Keys.doors |
on | Config.Keys |
| Locksmith (copy, re-key) | Hardware store counter; only the registered owner of the car. Ownership is read from the ESX, QBCore and QBox vehicle tables through oxmysql; other frameworks need Config.Vehicles.ownedTable and Config.Keys.ownerColumn |
on | Config.Keys.locksmith |
Weapons#
| Feature | How a player reaches it | Default | Switch |
|---|---|---|---|
| Draw and holster | Click the weapon or press its hotbar key | on | Config.Weapons.drawAnim |
| Reload, clear a jam | R with a gun drawn. An empty gun also reloads by itself while you carry its ammo | on | Config.Weapons.reload, Config.Weapons.reload.auto, Config.Weapons.jam |
| Attachments | Drag a part onto the gun; a bar runs while the character fits it. Switched off, nothing can be fitted, but parts already fitted can still be taken off from the gun's menu | on | Config.Weapons.attachments, Config.Weapons.work |
| 3D gunsmith bench | Right-click a gun > Modify in 3D, or the 3D weapon modification button of the Gunsmith bench at Ammu-Nation (E or the target eye there opens the crafting panel; with the craft module off the bench has its own prompt) | on | Config.Modules.gunbench, Config.ModuleSettings.gunbench.fromInventory / benchOnly |
| Magazines | Drag ammo onto a magazine, the magazine onto the gun, or use it with the gun drawn; R swaps | off | Config.Weapons.magazines.enabled |
| Repair and clean | Right-click > Repair with… / Clean with…, or drag the kit onto the gun; a 5 s repair or 4 s clean bar | on | Config.Weapons.repairItems, Config.Weapons.work |
| Paid repair counter | E at the counter (two ship); a 6 s bar, paid when it ends | off | Config.Weapons.repairShop.enabled, Config.Weapons.work |
| Jerry can fill | Right-click the can next to a pump > Fill at the pump; the can is set down and a 4 s bar runs. You pay only for the fuel that goes in | on | Config.Weapons.pumpFill |
| Serial filing and restore | Drag the needle file, heavy drill or forensic kit onto the gun; the tool is in the hand, the drill plays its clip and sound. Restoring a serial needs an on-duty police or sheriff job | on | Config.Forensics |
| Ballistic shield | Use the ballistic shield with nothing drawn, a pistol-class gun or the stun gun | on | Config.Use.shield |
| Weapons on the body | Automatic | on | Config.Slings |
World#
| Feature | How a player reaches it | Default | Switch |
|---|---|---|---|
| Shops | E at a counter, or the target eye. With ncore_character running, the Binco clerk also opens its fitting room: G with the E prompt, a "Fitting room" option with the target eye | on | Config.Modules.shop |
| Pharmacy | Your ambulance script opens it with OpenShop(source, 'pharmacy'); the medical kit and trauma kit need the ambulance job |
on, no counter | openBy = 'export' in shops.lua |
| Selling | Hardware store and Binco: right-click your own item > Sell… while the counter is open. Fence and pawn shop: drag the item onto their tray. The fence buys only listed items and only from 22:00 to 05:00 server time | hardware, Binco, fence, pawn | sellBack, stockOnly, type in shops.lua; Config.ModuleSettings.shop.fence.enabled |
| Vending machines | E in front of a machine, or the target eye (needs the shop module too) | on | Config.Modules.vending |
| Bins and dumpsters | E at a bin, or the target eye | on | Config.Modules.dumpster |
| Hiding spots | E at a post box, letter box or news box, or the target eye. Electrical boxes are a set you can switch on | on | Config.Modules.cache, Config.ModuleSettings.cache.sets |
| World stashes, wardrobes, bar fridge and freezer | E at the marker; with ox_target or qb-target also the target eye on the floor and space around the marker | on | Config.Modules.stash, data/stashes.lua |
| Outfits | Outfits button while a wardrobe is open | on | Config.Clothing.asItems, Config.Clothing.outfits |
| Crafting | E at a bench or the target eye (the Workbench stands as a real bench; the Mechanic bench needs the mechanic job); Workbench tab on the rail; hand recipes anywhere | on | Config.Modules.craft |
| Evidence lockers | On-duty police or sheriff: E at the evidence desk, or /evidence <number> there. /evidenceclear <number> (grade 3 and up, at the desk) empties a locker |
off | Config.Evidence.enabled |
| License counters | E at the counter (one weapon license counter ships). Needs a framework that keeps licenses | off | Config.Licences.enabled |
| Disposal points | Map blip and a ring on the ground: Los Santos Foundry (weapons and evidence) and Rogers Salvage & Scrap (weapons) | on | Config.Disposal |
Automatic systems#
| Feature | Where it shows | Default | Switch |
|---|---|---|---|
| Carry strength | XP bar in the header | on | Config.Strength |
| Overload slowdown | Tier chip in the header | off | Config.Load.enabled |
| Spoilage | Freshness bar and tooltip; stacks merge only while their freshness and condition are close | on | Config.Decay, Config.Decay.mergeTolerance |
| Cold storage | Cooler bag, fridge and freezer stashes | on | Config.Cold |
| Water damage | Ruined items | on | Config.Water.enabled |
| Searching takes time | Searched players, bins, hiding spots, loot crates and the trunk and glovebox of a car nobody owns show their items one at a time | on | Config.Discover |
| Item notices | A short card for items gained or lost while the panel is shut | on | Config.Notify.items |
| Character speech bubble | Above the character while the panel is open: greeting, eating, drinking, drawing, holstering, using an item, low health, full inventory, item received | on | Config.Character.speech |
| Death drops and respawn wipe | On death | off | Config.Death.enabled |
| Starter kit | First login of a new character | frameworks off, standalone $500 on | Config.StarterKit |
| Premium coins | Rail | off | Config.Premium.enabled |
Admin#
| Feature | How an admin reaches it | Needs | Switch |
|---|---|---|---|
| Admin panel | /invadmin, the shield button in the inventory header, or a key binding (no default) |
lri.admin.panel |
Config.Admin.panel |
| Pose tool | /invpose [item], the Items tab button, or a key binding (no default) |
lri.admin.pose |
Config.Poses.enabled |
| Demo mode | /invadmin demo or the Demo tab |
lri.admin.panel and lri.admin.give (saving stop spots: lri.admin.config) |
Config.Admin.demo.enabled |
2. Item definitions (data/items.lua)#
Items are defined in data/items.lua, or registered from another resource with the server export exports.ncore_inventory:RegisterItem(name, definition), which returns ok, why. A name already in data/items.lua is refused; a resource may register its own item again to replace that definition. Item names are 1 to 64 letters, digits, _ and -. Old or foreign item names belong in data/aliases.lua, where each one resolves to the item it names.
Every definition is checked when it is loaded or registered. A wrong value is ignored or corrected, and the console names the item and the cause.
Basics#
| Field | Value | What it does |
|---|---|---|
label |
text | The name players read. The item name when left out. |
weight |
grams | The weight of one unit, rounded to a whole number. |
stack |
whole number | Units per slot; 1 never stacks. Forced to 1 for unique items, containers, clothing, guns (magazine), vests (armour), parachutes, shields and bind = 'first' items. |
category |
'item', 'key', 'weapon' or 'clothing' |
The rail tab it lands in. Anything else is read as 'item'. |
sub |
for example 'food', 'drink', 'medical', 'tool', 'document', 'material', 'money', 'other', 'clothing', and 'ammo' on a weapon-category round |
A finer class used by container accepts lists, sorting and the filter chips. |
rarity |
'common' (default), 'uncommon', 'rare', 'job', 'unique', 'contraband', 'evidence' |
The corner dot and accent. An 'evidence' item can only be destroyed at a disposal point, cannot go into bins, is never ruined by water and is never drawn as a weapon. |
value |
whole number | Base worth: shown on the tooltip (Config.Panel.showValues), the buy-back price of a shop that has sellBack = true (value times Config.ModuleSettings.shop.sellRate) and the price a fence pays through its buyRarity rates (value times the rate for the item's rarity). |
size |
'tiny', 'small' (default), 'medium', 'large' |
The grid footprint (Config.Grid.sizes) and what fits where, such as a hiding spot's maxSize. |
grid |
{ w = 2, h = 1 } |
An exact footprint that wins over size. Whole numbers from 1 to Config.Grid.maxColumns. Without it, guns take their weapon group's footprint from Config.Grid.weapons, melee weapons take Config.Grid.melee by size, and everything else takes Config.Grid.sizes. |
image |
'name.webp' or an address |
A file in web/images/. An https:// address is used only when its host is listed in Config.Panel.imageHosts; otherwise the item shows the placeholder and the console says so once per host. https://cfx-nui-<resource>/ addresses and nui:// paths are always accepted. A picture saved with the thumbnail capture command (/invthumbs) takes the place of this field. |
description |
text | Tooltip and inspect text, up to Config.Panel.descriptionMax (240) characters; longer text is cut and named in the console. Config.Panel.descriptions = false hides descriptions. Translations live in data/descriptions.lua, one table per language (en, hu, fr, de, es, pt-br, pl, tr) of item = 'text'. The first text found is used, in this order: text set in the admin item editor for the server language, the locale key item_desc_<item>, data/descriptions.lua in the server language, the admin editor's English text, data/descriptions.lua in English, then this field. |
unique |
true |
Every unit gets its own id and never stacks. |
meta |
table | Metadata copied onto every new unit. Values given by the script that creates the unit win. |
legacy |
true |
Kept so saved stacks survive. It can be held and used, but no shop sells it, no recipe makes it and the gunsmith bench does not offer it. The admin Items list hides it behind the Retired filter; an admin can still give it. |
dropModel |
model name | The prop the item is drawn as on the ground, when placed and when thrown. Without it, the class model in Config.Drops.models is used. |
dropRotation |
{ pitch, roll, yaw } |
How the ground prop lies. |
dropOffset |
meters, -1 to 1 | Height offset of the ground prop. |
throwHand |
{ pos = { x, y, z }, rot = { x, y, z } } |
How the item sits in the hand when thrown. |
dropPed |
ped model name | A dropped pile holding only this item lies on the ground as that dead animal ('a_c_sharktiger' for the shark, 'a_c_fish' for the fish). Config.Drops.peds = false draws it as an object. A model that is not a ped falls back to an object and the client console says so once. dropModel is still what the Place ghost, a thrown unit and the hand copy are drawn as. |
dropSolid |
true |
The pile's prop keeps its collision (the traffic cone). |
close |
false |
The panel stays open after the item is used. ox_inventory's shouldClose = false is read the same way. |
notes |
false |
Players cannot write a note on it. Config.Panel.notes = false turns notes off for every item. |
rename |
false |
Players cannot give it a custom label. |
Use, food and decay#
| Field | Value | What it does |
|---|---|---|
use |
'eat', 'drink' or 'use' |
What a left click does. Without it a click does nothing, unless the item is worn, a weapon, a reaction, a bundle, a blueprint, routed to another resource or registered as usable by the framework. |
useTime |
milliseconds | How long the use takes, 250 to 60000. Config.Use.defaultTimeMs otherwise. |
useAnim |
preset name or { dict, clip, flag, ms } |
The clip played during the use. A name is a preset in Config.Use.anims. A table may also set enter, exit, idles, fp, face, faceOut, blendIn, blendOut, female, walk, car and hand. Without it the preset of the item's use plays. |
holdAnim |
preset name or { dict, clip, flag } |
The pose between bites, sips or puffs of an item kept in the hand. A name is a pose in Config.Use.holds. The flag must include the upper body (16) and secondary (32) bits, and the pose must hold the same hand as the useAnim. |
prop, prop2 |
{ model, bone, pos, rot } or a model name |
Objects held during the use. prop2 defaults to the other hand's bone. |
useScenario |
scenario name | A scenario played instead of a clip (the kneeling first aid kits). |
useLock |
{ combat, move, sprint, vehicle, mouse }, each true or false |
What the player cannot do during the use. Keys left out follow Config.Use.locks. |
useBar |
true or false |
Show or hide the progress bar. Without it the bar shows for uses of Config.Use.barFromMs or longer. |
useMessage |
true or a locale key |
A toast when the use is done. true uses the locale key item_used_<item>. |
allowArmed |
true |
Can be used with a weapon drawn, whatever Config.Use.armed says. |
status |
{ hunger = 30, thirst = 10, stress = -5 } |
Changes through the framework's status system, -100 to 100 each. Hunger and thirst are applied on QBCore, Qbox, ESX and ox_core. On ND_Core and standalone nothing is applied and the console says so once. Stress needs a stress status on the framework side, otherwise the console says so once and nothing is applied. |
portions |
2 to 20 | Eaten, drunk or used in that many bites, sips or portions, with status shared out over them. Needs use = 'eat', 'drink' or 'use', or fire = true. Not together with uses, a container, armour or plate. |
emptyWeight |
grams | What a unit still weighs at its last portion (the bottle). A whole number below weight. Needs portions. |
portionTime |
milliseconds, 250 to 60000 | Length of one bite, sip or puff. Without it, Config.Use.portionTimes by kind (eat, drink, smoke), then Config.Use.portionTimeMs. Needs portions. |
share |
false |
Cannot be offered to the player beside you (offering is Config.Offer). |
unpack |
item name | A pack: using it takes one of that item out and uses it (the pack of cigarettes lights one cigarette). Needs portions. |
fire |
true |
A light (the lighter, the matchbox). While Config.Use.needFire is on, lighting a smoke needs one carried. With portions, each light spends one portion (one match). A ruined one does not light. |
smoke |
true |
Smoked from the hand and lit with a fire item, with the light-up clip of Config.Use.light. With hand smoking off (Config.Use.hand.enabled = false or kinds.smoke = false) it is used whole. |
puffs |
whole number, 1 to 200 | On a smoke item: it burns down after that many puffs (the cigarette 10, the joint 8), or after Config.Use.butt.burnMs if that comes first. |
ember |
particle name | On a smoke item: the smoke particle from the game's core asset. The default is ent_anim_cig_smoke; the joint uses ent_anim_weed_smoke. |
alcohol |
number above 0, up to 20 | The drinks in one whole unit (a beer 1, a bottle of spirits 4), shared out over the sips like status. Needs use = 'eat' or 'drink'. See Config.Use.alcohol. |
buff |
{ sleep = 8, sprint = 1.2, seconds = 30, stamina = 0.2 } |
For coffee and energy drinks. sleep (0.1 to 100) is the percent of the sleep need one whole unit refills, shared out over the sips: it goes to ncore_hud when that is started, and the client event ncore_inventory:sleep always fires for another needs script. sprint (1.01 to 1.49) runs faster for seconds (1 to 600, default 30). stamina (0.01 to 1) refills that share of the stamina bar on every sip, 0.2 when a sprint buff names none. Needs sleep or sprint, and use = 'eat' or 'drink'. See Config.Use.buff. |
effect |
{ ms = 20000, timecycle = 'drug_wobbly', strength = 0.3, shake = 'DRUNK_SHAKE', shakeAmp = 0.3, sprint = 1.1, stamina = 0.25, heal = { perSec = 6, secs = 9 }, clearBlood = true, evidence = 'widepupils', evidenceSec = 300 } |
What a drug or pill does once its clip is done (a joint: while it is smoked). ms is 1000 to 600000 and defaults to 10000 when a screen filter, shake, sprint or stamina is set without it. timecycle is a screen filter with strength 0.01 to 1 (default 0.5). shake is a camera shake name with shakeAmp 0.01 to 2 (default 0.3). stamina is 0.01 to 1 per second, or true for 0.25. heal adds perSec health (1 to 50) every second for secs seconds (1 to 120), stops if the player dies and follows Config.Use.healing. evidence is one status id or a list of up to six, sent through evidence:client:SetStatus for evidenceSec seconds (10 to 3600, default 300). One effect runs at a time: a second dose of the same item restarts the timer, another item's effect replaces it. Needs a use or smoke = true. See Config.Use.drugs. |
heal |
{ amount = 15, cap = 100, clean = true } |
Heals amount health points (1 to 200) up to cap percent (1 to 100, default 100) of the ped's maximum health (200 in the game, so cap = 85 stops at 170), not of the bar. Refused while dead or downed and when health is already at the cap. clean = true also washes off blood and wounds, false never does, and without it a heal of 40 or more does. An item with useScenario cannot be used in a vehicle. Config.Use.healing.enabled = false or a started resource in Config.Use.healing.standDownFor leaves healing to another script. |
fresh |
0 to 100 | Starting freshness; makes the item perishable. |
freshFor |
seconds | Shelf life from 100 to 0. Config.Decay.defaultSeconds (3 days) otherwise. |
degrade |
minutes | ox_inventory's shelf life. Read as fresh = 100 and freshFor of that many minutes when neither is set. |
spoilsInto |
item name | What it becomes when it spoils while Config.Decay.spoiled = 'convert'. Config.Decay.into otherwise. |
durability |
0 to 100 | Starting condition. Guns wear per round, melee weapons per hit, and tools when a recipe wears them. |
uses |
whole number, 1 to 100000 | Uses before the item is spent; one is taken per use. Only for items that do not stack, and not for containers. |
waterDamage |
true |
Ruined by water while Config.Water.enabled is on. Protected items, evidence and items in a waterproof container are never ruined. |
ruinedItem |
item name | What a water-ruined unit turns into. Without it, or when the name is not a registered item or is a container, the item is ruined in place. A weapon, a container item, or a stack bigger than the new item's stack is ruined in place too. |
tool |
true |
Flagged as a tool on the tooltip. |
money |
true |
Counts as cash: the panel prints $ instead of a count, police can Seize it in a lawful search, and shops never buy it back. |
Containers and storage#
| Field | Value | What it does |
|---|---|---|
container |
table | Makes the item hold other items (forces stack = 1). Fields: slots (default 1), maxWeight (grams, default 1000), accepts (a list of sub values, or the category for items without one), whitelist / blacklist (item names), label, grid = { w, h } (its inner grid, h up to 200), cold = 'fridge' / 'freezer' or a rate from 0 to 1 (Config.Cold.rates: how fast food spoils inside, 0 stops it), draw = false (weapons inside cannot be drawn and reloading takes no rounds from it, like the gun case). How deep containers may nest is Config.Containers.maxDepth (1: a container may not hold another). |
waterproof |
true |
A container whose contents water never ruins (the waterproof pouch). Ignored on an item without a container. |
equip |
'Back' or 'Vest' |
'Back' with a container is a worn bag; 'Vest' with armour is a vest, with pockets when it has a container. |
look |
{ male = { c, col, d, t }, female = { ... }, jobs = { police = { male, female } } } |
The clothing component a worn bag (component 5) or a vest (component 9) is drawn with on a freemode character: c component, col collection, d drawable, t texture. A jobs entry wins for players with that job. A part the game index does not have is removed and named in the console. |
bagProp |
model name or false |
The object on the back for a bag shown as an object (a non-freemode ped, or a bag without a look). The model needs a row in Config.Bags.props; without the field Config.Bags.prop is used, false shows none. |
armour |
whole number, 1 to 100 | A vest's armor (forces stack = 1). Ignored on a worn back bag. |
plate |
whole number, 1 to 100 | An armor plate: using it adds that much armor to the worn vest, up to the vest's own value. Read as a vest when the item also has armour. |
placeStash |
true or { access = 'owner' \| 'groups' \| 'public', groups = { ballas = 0 }, label } |
Place puts the item in the world as storage with its contents. access decides who may open it (default 'owner', or 'groups' when groups is set); only the placing character (or an admin) can pick it up. Needs a container, and not a worn bag. |
bundle |
{ { 'water', 1 }, { 'sandwich', 1 } } |
Using it opens it into these items in the player's pockets and bags, all or nothing; when they do not fit, nothing is opened. Logged, and fired as the server event ncore_inventory:bundleOpened (source, item, list, where list holds { name, count } rows). A row may also be { item = 'water', count = 1 }; the count defaults to 1. An item with a bundle has no other job: not a container, food, smoke, worn item, weapon, reaction or use. |
Rules: who may do what#
| Field | Value | What it does |
|---|---|---|
block |
{ 'drop', 'throw', 'place' } |
Per-action bans: drop (to the ground), give (hand-overs, trades and counters), throw, place, destroy, stash (stashes, hiding spots and other storage), vehicle (trunks and gloveboxes), player (into another player's inventory, such as a robber's). Also enforced when the item is inside a bag, wallet or vest, and for parts fitted to a gun and the ammo loaded in it. |
tradable |
false |
Shorthand that blocks give, player, drop, throw, stash and vehicle: the item stays with its holder but can still be used, placed or destroyed. |
protected |
true |
Nobody else can take it from its holder, except police on a lawful search while Config.Protect.policeMayTake is on. Water never ruins it. The ID card, the licenses, the lawyer pass and the bank card ship protected. |
locked |
true |
Never leaves its holder's own inventory: drop, throw, place, give, trade, sell, destroy, storage and crafting are refused. |
bind |
'first' |
Bound to the first character who carries it. It can only sit with that character (or in their personal stash), and can still be used, crafted with or destroyed. Forces stack = 1. |
protected, locked and the binding can also be set on one stack with the server export SetItemFlags(inv, slot, { protected, locked, boundTo }) and read with GetItemFlags(inv, slot). Config.Protect.enabled = false turns all three off. Shipped examples: family_heirloom (locked), id_badge (bound to its first holder), quest_parcel (not tradable), case_file (no drop, throw or place), starter_box (bundle), crate_public and crate_gang (public and gang crates; change ballas to your gang).
Weapons, keys and clothing#
| Field | Value | What it does |
|---|---|---|
magazine |
{ ammo = 'ammo-9', capacity = 12, items = { 'mag9' } } |
Makes the item a firearm with its ammo type and clip size (forces stack = 1). items lists the magazine items it takes while Config.Weapons.magazines.enabled is on; a name that is not a magazine for this gun is left out. fill = true (the jerry can, the fire extinguisher) means it holds its own contents with no ammo item: capacity is how much, and a new one starts full. |
mag |
{ ammo = 'ammo-9', capacity = 12, weapons = { 'weapon_pistol' }, clip = 'default' } |
A magazine item. ammo must be an ammo item, and every gun in weapons must fire that ammo and list this item in its magazine.items. clip is 'default' or the extended or drum clip component the gun shows while it is inserted. Used only while Config.Weapons.magazines.enabled is on (it ships off); shop rows for magazines are left out while it is off. |
serial |
true or false |
Every non-stacking item with a magazine gets a serial number while Config.Weapons.serials is on. false gives it none (the jerry can, the fire extinguisher); true gives one to an item without a magazine. |
attach |
{ slot = 'muzzle', components = { 'COMPONENT_...' } } |
A weapon part or skin for the slot it fits; components the game index does not have are left out. Config.Weapons.attachments = false stops fitting. |
tint |
whole number, 1 to 32 | A weapon finish item that sets that tint index on the gun it is fitted to. |
scratch |
'half' or 'full' |
A tool that takes a gun's serial off when dragged onto it: 'half' files it (a forensic kit can restore it), 'full' grinds it off for good. Needs Config.Forensics.enabled. |
restore |
true |
A tool that restores a filed serial when dragged onto the gun (the forensic kit). Also needs Config.Forensics.enabled. |
weapon |
'WEAPON_FLASHLIGHT' |
The game weapon of a weapon-category item whose name does not start with weapon_. |
sling |
'back', 'backMelee', 'thigh', 'thighL', 'hip', 'chest', 'front' or false |
Where the weapon hangs on the body (Config.Slings), or never. Without it, its weapon group's default spot. |
wear |
number | Condition this gun loses per round, instead of Config.Weapons.wear for its weapon group. 0 for no wear. |
wearPerHit |
number | Condition this melee weapon loses per hit, instead of Config.Weapons.meleeWear. 0 for no wear. |
keyType |
'vehicle', 'property', 'business', 'safe', 'storage', 'door' |
The kind of key, on a category = 'key' item. A key without one is read as 'door'. |
keyAccess |
'valet' |
A vehicle key that locks, unlocks and drives, but never opens the trunk or glovebox. |
clothing |
{ area = 'top' } |
A clothing piece for that area: hat, glasses, mask, ears, chain, watch, top, vest, bag, bracelet, pants, shoes or gloves. Worn as an item while Config.Clothing.asItems is on. |
parachute |
{ tint = -1 to 13, pack = 0 to 13 } |
A parachute strapped on with Use (Config.Use.parachute). Not on a container. |
shield |
true |
A ballistic shield, raised and put away with Use (Config.Use.shield). Not on a container or parachute. |
A gun or melee weapon item that does not stack gets its own id the first time it is drawn. Give guns unique = true anyway: a serial can only be filed off a gun that already has an id.
Reactions, blueprints and routing to other resources#
| Field | Value | What it does |
|---|---|---|
react |
'binoculars', 'newscam', 'document', 'note', 'gps', 'watch', 'fitbit', 'mask', 'towel', 'cone', 'cashbag', 'wash', 'vehicle', 'diving', 'firework', 'refill', 'hold' |
Built-in behavior on use (Config.Use.reactions). A reaction steps aside when the framework registers the same item as usable, or when a resource named for that item in Config.Use.reactions.standDownFor ({ item = { 'resource' } }) is started. |
document |
'card', 'paper', 'photo' or 'news' |
How a react = 'document' item is shown. Default 'paper'. |
repair |
'basic', 'full', 'tyre', 'wash' or 'bodge' |
What a react = 'vehicle' kit does (Config.Use.reactions.repair). Required for that reaction. |
firework |
{ model, dict, clip, asset, effect, shots, height } |
Required for react = 'firework'. shots 1 to 20 (default 1), height 0 to 120. |
hold |
{ model, bone, pos, rot, anim, off, walk } |
For react = 'hold': the object held up, the clip while holding it, the clip when putting it away and a movement clipset. |
blueprint |
{ recipes = { 'workbench:advancedlockpick' } } |
Using it teaches those recipes when they are gated by this blueprint in learn mode, and spends it. Needs the craft module with crafting progress on. |
client |
{ event = 'res:event' } or { export = 'resource.function' }, plus anim, scenario, prop, propTwo, usetime, disable, notification |
Hands the use to another resource on the client, in ox_inventory's shape. The event or export receives the item and its data. To spend it, the handler calls exports.ncore_inventory:useItem(data, cb) within Config.Use.routeTokenMs; nothing is spent unless that call goes through. anim, scenario, prop, propTwo, usetime (0 to 60000 ms), disable (move, car, combat, mouse, sprint) and notification fill useAnim, useScenario, prop, prop2, useTime, useLock and the use toast when the item does not set them itself. |
server |
{ export = 'resource.function' } |
Called like an ox_inventory server item callback: with 'usingItem' first (return false to refuse, nothing is spent), then 'usedItem' after the item is spent. |
consume |
0 to 100 | Units a routed use spends; between 0 and 1, the share of durability it takes (needs durability). Default 1 when the route has a client export, usetime, a server export or a client status; a route with only a client event spends nothing unless consume is set. |
A route is skipped for container items, when the framework registers the same item as usable (the framework callback wins), and while Config.Use.routing = false. When the export's resource is not started, the use is refused before anything is spent.
3. Settings#
Every setting below lives in config.lua. The default is the value config.lua ships with. When a key is missing from your config.lua, shared/defaults.lua fills it in with that same value (only the lists Config.Player.tiers, Config.Combine.recipes and Config.Vehicles.loot come back empty), so you can delete what you never change. A setting saved from the admin panel's Config tab is laid over config.lua at every start until you use Reset to file there. Protected settings and prices are changed in config.lua only.
Units: distances are in meters, weights in grams (32000 is 32 kg), and keys that end in Ms are milliseconds. "Target eye" means ox_target or qb-target. A target setting of 'auto' (or true) uses whichever of the two is running and falls back to an E prompt where the feature has one (the give and offer options exist only on the target eye); 'ox_target' or 'qb-target' names one; 'prompt' always uses the E prompt.
config.lua is a shared script, so every player downloads it. Never put a password, a token or a webhook address in it.
Framework, storage and language#
| Setting | Default | What it does |
|---|---|---|
Config.Locale |
'auto' |
The language of the whole server. 'auto' reads the lr:locale convar, then locale, ox:locale, esx:locale and txAdmin-locale, and falls back to English. Or set a pack from locales/ directly: 'en', 'hu', 'de', 'es', 'fr', 'pl', 'pt-br' or 'tr'. A string missing from a pack shows in English. |
Config.Framework |
'auto' |
Detected once at start. Pin one with 'esx', 'qb', 'qbox', 'nd', 'oxcore' or 'standalone'; a pinned framework that is not running is ignored with a console warning and detection runs instead. Ensure the framework before this resource. |
Config.FrameworkPriority |
{ 'qbox', 'qb', 'esx', 'nd', 'oxcore', 'standalone' } |
The order detection tries. standalone is only used when nothing else is found. |
Config.FrameworkResources |
{ esx = 'es_extended', qb = 'qb-core', qbox = 'qbx_core', nd = 'ND_Core', oxcore = 'ox_core' } |
The resource name of each framework, for servers that renamed theirs. |
Config.Identifier |
'character' |
What a player's inventory is keyed by. 'character' uses the framework's character id (what a multi-character server needs); with no framework it falls back to the license and says so once. 'license' survives a character wipe and needs no framework. |
Config.Database.prefer |
'auto' |
'auto' uses oxmysql when it is started, otherwise the server's own KVP store. 'mysql' falls back to KVP with an error when oxmysql is missing. 'kvp' always uses KVP. 'none' saves nothing, even with oxmysql running. The console says at start which one is in use. |
Config.Database.table |
'ncore_inventory' |
The table name. Premium coins and placed storage use tables named after it (_premium and _placed added to the name). The log store has its own table, Config.Logs.table. |
Config.Database.saveIntervalMs |
300000 |
The autosave interval (at least 30 seconds). Inventories are also saved on logout and when the resource stops. |
Config.Database.keepLoadedMs |
600000 |
A container nobody has touched for this long is saved and released from memory. 0 keeps everything loaded. |
Config.Conflicts.enabled |
true |
The resource refuses to start when another inventory resource is running, and names it in the server log. checkKnown checks the built-in list, extra adds names, and allow lists one you run on purpose during a migration (for ox_inventory, qb-inventory, ps-inventory and qs-inventory the matching Config.Compat switch is turned off for you). The ox_inventory compatibility folder shipped with this resource is always allowed. |
Config.Compat |
all switches true except qbEvents.enabled = false |
The export shapes other scripts already call: oxInventory (ox_inventory style exports), qbExports (the QBCore inventory exports and Player.Functions item calls), esxEvents, oxEvents (openedInventory, closedInventory, usedItem, updateInventory), clientMirror (the client-side compatibility exports), containerTargets (item exports also accept stash, trunk, glovebox, pile and container ids). Turn one off if another resource still answers it. phoneItem = 'phone' is the item a supported phone resource needs the player to carry. |
Config.Compat.qbEvents |
{ enabled = false, stashes = {}, stashSlots = 50, stashMaxWeight = 100000, fill = { jobs = {}, items = {} } } |
Answers the classic QB inventory:server:OpenInventory event. A stash id that matches a Lua pattern in stashes opens as a stash of at most stashSlots slots and stashMaxWeight grams. fill.jobs and fill.items let those jobs fill a trunk or glovebox through inventory:server:addTrunkItems and addGloveboxItems. |
Config.Migrate |
{ command = 'invmigrate', rename = { money = 'cash' }, money = 'auto', loadoutAmmo = true } |
The import from another inventory's tables (see Migration). rename maps old item names to new ones. |
Config.Identity.items |
id_card: Name, DOB, Sex, Nationality; driver_license: Name, DOB; weaponlicense, pilot_license, lawyerpass: Name |
The fields filled in from the character when one of these items is created for a player. enabled = false turns it off. |
Panel#
| Setting | Default | What it does |
|---|---|---|
Config.Player.keybind |
'F2' |
The default key of the open command. Players rebind it under Settings, Key Bindings, FiveM. '' leaves it unbound. |
Config.Player.command |
'inventory' |
The open command. |
Config.Panel.scale |
0.85 |
Size of the panel on top of its automatic scaling by screen height. Held between 0.5 and 2.0. |
Config.Panel.blur, .blurMs |
true, 320.0 |
GTA's own pause-menu blur behind the panel, faded in over this many ms. Players can switch it off in their settings. |
Config.Panel.imagePath |
'images/' |
Where item pictures come from. Point it at another resource's folder ('nui://your_resource/path/') to use those pictures first; a picture that folder lacks comes from this resource's own folder. |
Config.Panel.imageHosts |
{} |
The https hosts an item's own image URL may load from. An item whose picture is on a host not listed here shows the placeholder. |
Config.Panel.detailedDefault |
false |
Whether the Compact / Detailed toggle starts on Detailed. A player's own choice is remembered. |
Config.Panel.showValues |
true |
The money value on the detail line and in the tooltip. |
Config.Panel.showCash |
true |
The cash line in the panel. On ox_core and standalone, where cash is an item, it adds up the cash items you carry. |
Config.Panel.gridOnOpen |
false |
true opens the panel with the grid expanded. |
Config.Panel.sorts |
{ 'name', 'weight', 'amount', 'rarity', 'condition', 'category', 'newest', 'oldest', 'size' } |
The sort orders offered. Remove any you do not want. |
Config.Panel.filters |
{ 'worn', 'fresh', 'illegal', 'heavy' } |
The filter chips. worn and fresh only appear when an item in view has condition or freshness. |
Config.Panel.transfer |
true |
Moving items between the body and an open container. Checked on the server. |
Config.Panel.modifiers |
true |
Shift, Alt and Ctrl on drag (half, one, place precisely) and Ctrl-click multi-select. |
Config.Panel.descriptions, .descriptionMax |
true, 240 |
Item descriptions, and their length limit in characters (longer ones are cut with a console warning). |
Config.Panel.notes |
true |
Notes on items. false is also enforced on the server: a new note is refused, clearing an old one still works. |
Config.Panel.help |
true |
The "?" help buttons and the help sheet. |
Config.Panel.settings |
true |
The gear button with the player's own settings (sounds, HUD, character, hints, density, accent color, blur, bound keys). |
Config.Panel.vitals |
true |
Health and armor in the panel header, plus hunger, thirst and stress where the framework provides them. |
Config.Panel.identity |
{ serverId = true, citizenId = true, phone = true } |
What shows under the player's name. The server id always works; citizen id where the framework provides one (ESX, QBCore, Qbox, ND_Core); the phone number on QBCore and Qbox. |
Config.Panel.dropToUse |
true |
Dragging an item onto the character uses or wears it. |
Config.Panel.hideHud |
true |
Hides ncore_hud, ncore_vibehud and the radar while the panel is open, and offers players a setting to turn that off. |
Config.Panel.hideGameHud |
true |
Hides GTA's own HUD pieces while the panel is open. |
Config.Panel.hudResources |
{ { resource = 'qs-hud', event = 'qs-hud:toggleHud' } } |
Other HUDs to hide while the panel is open: { resource, event } or { resource, export }, called with false on open and true on close, only while that resource runs. |
Config.Panel.keepInput |
{ enabled = false, walk = false } |
enabled = true keeps push-to-talk working while the panel is open; walk = true also lets the player walk. |
Config.Panel.buttons |
{} |
Up to 6 extra header buttons: { label, command or event, glyph, close }. A button with neither a command nor an event is not shown. |
Config.Categories |
Items, Keys, Weapons, Bag | The rail tabs. match is the item category a tab collects; the Bag tab shows the worn bag. With Config.Clothing.asItems on, a Clothes tab is added before Bag. |
Config.Hotbar.enabled, .slots |
true, 5 |
The hotbar and how many number keys it uses (up to 9 on the grid). On the grid a key is bound to an item where it lies; when that stack runs out the key uses the same item from elsewhere in the body, then from a worn bag. |
Config.Hotbar.keys |
'1' to '9' |
The default key of each hotbar key mapping. '' leaves that number key alone. Each cell shows the key the player actually bound. |
Config.Hotbar.showMs, .showOnChange |
4000, true |
How long the row stays on screen after a key press, a pickup or a hand-over (0 keeps it up), and whether a change of contents also shows it. |
Config.Hotbar.blockGameKeys |
true |
Keeps GTA's own weapon selection off: the number keys and the TAB weapon wheel. The WeaponWheel export still lends the wheel to another resource. false gives both back. |
Config.Hotbar.peekKey |
'' |
A key that only shows the row. No default. |
Config.Binds |
{ enabled = true, slots = 4, keys = { '', '', '', '' } } |
Bound item keys (right-click > Bind to a key), up to 9. No key ships bound; players set them in FiveM's key bindings. |
Config.Character.enabled |
true |
The character preview in the panel. |
Config.Character.mode |
'camera' |
How the preview is drawn: 'camera' or 'clone'. Config.Character.camera = true (off by default) applies to 'clone' only and holds your exact view with depth of field. |
Config.Character.rotate, .zoom |
true, true |
Drag to turn the character, scroll to zoom between 0.8x and 1.3x. |
Config.Character.speech |
enabled = true, aloud = false |
Short reactions in a speech bubble while the panel is open (greeting, eating, drinking, using an item, drawing or holstering a weapon, receiving an item, low health, a full inventory). aloud = true also plays them as the character's voice, for the player only; voices is the fallback voice per sex for characters without one (false keeps them silent). |
Config.Sounds |
enabled = true, a GTA frontend sound per action |
The panel sounds (open, close, move, use, drop, give, buy, tab, toggle, error), each { name, set }. |
Config.Notify.enabled, .provider |
true, 'auto' |
Notifications go to ncore_hud when it runs (useNcoreHud), otherwise the framework's own, otherwise the panel's own toast. provider = 'ox_lib' sends them to ox_lib instead; provider = 'event' fires Config.Notify.event on the client instead. |
Config.Notify.items |
{ enabled = true, whileOpen = false, losses = true, showMs = 3000, max = 4 } |
The pick-up rows that name items gained and lost. losses = false shows gains only; whileOpen = true also shows them with the panel open. |
Players#
| Setting | Default | What it does |
|---|---|---|
Config.Give.enabled, .command |
true, 'give' |
Giving items by drag, right-click and /give. |
Config.Give.distance |
3.0 |
How far the receiver may stand. Checked on the server. |
Config.Give.requireFacing |
true |
The receiver has to be in front of you; the giver turns toward them first (not in a vehicle). Two players in the same vehicle skip the facing check (sameVehicle = true). |
Config.Give.nameAs |
'character' |
How nearby players are named in the give list: 'character' (character name), 'initials' (first name and last initial), 'id' (# server id) or 'player' (FiveM name). |
Config.Give.toBags |
true |
A given item that does not fit the receiver's body goes into their worn bag. |
Config.Give.animation, .sound |
true, true |
The hand-over clip and a short pick-up sound for both players. |
Config.Give.target |
true |
"Give an item", and while holding food or a drink "Offer a bite" or "Offer a sip", on the target eye. false removes them. |
Config.Trade.enabled, .command |
true, 'trade' |
The two-sided trade window. |
Config.Trade.target |
true |
true or 'auto': the target eye when one runs, otherwise an E prompt when you face a player. 'ox_target', 'qb-target', 'prompt', or false (the command still works). |
Config.Trade.key |
'' |
The default key of the trade key mapping. Unbound. |
Config.Trade.slots |
10 |
Slots per side. |
Config.Trade.money, .maxMoney, .account |
true, 1000000, 'cash' |
Money in the trade, from and to this framework account. Only on frameworks that keep cash in an account (ESX, QBCore, Qbox, ND_Core); on ox_core and standalone cash is an item and is traded like one. |
Config.Trade.distance, .keepDistance |
3.0, 4.0 |
How close to start, and how far apart before the trade closes. |
Config.Trade.askMs, .cooldownMs, .reviewMs, .maxMs |
10000, 10000, 3000, 600000 |
The request time, the wait before asking the same player again, the wait after both lock in before Confirm works, and the longest a trade may stay open. |
Config.Offer |
{ enabled = true, distance = nil, requireFacing = true, askMs = 8000, cooldownMs = 8000, allowCuffed = true, animation = true, handOffPhase = 0.5 } |
Offering a bite or a sip of what you hold. distance = nil uses Config.Give.distance. |
Config.Search.enabled, .command |
true, { 'search', 'rob' } |
Searching other players. |
Config.Search.target, .key |
true, '' |
Same choices as Config.Trade.target and .key. |
Config.Search.distance, .keepDistance |
1.8, 3.0 |
How close to start a search, and how far before it ends. |
Config.Search.jobs |
{ police = 0, sheriff = 0 } |
Jobs (with the lowest grade) that search on duty without asking. The duty flag is read on QBCore, Qbox and ESX; ND_Core and ox_core count everyone as on duty. |
Config.Search.jobNeedsGround |
false |
true: an on-duty officer searches without asking only when the target is dead, down or cuffed. Otherwise the target gets the same request as anyone else, and if they answer with hands up the officer keeps police rights (Seize, protected items). |
Config.Search.consent, .consentMs |
true, 8000 |
Anyone may ask to search; the target accepts (Y) or declines (U) within this time. |
Config.Search.acceptKey, .declineKey |
'Y', 'U' |
The default keys of the shared request prompt (trade, offer and search). |
Config.Search.handsUp |
true |
The target can also answer a request by raising their hands, which allows a robbery. |
Config.Search.handsUpNeedsWeapon |
false |
true: a hands-up robbery needs a weapon in the robber's hand. |
Config.Search.allowDead, .allowCuffed |
true, true |
Dead or downed, and cuffed, players can be searched without asking. |
Config.Search.robGrounds, .robMs |
{ dead = true, down = true, cuffed = true, hands_up = true }, 3000 |
On these grounds a non-police search first runs a timed rob of this length. |
Config.Search.witnesses, .witnessSeconds, .witnessDead |
true, 15.0, false |
A robbery raises GTA's mugging event on the robber's game so ambient peds may react. Nothing is sent to a police or dispatch resource. Not for police, and not on a dead target unless witnessDead = true. |
Config.Search.includeBags, .takeBags, .includeWorn |
true, true, true |
A search shows the target's worn bags (and lets you take them) and their worn clothing. Config.Clothing.stealable decides which clothing areas can be taken. |
Config.Search.cash, .accounts |
true, { 'cash' } |
Taking money from these framework accounts in a search. Not on ox_core and standalone, where cash is an item. |
Config.Search.freezeTarget, .notifyTarget, .animation |
true, true, true |
The target is held still during a rob and told about the search; the searcher plays a clip. |
Config.Search.seizeJobs, .seizeTo, .seizeItem |
false, 'evidence', 'seized_cash' |
Who may Seize money in a lawful search (false uses Config.Protect.policeJobs, then Config.Search.jobs) and where it goes: 'evidence' hands the officer a sealed seized_cash item, 'destroy' removes it, 'event' leaves it to your own handler. |
Config.HandsUp |
{ enabled = true, command = 'handsup', key = 'X', standDownFor = 'auto' } |
/handsup and its key. 'auto' steps aside for qb-smallresources, rpemotes, rpemotes-reborn, dpemotes and scully_emotemenu, also when one of them starts later (a press then goes to that resource, unless this one raised the hands). A table names your own list; {} none. |
Config.Protect |
{ enabled = true, policeMayTake = true, policeJobs = false, bindOnFirstBody = true } |
Protected and bound items. policeMayTake: police in a lawful search may take protected items. policeJobs = false uses Config.Search.jobs. bindOnFirstBody: an item with bind = 'first' binds to the first player who carries it. |
Config.Death.enabled |
false |
The death rules below. |
Config.Death.dropWeapon |
true |
The gun in hand falls where the player died. |
Config.Death.cash |
{ drop = false, min = 0, max = 0, bag = 'moneybag' } |
Cash dropped on death (max = 0 means all of it, nothing below min). It drops in a money bag item on frameworks with a cash account, and as a plain cash pile on ox_core and standalone. |
Config.Death.wipe |
{ by = 'auto', keep = { 'phone' }, keepFlagged = true, to = 'destroy', withinMs = 600000 } |
When an ambulance resource clears the inventory on respawn ('auto': qb-ambulancejob, esx_ambulancejob, qbx_ambulancejob, or a table of names), the keep items and protected, locked or bound items stay. to = 'ground' leaves the rest where the player died; 'destroy' removes it. |
Config.Evidence |
enabled = false, command = 'evidence', clearCommand = 'evidenceclear', jobs = { police = 0, sheriff = 0 }, clearGrade = 3, maxLocker = 9999, slots = 60, maxWeight = 300000, distance = 2.0, one location at 483.74, -987.89, 30.69 |
Numbered evidence lockers. On-duty job members open locker N with /evidence N at a location; /evidenceclear N empties one, for members from clearGrade up standing at a location, or from the server console. |
Vehicles and keys#
| Setting | Default | What it does |
|---|---|---|
Config.Vehicles.enabled |
true |
Trunks and gloveboxes. |
Config.Vehicles.persist |
'owned' |
'owned' saves the trunk and glovebox of cars in the framework's owned-vehicle table (it reads that table through oxmysql); others last until a restart. 'all' saves every car's, 'none' none. |
Config.Vehicles.verify |
'model' |
How a saved trunk is matched to a car, since plate text can be set by any client: 'model' also checks the model; 'strict' keeps a trunk shut when no model is known; 'registry' opens only cars a garage registered with the RegisterVehicle export; 'plate' trusts the plate alone. |
Config.Vehicles.ownedTable |
'' |
The owned-vehicle table. '' reads it from the framework: ESX owned_vehicles, QBCore and Qbox player_vehicles. ND_Core, ox_core and standalone need it set (with Config.Keys.ownerColumn). |
Config.Vehicles.trunkLocks |
{ 0, 1, 8 } |
Door lock states with which a trunk opens: none, unlocked, and locked with the boot open. 0 and 1 count as the same state. |
Config.Vehicles.gloveboxFrontOnly |
true |
The glovebox opens from the driver and front passenger seats only. It always needs the player in the car. |
Config.Vehicles.bootDistance, .openDoor |
1.5, true |
How close to the boot the player must stand, and whether the lid opens while the trunk is open. |
Config.Vehicles.access |
{ owned = 'anyone', jobs = nil, keys = true, cacheMs = 60000 } |
owned = 'owner': an owned car's trunk and glovebox open only for its owner, a holder of a permanent key (keys = true) or an on-duty job (jobs = nil uses Config.Search.jobs). |
Config.Vehicles.target |
'auto' |
"Open the trunk" on the target eye. Without one, the inventory key at the boot opens it. |
Config.Vehicles.default |
trunk 20 slots / 60 kg, glovebox 5 slots / 5 kg, reach = 4.5 |
The size of a car with no class or model row. reach is how far from the car's center the server allows the trunk to be used. |
Config.Vehicles.classes |
a row per GTA vehicle class 0 to 22 | Trunk, glovebox and reach per class. false means none (for example, motorcycles and bicycles have neither). |
Config.Vehicles.models |
supercars with front = true or trunk = false |
Per-model overrides. front = true puts the trunk under the hood. Add a row with an explicit size for each addon vehicle. |
Config.Vehicles.loot |
enabled = false, a few trunk and glovebox rows |
Items rolled into unowned cars the first time they are opened. chance is a percent from 0 to 100; a value of 1 or less is read as a share, so chance = 1 always drops. |
Config.Vehicles.trunkAnim |
enabled = true, separate male and female clips |
The clip played when opening a shut boot on foot, timed with the lid. Not for front-trunk models. |
Config.Keys.enabled |
true |
Key items lock and unlock what they are cut for. Only keys the player carries count (pockets, key ring, worn bags). |
Config.Keys.standDownFor |
{} |
Resources that handle key items themselves. While one runs, a used key fires Config.Use.event and this inventory locks nothing. |
Config.Keys.vehicle.script |
'auto' |
Finds a running vehicle key resource this inventory supports (qbx_vehiclekeys, qb-vehiclekeys, Renewed-Vehiclekeys, MrNewbVehicleKeys, t1ger_keys, qs-vehiclekeys, wasabi_carlock, vehicles_keys, jaksams_VehiclesKeys), or name one. 'none' always locks by plate. |
Config.Keys.vehicle.key |
'L' |
The default key of "Lock or unlock the nearest car you hold a key for" (lri_carkey). While a vehicle key resource with its own lock key runs, the press is left to it (with ncore_hud, only while seated in a vehicle). |
Config.Keys.vehicle.range |
20.0 |
How far the nearest keyed car may be (2 to 100). |
Config.Keys.vehicle.matchModel |
true |
A key cut with a car's model opens only that model under that plate. |
Config.Keys.vehicle.hazards |
{ lock = 2, unlock = 2 } |
How many times the indicators flash on lock and unlock (1 to 3), through ncore_hud, ncore_vibehud or the game itself. true flashes twice, false none. |
Config.Keys.vehicle.issueOnGive |
true |
A garage's or vehicle shop's "give keys" event makes a key item: a permanent one for a car the player owns, a garage key (only that car, gone when the car is) for one their game has just spawned (spawnedWithinMs = 60000). giveEvents = 'auto' listens for vehiclekeys:client:SetOwner and qb-vehiclekeys:client:AddKeys; a table names your own events. |
Config.Keys.doorScript |
'auto' |
Uses a supported door lock resource when one runs (ox_doorlock or qb-doorlock), or name one. nui_doorlock is not supported: a door key refuses there and the console warns once. 'none' never uses one. |
Config.Keys.doorFeedback |
key-turn clip anim@heists@keycard@ / exit, click sound UNLOCK_DOOR |
The clip when a door key locks or unlocks through this inventory's own doors or ox_doorlock, and the click at the door for doors in Config.Keys.doors. false none; sound = false clip only. |
Config.Keys.doors |
{} |
Doors this inventory locks itself, for doors no door script manages: id = { model, coords, locked, maxDistance }. |
Config.Keys.ownerColumn |
nil |
The owner column of the vehicle table. nil reads it from the framework. |
Config.Keys.items |
vehicle = 'key_vehicle', valet = 'key_valet', house = 'key_property', door = 'key_door', stash = 'key_safe' |
The item each kind of key is cut as by /invkey, the IssueKey export and garage keys. |
Config.Keys.locksmith |
{ enabled = true, shops = { 'hardware' }, distance = 3.0, copy = { price = 45 }, rekey = { price = 250 }, pay = 'cash' } |
Copying and re-keying car keys at the counters of these shops. Only the registered owner of the car may do either. Needs the shop module. |
Config.Discover |
enabled = true |
Timed searching: items in searched players, bins, hiding spots, loot crates and unowned trunks and gloveboxes are revealed one by one (revealMs by item size, rareExtraMs more for rare ones). transfer adds a take-out time by weight (baseMs = 250, perKgMs = 180, up to maxMs = 4000). 'unowned' trunks only count when the owned-vehicle lookup answers. |
Stashes#
| Setting | Default | What it does |
|---|---|---|
Config.ModuleSettings.stash.openDistance |
2.0 |
How close to a data/stashes.lua stash the E prompt and target option show. The limit is the smaller of this and the larger of Config.Player.reachDistance and Config.Drops.openDistance; the server allows 1 m more. |
Config.ModuleSettings.stash.target, .marker |
'auto', true |
The target eye option, and the ground marker. World stashes keep their E prompt also next to the target eye; marker = false removes the marker. |
Config.Stashes.openDistance |
2.5 |
The reach of a stash registered by a script with coords and no openDistance of its own. |
Config.Stashes.clientOpenUnguarded |
false |
A stash with no coords and no job is opened only by a server script, never by a client naming it. true allows clients. |
Config.Stashes.temporaryIdleMs |
1800000 |
An empty temporary stash nobody has opened is released after this long. |
Config.Stashes.prune |
{ enabled = false, days = 90, emptyOnly = true } |
Removes per-player stash boxes of owners who have not logged in for this many days (counted from when the resource was installed). emptyOnly = false also removes boxes with items. |
Config.Groups.gangs |
true |
Job-named gates also match gangs and groups where the framework has them (QBCore and Qbox gangs, ND_Core and ox_core groups). |
Config.Groups.hidePoints |
true |
A player outside a stash's job, jobs or groups gets no marker, blip, prompt or target zone for it. The list is sent again after a job change. |
Config.Groups.pollMs, .events |
5000, true |
How often job and gang changes are checked, and whether the framework's job and gang update events trigger a check at once. |
Config.Cold |
{ enabled = true, rates = { fridge = 0.25, freezer = 0.0 }, stashes = {} } |
Cold storage. Food in a fridge stash loses freshness at a quarter of the speed, in a freezer not at all. stashes sets a stash id to 'fridge', 'freezer' or a rate and wins over the stash's own cold. |
Food and bags#
| Setting | Default | What it does |
|---|---|---|
Config.Decay.enabled |
true |
Freshness. It is worked out from the time an item was made, so it keeps falling in a stash, while the player is offline and across a restart. |
Config.Decay.defaultSeconds |
259200 |
Shelf life of an item without its own freshFor (three days from 100 to 0). |
Config.Decay.refuseSpoiled |
true |
Spoiled food cannot be eaten or drunk. |
Config.Decay.spoiled |
'keep' |
What happens to spoiled food: 'keep' leaves it, 'remove' throws it away, 'convert' turns it into the item's spoilsInto or Config.Decay.into. |
Config.Decay.into |
'spoiled_food' |
What spoiled food becomes with 'convert' when the item names no spoilsInto. '' also means spoiled_food; false throws it away. |
Config.Decay.mergeTolerance |
10 |
Two stacks of one item merge only while their freshness and condition are each within this many points (0 to 100). The merged stack keeps the count-weighted freshness. |
Config.Use.defaultTimeMs |
1500 |
How long a use takes when the item sets no time. |
Config.Use.barFromMs |
1500 |
Uses this long or longer show a progress bar. |
Config.Use.cancel |
{ key = 'BACK', move = true } |
The default key of the rebindable "Stop the current action" binding (ncore_cancel_use). A timed use also stops on right click, on moving where the use holds the player still (move = false turns that off), on getting into a vehicle, and on death or being knocked over. The item comes back once and nothing is applied. false: only death, being knocked over and getting into a vehicle stop a use. |
Config.Use.event |
'ncore_inventory:itemUsed' |
Fired for items with a use this resource does not handle itself, when the use is done. |
Config.Use.status |
true |
Hunger, thirst and stress changes through the framework's status system. |
Config.Use.props |
true |
Items held in the hand while they are used. |
Config.Use.armed |
'holster' |
Using an item with a weapon drawn: 'holster' puts the weapon away first, 'refuse' refuses, 'allow' allows. |
Config.Use.locks |
{ combat = true, move = false, sprint = false, vehicle = false, mouse = false } |
What a use blocks while it runs, unless the item sets its own useLock. |
Config.Use.healing |
{ enabled = true, standDownFor = {} } |
Healing items heal. Resources named in standDownFor take the heal over: the clip plays and Config.Use.event fires. |
Config.Use.anims, .holds |
clip sets eat, drink, use, pills, smoke, medic, sip, swig, puff, puff_pot, bite; holds cup, bottle, smoke, smoke_pot, food |
The use clips and the poses between bites. Each names the hand it uses; an item's holdAnim must name the same hand as its useAnim. |
Config.Use.hand |
{ enabled = true, kinds = { eat = true, drink = true, smoke = true }, helpMs = 6000 } |
Food, drinks and smokables go into the hand: left click takes a bite or sip, right click puts it away, Finish it takes one after another. helpMs is how long the help line stays (0 keeps it up). |
Config.Use.portionTimeMs, .portionTimes |
1500, { eat = 3000, drink = 2500, smoke = 3500 } |
The length of one bite, sip or puff. An item's own portionTime wins. |
Config.Use.preferPortions |
true |
Items in data/items.lua with portions are eaten here bite by bite even when the framework also registers them as usable; the console lists them at start. false leaves them to the framework callback. |
Config.Use.needFire |
true |
Lighting a cigarette or joint needs a lighter or matches. |
Config.Use.light |
lighter clip, ms = 2600, lighter = 'p_cs_lighter_01', side = 'left' |
The clip when a smoke is lit, with the lighter in the side hand (a match shows none). lighter = false shows no lighter; false lights at once. |
Config.Use.butt |
dropAtMs = 700, lieMs = 8000, burnMs = 300000 |
The flick that throws a butt away. burnMs is how long after lighting a smoke burns down (0 never; an item's puffs can end it sooner). |
Config.Use.alcohol |
{ enabled = true, decayMs = 180000, max = 10, evidence = true, evidenceSec = 200 } |
The drunk level from items with alcohol: from 2 a tipsy walk, from 4 a drunk walk and a blurred screen, from 7 a staggering walk and a swaying camera. One drink wears off every decayMs. evidence sends evidence:client:SetStatus with 'alcohol' or 'heavyalcohol' for evidenceSec seconds. |
Config.Use.buff |
{ enabled = true } |
Coffee and energy drinks refill ncore_hud's sleep need (or fire the client event ncore_inventory:sleep for another needs script) and give sprint and stamina for a while. |
Config.Use.drugs |
{ enabled = true, evidence = true } |
Drugs and pills play their screen effect, sway, sprint, stamina or heal once the clip is done; a second dose restarts the timer. evidence sends the item's statuses (widepupils, agitated, weedsmell) to the evidence script. |
Config.Use.hygiene |
{ soap = 35 } |
Percent of the hygiene need a finished soap wash restores in ncore_hud, also sent as the client event ncore_inventory:hygiene. 0 or false none. |
Config.Use.kitGround |
{ x = 0.0, y = 0.55, heading = 0.0 } |
Where a kneeling kit's model lies while it is used: meters right and forward of the player, and a heading added to theirs. false none. |
Config.Use.parachute |
{ enabled = true, pack = true } |
The parachute item is strapped on with Use and taken off with Use; nothing about it can be done in the air. pack = true shows it on the back. enabled = false makes it an ordinary item. |
Config.Use.shield |
{ enabled = true, wearPerHit = 1 } |
The ballistic shield is raised and put away with Use. wearPerHit is the condition lost per hit on the shield; 0 never wears it. Under sv_entityLockdown the shield is an object only its holder sees, so it stops no other player's shots and does not wear. |
Config.Use.routing, .routeTokenMs |
true, 10000 |
Items whose definition names a client or server handler hand their use to that resource, which has this long to confirm it. |
Config.Use.reactions |
enabled = true |
What reacting items do (binoculars, documents, the vehicle kits, diving gear, fireworks and the rest). Each steps aside when the framework already has a usable callback of the same name; standDownFor = { item = { 'resource' } } names others. repair sets what each vehicle kit restores and how long it takes (floor is the engine health a dead engine is brought up to), diving.oxygen = 600 the seconds in a full tank, documents.imageHosts the hosts a photo may load from. |
Config.Water |
{ enabled = true, seconds = 3, swimSeconds = 10, cooldownMs = 30000, submerged = 0.9 } |
Water ruins items with waterDamage after seconds diving or sitting in a vehicle that is submerged this deep (0 to 1), or after swimSeconds of swimming (false keeps surface swimming harmless). Boats and submarines never count. |
Config.Combine |
enabled = true, joint recipes from each weed strain and rolling paper |
Drag-onto recipes: { a, b, result, count }. |
Config.Combine.strainStress |
{ ['OG Kush'] = -15, ['Purple Haze'] = -18, ['White Widow'] = -20, ['Skunk'] = -16, ['Amnesia Haze'] = -17, ['AK-47'] = -17, ['Cannabis bud'] = -12 } |
The stress a lit joint takes off, by the strain it was rolled from. A strain not listed uses the joint's own status. |
Config.Bags.enabled, .maxWorn |
true, 1 |
Bags, and how many one player may wear. A bag's contents never count toward the body, so a bag is real extra capacity. |
Config.Bags.wornOnly |
true |
A bag is always worn: picking one up puts it on, taking it off sets it down. With false, dropOnTakeOff = false keeps a taken-off bag in the body as an item. |
Config.Bags.dropAhead |
0.45 |
How far in front a taken-off bag is set down; at the feet when something is in the way. |
Config.Bags.anim |
{ enabled = true, on = grab_cash exit, off = grab_cash intro, showAt = 0.5, releaseAt = 0.5 } |
The put-on and take-off clips, and at which share of the clip the bag appears or is released. |
Config.Bags.visible, .reapply |
true, false |
A worn bag shows on the character. reapply = true puts the bag look back when another script changes that clothing slot. |
Config.Bags.propFallback, .prop, .props |
true, 'p_michael_backpack_s', rows per model |
A bag the character cannot show as clothing (every non-freemode ped, or a bag without a look) is drawn as an object on the back. An item picks its object with bagProp. Each row in props is { bone, pos, rot, isPed, order } and may add female offsets, build with instead for older game builds, and carry to hold it in the hand (the suitcase and briefcase rows do). Adjust them with /invpose. |
Config.Containers |
{ enabled = true, maxDepth = 1 } |
Container items (wallets, pouches, ammo boxes). At maxDepth = 1 a container cannot go inside another container, and the check counts what the moved item holds, so a bag holding a wallet cannot be put in a stash, trunk or glovebox. On the ground it can. |
Carrying and the ground#
| Setting | Default | What it does |
|---|---|---|
Config.Player.slots, .maxWeight |
24, 32000 |
The body's slots and weight limit. |
Config.Player.tiers |
{ { ace = 'lri.tier.vip', slots = 30, maxWeight = 45000 } } |
Larger bodies for players holding an ace. The highest value of each kind wins. |
Config.Player.reachDistance |
2.5 |
How far a player may move from an open drop or stash before the panel closes. The server checks the same distance. |
Config.Player.openInVehicle, .openWhileDead, .openWhileCuffed |
true, false, false |
When the inventory can be opened. |
Config.Player.overflowToGround |
false |
true: items a script gives that do not fit go to the ground at the player's feet. |
Config.Grid.enabled |
true |
Items take grid cells by size. false uses plain slot lists. |
Config.Grid.kinds |
player, bag, container, stash, trunk, glovebox all true |
Which containers use the grid. |
Config.Grid.cellsPerSlot, .maxColumns |
2.5, 10 |
How many cells one slot of slots gives, and the widest a grid may be (up to 20). |
Config.Grid.rotateKey, .autoRotate |
'R', true |
The key that turns an item while dragging, and whether an item is turned automatically when it only fits that way. |
Config.Grid.sizes, .weapons, .melee |
sizes tiny/small 1x1, medium 2x2, large 3x3; pistol 2x1, rifle 4x2 and so on |
Cell sizes by item size and weapon group. An item's own grid wins. |
Config.Grid.zones |
{ enabled = true, main = 'items', width = 8, areas = { keys = 6x2, weapons = 8x5, clothes = 8x4 } } |
Separate grid areas inside the body for keys, weapons and clothes. |
Config.Load |
enabled = false, { at = 0.85, maxMove = 2.0 }, { at = 0.95, maxMove = 1.0 } |
Weight slows the player, measured against the body and worn bags together: from 85% full no sprint, from 95% walk only. |
Config.Strength.enabled |
true |
Carry strength. Walking with at least minLoad (half) of the carry limit earns XP (xpPerMeter = 0.1, up to hourlyCap = 600 an hour). Time in a vehicle, dead, down or cuffed, and moves faster than maxSpeed = 10.0 m/s, earn nothing. Admins change it in the panel's Capacity tab. |
Config.Strength.levels |
250 XP: +2 kg; 3000: +4 kg and 1 row; 6000: +6 kg, 1 row; 10000: +8 kg, 2 rows; 15000: +10 kg, 2 rows | The total bonus of each level. Without the grid a row is slotsPerRow = 5 slots. |
Config.Strength.notify, .notifyEvery |
true, 100 |
A toast every this many XP. |
Config.Drops.enabled, .slots |
true, 12 |
Ground piles and their slot count (piles have no weight limit). |
Config.Drops.mergeDistance |
1.5 |
Two drops closer than this share one pile. 0 gives every drop its own. |
Config.Drops.render |
'prop' |
'prop' draws objects; 'marker' draws a chevron and streams nothing. |
Config.Drops.model, .multiModel, .models |
'prop_paper_bag_01', 'ng_proc_box_01a', a model per category |
The pile object by category for items without their own dropModel, and for a mixed pile. |
Config.Drops.scatter |
{ enabled = true, max = 4, radius = 0.35 } |
A mixed pile is drawn as the items themselves in a small ring. |
Config.Drops.peds |
true |
A pile of one item with a dropPed lies as that animal. |
Config.Drops.weaponLooks |
10 |
At most this many dropped guns are drawn with their finish and parts at once. |
Config.Drops.drawDistance, .openDistance |
30.0, 1.6 |
Where a pile appears, and where E opens it. |
Config.Drops.gatherRadius, .gatherMax |
2.5, 8 |
The inventory key or E at a pile lists every pile within this radius (never more than the reach), nearest first, up to this many. false or 1 shows only the nearest. |
Config.Drops.expireMs |
1800000 |
A pile nobody touched for this long is removed and logged. A pile holding a weapon or evidence is never removed this way. 0 never. |
Config.Drops.persist |
false |
true keeps piles across a restart. Needs saved storage (not 'none') with the modstate column. The column is added at start; if the database user cannot add it, the console prints the exact ALTER TABLE to run. |
Config.Drops.quickPickup, .holdMs |
true, 450 |
Holding E this long takes the whole nearest pile (not in a vehicle). |
Config.Drops.sounds |
pickup, money and weapon frontend sounds |
Played when the hand reaches the pile. A row set to false is silent; false turns all off. |
Config.Drops.throw |
enabled = true, four weight tiers up to 25 kg |
Right-click > Throw. Heavier items fly slower; the heaviest tier is an underhand drop. |
Config.Drops.place |
enabled = true, maxPerPlayer = 10, expireMs = 7200000 |
Right-click > Place precisely. Placed items follow the same expiry rule as piles. |
Config.Drops.place.storage |
{ enabled = true, maxPerOwner = 3, openDistance = 2.0, drawDistance = 60.0, target = 'auto' } |
Placed storage crates. Only the player who placed one (or an admin) can pick it up. |
Weapons#
| Setting | Default | What it does |
|---|---|---|
Config.Weapons.wear |
pistol 0.05, smg 0.03, rifle 0.025, shotgun 0.1, sniper 0.1, mg 0.02, stungun 0.1, heavy 0.5 |
Condition lost per shot, by weapon group. |
Config.Weapons.meleeWear, .meleeEveryMs |
0.1, 400 |
Condition lost per melee hit, counted at most once per this many ms. |
Config.Weapons.deleteBroken |
false |
true removes a gun that reaches 0 condition; otherwise it stays, broken. |
Config.Weapons.repairItems |
{ repairkit_weapon = 100, cleaningkit = 10 } |
Kits and the condition they restore. |
Config.Weapons.serials, .serialReserved |
true, { 'POL', 'EMS' } |
Serial numbers on firearms, and prefixes a minted serial never starts with. |
Config.Weapons.mdt |
'auto' |
Registers each serial with ps-mdt (through its CreateWeaponInfo export) when it runs, or name another resource that has that export. false never does. |
Config.Weapons.attachments |
true |
Weapon parts. false stops fitting and hides the gunsmith bench prompts, blips and craft-panel button; parts already fitted can still be taken off from the item's menu. |
Config.Weapons.benchXp |
{ track = 'gunsmithing', perPart = 3, inventory = false } |
XP for the first fit of each part on each gun at a gunsmith bench, through the craft progress tracks (needs the craft module with progress on, and counts toward its hourly cap). inventory = true also pays for "Modify in 3D" from the inventory. |
Config.Weapons.drawAnim |
draw and holster clips for pistol, smg, rifle, shotgun, stungun and melee; a police style for police and sheriff |
Per group, and per job in jobs. |
Config.Weapons.fireOnly |
{ petrolcan = true } |
Weapon groups that cannot be aimed in third person, so the jerry can pours without a gun-like aim pose. false turns it off. |
Config.Weapons.pourSeconds |
{ petrolcan = 20 } |
Seconds of pouring that empty a full can, by group. GTA's own rate is never slowed down. A group set to false pours at GTA's rate; false turns it off. |
Config.Weapons.clip |
{ maxFactor = 4, hardMax = 250, sizes = {}, learn = 2 } |
Extended and drum clip sizes. sizes pins a size per part; otherwise data/generated/clipsizes.lua, then a size measured by learn players on different licenses, else the base size. Never more than base x maxFactor or hardMax. /invclips lists learned sizes. |
Config.Weapons.magazines |
{ enabled = false, allowLoose = true } |
Magazine items. allowLoose still lets loose rounds load a gun. |
Config.Weapons.jam |
enabled = true, below = 60, maxChance = 0.02, curve = 1.5, clearMs = 1800, cleanShots = 150, kits = { cleaningkit = true } |
Guns below 60 condition can jam, more often the lower they go (up to 2% per shot). A cleaning kit gives cleanShots jam-free shots. groups lists the weapon groups that jam. |
Config.Weapons.reload |
{ engineAnim = true, auto = 'instant', autoEveryMs = 1500, noAutoReload = false, noAutoSwap = true } |
auto = 'instant' reloads an empty gun from carried ammo by itself; 'onFire' only when the player pulls the trigger; anything else never. |
Config.Weapons.pickups |
{ suppress = true, vehicleRewards = false } |
Blocks GTA's weapon and ammo pickups, and the weapons police cars and fire trucks hand out. This does not stop other scripts from giving weapons. |
Config.Weapons.jobGates |
{} |
Weapon item name to { job = grade }: who may draw it. Overrides the item's own jobs; false removes a gate. |
Config.Weapons.repairShop |
enabled = false, two counters, pricePerPoint = 5, minimum = 50, pay = { 'cash', 'bank' } |
Paid gun repair counters. |
Config.Weapons.work |
enabled = true, moveTolerance = 1.0, and an ms for each kind: fit = { ms = 2500 }, unfit 2000, repair 5000, clean 4000, counter 6000 |
Fitting or removing a part, kit repairs and cleaning, and the paid counter are timed with a bar, a clip and a tool. The part or kit is used only when the bar finishes; walking off, the stop key, a vehicle or death cancels it. ms = 0, enabled = false or work = false makes it instant. |
Config.Weapons.pumpFill |
{ enabled = true, distance = 3.0, fillMs = 4000, pay = { 'cash', 'bank' }, items = { weapon_petrolcan = 100 } } |
Right-click the jerry can next to a gas pump to fill it. A full fill costs 100, a part fill its share. Works at the map pumps of the listed models. |
Config.Forensics |
enabled = true, halfMs = 6000, fullMs = 9000, restoreMs = 12000, jobs = { 'police', 'sheriff' }, drillWear = 10 |
Filing a serial off (police of these jobs can restore it) or grinding it off for good. drillWear is the condition the tool loses per job. fullAnim, restoreAnim and sounds set the clips and sounds. |
Config.Slings.enabled, .source |
true, 'body' |
Carried weapons shown on the body. 'body' shows every carried weapon; 'hotbar' only those on hotbar keys. |
Config.Slings.range, .maxObjects |
60.0, 48 |
How far other players' weapons are drawn, and the object budget (gun, magazine and each part count; up to 256), nearest players first. |
Config.Slings.hideInVehicle, .showOnBikes |
true, true |
Slung weapons hide in vehicles but stay visible on motorcycles and bicycles. |
Config.Slings.hideOwnFirstPerson |
true |
Hides your own slung weapons in first person: true, false, or per spot. |
Config.Slings.showTint |
true |
A slung gun with a finish is drawn as a real weapon object so the finish shows. |
Config.Slings.max, .place, .weapons, .jobs, .byWeapon, .spots |
back 3, backMelee 2, thigh 1, thighL 1, hip 2, chest 1, front 1, total 8 | How many weapons each spot holds, which spot a group, a weapon or a job's weapons use, and the bone rows of each spot. spots.female rows may be added. Adjust positions with /invpose. |
Disposal#
| Setting | Default | What it does |
|---|---|---|
Config.Disposal.enabled |
true |
Weapons and evidence can only be destroyed at a disposal point. Elsewhere the Destroy sheet names the nearest point with a Set GPS button. They also cannot be dumped in bins. |
Config.Disposal.timeMs |
2500 |
How long destroying takes (0.5 to 15 s). It is canceled if the player is cuffed, downed, killed, gets into a vehicle or walks off the point meanwhile. |
Config.Disposal.weaponKinds |
{ firearm = true, melee = true, thrown = true } |
Which weapons need a point: firearm (items with a magazine), thrown (grenades and other thrown weapons), melee (every other weapon). |
Config.Disposal.exempt |
{ 'weapon_petrolcan', 'weapon_fireextinguisher', 'weapon_ball', 'weapon_snowball', 'weapon_flare', 'flashlight', 'weapon_flashlight', 'weapon_metaldetector' } |
Items that can be destroyed anywhere. |
Config.Disposal.marker |
true |
A ring on the ground and a help text at each point. false for hidden points. |
Config.Disposal.points |
Los Santos Foundry (weapons and evidence), Rogers Salvage & Scrap (weapons) | Each point: id, label, coords, radius, blip (false hides it), kinds = { weapon, evidence } and jobs (nil for anyone). |
Starter kit#
| Setting | Default | What it does |
|---|---|---|
Config.StarterKit.enabled |
false |
Gives items once to each new character. A character whose inventory already held items in the framework's own inventory column is skipped (the console says so once). |
Config.StarterKit.items |
{ { 'phone', 1 }, { 'water', 2 }, { 'burger', 2 }, { 'bandage', 2 } } |
The kit. Rows are { item, count } and may add metadata. |
Config.StarterKit.standalone |
true |
On a standalone server every new character gets standaloneItems once, even with enabled = false. |
Config.StarterKit.standaloneItems |
{ { 'cash', 500 } } |
What standalone characters start with. |
Modules#
| Setting | Default | What it does |
|---|---|---|
Config.Modules |
shop, stash, craft, vending, dumpster, gunbench, cache all true |
Each optional system's switch. A module that is off runs no threads, events or exports. Restart the resource after a change. |
Config.ModuleSettings.shop.target, .openDistance |
'auto', 2.5 |
How shop counters open. |
Config.ModuleSettings.shop.currency |
'auto' |
'auto' spends the cash item on ox_core and standalone and the framework's cash account elsewhere. 'item' always spends moneyItem = 'cash'; 'account' always spends account = 'cash'. |
Config.ModuleSettings.shop.pay, .bankAccount |
{ 'cash' }, 'bank' |
The payment methods offered; 'bank' pays from this account. |
Config.ModuleSettings.shop.sellRate |
0.4 |
What a shop with sellBack = true pays, as a share of the item's value. 0 refuses all buy-backs. |
Config.ModuleSettings.shop.restockMs, .restockMode |
900000, 'topup' |
How often stock comes back (0 never, so a sold-out shop stays empty until a restart), and how: 'topup' refills each row to its count, 'reset' clears the shelf and lays it out fresh. A shop may set its own restockMode. lowStock = 0.2 is the share below which a row shows as low; restockNotice = true tells players looking at the shop when it restocks. |
Config.ModuleSettings.shop.shopkeepers |
true, shopkeeperDistance = 30.0 |
Clerks behind the counters. |
Config.ModuleSettings.shop.fence |
{ enabled = true } |
Fence, pawn and clothes buy-back counters. false leaves them all out. |
Config.ModuleSettings.shop.runtime |
{ enabled = true } |
The RegisterShop, CreateShop and OpenShop exports for other resources. |
Config.ModuleSettings.shop.showRequires |
true |
Shows a row's required item as a lock note on the shelf. |
Config.ModuleSettings.vending |
target = 'auto', openDistance = 1.5, pay = { 'cash' } |
Vending machines by model (models) and their stock lists (stock). |
Config.ModuleSettings.dumpster.chance, .mode, .maxItems |
80, 'independent', 3 |
The percent chance a bin holds anything, how rows roll ('independent', 'single' or 'weighted', where the chances must add up to 100), and the most items a bin gives. |
Config.ModuleSettings.dumpster.loot, .lootByTag |
plain bins: scrap and materials; dumpster and recycle tags: own lists |
What bins give. Dumpsters and recycling bins use their tag's list and are the only bins that can give blueprints (1% per blueprint row). An empty tag list uses loot. |
Config.ModuleSettings.dumpster.searchMs, .cooldownMs, .refillMs |
3500, 45000, 1800000 |
Search time, the wait between two different bins, and when a searched bin refills. |
Config.ModuleSettings.dumpster.unlisted |
false |
true also lets players search bins that are not in the shipped bin map (up to unlistedMax = 300 in memory and unlistedPerHour = 3 per player). |
Config.ModuleSettings.cache |
target = 'auto', openMs = 1200, expireDays = 14, bucketed = true |
Hiding spots in postboxes, letterboxes and newspaper boxes (sets; electrical boxes ship off). Contents of a spot nobody has put in or taken from for expireDays are removed; this needs the modstate column. |
Config.ModuleSettings.craft.target, .openDistance |
'auto', 2.5 |
How benches open. |
Config.ModuleSettings.craft.maxBatch, .defaultTimeMs, .overflow |
10, 3000, true |
Batch size, the time of a recipe without its own, and whether output that does not fit goes to the ground. |
Config.ModuleSettings.craft.blips, .blipShortRange |
true, false |
Bench blips; false shows them at the minimap edge from anywhere, true only nearby. |
Config.ModuleSettings.craft.handRecipes |
true |
Recipes marked hand = true are crafted from the Workbench tab anywhere. false makes every recipe need its bench. |
Config.ModuleSettings.craft.showLocked |
true |
A bench limited to another job shows grayed with the reason in the Workbench tab; gang and group benches stay hidden. |
Config.ModuleSettings.craft.queue |
enabled = true, maxJobs = 5, parallel = false, offline = 'pause', deliver = 'tray', refundTo = 'auto', traySlots = 24 |
Queued crafting. Materials and tools go into the bench's escrow at once and are used per batch; canceling refunds them. parallel = true runs one job per bench at once instead of one at a time. offline = 'run' keeps the queue going while the player is away; 'cancel' refunds their jobs to the tray when they log out. Output goes to the bench's tray ('pockets' to the player); refunds go to the pockets at a bench and to the tray elsewhere. Before switching the queue off, let players collect their trays: while it is off, escrow and tray contents stay saved but out of reach. |
Config.ModuleSettings.craft.progress |
enabled = true, tracks crafting and gunsmithing, maxLevel = 20, hourlyCap = 600 |
Crafting levels. Each level makes crafting faster (speedPerLevel) and more likely to succeed (chancePerLevel); recipes can require a level. hourlyCap = false removes the cap. |
Config.ModuleSettings.gunbench |
target = 'auto', openDistance = 2.0, blips = true, benchOnly = false, fromInventory = true |
The 3D gunsmith bench. benchOnly = true allows fitting and removing parts only at a bench; fromInventory offers "Modify in 3D" in the inventory. |
Config.Licences |
enabled = false, distance = 2.0, target = 'prompt', one weapon license point for 5000 |
Counters where players buy a license through the framework's license system (needs the shop module for payment). |
Admin and debug#
| Setting | Default | What it does |
|---|---|---|
Config.Admin.ace, .labAce |
'lri.admin', 'lri.lab' |
The root aces. Panel parts are aces under the root (see Aces). |
Config.Admin.panel, .panelCommand, .panelKey |
true, 'invadmin', '' |
The admin panel, its command and its default key (unbound). |
Config.Admin.viewCommand, .confiscateCommand, .returnCommand |
'invview', 'invconfiscate', 'invreturn' |
The admin commands. |
Config.Admin.tellTarget |
true |
A player whose inventory an admin opens in edit mode is told once. |
Config.Admin.maxGive |
1000000 |
The largest amount one admin give may create. |
Config.Admin.confiscateWorn |
false |
true also takes worn clothing on confiscation. |
Config.Admin.minting |
{ spikeFactor = 5, minUnits = 50, maxHours = 168, announce = true, notify = true, webhook = true } |
Flags a resource that creates far more items in an hour than usual: at least minUnits and more than spikeFactor times its median over its active hours (it needs at least 6 of them). Item creation with no named resource and this inventory's own gives are never flagged. notify alerts online admins with the economy ace; webhook posts to your webhook. It reads the log store, so it needs the store on with the creation channel kept (both are the default). |
Config.Admin.kits |
{ starter = { label = 'Starter pack', items = … } } |
Your own kits, listed first under Items > Kits (see Kits). |
Config.Admin.lab |
enabled = 'debug', allowWithPlayers = false |
The test lab. 'debug' follows Config.Debug.commands; true turns it on regardless. With other players online it refuses to run unless allowWithPlayers = true. |
Config.Poses |
{ enabled = true, command = 'invpose', listCommand = 'invposes', key = '' } |
The pose tool for bag, sling and hand object positions. Needs the pose ace. |
Config.Premium |
{ enabled = false, scope = 'account', identifier = 'license', rail = true, command = 'invpremium', ace = 'lri.admin.premium' } |
Premium coins as a shop currency. scope = 'character' keeps a balance per character instead of per account. rail shows the Coins row. |
Config.Logs.creation, .destruction, .transfers |
true, true, false |
Console lines (and webhook posts) for items that appear from nothing, items that vanish, and every hand-over and drop. |
Config.Logs.shop, .craft, .premium |
false, true, true |
The other channels. Admin actions are always printed to the console and never posted to the webhook, whatever Config.Logs.admin says. |
Config.Logs.store |
'auto' |
The searchable log store behind the admin Logs tab: 'auto', 'mysql', 'kvp', 'memory' or false. storeChannels picks which of the creation, destruction, transfers, shop and craft channels it keeps (admin and premium lines are always kept), keepDays = 30 how long. |
| Webhook | none | Set your own webhook address in server.cfg as set lri_webhook "https://...". It has to be an https address. Nothing is sent anywhere until it is set. A webhook address in config.lua is still used when the convar is empty, with a console warning, because every player can read it. |
Config.Debug.console |
false |
Extra console lines. |
Config.Debug.commands |
false |
The test commands (invitem, invset, invfill, invpile, invmoney, invopen and the rest, listed by /invdebughelp), plus /invhere and /invpics. Anyone with Config.Debug.ace can then give themselves any item and open any inventory, so keep it off on a live server; the resource warns at start while it is on. |
Config.Debug.ace |
'lri.admin' |
The ace for the debug commands. '' uses Config.Admin.ace. Debug mode never opens the admin panel to anyone without its own aces. |
Config.Debug.command |
'invdebug' |
Server console only; prints what the server is holding. |
Config.Debug.thumbs |
{ command = 'invthumbs', size = 256, quality = 0.92, endpoint = '', height = 40.0, settleMs = 300, fov = 30.0 } |
/invthumbs takes a picture of every item with a model of its own and saves it as web/images/<item>.webp. Needs screenshot-basic and the config ace. Shipped pictures are never overwritten unless you add own. Restart the resource afterwards. |
Clothing#
| Setting | Default | What it does |
|---|---|---|
Config.Clothing.asItems |
true |
Clothing as items, with the Clothes tab. Wardrobes and outfits need it. |
Config.Clothing.gloves |
false |
The gloves slot. While gloves are worn it owns component 3 (arms). |
Config.Clothing.anims |
a put-on clip per area, with off clips for some |
The clips for putting a piece on and taking it off. off is a clip of the same dictionary or { dict, clip }. |
Config.Clothing.appearance |
'auto' |
Where worn clothes are read from and saved to: the first running of ncore_character, illenium-appearance, fivem-appearance, qb-clothing and skinchanger (esx_skin). Name one, or false for none. No appearance resource is required. |
Config.Clothing.seed |
true |
Fills a player's worn clothing items from their saved skin on first login. |
Config.Clothing.saveEvent |
false |
The server event a save script listens to, for fivem-appearance, which keeps no saved skin of its own. |
Config.Clothing.adoptExternal |
false |
true turns clothes changed inside the appearance resource into worn items (worth nothing at a shop). |
Config.Clothing.countWorn, .clearWorn |
false, false |
Whether worn pieces count in item exports, and whether ClearInventory also removes them. |
Config.Clothing.stealable |
every area true |
Which worn areas can be taken in a search. |
Config.Clothing.outfits, .outfitPartial |
10, true |
Outfits each player can save at a wardrobe, and whether an outfit with missing pieces is put on partly. |
Config.Clothing.resale |
0.3 |
A piece bought in a shop is worth floor(price x resale) when sold back at Binco or the clothes buy-back counter. |
Config.Clothing.bagItem |
'bag_duffel' |
The item a bag bought at an ncore_character clothing store becomes. While it has its own look the store sells only the bag items' own looks; a bag drawn as its own object cannot be one; false sells no bags there. |
Config.Clothing.adminLooks |
a look per area and sex | The look of each piece an admin gives. |
Config.Clothing.addonCollections |
{} |
Addon clothing collections and how many drawables each has: { collection_name = { drawables = n } }. |
Armor#
| Setting | Default | What it does |
|---|---|---|
Config.Armour.enabled, .pollMs |
true, 2000 |
Vests as items, and how often worn armor is read back into the vest. Armor is also saved at its current value when the player leaves. |
Config.Armour.visible |
true |
A worn vest shows on the character. |
Config.Armour.foreign |
'replace' |
A vest put on replaces armor the player already has from another resource. 'refuse' refuses the vest until that armor runs out. |
Config.Armour.propFallback |
{ model = 'prop_bodyarmour_02', bone = 'SKEL_Spine3', pos = { -0.12, 0.0, 0.0 }, rot = { 0.0, 90.0, 180.0 }, isPed = true, order = 1 } |
A vest the character cannot show on component 9 (every non-freemode ped, or a vest with no look) is drawn as this object, seen by everyone. false draws nothing and tells the wearer once. |
Config.Armour.anims |
on 3500 ms, off 2500 ms, plate 3000 ms |
Putting a vest on, taking it off and fitting a plate play these clips under a bar; the change lands when the bar ends and the stop key cancels it. Dragging the vest to a slot stays instant. false makes all three instant, on = false only that one. |
Hints#
Every key hint of the inventory (the stop key, E prompts, trade and search requests, the item in your hand, camera views, placing and throwing, first-time tips) goes through one owner, so two hints never fight over GTA's single help box. The key caps show the key each player actually bound.
| Setting | Default | What it does |
|---|---|---|
Config.Hints.enabled |
true |
false draws no hint. E, G, Y and U still work. |
Config.Hints.style |
'nui' |
'nui': key-cap hints on the inventory page. 'native': GTA's help box. |
Config.Hints.gamepad |
'native' |
With a controller, GTA's help box draws the pad buttons. 'nui' keeps the page (experimental). |
Config.Hints.position |
'bottom' |
'bottom' (above the progress card and hotbar), 'left' or 'right' (vertically centered). A request shown while the panel is open goes to the top. |
Config.Hints.graceMs |
150 |
How long a hint stays after its last frame (50 to 1000). |
Config.Hints.maxRows |
3 |
Most lines at once (1 to 6). Placing, throwing and the pose tool may use 6. |
Config.Hints.keyRefreshMs |
1000 |
How often a shown key cap is read again, so a rebind shows within that time (250 to 10000). |
Config.Hints.sound |
true |
GTA's INFO beep when a request or a tip first appears. The player's Sounds setting also mutes it. |
Config.Hints.hideOnFocus |
'nokeep' |
'nokeep': a UI that keeps game input (most phones) leaves hints up. 'any': every focused UI hides them. A request always stays. |
Demo#
| Setting | Default | What it does |
|---|---|---|
Config.Admin.demo.enabled |
true |
The Demo tab of the admin panel (needs the give ace). |
Config.Admin.demo.nextKey, .prevKey, .cueKey |
'PAGEDOWN', 'PAGEUP', 'HOME' |
Presenter keys: next point, previous point, the point's action. |
Config.Admin.demo.departKey, .peekKey |
'RETURN', 'END' |
Enter departs from a stop's briefing; holding End shows the script during a stop. |
Config.Admin.demo.introKey |
'INSERT' |
Shows and hides the video intro of the current stop. |
Config.Admin.demo.calloutKey |
'DELETE' |
The next feature callout at the current point. At the last point of the finale it shows the closing card; pressed again it hides it. |
Config.Admin.demo.cardKey, .clearKey |
'6', '7' |
Shows the current stop's title card and keeps it up; fades out whatever overlay is on screen so the action can be filmed. |
Config.Admin.demo.travel |
'switch' |
'switch' travels with the GTA sky camera and falls back to a fade; 'fade' always fades. |
Config.Admin.demo.clock, .introCam, .fresh |
true, true, true |
Defaults of the tab's options: each stop's time of day, the arrival camera, and a fresh pocket kit at each stop. |
Config.Admin.demo.titleCard |
false |
Default of the arrival title card option. Off, the card shows only on the card key. |
Config.Admin.demo.autoSkins, .introOrbit |
true, true |
Defaults of the fitting-character-at-every-stop option and of the orbiting intro camera. |
Config.Admin.demo.callouts |
false |
true: callouts also fire on their own when their container opens or their cue runs. Off, only the callout key shows them. |
Config.Admin.demo.timeSync |
'auto' |
With qb-weathersync running and the time-of-day option on, it is set to each stop's time and weather for the whole server, and put back when the tour ends. false never touches it; without it the time and weather are set on the presenter's game only. |
Config.Admin.demo.weather |
'EXTRASUNNY' |
The weather of a stop that sets none of its own. |
Config.Admin.demo.mpSex |
'm' |
Body of the Binco model at the Clothing as Items stop when the presenter does not play a freemode character ('m' or 'f'). |
All presenter keys are key mappings, so players can rebind them in FiveM's key settings.
Data files#
These files hold the world content. Each one documents its own fields at the top.
modules/shop/shops.lua:
- A shop has
id,label,locations(each counter gets its own shelf),blip,jobandgradeorgroups,stockrows{ item, price, count }(count per counter),categoriesandped(the clerks, one per counter). - Stock rows may add
grade,groups,requires = { item, count, take },metadataandcategory. A clothing row may addlabeland alook. sellBack = truemakes a shop buy back atvalue x Config.ModuleSettings.shop.sellRate;stockOnly = truelimits that to items the shop sells itself. The hardware store and Binco ship with both.type = 'fence'or'pawn'makes a counter that only buys (buys,illegalOnly,capacity,hours). A fence pays black money, a pawn shop cash.openBy = 'export'makes a counter with no locations that onlyOpenShopopens, likepharmacyandclothing_buyback.blip.yieldToandped.yieldToname a resource that marks the same store; while it runs, the shop draws no blip and its clerk stands down. Binco yields to ncore_character.enabled = falsekeeps a shop as a template that is not built.
data/stashes.lua:
- A stash has
id,label,coords(one vector3 or a list),slots,maxWeight(grams) andowner:'shared'(one box),'player'(one box per player) or'job'(one box per job). jobwithgrade,jobs = { job = grade }andgroups = { name = grade }are one gate (groupsis read first, thenjobs, thenjob). A field that is set but names no usable job or gang skips the stash with a console error instead of opening it to everyone. A'shared'stash with no gate is public.accepts,rejectsandcapslimit what goes in;takeGradeis the rank needed to take items out.cold = 'fridge'or'freezer'makes it cold storage (the two Yellow Jack stashes ship that way).wardrobe = trueadds the Outfits button and needsConfig.Clothing.asItems. The shippedwardrobe_storestands at eight clothing stores, one box per player.lock = trueopens it only for a player carrying a stash key cut for this id.enabled = falsekeeps an entry as an example.
modules/craft/benches.lua:
- A bench has
id,label,blip,track(the progress track),locationsandrecipes. - A location is a
vector3, avector4(the heading is ignored) or{ coords, prop = { model, heading } }. With a prop the game draws the bench object within 60 m;prop = trueuses the default model, and a model the game build lacks falls back toprop_tool_bench02. - A recipe has
item,count,time,costs,tools(withwear), and may addchance,level,blueprintwithblueprintMode, andhand = trueto craft it anywhere.
4. For script authors#
Every export is called as exports.ncore_inventory:Name(...). Exports are server side unless the heading says client. A call that is refused returns false (or nil, or 0 for a count) plus a reason string; most reasons are keys from locales/en.lua, where the sentence the player would see lives. Item names, stash ids and every other id are the ones in your data files.
Inventory ids and slot numbers#
inv in the tables below is a player's server id. With Config.Compat.containerTargets = true (the default) the item exports also take:
- a registered stash id (
'police_locker'or'stash-police_locker'), or{ type = 'stash', id = 'police_locker', owner = ... }for a per-player or per-job stash - a vehicle part:
'trunkABC123','trunk-ABC123','gloveABC123','glovebox-ABC123', or{ type = 'trunk', id = 'ABC123' }; it is loaded from its spawned vehicle, and with no vehicle carrying that plate the call is refused withvehicle_not_loaded - the id of any loaded container
A stash that is not in memory yet is loaded first; the call waits up to Config.Compat.loadMs (3000) for it. Container kinds listed in Config.Compat.refuseKinds (worn clothing, crafting queues, trade escrow, admin views, shop and bench fixtures and similar) never answer to an id. When a call names something nothing answers to, the console says so once per resource and id form. UseItem takes a player only, and SetSlotMetadata takes the inventory's own container id.
For a player, "what they carry" is the pockets, the worn bags and every container nested in them. Slot numbers from 1 to the pocket slot count are the pockets; higher numbers continue through the worn bags and their nested containers in a fixed order. GetSlot, the slot argument of RemoveItem, SetMetadata, RepairWeapon and SetDurability read slot numbers this way. In Search and the GetSlot*WithItem calls a row from a bag comes back with slot = nil and container = <id>; GetSlot keeps the number you asked for and adds container.
Metadata filters: a string is read as { type = value }. Without strict a stack matches when it carries every key you pass with the same value. With strict it must match exactly, apart from fields the inventory stamps itself (such as uid) that you did not pass.
Item exports#
| Export | Returns | Notes |
|---|---|---|
AddItem(inv, name, count, metadata, slot) |
added, reason |
Partial adds are reported, not rolled back: ask CanCarry first for all or nothing. The fourth argument may also be a slot number (AddItem(src, name, count, slot, metadata)): a table there is metadata, a number is a slot. A named slot is a preference; what does not fit there goes wherever it fits. For a player, what does not fit the pockets goes into worn bags, and with Config.Player.overflowToGround = true the rest lands at their feet. With serials on, a gun gets a serial and the character's name as its registered owner unless metadata.registered = false; ID items are filled from the character (Config.Identity). |
AddItemOrDrop(inv, name, count, metadata, slot) |
added, reason, dropped, pileId |
Like AddItem, and what does not fit a player is put on the ground at their feet. |
RemoveItem(inv, name, count, metadata, slot) |
removed, reason |
The named slot is emptied first, then the rest is taken from everything the player carries. With metadata, the match is strict unless the seventh argument is false. Short: 'not_enough'. |
GetItemCount(inv, name, metadata, strict) |
number | Everything carried, plus worn clothing with Config.Clothing.countWorn = true. |
Search(inv, query, name, metadata) |
count or rows | query is 'count' (or 2) or 'slots' (or 1). name may be a list; the answer is then keyed by the names exactly as you passed them. The count path always returns a number, 0 for a name nobody holds or nobody knows. Rows are { name, label, count, slot, weight, metadata, stack }; worn clothing rows have worn = true. |
GetSlot(inv, slot) |
row or nil |
|
GetSlotWithItem(inv, name, metadata, strict) |
row or nil |
The first matching stack. |
GetSlotsWithItem(inv, name, metadata, strict) |
list of rows | |
GetEmptySlot(inv) |
slot or nil |
|
SetItem(inv, name, count, metadata) |
true or false, reason |
count is the total the inventory should end up with. |
CanCarry(inv, name, count, metadata) |
true or false, reason |
Pockets first, then worn bags. Reasons include over_weight, no_free_slot and unknown_item. |
CanCarryAmount(inv, name, metadata) |
number | How many units would fit. |
CanCarryWeight(inv, grams) |
fits, freeGrams |
|
CanSwapItem(inv, first, firstCount, test, testCount) |
true or false, reason |
Whether test fits once firstCount of first is gone. No metadata argument. |
UseItem(src, name, slot) |
ok, reason |
Uses one unit exactly as a left click would, with the same events and refusals. |
SetSlotMetadata(src, containerId, slot, metadata) |
true or false, reason |
Replaces the stack's metadata. A container item keeps the link to its contents; fields only the server may write keep their stored value; uid, bornAt and expiresAt are kept when you leave them out. A gun's ammo is capped at what its magazine holds. |
ClearInventory(inv, keep) |
true or false, reason |
keep is an item name or a list of names to leave. On a player it clears the pockets, the worn bags and everything nested in them (worn clothing too with Config.Clothing.clearWorn = true). With Config.Death.enabled = true, a call from a resource in Config.Death.wipe.by ('auto' is qb-ambulancejob, esx_ambulancejob and qbx_ambulancejob) follows the death keep and drop rules instead. |
GetInventory(inv) |
{ body, bags } or nil |
Snapshots of the pockets and each worn bag. |
GetContainer(id) |
snapshot or nil |
Any loaded container, by the inventory's own id. |
CreateDrop(coords, items, bucket) |
pileId or nil, reason |
items is { { name, count, metadata } } (item, amount and meta are read too). When none of the items could be added it leaves no empty pile and returns the first refusal (unknown_item, bad_count, inventory_full and so on). |
Items(name) |
definition or all definitions | Also a client export. |
RegisterItem(name, definition) |
ok, why |
See section 2. |
SetContainerProperties(item, { slots, maxWeight, whitelist, blacklist }) |
true or false, why |
Makes an item a container item, or changes its size and its allowed or refused items. Weapons, clothing, vests, armor plates, portioned food, bundles and items with uses are refused. |
Modules() |
list | { name, description, enabled, started } for every module. |
Search, HasItem, GetItemByName, GetItemsByName and the qb-inventory GetItemCount leave out a door key the player may not use: one cut for another job or a higher grade (IssueKey with job and grade), or one cut before the door was re-keyed with RevokeKeys. Door scripts that check keys through those calls (ox_doorlock, qb-doorlock) then refuse such a key.
Stashes, piles and opening#
| Export | Returns | Notes |
|---|---|---|
RegisterStash(id, label, slots, maxWeight, owner, groups, coords, options) |
true or false, reason |
id is 1 to 48 letters, digits, _, - or .. owner = true gives every player their own copy; a string or number is one fixed owner; nil is one shared stash. groups is 'police', { 'police', 'ambulance' } or { police = 2 } (lowest grade). coords is a vector3 or a list of them; with coords the player must stand within reach. options: lock = true (only a player carrying a key from IssueKey(src, 'stash', id) opens it), takeGrade (lowest grade that may take out, needs groups), accepts, rejects, caps, grid = { w, h }, cold, wardrobe = true, bucket. A stash defined in data/stashes.lua cannot be taken over. |
CreateTemporaryStash({ label, slots, maxWeight, groups, coords, options, items }) |
id or nil, reason |
Never saved. An empty, unused one is let go after Config.Stashes.temporaryIdleMs (30 minutes). Items that do not fit are not created, and the console says how many. |
OpenStash(src, id, owner) |
containerId or nil, reason |
Checks the stash's groups, its distance (when it has coords) and the routing bucket. May answer containerId, 'stash_loading' while it loads; it opens when ready. |
ForceOpenInventory(src, kind, data) |
id or nil, reason |
kind is 'stash' (data is the id or { id, owner }), 'player' (runs SearchPlayer), 'trunk', 'glovebox', 'drop' or 'policeevidence'. |
GetStashItems(id, owner) |
rows or nil, reason |
{ name, label, count, slot, metadata, weight }. |
ClearStash(id, owner) |
true or false, reason |
|
StashList() |
list | Exists while the stash module runs. |
SetColdStorage(stashId, mode) |
true or false, reason |
'fridge', 'freezer' (rates from Config.Cold.rates), a number from 0 to 1, false for none, nil for the stash's own setting. A stash named in Config.Cold.stashes keeps that value. |
IsColdStorage(containerOrStashId) |
mode or nil |
|
OpenLoot(src, id, loot, opts) |
true, containerId or false, reason |
A loot container rolled from loot = { mode, chance, maxItems, loot = { { item, min, max, chance, metadata } } } (mode is 'independent', 'single' or 'weighted'; a weighted table adds up to 100). opts: label, slots (10), maxWeight (50000), coords, distance (2.5), refillMs (30 minutes), takeOnly (true), bucket. |
CustomDrop(label, items, coords, slots, maxWeight, bucket) |
pileId, info or nil, reason, info |
A labeled pile. A seventh (model) argument is ignored: the pile's look comes from what it holds. |
CreateDropFromPlayer(src) |
pileId, info or nil, reason, info |
Puts the player's pocket stacks on the ground where they stand; protected stacks stay and are listed in info.refused. |
RemoveInventory(id) |
true or false, reason |
Unloads a stash (after saving it) or deletes a ground pile. |
SwapSlots(fromInv, toInv, fromSlot, toSlot) |
true or false, reason |
Moves through the same rules and hooks as a drag. |
Client: OpenStash(id) asks the server to open a stash. A stash that is not per-player and has no coords and no groups is opened by a server script only, unless Config.Stashes.clientOpenUnguarded = true. SetStashTarget(id) makes the next press of the inventory key open that stash (nil clears it); GetStashTarget() reads it.
Players, trades and searches#
| Export | Returns | Notes |
|---|---|---|
SearchPlayer(src, target, { vouched = true }) |
true, ground or false, reason |
Opens the target's inventory on the grounds in Config.Search. Without a ground the target is asked first and the call returns false, 'search_asked'. vouched = true skips consent and grounds; use it for your own job checks. |
SetSearchProtected(src, on, reason) |
true |
While on, a search without a lawful ground is refused with search_protected. |
OpenTrade(src, target, { vouched = true }) |
true or false, reason |
Sends a trade request (false, 'trade_asked'); vouched opens the trade at once. |
CancelTrade(src, reason) / GetTrade(src) |
true / { id, partner, phase } |
|
InspectInventory(admin, target) |
true or false, reason |
Read-only view of a player, or of a container when target is not a number. |
ConfiscateInventory(target, reason) / ReturnInventory(target) |
true, count / result |
Moves a player's items into a holding container and back. |
WipeOnDeath(src) |
result | Runs the death wipe now. Needs Config.Death.enabled = true. |
HasGroup(src, spec) |
boolean | spec is the same shape as stash groups. Gangs and groups count on QBCore, QBox, ND_Core and ox_core; ESX and standalone have jobs only. |
SuppressItemToasts(src, ms) |
boolean | No item cards for that player for ms (default 1000, at most 300000; 0 ends it). |
HasPhone(src) |
has, item |
has is true while the player carries Config.Compat.phoneItem ('phone'); with that set to '' it is always true. |
Capacity and item flags#
| Export | Returns | Notes |
|---|---|---|
SetMaxWeight(inv, grams, persist) |
true, now or false, reason |
On a player, persist = true keeps it across relogs, otherwise it lasts the session; nil clears your override. On a stash or container id it changes that container while it stays loaded. |
SetSlotCount(inv, slots, persist) |
as above | A container item's own size comes from its item and is refused (capacity_from_item); a size that would cut off items is refused (slots_in_use). |
SetGridWidth(src, columns, persist) / SetGridRows(src, rows, persist) |
as above | Player pockets on the grid. |
GetCapacity(src) |
table | slots, maxWeight, weight, grid size, base, tiers, saved, live. |
SetItemFlags(inv, slot, flags) / GetItemFlags(inv, slot) |
See section 2. |
Weapons#
| Export | Returns | Notes |
|---|---|---|
GetWeaponBySerial(serial) |
row or nil |
{ name, label, slot, count, serial, registered, durability, ammo, metadata, container, kind, holder, owner }, wherever the gun is loaded. |
RepairWeapon(src, slotOrSerial, amount) |
true or false, reason |
slotOrSerial is a slot number, a serial or a uid. amount defaults to 100; it also clears a jam. |
SetDurability(src, slotOrSerial, value) |
true or false, reason |
0 to 100. A gun set to 0 breaks. |
IsSerialScratched(inv, slot) |
'filed', 'ground' or false |
|
RestoreSerial(inv, slot) |
true or false, reason |
Brings back a filed serial from the forensics record; a ground-off serial cannot come back (serial_destroyed). |
GetCurrentWeapon(src) |
row or nil |
The drawn gun as a slot row, plus hash, durability and ammo (the ammo item it takes). |
IsShieldRaised(src) / IsParachuteStrapped(src) |
boolean |
Using, portions and item buttons#
| Export | Returns | Notes |
|---|---|---|
SpendUse(src, slot, n) |
uses left or false, reason |
For an item with uses, in the pockets. |
SpendPortion(src, slot, n) / GetPortions(src, slot) |
portions left / left, of |
For a portioned item in the pockets. |
RegisterItemButton(item, id, label, handler, icon) |
true or false, reason |
Adds a button to the item's menu. handler(source, ref, item) runs on the server after the same checks as any item action; ref is { container, slot }, item is { name, label, count, slot, metadata }. Return false, reason to refuse. id is 1 to 48 letters, digits, _ or -; unload, repair, unfit and wear_set are taken. Removed when your resource stops. |
RemoveItemButton(item, id) |
boolean |
An item can also list buttons in its definition: buttons = { { id = 'inspect', label = 'Inspect', icon = 'inspect' } }. Pressed with no registered handler, such a button fires the server event ncore_inventory:itemButton (source, id, item, ref).
Client: AddItemButton(item, id, label, handler, { group, icon, close }) adds a button that runs handler({ name, slot, container, count, metadata }) on the client. The server is not asked, so do not change items from it. RemoveItemButton(item, id) takes it off.
Clothing#
| Export | Returns | Notes |
|---|---|---|
ClothingMode() |
'items' or 'toggle' |
'items' while clothes are items (Config.Clothing.asItems). |
ClothingAreas() |
list | Empty while clothes are not items. Otherwise hat, glasses, mask, ears, chain, watch, top, vest, bag, bracelet, pants, shoes, and gloves when gloves are on. |
GetWorn(src) / IsWearing(src, area) |
list / boolean | { area, name, uid, look } per worn piece. |
GiveClothing(src, area, look, opts) |
true, uid or false, reason |
look = { model = 'mp_m_freemode_01', parts = { { c = 11, d = 15, t = 0 } } } (c a component or a a prop, d drawable, t texture); freemode models only. opts.origin is required: 'shop', 'wardrobe', 'script', 'external' or 'admin'. Also value or paid (resale value is paid times Config.Clothing.resale), label, and wear = true to put it on. |
StripArea(src, area) |
ok, reason |
Takes the piece off into the pockets or bags, or onto the ground when there is no room. |
Premium coins#
These need Config.Premium.enabled = true (it ships off); until then they answer false, 'premium_off'.
| Export | Returns | Notes |
|---|---|---|
GetPremiumCoins(target) |
balance or nil, reason |
target is a server id, or an identifier such as 'license:...' for a player who is offline. |
AddPremiumCoins(target, amount, reason) |
true, balance or false, reason |
|
RemovePremiumCoins(target, amount, reason) |
as above | Refused with premium_short when the balance is too low. |
SetPremiumCoins(target, amount, reason) |
as above |
Client: GetPremiumCoins() is the balance the server last sent this player.
Vehicles and keys#
| Export | Returns | Notes |
|---|---|---|
RegisterVehicle(netId, plate) |
true or false, reason |
A garage vouches for its car, so its trunk and glovebox open under Config.Vehicles.verify = 'strict'. |
UpdateVehiclePlate(oldPlate, newPlate) |
true or false, reason |
Moves the saved trunk and glovebox to the new plate. |
IssueKey(src, kind, target, opts) |
key uid (or true) or false, reason |
See below. |
RevokeKeys(kind, target) |
new cut number or false, reason |
Re-keys the lock: every key cut before stops working. |
HasKey(src, kind, target, opts) |
boolean | opts.full = true ignores valet keys. |
HasVehicleKey(src, plate, full) |
has, access |
access is 'full' or 'valet'. |
GetKeys(src, kind) |
list | { name, slot, container, kind, target, valet, current, garage, metadata }. |
exports.ncore_inventory:IssueKey(source, 'vehicle', 'ABC123', { model = GetEntityModel(vehicle) })
exports.ncore_inventory:IssueKey(source, 'door', 'mrpd_front', { item = 'key_job', job = 'police', grade = 2 })Kinds are 'vehicle' (plate), 'house' (property id), 'door' (door name or id) and 'stash' (stash id). Options: valet = true (a valet key), model (a model name or hash; with Config.Keys.vehicle.matchModel = true, the default, the key only works on that model under that plate), type (a door script's door type; with nil as the target the key opens by type alone, which needs ox_doorlock 1.18.0 or newer), script (the housing resource), address (text on the key, up to 64 characters), houseKey (the housing script's own key id), job and grade (only that job from that grade may use it), item (a specific key item of that kind).
Shops#
local ok, idOrReason = exports.ncore_inventory:RegisterShop('mystore', {
name = 'My store',
inventory = { { name = 'water', price = 10 }, { name = 'weapon_pistol', price = 2500, license = 'weapon' } },
locations = { vector3(25.7, -1347.3, 29.49) },
groups = { police = 0 }, -- optional
blip = { id = 52, colour = 2, scale = 0.7 }
})
exports.ncore_inventory:OpenShop(source, 'mystore')RegisterShop(id, data) takes the ox_inventory shape (a stock row may also carry count, metadata, currency and grade). CreateShop(data) takes the QBCore shape ({ name, label, coords, items = { { name, price, amount, info } } }, or a table of such shops keyed by name). A shop registered while the shop module is still starting is queued, built the moment the module starts, and the call returns true, id. A refusal returns false and a reason, for example shop_runtime_off, shop_bad_id, shop_off, shop_id_taken or shop_bad_spec, and is logged. A shop is removed when the resource that registered it stops. Price and stock edits made in the admin panel are applied again each time that resource registers the shop.
OpenShop(src, id) returns true, containerId or false, reason. With locations, the player must be within Config.ModuleSettings.shop.openDistance plus 1 meter of a counter. A shop registered with no locations opens anywhere, through OpenShop only. ShopList() returns {} while the shop module is off, starting or failed. A gun with a serial bought in a shop is registered to the buyer, unless its row has metadata = { Registered = false }.
Client: OpenShop(id) asks to open a shop; IsShopkeeperPed(ped) says whether a ped is one of the inventory's shopkeepers.
Crafting and benches#
-- server
local ok, wasKnown = exports.ncore_inventory:ForgetCraftRecipe(source, 'workbench:advancedlockpick')
local ok2, result = exports.ncore_inventory:ResetCraftQueue(source, { to = 'pockets', collect = true })A recipe id is the recipe's own id, or the bench id, a colon and the item it makes ('workbench:advancedlockpick').
| Export | Returns | Notes |
|---|---|---|
RegisterBench(definition) |
ok, why |
The same shape as an entry in modules/craft/benches.lua. Removed when your resource stops, so a restart registers it cleanly. |
OpenBench(src, benchId, index) |
ok, why |
The player must be within reach of that bench location. |
BenchList() |
list | |
GetCraftLevel(src, track) |
level, xp, need |
track defaults to 'crafting'; 'gunsmithing' is the other shipped track. |
AddCraftXp(src, track, n, reason) |
true, given or false, reason |
given can be less than n (hourly cap). |
SetCraftLevel(src, track, level) |
true or false, reason |
|
HasCraftRecipe(src, recipeId) / TeachCraftRecipe(src, recipeId) |
boolean / ok, why |
|
ForgetCraftRecipe(src, recipeId) |
true, wasKnown or false, reason |
no_session or craft_not_a_recipe. Works with crafting progress on or off. |
GetCraftQueue(src) |
table or nil |
nil while the queue is off. |
CancelCraft(src, jobId) |
ok, why |
|
ResetCraftQueue(src, opts) |
true, { jobs, units, collected, left } or false, reason |
Cancels a pending craft and every queued job of that player. What each job held goes to the output shelf (opts.to = 'tray', the default) or into the pockets ('pockets'; what does not fit lands on the shelf), and opts.collect = true then moves the shelf into the pockets. Reasons: no_session, craft_off, inventory_locked, craft_queue_unreadable. While the queue is off it only cancels a pending craft and returns zero counts. |
OpenGunbench(src, benchId, index) |
ok, why |
The player must be within reach of that bench, pass its job or group check and carry a gun. |
The gun bench, the crafting benches and the queue each need their module on. Client: OpenBench(benchId, index) and OpenGunbench(benchId, index) send the request and return true whatever the server decides (false while the module is off).
Hooks: RegisterHook#
local id = exports.ncore_inventory:RegisterHook('take', function(p)
if p.item == 'evidence_bag' and p.action == 'drop' then return false end
end, { itemFilter = { 'evidence_bag' } })
exports.ncore_inventory:RemoveHooks(id) -- or RemoveHooks() for all of yoursRegisterHook(event, fn, options) returns a hook id, or nil and unknown_hook_event or not_a_function. event is one of the names below or a list of them. Returning false from fn refuses the action (the player sees refused_by:<your resource>); anything else lets it through. A hook that errors lets the action through and the error is logged; one that takes 100 ms or more is logged as slow. Your hooks are removed when your resource stops.
Options: itemFilter (item names), inventoryFilter (Lua patterns matched against inventory ids; with oxIds = true they are also matched against ox-style ids such as 'police_locker' or 'trunkABC123'), typeFilter (container kinds such as 'player', 'stash', 'drop', 'trunk', or a shop id for buy), actionFilter, print = true (logs each run).
| Event | When | Payload |
|---|---|---|
move |
A drag between or inside inventories | source, action ('move', 'stack' or 'swap'), item, count, fromInventory, fromType, fromPlayer, fromSlot, toInventory, toType, toPlayer, toSlot |
take |
An item leaves its slot in any other way | source, action, item, count, fromInventory, fromType, fromPlayer, fromSlot, toInventory, toType, toPlayer. action is for example 'use', 'drop', 'throw', 'give', 'offer', 'place', 'destroy', 'combine', 'wear', 'takeoff', 'fit', or 'script' for a RemoveItem on a container (then source is nil). |
use |
A use, after take with action = 'use'; also a gun being drawn, not one being holstered |
source, action, item, count, slot, inventoryId, inventoryType, inventoryPlayer, metadata, fromSlot |
open |
An inventory, container, ground pile or player search opens | source, inventoryId, inventoryType, label |
buy |
A shop purchase | source, item, shopType (the shop id), shopId (the counter number), count, price, totalPrice, currency, method, fromInventory, toInventory, toSlot, metadata |
craft |
A bench craft, a queued craft or a combine | source, item, count, recipe, benchId, benchIndex, fromInventory, toInventory, fromSlot, toSlot |
trade |
A trade is about to complete, once for each side | source, tradeId, target, money, items (what source gives), count, fromInventory, fromPlayer, toInventory, toPlayer |
create |
An item is created | source, inventoryId, inventoryType, rootType, item, label, weight, count, metadata. It cannot refuse: return a table to replace the new item's metadata (container and weight stay as they were). |
Slot payloads (fromSlot, toSlot) are { name, label, count, slot, metadata, weight }, except a move into an empty slot, where toSlot is the slot number.
Events#
Server events (AddEventHandler on the server):
| Event | Arguments | When |
|---|---|---|
Config.Use.event (ncore_inventory:itemUsed) |
source, itemName, kind, meta |
When a use is done. A plain use (use = 'eat', 'drink' or 'use') and a healing item fire it when the client reports the end of the bar, or at the latest 3 seconds after the use time (15 seconds for a healing item). A use the player cancels does not fire it, and the unit is given back. A bite of a portioned item, lighting a smoke, reading a blueprint, a bite offered to another player (then source is the one who ate and meta.offeredBy the one who offered) and a key whose script stands down (Config.Keys.standDownFor) fire it at once. For a bite, meta.portion = { of, left, take }: how many portions the unit had, how many are left and how many this use spent. |
ncore_inventory:weaponRegistered |
e |
See below. |
ncore_inventory:bundleOpened |
source, item, list |
A bundle was opened; list is { { name, count } }. |
ncore_inventory:disposed |
source, item, count, pointId |
Items were destroyed at a disposal point; once more for each item that was inside a destroyed container. |
ncore_inventory:licenceBought |
source, license, price |
A license was bought at a license point (Config.Licences). |
ncore_inventory:weaponRepaired |
source, item, price |
A gun was repaired at a gun repair counter. |
ncore_inventory:pumpFilled |
source, item, amount, price |
A jerry can was filled at a fuel pump. |
ncore_inventory:premiumChanged |
{ source, account, balance, delta, op, reason } |
A premium coin balance changed. source is nil for an offline account. |
ncore_inventory:cashSeized |
{ source, target, account, amount, job } |
Cash was seized in a search, with Config.Search.seizeTo = 'event'. |
ncore_inventory:playerDied |
source, coords |
A player died, with Config.Death.enabled = true. |
ncore_inventory:itemButton |
source, id, item, ref |
See item buttons above. |
Client events (AddEventHandler on the player's own client):
| Event | Arguments | When |
|---|---|---|
ncore_inventory:opened / ncore_inventory:closed |
none | The panel opened or closed. |
ncore_inventory:itemUsed |
name, kind, result, share |
After a use on this client, except one handed to another resource. result is 'done' or 'cancelled'; share is the part of the item this use spent, 0 to 1. |
ncore_inventory:itemDelta |
list |
What the player carries changed (pockets, worn bags, nested containers, worn clothing). list is { { name, count, quiet, own, note } }; count is the gain or loss and quiet names why no card was shown. Changes within 150 ms arrive together. |
ncore_inventory:alcohol |
level, item, added |
After each use of an item with alcohol: the drunk level after it and what this use added. |
ncore_inventory:sleep |
percent, item |
After each use of an item with buff.sleep, whether or not ncore_hud runs. |
ncore_inventory:drug |
item, ms |
A drug or pill effect starts (ms is 0 for a heal-only effect such as oxycodone). |
ncore_inventory:hygiene |
percent, item |
After a finished wash with soap (Config.Use.hygiene). |
ncore_inventory:phoneCarried |
has, item |
The player started or stopped carrying Config.Compat.phoneItem. npwd is switched off and on by the inventory itself. |
ncore_inventory:handsUp |
raised |
The player raised or lowered their hands through the inventory. |
ncore_inventory:pickupAnswer |
id, ok |
Sent to the taker only, after every hold-E pick-up request. |
Alcohol and drug items also send evidence:client:SetStatus. Food, drink and smoking items that the framework also registers as usable are eaten, drunk and smoked by the inventory while Config.Use.preferPortions = true, and the framework's callback is not called for them; listen to the events above instead.
With Config.Compat.oxEvents = true and no other ox_inventory running, these ox_inventory events are fired as well: ox_inventory:openedInventory, ox_inventory:closedInventory and ox_inventory:usedItem on the server (ox-style ids such as 'police_locker', 'trunkABC123' or 'drop-5'; a player inventory passes the inventory's own id), and ox_inventory:updateInventory, ox_inventory:itemCount, ox_inventory:usedItem, ox_inventory:currentWeapon and ox_inventory:updateWeaponComponent on the client.
Weapon registration: weaponRegistered#
-- server
AddEventHandler('ncore_inventory:weaponRegistered', function(e)
-- e.source, e.item, e.label, e.serial, e.owner, e.uid, e.container, e.how ('purchase' or 'issued')
end)It fires when a gun with a serial and a registered owner is bought in a shop ('purchase') or handed out by a script or an admin ('issued'). A gun with no registered owner has a serial but does not fire it. The serial is also sent to an MDT: with Config.Weapons.mdt = 'auto' to ps-mdt when it runs, a resource name sends it to that resource's CreateWeaponInfo export, and false sends nothing.
State bags#
Set by the inventory:
| Bag | Value | Use |
|---|---|---|
invOpen |
true while the panel is open |
Hide your HUD: LocalPlayer.state.invOpen on the client, Player(source).state.invOpen on the server, or AddStateBagChangeHandler('invOpen', nil, fn). |
lri_handsup |
true while hands are up |
For emote and police scripts. |
lri_restrained |
'dead', 'down', 'cuffed' or false |
What the game says restrains the player, reported by their client every 500 ms. |
lri_vest |
{ n, i } |
The vest object drawn on a character whose model does not show the vest; i is the vest item. Written by the server only. |
lri_demoped |
'own', 'mp', 'gta' or unset |
The demo character of the player while a demo tour runs. For UI only: read DemoPed() instead. |
Read by the inventory, set by your scripts on the player:
| Bag | Effect |
|---|---|
isCuffed, handcuffed or cuffed |
Truthy counts as cuffed: the panel will not open and an open one closes, unless Config.Player.openWhileCuffed = true. |
invBusy or inv_busy |
Truthy marks the player busy: the panel will not open and an open one closes until you clear it. |
Other lri_ keys are the inventory's own; do not write them.
Client exports#
| Export | Returns | Notes |
|---|---|---|
OpenInventory(target) |
Opens the panel, or closes it when open. With no target it opens with the nearest trunk or ground pile; { id = pileId } opens that pile. |
|
CloseInventory() |
||
IsInventoryOpen() / IsReady() |
boolean | |
GetState() |
table or nil |
A copy of the last full state the server sent. |
Items(name) |
definition(s) | |
HasItem(items, amount) |
boolean | items is a name, a list of names, or { name = count }. Also answers exports['qb-inventory']:HasItem while no qb-inventory runs and Config.Compat.qbExports = true. |
GetItemCount(name, metadata, strict) |
number | |
Search(query, name, metadata) |
count or rows | Like the server export, from what the server last sent. |
getCurrentWeapon() |
table or nil |
The drawn weapon. |
ClosestDrop() |
id, distance |
The pile the player stands at. |
GetImagePath() / GetItemImage(name) |
address | GetItemImage returns nil for an item with no picture. |
Hint(id, text, opts) / HintKey(spec, fallback) |
See below. | |
HasHotbar(), ShowHotbar(), HideHotbar(), IsHotbarVisible() |
||
IsHandsUp() / SetHandsUp(on) |
boolean | |
OpenTrade(target) |
Asks target (a server id) to trade, or the nearest player with no argument. |
|
OpenNearbyInventory() |
Searches the nearest player. | |
GetPlayerPrefs() |
table | The player's own panel preferences. |
IsPreviewPed(ped) |
boolean | Whether a ped is the inventory's character preview copy. |
With Config.Compat.clientMirror = true the player's pockets are mirrored to their client for the ox-shaped client exports GetPlayerItems, GetPlayerWeight, GetPlayerMaxWeight, GetSlotWithItem, GetSlotIdWithItem, GetSlotsWithItem, GetSlotIdsWithItem, useSlot(slot), useItem(data, cb) and giveItemToTarget(serverId, slot, count).
-- server
local has, item = exports.ncore_inventory:HasPhone(source)
-- client
local has, item = exports.ncore_inventory:HasPhone()
AddEventHandler('ncore_inventory:phoneCarried', function(has, item) end)Key hints: Hint and HintKey#
local token = exports.ncore_inventory:HintKey(47, 'G') -- '~INPUT_DETONATE~': the cap shows the key of control 47
CreateThread(function()
while nearMyThing() do
local shown = exports.ncore_inventory:Hint('open', token .. ' Open the safe', { lane = 'prompt', d = distance, ttl = 300 })
if shown and IsControlJustReleased(0, 47) then openSafe() end
Wait(0)
end
exports.ncore_inventory:Hint('open', nil)
end)With your own key mapping, act in the command and gate it on the last answer, so the cap and the key are always the same binding:
local shown = false
RegisterCommand('my_command', function() if shown then openSafe() end end, false)
RegisterKeyMapping('my_command', 'Open the safe', 'keyboard', 'G')
local token = exports.ncore_inventory:HintKey('cmd:my_command', 'G') -- '~INPUT_xxxxxxxx~' of your mapping
CreateThread(function()
while nearMyThing() do
shown = exports.ncore_inventory:Hint('open', token .. ' Open the safe', { lane = 'prompt', d = distance, ttl = 300 })
Wait(0)
end
shown = false
exports.ncore_inventory:Hint('open', nil)
end)Hint(id, text, opts)showstext(GTA help format:~INPUT_PICKUP~,~n~,~r~/~g~/~y~/~b~/~s~) in the inventory's own hint stack foropts.ttlms (100 to 10000, default 300): call it again for as long as you want it shown.niltext hides it. The id is private to your resource. It returnsshown, active, why:shownis whether it is on screen now (gate your key on it so one press never does two things),activeisConfig.Hints.enabled,whysays why it is not shown (for example'wait'on the first call,'lane'when another hint won,'panel','pause','hud','limit').opts:laneis'prompt'(an E or G style prompt, priority up to 50, default 30),'action'(what the player is doing, up to 75) or'notice'(a tip or message, up to 90; the default lane; default priority 20 for both);prio;d(meters, nearer prompts win);tone('prompt','act','stop','warn'or'note');icon('stop','person','action','inspect','alert'or'use');rows(1 to 3 lines, default 2);beep = true;tip = trueto follow the player's Key hints preference.- At most 8 hints per resource at once; they all go when your resource stops. Text is cut to 600 characters.
HintKey(spec, fallback)gives the help-text token for a control index (38), a control name ('PICKUP') or a key mapping ('cmd:<command>', exactly as registered). For a key mapping it is~INPUT_%08X~of the command's hash.fallbackis the keyboard key shown when the game cannot read the binding. Never mix the two: acmd:cap with anIsControlJustReleasedcheck shows one key and acts on another after a rebind.
Demo character: DemoPed and ncore_character#
-- server
local ped = exports.ncore_inventory:DemoPed(source)
-- client, for UI only
local ped = exports.ncore_inventory:DemoPed()Both return nil, 'own', 'mp' or 'gta'; the server value is read from server state only.
| Value | Meaning |
|---|---|
nil |
No demo tour runs for that player. |
'own' |
A tour runs and the presenter is on their own ped, with no swap pending. |
'mp' |
The presenter is the Binco model (see Demo stops in section 5): the stand-in closet is lent and the server ped model is mp_m_freemode_01 or mp_f_freemode_01. |
'gta' |
Any other demo ped, a swap that is still pending, or a Binco model whose own character has not been confirmed back yet (also after the tour ended). |
While the value is 'mp' or 'gta', ncore_inventory saves no worn clothes back to illenium-appearance, fivem-appearance, skinchanger or qb-clothing, and adopts no external appearance save.
With ncore_character:
- Its server export
DemoAware()returnstrue. nCore Inventory reads it before it lends the MP character; without it, the stop with the MP character keeps the presenter's own character. - Its items-only clothing store serves MP (freemode) characters only; a GTA character gets
app_shop_mp_only. - While
DemoPedis'mp'or'gta', ncore_character refuses its counters withapp_demo_ped, except that an'mp'presenter can still use the items-only clothing store, and it never saves or adopts the demo look.
Combine recipes#
Config.Combine.recipes = {
{ a = 'weed_og', b = 'rolling_paper', result = 'joint', count = 1 },
{ a = 'lockpick', b = 'wrench', result = 'advancedlockpick', count = 1, keepB = true }
}Drag a onto b or the other way round. count is how many results one combination makes, and one drag combines as often as both stacks allow. When the results do not fit, the batch is halved until it does, or the drag is refused with combine_no_room. keepA or keepB = true means that ingredient is not used up (a tool); a kept ingredient is not checked or worn. A spoiled ingredient is refused when Config.Decay.refuseSpoiled = true. Combining fires the craft hook.
Compatibility switches (Config.Compat)#
| Key | Default | What it does |
|---|---|---|
oxInventory |
true |
The ox_inventory-shaped server exports (GetItem, CanCarryItem) and the client setCurrentWeapon (which does nothing). |
qbExports |
true |
The QBCore-shaped exports under this resource's name (HasItem, GetItemByName, GetItemsByName), and exports['qb-inventory'] while no real qb-inventory runs: AddItem, RemoveItem, HasItem, GetItemByName, GetItemsByName, GetItemBySlot, GetItemCount, CanAddItem, ClearInventory, SetInventory, SetItemData, UseItem, GetTotalWeight, GetSlotsByItem, GetFirstSlotByItem, GetFreeWeight, GetSlots, LoadInventory, SaveInventory, CloseInventory, OpenInventory, CreateInventory, ClearStash, GetInventory, OpenInventoryById, RemoveInventory, CreateShop, OpenShop, CreateUsableItem, GetUsableItem, addTrunkItems, addGloveboxItems. AddHook, RemoveHook, AddListener and RemoveListener answer false with a console warning. A resource keeps the qb-inventory export it was handed until it restarts, so restart those resources after restarting ncore_inventory. |
esxEvents |
true |
esx:onPlayerSpawn asks the client to report ready. |
oxEvents |
true |
The ox_inventory events listed under Events. |
clientMirror |
true |
The pockets mirror behind the ox-shaped client exports. |
containerTargets |
true |
Item exports also answer stash, trunk, glovebox, pile and container ids; false keeps them player-only. |
openByIdVouched |
true |
qb OpenInventoryById by a caller holding a police job opens on the vouched ground. |
loadMs |
3000 |
How long an export waits for a stash to load. |
phoneItem |
'phone' |
The item HasPhone and npwd look for; '' means always true. |
qbEvents.enabled |
false |
Answers inventory:server:OpenInventory for 'stash' (an id that matches a Lua pattern in qbEvents.stashes opens sized at most stashSlots and stashMaxWeight; a registered stash with coords or groups keeps its own rules), 'trunk', 'glovebox' and 'otherplayer', plus inventory:server:addTrunkItems and addGloveboxItems. Those two fill events need a job from qbEvents.fill.jobs, a spot within 10 meters of the plate, an empty trunk or glovebox, and only place items named in qbEvents.fill.items (item name = most per fill). A dead, cuffed, busy or in-vehicle player is refused. |
The bundled ox_inventory folder forwards ox_inventory calls to this resource through OxAddItem, OxRemoveItem, OxOpen, GetOxInventory, OxClientInventory and OxClientCount; call the exports above instead.
Migration: invmigrate#
Server console only, with oxmysql and Config.Database.prefer left at 'auto' or 'mysql' (with 'kvp' or 'none' the command refuses):
invmigrate <metadata|qb|esx|split|kvp> [apply] [merge] [skipunknown]| Mode | Reads |
|---|---|
metadata |
ox_inventory: the framework's player inventory column, the ox_inventory stash table, and the trunk and glovebox columns of the vehicle tables |
qb |
qb-inventory: players.inventory, and the inventories table or the older stashitems, trunkitems and gloveboxitems tables |
esx |
ESX: users.inventory, plus the loadout and accounts columns when they exist (ESX keeps no stash tables) |
split |
split-table inventories (qs_stash, qs_trunk, qs_glovebox or inventory_stash, inventory_trunk, inventory_glovebox) |
kvp |
this inventory's own KVP saves, for a server that added oxmysql later |
Without apply it is a dry run that prints what it would import and every item name it does not know. apply writes, only with nobody online, and refuses while names are unknown unless skipunknown is given, which leaves them behind. merge adds to inventories already saved here. The source tables are only read. The command name is Config.Migrate.command.
kvp copies inventory and container rows only, and skips an owner who already has rows in the database (so a player who joined before the import keeps the new inventory and their KVP one is left alone). Premium coin balances are read from KVP until each one is next saved to the database. Old log lines stay in KVP; with Config.Logs.store = 'auto' the Logs tab then reads the database only. Item edits made in the admin panel are always kept in KVP.
5. Admin#
Aces#
add_ace group.admin lri.admin allow grants every admin part below. For smaller staff roles, grant single parts instead, and always include lri.admin.panel: the panel, the shield button and the panel key open only with it, so a role that holds only lri.admin.logs or lri.admin.economy can run that part's commands but cannot reach its tab. The ace names follow Config.Admin.ace (default lri.admin) and Config.Admin.labAce (default lri.lab). A deny entry is respected. A refused admin gets the exact add_ace line as a notification, and the server console prints the matching add_principal line.
| Ace | Allows |
|---|---|
lri.admin |
Every part below, plus invview, invgridflatten, and demo cash or bank money paid into a framework account |
lri.admin.panel |
Opening the panel. The Testing, Server status, Players, Inventory, Items and Registry tabs; reading an online player's inventory or any container; viewing held stores; /invslings |
lri.admin.give |
Giving items and kits, Take on the Players tab, the Demo tab, invgive and invkey while debug mode is off (see below) |
lri.admin.edit |
Changing inventories, confiscate and return, the item editor, crafting level changes, invcraftxp (see below) |
lri.admin.capacity |
Capacity tab: slots, weight, tiers, carry strength, reading crafting levels |
lri.admin.storage |
Storages tab, the offline player browser |
lri.admin.shops |
Shops tab and Menus tab (a stash in the Menus tab needs lri.admin.storage instead) |
lri.admin.economy |
Economy tab, invcheckitem, invminting, minting alerts |
lri.admin.logs |
Logs tab, invhistory |
lri.admin.config |
Config tab, maintenance lock, Save now, /invthumbs, invclips, saving Demo stop spots |
lri.admin.pose |
Pose tool, invposes |
lri.admin.premium |
invpremium (the ace is Config.Premium.ace) |
lri.lab, lri.lab.world, lri.lab.server, lri.lab.forge |
The test lab tabs, only while the lab runs. lri.admin does not grant them |
The lab runs when Config.Admin.lab.enabled is true, or 'debug' (the default) while Config.Debug.commands is on. Debug mode grants nothing in the panel. The bench commands (invitem, invmoney, invfill and the rest) need Config.Debug.ace (default lri.admin); the server console always passes. With debug mode on, invgive and invkey also take Config.Debug.ace instead of lri.admin.give.
Give and edit#
The two parts that change items are split this way.
lri.admin.give:
- Items tab: the give sheet (item, count, metadata, clothing look) to yourself, a player, a container or the ground, and its "Take back" button.
- Items tab > Kits, and the carry check (can this player carry this many).
- Players tab > Take: moves a chosen stack from an online player into that player's held store. Return needs
lri.admin.edit. - The Demo tab, together with
lri.admin.panel. Saving or clearing a stop spot also needslri.admin.config. invgiveandinvkeywhileConfig.Debug.commandsis off.
lri.admin.edit:
- Opening an online player's inventory, or any container, in Edit mode (Read needs only
lri.admin.panel). - The stack editor on the Inventory tab, "Age this stack", slot moves, and the protected, locked and bound flags of a stack.
- Clear (everything except a keep list), Confiscate and Return on the panel, the same Confiscate and Return as
invconfiscateandinvreturn, and purging a held store. - Editing an offline inventory and clearing it into a held store (both with
lri.admin.storage). - Deleting a storage (with
lri.admin.storage), and opening a stash for editing from the Menus tab (withlri.admin.storage). - The item editor: editing, creating, retiring and resetting item definitions.
- Changing crafting levels on the Capacity tab (with
lri.admin.capacity), andinvcraftxp. - During a demo tour, searching, robbing or looting the presenter.
Revert on a log row needs lri.admin.logs and the part of the original action: give for a give, kit or take row; edit for a stack edit, clear, confiscate or remove row; capacity for a capacity row; config for a config or log switch row.
/invadmin#
/invadmin opens the panel, on the Testing tab the first time and then on the tab you last used. /invadmin <tab> [player id or container id] opens a tab directly: testing, demo, status, players, inventory, items, capacity, storages, shops, menus, economy, logs, config, registry, and while the lab runs scenarios, state, world, serverlab, probes, refusals, ui. /invadmin lab [scenario] opens the Scenarios tab and /invadmin release releases your lab changes; both need lri.lab. In the server console: invadmin status | lab | release <player id>.
The shield button in the inventory header and a key binding (Config.Admin.panelKey, no default key, set under FiveM Settings > Key Bindings) open it too. At start the console prints "Admins: /invadmin opens the panel and the test guide". The command name is Config.Admin.panelCommand; Config.Admin.panel = false removes the command and the button.
| Tab | Part |
|---|---|
| Testing, Server status, Players, Inventory, Items, Registry | panel |
| Demo | give |
| Capacity | capacity |
| Storages | storage |
| Shops, Menus | shops |
| Economy | economy |
| Logs | logs |
| Config | config |
| Scenarios, Lab states, Probes, Refusals, UI lab | lri.lab |
| World | lri.lab.world |
| Server lab | lri.lab.server |
The lab tabs show only while the lab runs and the "Developer tools" switch at the bottom of the tab list is on.
Tabs#
- Testing: a guided test of 326 steps in 42 parts, in English and Hungarian. Setup buttons give items and kits, open the right tab or copy a server.cfg line. "Show on map" sets a waypoint and works with the lab off. Buttons that teleport you, put a vehicle next to you, force a state or give money need the lab, and a banner says so while it is off. Works, Broken and Skip marks are saved per inventory owner (the character on multi-character frameworks); a note of up to 240 characters can be added to a Broken mark. A mark belongs to the text of its step, so a step whose English text changes loses its mark. "Start over" clears the marks, and the bug report (broken, skipped and working steps with their text) can be copied.
- Demo: the guided showcase, see "Demo tab" below.
- Server status: version, framework, storage, maintenance state, items, locale parity, containers and the log store, refreshed every 5 seconds. A Platform card shows the framework, each module and whether it opens by ox_target, qb-target or E, the state of ox_lib, ox_target and qb-target, the compatibility folder, and how many hooks, item buttons and runtime shops other resources added. Other cards: an access probe with copyable allow and deny lines, conflicts with other inventories, modules, sibling resources, a framework probe with a test notification, performance and privacy. The maintenance lock (blocks every inventory write with a reason) and Save now need
lri.admin.config. - Players: online players with id, character, job, routing bucket, slots, weight, bags, ping and distance, refreshed every 3 seconds. Open a player Read or Edit; with
Config.Admin.tellTargeton (default) the player gets a warning each time an admin opens them in Edit mode (not again while that admin keeps the same player open), and Read is silent. The player drawer has Mirror (your own inventory, read-only), a session inspector, Take, Clear, Confiscate and Return, and the held store (view, or Purge with a typed word). The offline player browser lists saved inventories to open read-only, edit (the player's login waits until you close it orConfig.Admin.offlineEditMsruns out, 5 minutes by default) or clear. - Inventory: the container tree of any player or container id, opening a container Read or Edit, the stack editor (durability, ammo, components, tint, serial, uses, armor, label, look, freshness, age, jammed, oxygen, count and more), "Age this stack" (needs
Config.Decay.enabled), slot moves with a preview, a grid audit, a uid and serial lookup, and a memory versus saved comparison. - Items: the catalog with what every item does on this server (handled here, by another script, a material, or waiting because its setting is off or nothing handles it), the give sheet, kits, and the item editor (label, weight, stack, value, picture, category, sub-class, rarity, English, Hungarian and local descriptions, protected, locked, tradable, bound, uses, per-action bans and crate access). The editor refuses a stack size below any stack that already exists. Simple items can be created, retired (shown behind the Retired filter) or reset to
data/items.lua. "Open pose tool" needslri.admin.pose. - Capacity: slots, max weight and grid size per player (this session, kept across relogs, or back to the tier default; refused when items would be displaced), tiers, carry strength and a Crafting levels card.
- Storages: stashes, placed stashes, trunks, gloveboxes, bins, ground piles, held stores, offline players, hiding spots and craft queues, with search and paging. Every entry opens; Edit works while it is loaded and needs
lri.admin.edit. Locate sets a waypoint for stashes, placed stashes, trunks and gloveboxes of a vehicle that is out, bins, piles and hiding spots. Delete asks for the typed id and is refused for player inventories, held stores, craft queues, bags, worn items, trades and containers inside other containers.invdelstorage <id> confirmdoes the same from chat or the console. - Shops: per-row price and stock, adding (with its currency), removing and restoring rows, resetting a shop and restocking it now.
- Menus: open any shop, vending machine, crafting bench, gunsmith bench, stash or ncore_character menu for yourself. Purchases are paid from your own money.
- Economy: the money value of money items, framework accounts (online players by default;
Config.Admin.economy.accounts = 'all'reads saved accounts and needs oxmysql and ESX, QBCore or Qbox), holders, storages and a per-item census, cached for 300 seconds. Click an item to see who holds it. The minting report lists which resources created items. A resource is flagged when its last full hour reachesminUnits(50) and more thanspikeFactor(5) times its usual hour, the median of its active hours in the previous 168; it is judged only after 6 active hours, and item creation with no named resource (crafting, loot, starter kits) and the inventory's own admin gives are never flagged. A flag is printed, sent to online admins withlri.admin.economyand posted to the log webhook, once per resource per hour (Config.Admin.minting.announce,.notify,.webhook). It needs thecreationlog channel stored. - Logs: time range, channel, op, actor, target, item, container, uid and text filters, paging, follow mode and copy as CSV. The Audit preset shows the admin and lab channels. Revert works on capacity, stack edit, give, kit, take, clear, confiscate, remove, config and log switch rows; a give or kit row reverts only while its stacks are in loaded containers. Item history by uid or serial shows the newest 200 rows within
Config.Logs.keepDays. Log switches for the creation, destruction, transfers, shop and craft channels needlri.admin.config. - Config: every setting with when it takes effect (live, client, page, restart, protected, price). A session change of a live setting applies server-wide at once; a session change of a client or page setting reaches only your own client. A saved change applies at every start. Protected settings and prices are changed in
config.luaonly. Reset to file removes a saved change. - Registry: what other resources added: items, hooks, item buttons, stashes, benches, shops and modules.
Demo tab#
A guided showcase of the inventory for recording a video: 10 themed stops and 6 bonus stops, defined in data/demo.lua. It needs lri.admin.panel and lri.admin.give, and Config.Admin.demo.enabled (default true).
- Start the tour parks your own items in a held store and remembers your worn clothes, bag and vest. Every stop wipes your pockets and gives that stop's kit, plus its cash, bank money and vehicle where the stop has them (the Car Keys, Trunk & Glovebox stop brings a damaged van with keys). Each stop's kit is also listed under Items tab > Kits as
demo.<stop id>. - End the tour, or your next join after a disconnect, crash or restart, removes the demo items, cleans up the demo's own ground piles, crates and vehicles, and gives everything back, worn clothes, bag and vest included. Crafting jobs queued, outfits saved, recipes learned, crafting XP earned, recipes a stop reset, and hunger and thirst lowered during the tour are put back. The closing card then shows for 14 seconds.
- Briefing: before each stop a full-screen briefing shows its whole script only to you ("Only you see this. It is not in the video."). Enter departs; "Stay here" cancels.
- Travel and look: travel uses the GTA sky camera, or a fade. Each stop sets your local time of day and weather. Every stop turns you into a fitting GTA character, and the Clothing as Items stop makes you the Binco model, a GTA Online character dressed only in clothing items. Your look comes back at the end through your appearance resource, or from a snapshot when there is none. With
Config.Admin.demo.timeSyncon and qb-weathersync started, the tour sets the whole server's time and weather until it ends (see section 3). - Cleanup: every demo item carries a hidden tag and is removed from pockets, bags, piles, crates, vehicles, stashes and other players at each stop, at the end and when a new tour starts; a container that was not loaded is cleaned when it loads. Demo items on a craft output shelf are removed too.
- Protection: while a tour runs, nobody without
lri.admin.editcan search, rob or loot the presenter or the demo piles. - Money: cash is the cash item where money is an item; otherwise it is paid into the framework cash account. Paying into the cash or bank account needs the full
lri.adminace. At the end, up to the amount paid is taken back, never below the balance the tour started with. - Buttons: "Retake this stop" restarts the current stop from the top with a fresh kit (cash and bank money are topped up to the first take's balance, not paid twice). "Give the items again" refills the kit without a wipe. "Back to where I started" takes you home during a tour, or within 15 minutes after a tour wound up on join. "Clean up leftovers" removes demo piles, crates, vehicles and tagged stacks now. Each stop card has "Show on map". "Video intro", "Opening card" and "Closing card" show those overlays.
- Spots: "Save this spot for the stop" stores a corrected stop position on the server, "Use the shipped spot" drops it, and "Copy spots as Lua" copies a
-- <stop id>line and acoords = vector4(x, y, z, h),line for each saved stop, to paste over that stop'scoordsline indata/demo.lua. Saving needslri.admin.config. - Options: chips saved in your browser, with defaults from
Config.Admin.demo: Fresh pockets at each stop (fresh), Cinematic time of day (clock), Sky camera travel (travel), Arrival camera (introCam), Arrival title card (titleCard, default off), A fitting ped at every stop (autoSkins), Orbit camera in the intro (introOrbit) and Feature callouts (callouts, default off). The script language is auto, en or hu. - Admin panel at a point: a point with
admin = '<tab id>'opens that tab instead of the Demo tab when you open the panel there, so the Demo dashboard never reaches the video.
Presenter keys#
The keys work while a tour stands at a stop, also with the inventory open. They are FiveM key bindings, so each presenter can rebind them under Settings > Key Bindings; the defaults come from Config.Admin.demo.
| Key | Setting | What it does |
|---|---|---|
| Enter | departKey |
Departs from the briefing to the stop. |
| Page Down | nextKey |
Next point of the script. At the last point the first press arms the next stop, the second travels there. |
| Page Up | prevKey |
Previous point, or disarms the next stop. |
| Home | cueKey |
Runs the current point's cue. |
| End (hold) | peekKey |
Shows the script of the current stop while held. The peek shows which callout the callout key fires next. |
| Insert | introKey |
Shows the video intro of the current stop (with the orbit camera when introOrbit is on); pressed again, hides it. |
| Delete | calloutKey |
Shows the next key = true callout of the current point. At the last point of the finale it shows the closing card, and pressed again it hides it. Also works in the 3D gun bench. |
| 6 | cardKey |
Shows the current stop's title card and keeps it up. With titleCard = false (default) this is the only way the card appears. |
| 7 | clearKey |
Fades out whatever overlay is on screen (title card, video intro, callout, opening or closing card) so the action can be filmed. |
With callouts = false (default) only the Delete key shows callouts. With true, callouts also fire on their own when their container opens or their cue runs, and the tour.firstOpen callouts show at the tour's first inventory open. Config.Hotbar.slots ships at 5, so 6 and 7 are free; if you raise it above 5, rebind the presenter keys.
Demo stops#
Stops, kits and script text live in data/demo.lua. The file is checked when the Demo tab loads it; a wrong field stops the tour and the console names the stop and the field.
| Stop field | What it does |
|---|---|
id, order |
Unique id and order (1 to 99). |
bonus = true |
A bonus stop. The tour visits every bonus stop whose needs are met before the finale stop. |
finale = true |
On a main stop: the bonus stops come before it, so it closes the video. |
theme, glyph, title, place, blurb, features |
Look of the stop card: theme amber, mint, sky, lilac, rose, red or peach, an icon, en and hu texts, and 2 to 6 feature names. |
coords, look, ground |
Arrival position (vector4), an optional point to face (vector3), and ground (true puts the presenter on the ground at that spot, false keeps the exact height). |
clock = { h, m } |
The stop's time of day. |
weather = 'CLEAR' |
EXTRASUNNY, CLEAR, NEUTRAL, SMOG, FOGGY, OVERCAST, CLOUDS, CLEARING, RAIN, THUNDER, SNOW, BLIZZARD, SNOWLIGHT, XMAS or HALLOWEEN; Config.Admin.demo.weather otherwise. |
money = 500, bank = 500 |
Cash and whole dollars of bank money for the presenter. |
items |
The kit, see the item rows below. bring lists items that are not wiped from the pockets on arrival. |
needs = { ... } |
The stop is marked with what the server is missing. |
car = { model, at, plate, dirt, valet, keys, wear } |
A vehicle at at (vector4) with a plate of up to 8 capital letters and digits, dirt 0 to 15, a full key unless keys = false, a valet key with valet = true. wear = { engine = 350.0, body = 520.0, burst = { 0 } } sets engine health (-4000 to 1000), body health (0 to 1000) and burst wheel ids (0 to 7, 45, 47). |
car2 |
A second vehicle in the same shape (a bike, boat, helicopter or plane is spawned as that type). It needs a car and its own plate, and gets no key unless keys = true. |
reset = { recipes = { 'workbench:advancedlockpick' }, queue = true, xp = true } |
On arrival the listed recipes (up to 16) are forgotten, crafting jobs queued during the tour are canceled and crafting XP goes back to its value at the start of the tour. |
prime = { dumpster = vector3(-44.36, -1758.91, 28.5), radius = 4.0 } |
On arrival every loaded bin within the radius (0.5 to 30) re-rolls, and the next search of each finds at least one item for certain (the preparation lasts 30 minutes). |
ped |
The stop's character: 'own', { m, f, label } with GTA ped models, or { mp = true, label } for the Binco model. random = true dresses the ped randomly; comps = { m = { { component, drawable, texture }, ... }, f = { ... } } and props = { m = { { anchor, drawable, texture }, ... }, f = { ... } } dress it exactly (a prop drawable of -1 clears the prop). |
skins |
One or two more characters ({ m, f, label }, with the same dress fields) for the skin and skin2 cues. |
points |
1 to 8 script points, each with say and act in en and hu, and optionally cue, needs and admin. |
Item rows are { name, count, meta } and may add bag = true (worn on the back; one per stop), ground = true, into = '<item of an earlier row>', ifMissing = true, look and worn. An item the server does not have is left out with a console warning. meta can carry the admin-give keys jammed = true (firearms) and oxygen = 90 (whole seconds of air in diving gear).
look = { m = { parts }, f = { parts } }gives a clothing item exactly that look for each body. A part is{ c = component or a = prop anchor, d = drawable, t = texture, col = collection };coldefaults to''(the base game). A look the clothing index refuses leaves the row out, with a console warning.worn = trueputs the piece straight on the Binco model: it needsped.mp, alook, a count of 1 and one row per area, and it cannot be used on the bag, vest or gloves areas.
| Cue | Side | What it does |
|---|---|---|
car |
Server | Brings the stop's vehicles back. A vehicle still within 40 m is kept and gets its dirt and damage again. |
skin, skin2 |
Server | Turns the presenter into the stop's first or second skins character. |
restore |
Server | Undoes skin and skin2 (at the Clothing as Items stop it rebuilds the Binco model). |
hurt |
Client | Health drops by 60, never below 130. For bandage and first aid points. |
soak |
Server | Ruins the carried water-sensitive items like a real dive, even with Config.Water.enabled = false. |
starve |
Server | Hunger and thirst go down to 30 (only lowered, never raised); the old values come back at the end or on a retake. Needs a status system. |
valet |
Server | Toggles: the first press takes the stop's full car key out of the pockets, the second hands a new one back. The stop's car needs valet = true. |
muddy |
Client | Dirties the presenter and, with ncore_hud, sets the hygiene need to 20 %. |
wade |
Client | Walks the presenter into knee-deep water ahead. |
orbit |
Client | A 6 second camera orbit for back shots (a backpack, slings, a vest). It ends early when a panel opens, during travel or on death. |
map |
Client | Opens the pause menu map. |
| Need | Met when |
|---|---|
wear |
Config.Clothing.asItems is true. |
water |
Config.Water.enabled is true. |
status |
The framework has a status system that answers for the presenter. |
police |
The presenter has an on-duty police job of grade 1 or higher. |
partner |
Another player in the same routing bucket stands within 30 m of the presenter. |
character |
ncore_character is started. |
appearance |
An appearance resource is found. |
disposal, drops |
That feature is enabled. |
craft, gunbench, shop, vending, dumpster, cache, stash |
That module is started. |
The shipped tour needs a second player within 30 m for the Give, Trade & Search stop, the diner's third point and the police station's third point, an on-duty police job of grade 1 or higher for the Police Armory & Forensics stop, and a status system for the diner's first point.
The Clothing as Items stop (ped.mp):
- On arrival the stop builds a GTA Online (freemode) character: a face, hair, eyebrows and the stop's worn items. The body is the presenter's own when they play a freemode character, otherwise
Config.Admin.demo.mpSex. During the stop the presenter wears a memory-only stand-in closet, so their own worn clothes are never moved, sold or saved over. Leaving the stop or ending the tour takes the demo pieces off, sends pieces bought at the stop to the pockets, and brings the own closet and character back. With clothing as items off or skins off, the stop keeps the presenter's own ped and gives the worn rows into the pockets. - With ncore_character running, the Binco model needs ncore_character 1.0.4 or newer (the build with the
DemoAwareexport). With an older build the stop keeps the presenter's own character and puts the worn rows in the pockets, and a one-time console warning names the reason. - When the own character cannot be confirmed after the tour (also for a tour wound up on join),
DemoPedstaysgta: appearance saves stay off, ncore_character keeps every counter except the items-only clothing store closed, and a new tour is refused. This lasts until the server sees the presenter's own model again, or the presenter switches character or joins again. Ending the tour while dead at this stop is refused ("You are dead. Get up first."). - Do not open another appearance script's own clothing menu (illenium-appearance, qb-clothing) at this stop. That menu saves the whole look it shows, the Binco model's face included, as the presenter's own, and the demo cannot stop a save made inside another script.
Demo video fields#
The overlays of the recorded tour (arrival title card, video intro, feature callouts, opening card and closing card) take every word from data/demo.lua; nothing for the video is in the locale files.
- Stop fields:
kicker(en and hu),emblem = { item = 'name' }(or{ icon }),chips(up to 3 of{ icon | item, label, at?, instead? }),intro = { promise, cards }(2 to 4 cards of{ icon | item, label, sub, at?, instead? }) andcallouts(up to 12 of{ at, key = true | cue = 'x' | on = 'trunk|glovebox|stash|container|drop' | stash = 'id', style = 'full|compact|slam', spare?, icon | item, label, sub }).intro = { blurb, points }with 2 to 5 lines is also accepted. A slam callout takes nosub. atandinstead:atties a chip or card to a point. When that point's need is missing, the entry is dropped, or replaced byinstead.insteadmay carry its ownat:instead = { at = 4, icon | item, label, sub? }; when that point's need is missing too, the entry is dropped (the diner shows "Spoiled Food" only while the spoiled-sandwich point runs).- Callouts: each takes exactly one trigger:
key = true(the Delete key),cue(the cue its point runs),on(that kind of container opens) orstash(that stash opens). Aspare = truecallout is akey = truecallout shown after the others. Over the open inventory a callout is always compact (a slam too) and sits bottom left, or top left when the panel fills that corner; in the 3D gun bench it is compact at the top center. - Tour fields:
tour = { title, outro, brand, tagline, proof, badges, pitch, pills, cta, url, by, firstOpen }.titleandoutroare required;brandandurlare short plain lines;badgesandpillshold up to 10 each. The opening card and the closing card read these. The closing card showsctaandurlas text. tour.firstOpen: up to 3 callouts (compactorfull) shown at a tour's first inventory open while automatic callouts are on. A row may carryneed = 'grid'(shown only withConfig.Grid.enabled = true) orneed = 'tabs'(shown only whenConfig.Categoriesis exactly items, keys, weapons, clothes, bag), and{key}in asubline is replaced withConfig.Grid.rotateKey. The shipped two name the grid and the five tabs.- Points:
admin = '<tab id>'(lowercase letters, up to 16, for example'logs'or'items') opens that admin tab instead of the Demo tab, see "Admin panel at a point" above. - Checks: icons must be glyphs the page draws, pictures must be items (an unknown item shows a box glyph with a console warning), every
atmust name an existing point, and a cue callout must sit on the point that runs that cue.
Kits#
Items tab > Kits gives a kit to yourself, another player, a container or the ground (a pile at your feet, in your routing bucket). It needs lri.admin.give. The result has a ticket, and "Take back" undoes it while the server runs. After a restart, Revert on the kit's log row undoes it (needs lri.admin.logs and lri.admin.give), while the given stacks are in loaded containers.
The list shows, in this order:
- Your own kits from
Config.Admin.kits(the shipped config hasstarter). - Preset kits from
data/admin_scenarios.lua: Food and drink, Medical, Tools, Containers, Evidence. Each demo stop's kit (demo.<stop id>) is listed here too. - Built in: Every firearm, loaded (a full magazine each); One of every stackable item (blueprints included); One of every evidence item; One of every key item; 1000 of each money item; and "Everything for <bench>" for each crafting bench (the materials and tools of all its recipes).
Config.Admin.kits = {
starter = { label = 'Starter pack', items = { { name = 'water', count = 2 }, { name = 'sandwich', count = 2 }, { name = 'bandage', count = 2 } } },
patrol = { label = { en = 'Patrol kit', hu = 'Járőr csomag' }, items = { { name = 'weapon_pistol', count = 1 }, { name = 'ammo-9', count = 48 } } }
}A kit id is up to 64 letters, digits, _, ., : and -. Each row is { name, count, meta }; count defaults to 1. A wrong row is left out with a console warning.
Admin commands#
| Command | Ace | What it does |
|---|---|---|
invview <player id> [held] |
lri.admin |
Opens a player's inventory, or their held store, read-only. In game only. |
invconfiscate <player id> [reason] |
lri.admin.edit |
Takes every body slot and worn bags with their contents into a held store and takes off a worn vest. Worn clothing stays on unless Config.Admin.confiscateWorn is true. |
invreturn <player id> |
lri.admin.edit |
Gives the held store back, onto the ground what does not fit. |
invgive <player id> <item> [count] |
lri.admin.give (debug mode: Config.Debug.ace) |
Gives an item. |
invkey <player id> <vehicle\|door\|house\|stash> <target> [extra] |
as invgive |
Cuts a key the way a garage or housing script would. |
invdelstorage <id> confirm |
lri.admin.storage and lri.admin.edit |
Deletes a storage. |
invcheckitem <item> [min] |
lri.admin.economy |
Who holds an item. |
invminting [hours] |
lri.admin.economy |
The minting report for the last 24 hours, or the hours you give (1 to Config.Admin.minting.maxHours, 168 by default). |
invhistory <uid> |
lri.admin.logs |
The history of one item, up to 500 rows. |
invcraftxp <player id> <track> <total XP> |
lri.admin.edit |
Sets a crafting track's XP. |
invclips [clear [weapon or part]] |
lri.admin.config |
Lists, or forgets, the magazine sizes measured from the game. |
invgridflatten [dry] |
lri.admin |
Turns saved grid inventories back into slot lists; stacks that do not fit go to a held store. dry only reports. Refused while Config.Grid.enabled is true. |
invpremium <add\|remove\|set\|get> <server id or identifier> [amount] |
Config.Premium.ace |
Premium currency. Works only while Config.Premium.enabled is true, and it ships off. |
The commands also run in the server console, except invview, /invslings, /invpose and /invthumbs. The names of invview, invconfiscate and invreturn are Config.Admin.viewCommand, .confiscateCommand and .returnCommand.
/invpose#
Needs lri.admin.pose and Config.Poses.enabled (true, or 'debug' with debug mode on). /invpose [item] opens the pose tool; it also opens from the Items tab and from a key binding with no default key (Config.Poses.key). It edits the pose of an item in the hand, on the ground, in a pile, on the body, as a worn bag and when thrown.
| Key | Action |
|---|---|
| Arrows, Page Up / Page Down | Move; Page Up and Page Down change height |
| Ctrl (hold) | Rotate instead of move |
| Shift (hold) | Finer step |
| Mouse wheel | Step size |
| Q | Up and down move on Y or Z |
| Tab | Next place (hand, ground, pile, body, bag, thrown) |
| E | Next target |
| R | Back to the shipped pose |
| C | Print the config line |
| Enter | Save for every player at once and print the config line |
| Backspace | Close |
Opened while you throw, place, offer, use or hold an item, it takes that item and pose and gives it back when you leave. "On the body" edits the sling spot your job uses. invposes prints every saved pose as config lines.
/invslings#
Needs lri.admin.panel. Prints in F8 what your own game draws on the body: each slung weapon, its spot and the object budget. It runs in game, not in the server console.
/invthumbs#
Needs lri.admin.config and a started screenshot-basic. It photographs an item's model in game and saves it as web/images/<item>.webp: /invthumbs missing takes items without a picture, /invthumbs item,item the named ones, own also replaces shipped pictures, list only lists, and /invthumbs stop ends a run. Shipped pictures are never replaced without own, and every skipped item is reported with its reason. Close the panel and leave any script camera first. Restart the resource afterwards so players get the new pictures. Config.Debug.thumbs sets size, quality, endpoint (set 'ip:port' when you join through a proxy), height, settleMs and fov.
nCore Development · https://intelnpc.com · support on intelnpc.com, reply within 72 hours
Grid inventory for FiveM. Standalone, ESX, QBCore, QBox, ND_Core and ox_core.
nCore Development · intelnpc.com · Resource: ncore_inventory · Version: see fxmanifest.lua
What it is#
A backpack is a real backpack on your character. A gun you drop lies on the ground as that gun. A burger goes one bite at a time, and a trade only happens when both players confirm it.
The inventory runs as one resource, on its own or on top of your framework, and saves to oxmysql or to the server's own storage. The server decides every move, the panel only asks.
What it does#
- Grid inventory where every item takes real cells. R rotates, and the server re-checks every move.
- Five tabs on the body: items, keys, weapons, clothes and bag.
- Backpacks and vests show on your character. Backpacks, duffels and the plate carrier carry their own inventory.
- Clothing pieces are items. Outfits save at the wardrobes of 8 clothing stores.
- Drop, throw or place items. A pile shows the real model of what's in it.
- Food and drinks go bite by bite, spoil over time, and you can share them.
- 106 weapons as items with wear, jamming, serial numbers, weapons on the body and a 3D gun bench.
- Trade window for items and cash, searching and robbing, hands up.
- Trunks, gloveboxes and physical keys for cars, doors, houses, businesses and safes.
- 8 shop types on 44 counters, 256 vending machines, 7,884 searchable bins, 1,369 hiding spots.
- Crafting with blueprints, tool wear and a background queue. Carry strength that grows as you haul things around.
- Admin panel (
/invadmin) with online and offline inventories, kits, logs, an item editor, an economy view and live config. - Demo mode for recording showcase videos and a testing guide for your staff.
- 488 items with pictures and descriptions in 8 languages.
The full feature list, with how to reach each feature and the setting that switches it, is in FEATURES.md.
What's in the package#
| Folder | What it is |
|---|---|
ncore_inventory |
The inventory itself, with sql/install.sql for owners who create the tables by hand and the four docs listed at the bottom. |
ox_inventory |
A small compatibility folder for QBox and ESX Legacy. It has no inventory of its own and stores nothing, it forwards every call to ncore_inventory. Only install it on QBox or ESX Legacy, see INSTALLATION.md. |
Requirements#
- OneSync on.
- Optional: oxmysql (database storage,
invmigrate, saved trunks and gloveboxes of owned cars, which it reads from the framework's vehicle table), ox_target or qb-target, an appearance resource for clothing (ncore_character, illenium-appearance, fivem-appearance, qb-clothing or esx_skin). - No ox_lib and no build step. QBox needs ox_lib for qbx_core itself.
- Game build:
set sv_enforceGameBuild 3407or newer is recommended so every shipped weapon works.
Setup, server.cfg order per framework and the database notes are in INSTALLATION.md.
Works with#
| Area | Resources |
|---|---|
| Frameworks | Standalone, ESX (1.1 to Legacy), QBCore, QBox, ND_Core, ox_core. Picked up at start, so they go above ensure ncore_inventory. |
| Storage | oxmysql, or the server's own KVP store without it |
| Target eye | ox_target or qb-target. Without one, everything opens with E. |
| Clothing | ncore_character, illenium-appearance, fivem-appearance, qb-clothing, esx_skin |
| Door and house keys | ox_doorlock, qb-doorlock. House keys for bcs_housing, loaf_keysystem and qb-houses. nui_doorlock isn't supported. |
| Car keys | Work without a key script. FEATURES.md lists the vehicle key scripts it hands the lock to, and what each one gets. |
| Other | txAdmin for the save before a scheduled restart, ps-mdt for the gun registry, screenshot-basic for /invthumbs |
Your other scripts and old saves#
Scripts written for the QBCore inventory exports (AddItem, RemoveItem, HasItem, OpenInventory, CreateShop and the rest) keep working on any framework, and AddItem and RemoveItem take either common argument order. Search, GetItemCount, CanCarryItem and other common export names also answer under exports.ncore_inventory. On QBox and ESX Legacy the bundled ox_inventory folder answers for the frameworks and scripts that ask for an inventory by that name. A script that checks whether another inventory is running before it calls won't work unchanged. The details are in FEATURES.md under "Scripts that call other inventories".
Saved inventories come across with invmigrate in the server console, from four common saved-data layouts. It only reports until you add apply, which runs only with nobody online, and it only reads the old tables. Stashes, trunks and gloveboxes come along too, except from ESX, which has no stash tables. It needs oxmysql, see section 4 of DOCUMENTATION.md.
For your own resources, RegisterHook watches or refuses moves, takes, opens, uses, buys, crafts and trades, RegisterItem adds items at runtime, and RegisterStash adds stashes. Every export, event and state bag is in section 4 of DOCUMENTATION.md.
Keys and commands players use#
| What | Default |
|---|---|
| Open the inventory | F2 or /inventory |
| Hotbar | 1 to 5 |
| Rotate while dragging | R |
| Stop the current action | Backspace |
| Give an item | drag onto a player, or /give |
| Trade | /trade |
| Search or rob | /search, /rob |
| Hands up | X or /handsup |
| Accept or decline a request | Y or U |
| Lock or unlock the nearest car you have a key for | L |
| Fix a stuck screen | /invunstuck |
Every key can be changed by the player under Settings > Key Bindings > FiveM. Admin and console commands are in section 5 of DOCUMENTATION.md, and invmigrate is in section 4.
Where to configure#
| File | What's in it |
|---|---|
config.lua |
Every setting. Start here. |
shared/defaults.lua |
Fills in any setting missing from your config.lua. Don't edit it, copy the new one over when you update. |
data/items.lua |
Item definitions: weight, size, stack, use, food, containers, weapons. |
data/descriptions.lua |
Item descriptions in all 8 languages. |
data/aliases.lua |
Maps other scripts' item names onto the shipped items. |
data/stashes.lua |
World stashes, lockers, fridges and wardrobes. |
modules/shop/shops.lua |
Shops, counters, stock and prices. |
modules/craft/benches.lua |
Crafting benches and recipes. |
modules/gunbench/benches.lua |
Gun bench locations. |
locales/*.lua |
Interface text in 8 languages. |
data/demo.lua |
The demo tour. |
In the escrow edition all of these files stay readable, plus the framework bridges (bridge.lua, bridge/*.lua) and the web panel.
Updating#
Updates don't install themselves. Download the new version again (escrow from your Cfx.re account, full source from Tebex), keep your own config.lua, and copy the new shared/defaults.lua over the old one so every new setting gets its default. CHANGELOG.md says what else to copy for each version.
Troubleshooting#
The inventory stops at start with a red box that names another inventory. It won't run beside a known one. Take that resource out of server.cfg and restart.
QBox shuts the whole server down at start. Check that setr inventory:framework "qbx" is in server.cfg and that the bundled ox_inventory folder starts right after ncore_inventory. Delete any other folder named ox_inventory (stopping it isn't enough) and don't add provide 'ox_inventory' anywhere.
The console says your framework started after the inventory. Move the framework's ensure line above ensure ncore_inventory, the framework is only picked up at start.
On ESX Legacy the console shows a red "ESX IS RUNNING ITS OWN INVENTORY" box. Follow the fix printed in that box.
The console prints an ALTER TABLE line at start. Your database user can't add a column. Run that line as a user with ALTER rights, then restart the resource.
A player's screen stays blurred or the cursor is stuck. /invunstuck closes the panel and clears the blur, cursor and camera, and any player can run it.
One E press opens two menus at a Binco counter or a wardrobe. Your clothing resource has its own point there. Move one of them, or add enabled = false to wardrobe_store in data/stashes.lua and to binco in modules/shop/shops.lua.
Some weapons are refused as invalid. Your server enforces an older game build. Set sv_enforceGameBuild to 3407 or newer.
Hungarian or Turkish doesn't show. GTA has no such game language, so set Config.Locale = 'hu' (or 'tr') or add setr lr:locale "hu" (or "tr") to server.cfg.
Docs#
- INSTALLATION.md - setup step by step.
- FEATURES.md - everything the script does.
- DOCUMENTATION.md - every setting, item field, export, event and admin tool.
- CHANGELOG.md - what changed in each version.
Support#
Support is on intelnpc.com and I reply within 72 hours. It covers installing, configuring and bugs in the script as shipped. Send your framework, server build, the console error and your Tebex transaction ID.
nCore Inventory is made by nCore Development. It is not approved, sponsored or endorsed by Rockstar Games.
Requirements#
- OneSync on (
set onesync onin server.cfg, or the OneSync setting in txAdmin). The server reads player peds and vehicles for reach checks, clothing checks, ground drops, trunks, gloveboxes and car keys. With OneSync off those fail, and the console prints a warning at start. - oxmysql is optional. Without it everything is saved in the server's own KVP store (unless
Config.Database.preferis'none', which saves nothing). You need oxmysql for:invmigrate, which brings over another inventory's saved data;- keeping the trunks and gloveboxes of owned vehicles, and owner-only trunks (the framework's vehicle table is read through oxmysql);
- the starter kit's check, on a framework, that a character is really new.
- No ox_lib and no build step are needed.
- A framework is optional: ESX, QBCore, QBox, ND_Core or ox_core. Without one there are no jobs or police checks, no bank accounts and no licenses, and money is the
cashitem. - QBox and ESX Legacy also need the bundled
ox_inventorycompatibility folder (step 2). - A recent game build is recommended. Some shipped weapons and models come from recent GTA Online updates. On a server that enforces an older build (
sv_enforceGameBuildin server.cfg), those weapons are refused as invalid, and a pile model the build lacks falls back to a plainer one (the console says so once). The Large backpack's model needs build 2545 or newer and the Tactical backpack's needs 2802 or newer; below that they show an older bag model. Setsv_enforceGameBuildto a recent build your FiveM server artifacts support.
Steps#
-
Copy the
ncore_inventoryfolder intoresources/[ncore](create the[ncore]folder if you do not have one yet). Do not rename it. -
QBox and ESX Legacy only: copy the shipped
ox_inventoryfolder, a compatibility layer for ncore_inventory, intoresources/[ncore]next toncore_inventory. Delete any other folder namedox_inventoryfirst (stopping it is not enough). Do not lower itsversionline and do not addprovide 'ox_inventory': qbx_core reads that version and stops the server when it fails its check. QBCore, ND_Core, ox_core and standalone servers do not need this folder. -
Optional: if you run oxmysql, import
sql/install.sqlinto your database. The resource also creates its tables by itself at start, so this is only for owners who prefer to create the schema by hand. See Database below. -
Add the resource to
server.cfg. The framework is detected once, at start, so oxmysql and your framework go aboveensure ncore_inventory. If you use ox_target or qb-target, put it above as well. Resources that callRegisterStash(housing scripts and the like) go below it.Standalone
server.cfgensure oxmysql # optional ensure ncore_inventoryQBCore
server.cfgensure oxmysql ensure qb-core ensure ncore_inventory # your qb- resources after this lineESX Legacy (the bundled compatibility folder goes directly after ncore_inventory)
server.cfgsetr inventory:accounts "[]" ensure oxmysql ensure es_extended ensure ncore_inventory ensure ox_inventoryThe
setr inventory:accounts "[]"line is required on ESX Legacy 1.14 and 1.15. Without it es_extended uses["money", "black_money"], andblack_moneyis also an item in this inventory. es_extended copies every change to that ESX account into the item, and nothing copies the item back, so the two drift apart the first time a player drops or hands over the item. The console prints a warning at every start until the line is set. ESX 1.16 and newer always mirrorblack_moneyinto an item, with no write-back, whatever this line says; there the ESXblack_moneyaccount and theblack_moneyitem are separate balances.On ESX Legacy the console confirms "ESX is in its ox_inventory mode". If it prints a red "ESX IS RUNNING ITS OWN INVENTORY" box instead, follow the fix in that box. ESX 1.1 and 1.2 have no third-party inventory mode: xPlayer item calls keep using ESX's own inventory there, and the console says so at start.
QBox
server.cfgsetr inventory:framework "qbx" # qbx_core shuts the server down without this line ensure oxmysql ensure ox_lib # qbx_core needs it ensure qbx_core ensure ncore_inventory ensure ox_inventoryND_Core or ox_core: ensure the framework (and what it needs itself), then
ensure ncore_inventory.A framework that starts after ncore_inventory is not picked up. The console names it and tells you to move its
ensureline above. -
Grant the admin ace:
server.cfgadd_ace group.admin lri.admin allow add_principal identifier.license:<license> group.adminlri.admincovers every admin part (lri.admin.panel,.edit,.give,.capacity,.storage,.shops,.economy,.logs,.config,.pose) and premium coins (lri.admin.premium). For smaller staff roles grant single parts instead;lri.admin.panelis always needed to open the panel. The test lab has its ownlri.labace, for test servers only. A VIP capacity tier is granted withadd_ace group.vip lri.tier.vip allow.Make sure
Config.Debug.commandsisfalseinconfig.lua(that is how it ships). -
Language: with
Config.Locale = 'auto'the server picks one language for everyone from thelr:locale,locale,ox:locale,esx:localeortxAdmin-localeconvar, in that order, and otherwise uses English. The shipped languages areen,hu,de,fr,es,pt-br,plandtr. GTA has no Hungarian or Turkish game language, so a Hungarian or Turkish server setsConfig.Locale = 'hu'(or'tr') or addssetr lr:locale "hu"to server.cfg. -
Restart, join and press F2. From the server console,
invgive <player id> water 10proves the round trip.
Database#
This section applies only when oxmysql is running and Config.Database.prefer is 'auto' (the default) or 'mysql'. With 'kvp' the server's own KVP store is used, and with 'none' nothing is saved at all, even with oxmysql. The console confirms it at start with storage: oxmysql, table followed by the table name.
The main table is ncore_inventory (the name comes from Config.Database.table). At every start the resource creates it if it is missing and adds any column it lacks. The other tables are created the same way: ncore_inventory_logs (Config.Logs.table), ncore_inventory_placed for storages placed in the world, and ncore_inventory_premium when premium coins are switched on (Config.Premium.enabled).
If the database user has no ALTER right, a missing column cannot be added. The console then prints an error that names the column and the exact statement. Run that statement as a database user with ALTER rights, then restart the resource. For the default table name the statements are:
ALTER TABLE `ncore_inventory` ADD COLUMN `owner` VARCHAR(96) DEFAULT NULL;
ALTER TABLE `ncore_inventory` ADD COLUMN `kind` VARCHAR(24) NOT NULL DEFAULT 'player';
ALTER TABLE `ncore_inventory` ADD COLUMN `label` VARCHAR(96) DEFAULT NULL;
ALTER TABLE `ncore_inventory` ADD COLUMN `parent` VARCHAR(96) DEFAULT NULL;
ALTER TABLE `ncore_inventory` ADD COLUMN `slots` SMALLINT UNSIGNED NOT NULL DEFAULT 24;
ALTER TABLE `ncore_inventory` ADD COLUMN `max_weight` INT UNSIGNED NOT NULL DEFAULT 32000;
ALTER TABLE `ncore_inventory` ADD COLUMN `accepts` VARCHAR(255) DEFAULT NULL;
ALTER TABLE `ncore_inventory` ADD COLUMN `meta` VARCHAR(1024) DEFAULT NULL;
ALTER TABLE `ncore_inventory` ADD COLUMN `data` LONGTEXT DEFAULT NULL;
ALTER TABLE `ncore_inventory` ADD COLUMN `modstate` LONGTEXT DEFAULT NULL;
ALTER TABLE `ncore_inventory` ADD COLUMN `updated_at` DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP;Run only the lines the console names. If you changed Config.Database.table, use your table name; the console already prints it.
-
Without the
modstatecolumn, module state (crafting queue jobs, what a worn container remembers) lasts only until a restart. WithConfig.Drops.persiston, piles on the ground also last only until a restart, and the console prints the samemodstatestatement for that. -
The
metacolumn must be 1024 characters wide. The resource widens a narrower one at start; if it cannot, the console says how wide it still is, and a row whose meta is longer is not saved until the column is widened. As a user with ALTER rights run this, then restart the resource:SQLALTER TABLE `ncore_inventory` MODIFY COLUMN `meta` VARCHAR(1024) DEFAULT NULL; -
If a column cannot be added to
ncore_inventory_placed, the console tells you to run theCREATE TABLEfor that table fromsql/install.sql.
Test drive in 5 minutes#
- Add the two ace lines from step 5, restart and join.
- Type
/invadmin. The admin panel opens on the Testing tab: a guided tour (326 steps in 42 parts) with setup buttons and "Show on map" buttons that set a waypoint. The shield button in the inventory header opens the panel too. - Open the Items tab and its Kits view. Give yourself food and drink, medical supplies, tools, containers, evidence, every firearm loaded, one of every key item, 1000 of each money item, one of every stackable item, or everything a crafting bench needs. Your own kits go in
Config.Admin.kits. - From the server console:
invgive <id> cash 1000- on standalone and ox_core the cash item is the money shops take. On ESX, QBCore, QBox and ND_Core shops charge the framework's cash account, so use your framework's money command there.invkey <id> vehicle <plate>- cuts a car key for that plate. Using it near the car locks and unlocks it, and so does the L key (Settings, Key Bindings, FiveM, "Lock or unlock the nearest car you hold a key for"). Where a vehicle key resource with its own lock key runs, that resource handles the press.
- On a test server only, set
Config.Debug.commands = trueand addadd_ace group.admin lri.lab allow. That switches on the test lab and the bench commands: the Testing tab's teleport, car and money buttons,invitem,invfill,invmoney <amount> [player id](through the framework's cash account, or the cash item without one) and/invdebughelp. Never do this on a live server: anyone holding thelri.adminace can then create any item and open any inventory.
Important#
- Do not rename the
ncore_inventoryfolder; exports, pictures and the NUI page are found by that name. - Stop every other inventory resource first. This resource refuses to start beside a known one and names it in the console (add your own to
Config.Conflicts.extra). On QBCore also remove qb-weapons; the console warns while it runs. - A shop another resource registers while the inventory is still starting is built as soon as the shop module is up; a refused registration is logged with its reason.
- The Binco counters and the wardrobes stand inside GTA's clothing stores, where clothing resources often have their own spots. With ox_target or qb-target running, the Binco counter opens through the target eye. The wardrobe always keeps its marker and E prompt, also with a target eye. If your clothing resource opens its own menu with E in the same place, one E press opens both: move those points, or add
enabled = falsetowardrobe_storeindata/stashes.luaand tobincoinmodules/shop/shops.lua. - With ncore_character running, its own clerk stands at the Binco counter and the inventory draws no Binco blip of its own, because ncore_character marks the same store. E at the clerk opens the item shop and G opens ncore_character's fitting room. With ox_target or qb-target running, the fitting room is a "Fitting room" option on the target eye instead of G. The wardrobe has its own marker beside the counter.
- qb-pawnshop uses the same Vinewood counter as the shipped pawn shop; keep one of them (
enabled = falseonpawn_downtowninmodules/shop/shops.luaturns ours off). - Saved inventories from another inventory are brought across with
invmigratein the server console (needs oxmysql). The dry run works any time;applyruns only with nobody online. Stashes, trunks and gloveboxes come across from the ox, qb and qs-style sources; from ESX only player inventories (with loadout and accounts) come across. See DOCUMENTATION.md. - A server that ran on KVP and adds oxmysql later gets a console banner.
invmigrate kvpfollowed byinvmigrate kvp applycopies the saved containers from the KVP store into the database; the KVP rows stay where they are. Admin item edits and old log lines stay in KVP, premium coin balances are read from KVP until each one is next saved to the database, and owners that already have rows in the database are skipped. - Keep your own
config.lua: any setting it leaves out is filled in fromshared/defaults.lua. When you update, copy the newshared/defaults.luaover the old one.
Updates don't install themselves. When a new version is out, download it again (escrow from your Cfx.re account, full source from Tebex), keep your own config.lua, and copy the new shared/defaults.lua over the old one so every new setting gets its default. Each version below says what else to copy. New versions are announced on intelnpc.com.
1.0.33#
First public release. Everything the script does is listed in FEATURES.md.
€44.99
Ready when you are
Instant delivery, checkout right here on the site, and a Discord full of people who will answer before you pay.


