Inventories
Every inventory in Core Inventory — player pockets, backpacks, vehicle trunks, stashes, shops — is defined as an inventory type in Config.Inventories. When an inventory is opened or created, it uses one of these types to determine its size, position, and behavior.
How Inventories Work
An inventory is identified by a unique name string like stash-police1 or big_trunk-ABC123. The format is:
{inventoryType}-{uniqueId}inventoryType— the key fromConfig.Inventoriesthat defines the grid size and propertiesuniqueId— any string that makes this inventory unique (player ID, plate number, custom name, etc.)
When you call openInventory, the system checks if an inventory with that name already exists. If it does, it opens it with its saved contents. If not, it creates a new empty one using the inventory type definition.
TIP
This means you can create any stash on the fly — just think up a unique name and pass it to openInventory. No config entry needed for each individual stash.
Inventory Types
Inventory types are defined in config.lua under Config.Inventories:
lua
Inventories = {
["stash"] = {
slots = 100,
rows = 10,
x = "25%",
y = "55%",
label = "STASH",
},
["small_backpack"] = {
slots = 20,
rows = 5,
x = "25%",
y = "55%",
label = "BACKPACK",
},
["weapon_case"] = {
slots = 80,
rows = 10,
x = "25%",
y = "55%",
label = "WEAPON CASE",
restrictedTo = {'weapons'},
},
}Type Properties
| Property | Type | Description |
|---|---|---|
slots | number | Total grid slots available |
rows | number | Slots per row (determines grid width) |
x / y | string | Initial screen position (CSS percentage) |
label | string | Display name shown in the UI |
locked | boolean | Prevent dragging the inventory window |
isHolder | boolean | Single-item slot (weapon/clothing holders) |
isShop | boolean | Shop inventory (items are purchased, not moved) |
restrictedTo | table | Only allow items from these categories |
restrictedToItems | table | Only allow specific item names |
restrictedFor | table | Block items from these categories |
restrictedForItems | table | Block specific item names |
discoverItem | boolean | Items must be discovered each time this inventory opens |
placeholder | string | Placeholder image for empty holder slots |
Default Inventory Types
Backpacks
small_backpack (20 slots), medium_backpack (48), large_backpack (48)
Wallets
wallet (9 slots) — restricted to money category
Cases
weapon_case (80 slots, weapons only), storage_case (70 slots)
Storages
stash (100), small_storage (100), big_storage (150), weapon_storage (150)
Vehicle
small_trunk (50), big_trunk (100), glovebox (10)
Shops
smallshop (70), bigshop (240) — isShop flag enabled
Drop
drop — ground drop inventory for discarded items
Opening Inventories
server
exports['core_inventory']:openInventory(source, inventory, inventoryType, label, restrictedTo, openForSource)Opens or creates an inventory and optionally displays it to a player. If an inventory with that name already exists, it opens with its saved contents. If not, a new empty one is created using the inventory type definition.
| Parameter | Type | Description |
|---|---|---|
source | number|nil | Player source (nil to just create without opening UI) |
inventory | string | Unique inventory name |
inventoryType | string | Inventory type key from Config.Inventories |
label | string | Optional display label override |
restrictedTo | table | Optional category restrictions |
openForSource | boolean | Whether to open the UI for the player |
Returns:
voidExample
lua
-- Police evidence locker
exports['core_inventory']:openInventory(source, 'evidence-locker-1', 'stash', 'Evidence Locker', nil, true)
-- Player apartment stash (unique per player)
local citizenid = GetCitizenId(source)
exports['core_inventory']:openInventory(source, 'apartment-' .. citizenid, 'big_storage', 'Apartment Storage', nil, true)
-- Gang stash shared by all members
exports['core_inventory']:openInventory(source, 'ballas-warehouse', 'big_storage', 'Warehouse', nil, true)
-- Restricted stash (weapons only)
exports['core_inventory']:openInventory(source, 'armory-pd', 'weapon_storage', 'PD Armory', {'weapons', 'ammunition'}, true)
-- Pharmacy storage (only misc items allowed)
exports['core_inventory']:openInventory(source, 'pharmacy-storage', 'small_storage', 'Pharmacy', {'misc'}, true)INFO
The inventory name is the unique identifier. You don't need to register each stash individually — just pick a unique name. Two scripts calling openInventory with the same name will access the same inventory contents. Use descriptive prefixes to avoid collisions (e.g., gang-ballas, job-police-armory).
Opening Another Player's Inventory
server
exports['core_inventory']:openOtherPlayerInventory(source, target)Opens another player inventory for searching and transferring items.
| Parameter | Type | Description |
|---|---|---|
source | number | Player who is searching |
target | number | Player being searched |
Returns:
voidExample
lua
-- Police searching a suspect
exports['core_inventory']:openOtherPlayerInventory(copSource, suspectSource)Holder Slots
Holders are special single-item inventories used for weapon and clothing slots. They have isHolder = true and display a placeholder image when empty:
lua
["primary"] = {
slots = 10,
rows = 5,
x = "60%",
y = "25%",
label = "PRIMARY",
restrictedTo = {'weapons'},
isHolder = true,
placeholder = 'weapon_assaultrifle.png'
},When a weapon or clothing item is placed in a holder, it's equipped on the player character.
Player Inventory Layout
A player's full inventory consists of these connected inventories:
| Inventory | Type | Purpose |
|---|---|---|
content-{id} | content | Main pockets (100 slots) |
primary-{id} | primary | Primary weapon holder |
secondry-{id} | secondry | Secondary weapon holder |
melee-{id} | melee | Melee weapon holder |
mask-{id} | mask | Mask clothing slot |
hat-{id} | hat | Hat clothing slot |
tshirt-{id} | tshirt | T-shirt clothing slot |
torso-{id} | torso | Jacket/torso clothing slot |
pants-{id} | pants | Pants clothing slot |
shoes-{id} | shoes | Shoes clothing slot |
glass-{id} | glass | Glasses slot |
accessory-{id} | accessory | Accessory slot |
ear-{id} | ear | Earpiece slot |
watch-{id} | watch | Watch slot |
bracelet-{id} | bracelet | Bracelet slot |
The {id} is the player's citizen ID (QBCore) or identifier (ESX).
Item Inventories
Any item whose name matches an inventory type key automatically becomes a container. When a player uses or opens that item, it opens the matching inventory. This is how backpacks, wallets, cases, and any custom container items work.
For example, the item small_backpack opens the small_backpack inventory type. The item wallet opens the wallet inventory. The connection is purely by name — if the item name matches a key in Config.Inventories, it's a container.
How It Works
- Create an inventory type in
Config.Inventories - Create an item with the same name as the inventory type key
- That's it — the item is now a container
Each individual item instance gets its own unique inventory. If a player has two small_backpack items, each one has separate contents.
Examples
Custom wallet — a small container restricted to money:
lua
-- 1. Add the inventory type in config.lua
["designer_wallet"] = {
slots = 6,
rows = 3,
x = "25%",
y = "55%",
label = "DESIGNER WALLET",
restrictedTo = {'money'},
},
-- 2. Add the item to your framework (same name!)
['designer_wallet'] = {
name = 'designer_wallet',
label = 'Designer Wallet',
x = 1,
y = 1,
category = 'wallets',
description = 'A luxury wallet',
},Toolbox — a container that only holds misc items:
lua
-- Inventory type
["toolbox"] = {
slots = 30,
rows = 6,
x = "25%",
y = "55%",
label = "TOOLBOX",
restrictedTo = {'misc'},
},
-- Item
['toolbox'] = {
name = 'toolbox',
label = 'Toolbox',
x = 2,
y = 2,
category = 'cases',
description = 'A portable toolbox',
},Evidence bag — an unrestricted small container:
lua
-- Inventory type
["evidence_bag"] = {
slots = 15,
rows = 5,
x = "25%",
y = "55%",
label = "EVIDENCE",
},
-- Item
['evidence_bag'] = {
name = 'evidence_bag',
label = 'Evidence Bag',
x = 1,
y = 2,
category = 'misc',
description = 'A sealed evidence bag',
},WARNING
The item name must exactly match the inventory type key. If your inventory type is ["small_backpack"], the item must be named small_backpack — not smallbackpack or small_bp.
For more inventory-related exports like addItem, removeItem, hasItem, canCarry, clearInventory, and more — check out Exports & API.
