Description
A QBCore smash-and-grab: the thief breaks several jewelry display cases for loot, and the first hit trips a silent alarm that drops a flashing blip on every on-duty cop's map. It is the classic loud, time-pressured heist that turns a robbery into a police chase.
Prompt Template
You are writing a FiveM resource for qb-core. Produce TWO files (client.lua +
server.lua) for a jewelry store smash-and-grab with a police alert.
Framework: QBCore via exports['qb-core']:GetCoreObject().
Client:
- A Cases table of display-case coords [CASE_COORDS]. Track a `looted` table and a
one-shot `alarmRaised` flag.
- When within 1.5m of an un-looted case and the player presses E (control 38), play
'mp_smash_window'/'window_smash' (RequestAnimDict + `while not HasAnimDictLoaded`),
mark it looted, and TriggerServerEvent('jewelry:grabLoot', idx).
- On the FIRST grab only, TriggerServerEvent('jewelry:raiseAlarm', GetEntityCoords(ped)).
- RegisterNetEvent('jewelry:copBlip') to AddBlipForCoord, SetBlipFlashes(true), then
Wait(30000) and RemoveBlip.
Server:
- jewelry:raiseAlarm iterates QBCore.Functions.GetPlayers(), and for each whose
PlayerData.job.name == 'police' TriggerClientEvent('jewelry:copBlip', pid, loc).
- jewelry:grabLoot validates the player, then Player.Functions.AddItem('rolex',1) and
AddMoney('cash', [LOOT_PER_CASE]).
Use PlayerPedId(), never GetPlayerPed(-1). Police filtering and loot are server-side.
Return only Lua, separated by "-- ===== client.lua =====" / "-- ===== server.lua =====".
Expected Output
The reference Lua lives at content/expected-outputs/heists/02-jewelry-smash-grab-cops.lua. It implements the per-case smash loop with a one-shot alarm, a server fan-out that blips only on-duty police, and server-side loot grants. The fxmanifest splits it into a client_script (cases, smash, blip) and a server_script (alarm fan-out, loot).
-- Resource: jewelry-smash-grab (QBCore)
-- Smash display cases for loot; first grab triggers a silent alarm that dispatches cops.
-- client.lua handles target cases + smash anim; server.lua pays loot and alerts police.
-- ===== client.lua =====
local QBCore = exports['qb-core']:GetCoreObject()
local Cases = {
vector3(-630.3, -236.4, 38.0),
vector3(-625.1, -230.9, 38.0),
vector3(-622.0, -233.2, 38.0),
}
local looted = {}
local alarmRaised = false
local function smashCase(idx)
if looted[idx] then return end
local dict = 'mp_smash_window'
RequestAnimDict(dict)
while not HasAnimDictLoaded(dict) do Wait(0) end
TaskPlayAnim(PlayerPedId(), dict, 'window_smash', 8.0, -8.0, 1500, 0, 0, false, false, false)
Wait(1500)
ClearPedTasks(PlayerPedId())
looted[idx] = true
if not alarmRaised then
alarmRaised = true
TriggerServerEvent('jewelry:raiseAlarm', GetEntityCoords(PlayerPedId()))
end
TriggerServerEvent('jewelry:grabLoot', idx)
end
CreateThread(function()
while true do
local sleep = 1000
local coords = GetEntityCoords(PlayerPedId())
for i, c in ipairs(Cases) do
if not looted[i] and #(coords - c) < 1.5 then
sleep = 0
if IsControlJustReleased(0, 38) then smashCase(i) end
end
end
Wait(sleep)
end
end)
RegisterNetEvent('jewelry:copBlip')
AddEventHandler('jewelry:copBlip', function(loc)
local blip = AddBlipForCoord(loc.x, loc.y, loc.z)
SetBlipSprite(blip, 161)
SetBlipColour(blip, 1)
SetBlipFlashes(blip, true)
Wait(30000)
RemoveBlip(blip)
end)
-- ===== server.lua =====
local QBCore = exports['qb-core']:GetCoreObject()
local LootPerCase = 1800
RegisterNetEvent('jewelry:raiseAlarm')
AddEventHandler('jewelry:raiseAlarm', function(loc)
local cops = QBCore.Functions.GetPlayers()
for _, pid in ipairs(cops) do
local Player = QBCore.Functions.GetPlayer(pid)
if Player and Player.PlayerData.job.name == 'police' then
TriggerClientEvent('jewelry:copBlip', pid, loc)
end
end
end)
RegisterNetEvent('jewelry:grabLoot')
AddEventHandler('jewelry:grabLoot', function(idx)
local src = source
local Player = QBCore.Functions.GetPlayer(src)
if not Player then return end
Player.Functions.AddItem('rolex', 1)
Player.Functions.AddMoney('cash', LootPerCase)
TriggerClientEvent('QBCore:Notify', src, 'You grabbed loot from case '..idx, 'success')
end)
Known Failure Modes
- Client-side cop alert — Claude scans nearby players locally; instead fan out on the server filtered by
job.name == 'police'. - Spoofable loot — granting items client-side is exploitable; use
Player.Functions.AddItem/AddMoneyon the server only. - Permanent blips — a blip that is never removed clutters the map;
Wait(30000)thenRemoveBlip. - Repeating alarm — re-raising the alarm on every case spams cops; guard with a one-shot
alarmRaisedflag.
Integration Notes
- Split the banners into
client.luaandserver.lua; list both infxmanifest.lua. - Requires
qb-corestarted first and arolexitem defined in yourshared/items.lua. - Test on a dev server with two clients (one set to
police): smash a case as the thief and confirm only the on-duty cop receives the flashing blip and it disappears after 30s.
Profit Potential
$400–$6000/mo on Tebex (expected ~$1500). [INFERRED] priced inside the $50-389 FiveM script band against a hot heist niche; corpus median seller $11.85K/mo (signal-scraper tebex_snapshot n=100), scaled for an intermediate single-resource heist.
Trend Signal
🔥 hot — [INFERRED] multi-stage heists are flagship endgame content servers pay up for.
Sales Angle
Sell as the loud, time-pressured set-piece that turns a robbery into a police chase — the server-side on-duty cop fan-out is the hook. Recommended Tebex price $189.
Difficulty & Ship Time
intermediate · ships in 3-5h.