FiveM Police, EMS & Jobs — Quasar Framework (qs-core) | Quasar Store | Quasar Store
Documentation
Jobs, Police & EMS
FiveM police job, EMS ambulance job, job center, civilian jobs and drugs for Quasar Framework (qs-core), with grades, paychecks and ESX/QBCore job support.
Every roleplay server needs work. Players need ways to earn money, police need to arrest people, and medics need to pick players up off the street. Quasar Framework (qs-core) comes with all of it: a Job Center, four civilian jobs (miner, lumberjack, fisher and delivery driver), a complete FiveM police job, a FiveM EMS / ambulance job with body-zone injuries and a stretcher, and a drug economy with weed, cocaine and meth. Everything runs on the same job system that ESX and QBCore scripts read. A player you hire with /setjob is a cop for qs-police, for an ESX script that checks xPlayer.job.name and for a QBCore script that checks job.type == 'leo'.
This page explains how jobs, grades and paychecks work, then goes through each job: what the player does, where to go, what it pays and every setting that controls it.
Resource
Folder
What it adds
Needs
qs-jobs
[addons]
Job Center, miner, lumberjack, fisher, delivery driver
Weed, cocaine and meth: gather, process, sell to dealers
qs-core
The txAdmin recipe installs and starts all four. Job definitions, grades, salaries and the death system live in qs-core itself. Every message these jobs show follows the server language you set with setr qs:locale "<code>" in server.cfg.
A job is a name (police), a label players see (Police) and a list of grades. Each grade has its own label and salary. Every character holds exactly one job and one grade at a time. The job is saved with the character and shown on the HUD.
Jobs are defined in one file, [core]/qs-core/shared/jobs.lua:
Defined only. No activity ships for it, so it is ready for your own or a third-party hunting script.
New characters start as unemployed grade 0. You can change this with Config.DefaultJob and Config.DefaultJobGrade in [core]/qs-core/shared/config.lua. The job you set there must exist in jobs.lua.
Quasar Framework pays salaries itself, so no job script has to. Every 30 minutes, every player online with a loaded character receives the salary of their current grade in their bank account and sees Paycheck received: $X. A grade with salary = 0 gets nothing.
Server side. ESX and QBCore equivalents are in the tabs below.
If you ask for a grade the job doesn't have, the player gets the job's lowest grade. Police and EMS are not offered at the Job Center. They are whitelisted jobs, so you hire officers and medics with /setjob or the admin menu. Promotions work the same way: run /setjob again with the new grade.
bash
# hire player 12 as a Police Officer, promote them later to Sergeant
setjob 12 police 1
setjob 12 police 2
# hire player 7 as an EMS Trainee
setjob 7 ambulance 0
The es_extended and qb-core compatibility bridges read the job straight from qs-core, and they write it back to qs-core too. A job set by any script is the same job everywhere.
xPlayer.job and xPlayer.getJob() return the job in ESX Legacy shape:
lua
-- xPlayer.getJob() for a Police Sergeant
{
id = 1, name = 'police', label = 'Police',
grade = 2, grade_name = 'sergeant', grade_label = 'Sergeant', grade_salary = 1000,
skin_male = {}, skin_female = {},
}
ESX.GetJobs() returns every qs-core job in ESX shape (grades["0"], grades["1"]…). ESX.DoesJobExist(job, grade) checks qs-core jobs.
ESX.GetExtendedPlayers('job', 'police') returns every online officer.
esx:setJob fires on the server (source, job, lastJob) and on the client (job, lastJob) whenever the job changes.
xPlayer.setJob(name, grade) writes to qs-core. If the job doesn't exist yet, it is created with grades 0 employee, 1 experienced, 2 advanced and 3 boss.
Player.PlayerData.job returns the job in QBCore shape:
lua
-- PlayerData.job for an EMS Paramedic
{
name = 'ambulance', label = 'EMS', payment = 800,
type = 'ems', onduty = true, isboss = false,
grade = { name = 'Paramedic', level = 1 },
}
type is leo for police and ems for ambulance, so QBCore scripts that check the job type recognise both.
Native scripts use qs-core directly:
lua
-- server
exports['qs-core']:SetJob(source, 'ambulance', 1)
local jobs = exports['qs-core']:GetJobs()
local player = exports['qs-core']:GetPlayer(source)
local job = player.getJob()
-- { name, label, grade, gradeName, gradeLabel, salary, isBoss, onduty }
AddEventHandler('qs:server:jobChange', function(src, job)print(src, job.name, job.grade)
end)
lua
-- client
AddEventHandler('qs:client:onJobUpdate', function(job)print('My job is now', job.label, job.gradeLabel)
end)
exports['qs-core']:RegisterJob(name, def) adds a job at runtime on the server, using the same table shape as .
Installing an ESX or QBCore job script? Define the jobs and grades it expects in jobs.lua (or in qb-core/shared/jobs.lua for QBCore scripts) before you start it. See ESX & QBCore Compatibility.
The Job Center is where civilians find work. It is a public blip labelled Job Center in downtown Los Santos (vec4(-268.24, -957.29, 31.22, 205.0)), with a businessman holding a clipboard. New characters spawn right next to it (qs-core's Config.DefaultSpawn), so it is the first thing a new player sees.
Walk up to the clerk
Within 2.2 m you see Press E to browse jobs.
Press E
The Job Center window opens. Each job has a card with its name, a short description and its paycheck (the grade 0 salary). Your current job is marked Current job.
Apply
Click Apply on a job. You are hired at grade 0 (You are now employed as Miner), the window closes and that job's blips appear on your map.
Quit
Click Quit job to go back to Civilian (unemployed). You see You quit your job.
You have to stay at the Job Center while you apply, and you can't apply for the job you already have. Changing job has no cooldown.
The card text comes from the key desc_<job> in qs-jobs' language files. Add a line to [addons]/qs-jobs/locales/en.lua and to every other language you use:
lua
desc_mechanic = 'Repair and tune vehicles for the people of Los Santos.',
Without it the card has no description. Jobs without a built-in icon get a generic one.
Restart the server
The new job shows up on the Job Center list. Applicants always start at grade 0.
Civilian jobs: miner, lumberjack, fisher and delivery (qs-jobs)#
qs-jobs adds four legal jobs for roleplay servers: three gather → process → sell jobs (miner, lumberjack, fisher) and a delivery driver route. They all work the same way:
You need the job. Each job's blips appear only on the map of players who hold it. At another job's point you see You don't have the right job for this. The peds, rocks and trees are visible to everyone.
Press E within 2.2 m of a point. A progress bar runs while you are frozen in place. Press X to cancel, which gives no reward.
Spots deplete. A rock, tree or fishing spot you have just used is empty for you for 20 seconds. Move to the next one.
Full inventory. If the reward doesn't fit, you get Your inventory is full and nothing is lost.
You're paid in cash. Sales, delivery pay, the delivery bonus and the van deposit all use the cash account (Config.PayAccount).
Selling is all at once. At a buyer, one press of E sells every sellable item you carry. The buyer rolls one price per item type, within that item's range, and pays it for every unit of that type. The total goes into your cash (You sold your goods for $X).
Mine stone at the quarry, smelt it into ingots at the foundry and sell them. Keep an eye out for gold.
Mine at the Quarry
Go to one of the four Quarry zones at the Davis Quartz quarry. Each zone has 7 rocks, 28 in total. Press E at a rock to hammer for 7 seconds and get 1–2 Stone. Every successful swing also has a 6 % chance of a bonus Gold Nugget (You found something rare: Gold Nugget!).
Smelt at the Foundry
At the Foundry, press E to turn 3 Stone into 1 Metal Ingot (6 seconds). Repeat for each batch. If you don't have enough stone you see You don't have enough materials.
Sell to the Metal Buyer
Bring your ingots and nuggets to the Metal Buyer and press E to sell them all.
Cast your line off the pier. Different fish sell for different prices at the fish market. There is nothing to process.
Fish at a Fishing Spot
Stand at one of the three Fishing Spots at the end of Del Perro Pier and press E. Your character fishes for 9 seconds and catches one fish: Mackerel 60 % of the time, Bass 30 %, Tuna 10 %.
Sell at the Fish Market
Take your catch to the Fish Market and press E to sell every fish you carry.
Grab a van at the depot and deliver packages across the city. Finish the route for a bonus.
Start a shift at the Depot
Go to the Delivery Depot and press E (Press E to start a delivery shift). A $100 deposit is taken from your cash for the van. If you don't have it, you see You need $100 cash for the van deposit. You are given 5 stops, picked at random from 7 addresses across south and central Los Santos.
Take the van
A random van (Burrito, Rumpo or Speedo) spawns at the first free spot in the depot lot, with a full tank and a Delivery Van blip. If every spot is blocked, you see No room to spawn the van, try again. The shift is cancelled and your deposit refunded.
Follow the GPS
A Delivery route on your map leads to the current stop. Within 3 m of it, press E (Press E to deliver the package). Your character hands the package over for 3.5 seconds and you are paid $45–65 in cash on the spot. The route then moves to the next stop.
Return to the depot
After the last package (Last package delivered. Return the van to the depot!), the route leads back to the depot. Press E at the depot clerk to end the shift (Press E to end your shift).
Get paid
If you delivered every stop, you get a $150 bonus. Your $100 deposit is refunded in every case. The van is removed wherever it is.
What
Amount
Account
Van deposit
−$100 at the start, +$100 back at the end
Cash
Per package
$45–65 (paid at each stop)
Cash
Route bonus
$150 (all 5 stops delivered, shift ended at the depot)
Cash
A full route
$375–475 in total
Cash
Situation
What happens
You end the shift early at the depot
You keep what you earned per stop and get your deposit back, but no bonus.
You change job during a shift
The shift ends, the deposit is refunded, no bonus, the van is removed.
Account for sales, delivery pay, the bonus and the van deposit.
Config.GatherCooldown
20000
Milliseconds a rock, tree or fishing spot stays empty after you use it.
Config.Center
see above
Job Center ped, scenario, coords, blip and the jobs list it offers.
Config.Delivery.depot
ped s_m_m_postal_01 at vec4(60.7, 121.2, 79.1, 160.0)
Depot clerk and its blip.
Config.Delivery.vanSpawns
3 spots
Where the van spawns (first free spot).
Config.Delivery.vanModels
{ 'burrito3', 'rumpo', 'speedo' }
Van models, picked at random.
Config.Delivery.stopsPerShift
5
Stops per shift (never more than the number of stops).
Config.Delivery.payPerStop
{ min = 45, max = 65 }
Pay per package.
Config.Delivery.finishBonus
150
Bonus for a completed route.
Config.Delivery.deposit
100
Van deposit. 0 disables it.
Config.Delivery.deliverTime
3500
Milliseconds to hand over a package.
Config.Delivery.stops
7 × vec3
The pool of delivery addresses.
Config.Jobs.<job>.gather
per job
Harvest points (see below).
Config.Jobs.<job>.process
per job
Processing point. Optional (the fisher has none).
Config.Jobs.<job>.sell
per job
Buyer ped, location, blip and prices.
Keys inside Config.Jobs.<job>:
Block
Keys
gather
prop (model spawned at each point; leave it out for spots without a prop, like fishing), perZone (props per location), spread (scatter radius in metres), item, min, max, time (ms), bonus = { item, chance, count } (optional), catches = { { item, weight }, … } (optional; replaces item/min/max with a weighted roll of one item), anim = { dict, clip } or scenario, blip, locations.
process
input, inputAmount, output, outputAmount, time (ms), anim, blip, locations (vec4; the heading turns the player).
sell
ped, scenario, coords, blip, prices = { item = { min = …, max = … } }.
You can build a new activity job without writing any code. The key in Config.Jobs must be the job name.
Create the job and its items
Add the job to [core]/qs-core/shared/jobs.lua, as in Adding a job to the Job Center above. Then add any new items to the base table in [core]/qs-core/shared/items.lua:
qs-police is a complete FiveM police job for Quasar Framework. Officers can cuff, escort, search and confiscate, put suspects in vehicles and issue fines. They can collect bullet casings and blood samples at crime scenes, match DNA in a forensics lab, store evidence in a shared evidence locker, draw gear from the armory and take vehicles from the police garage. Dispatch alerts warn every officer about gunfire, vehicle break-ins and anything your own scripts report.
Everything requires the job police. Every grade can use every feature. Grades only set the salary, from Recruit ($500) to Chief ($2,000), and the boss flag that ESX and QBCore scripts read. Hire officers with /setjob <id> police <grade>.
The station is at Mission Row. Its Police Station blip is public. All the other points work only for police: other players standing there see You are not a police officer.
Point
Location (Config.Station)
How to use it
Station blip
coords = vec3(428.2, -984.5, 30.7)
Public map blip Police Station.
Armory
armory = vec4(452.0, -980.1, 30.7, 90.0)
Press E to open the armory, then Take any item.
Evidence locker
locker = vec4(452.5, -973.2, 30.7, 90.0)
Shared stash for all officers. See below.
Forensics lab
lab = vec4(437.13, -996.31, 30.69, 0.0)
Press E to use the forensics lab: analyse blood samples.
Garage
garage = vec4(454.6, -1017.4, 28.4, 90.0)
Press E to open the garage: spawn a police vehicle. Officers also get a Police Garage blip.
The armory hands out gear for free, with no stock limit and no grade restriction. Each Take gives the count below (as long as it fits in your inventory).
Item
Count per Take
weapon_pistol · Pistol
1
ammo_pistol · Pistol ammo
2
armor · Body Armor
1
handcuffs · Handcuffs
1
evidence_bag · Evidence Bag
5
bandage · Bandage
3
Change the list in Config.Armory. Any item that exists in the item catalogue works, including the weapons from qs-coreweapons:
lua
Config.Armory = {
{ name = 'weapon_pistol', count = 1 },
{ name = 'ammo_pistol', count = 2 },
{ name = 'weapon_stungun', count = 1 },
{ name = 'weapon_nightstick', count = 1 },
{ name = 'weapon_flashlight', count = 1 },
{ name = 'armor', count = 1 },
{ name = 'handcuffs', count = 1 },
{ name = 'evidence_bag', count = 5 },
{ name = 'bandage', count = 3 },
}
A shared stash, police_evidence (Evidence Locker), with 50 slots and 200 kg of space. Every officer sees the same contents, and they are saved by the inventory, so they survive restarts.
With qs-coreinventory: stand at the locker and open your inventory (F1). The locker opens next to it.
With qs-inventory: stand at the locker and press E.
Only police get access to the locker. There is no marker or prompt on the spot, so show new officers where it is.
On foot at the garage point, press E and pick a vehicle. It spawns at the garage spawn with a full tank, unless something is parked there (The spawn point is blocked). To put it back, drive onto the garage point and press E from the driver's seat (Vehicle stored).
Model
Label
police
Police Cruiser
police2
Police Buffalo
police3
Police Interceptor
policeb
Police Bike
Add more in Config.Garage, for example { model = 'police4', label = 'Unmarked Cruiser' }.
Field actions: cuff, escort, search, transport, fine#
Officers use chat commands, and each one acts on the nearest player. With nobody in range you see No one nearby.
Cuff the suspect
Stand within 3.5 m and type /cuff. You need handcuffs in your inventory (they are not used up). The suspect is put in the cuffed pose and their weapon is holstered (You have been cuffed).
Search them
/search opens a window with everything in the suspect's inventory, and they are told You are being searched. You can search anyone within 3.5 m. To Confiscate an item, the suspect must be cuffed and within 5 m: the whole stack moves into your inventory, if you can carry it.
Escort them
/escort attaches the cuffed suspect to you so they walk where you walk. Run /escort again to let go.
Put them in the car
Park nearby and type /putincar. The suspect is seated in the closest vehicle within 8 m of them, in the first free seat out of rear-left, rear-right and front passenger. This also ends the escort.
Fine them
/fine 500 Speeding through a red light takes the amount from the suspect's bank account. They see You received a $500 fine: …. If they can't pay, you see They can't afford that fine.
Release them
/outcar takes the cuffed suspect out of the vehicle, and /cuff again uncuffs them (no handcuffs needed to uncuff).
Action
Range
Rules
Cuff / uncuff
3.5 m
Cuffing needs handcuffs (not consumed). Uncuffing also ends an escort.
Escort
3.5 m
Target must be cuffed. Ends by itself if the officer leaves the server.
Put in vehicle
5.5 m
Target must be cuffed. Seats: rear-left, rear-right, front passenger.
Take out of vehicle
5.5 m
Target must be cuffed.
Search
3.5 m
No cuffs needed to look. Confiscating needs the target cuffed and within 5 m.
Fine
5 m
$1–$50,000 (Config.Fine). Reason up to 80 characters. Taken from the target's bank. It is not paid into any society account.
While cuffed, a player cannot sprint, jump, get into or out of vehicles, attack, aim, open the weapon wheel, take cover, reload, throw or melee. The cuffed state is shared with other scripts through the state bag Player(source).state.cuffed (LocalPlayer.state.cuffed on the client).
Crime scenes leave evidence that only police can see.
Evidence
How it appears
Bullet casings
Every shot fired by any player's firearm leaves a casing where the bullet hit (or at the shooter's feet if it hit nothing), at most one every 0.5 s per shooter. It records the weapon (Pistol, Carbine Rifle…) and the time.
Blood samples
Every time a player goes down, a blood sample is left where they fell. It carries their DNA, which is their citizen ID.
Lifetime
Each point lasts 30 minutes. Up to 400 points are kept at once, and all of them are cleared when qs-police restarts.
Seeing it
Officers see markers within 25 m: yellow for casings, red for blood.
Find the markers
Walk the scene as an officer. Casings and blood show up as markers on the ground.
Bag each piece
Within 2 m: Press E to collect the bullet casing (or blood sample). You need an Evidence Bag. Your character kneels for 3 seconds (X cancels), one bag is used, and you get an Evidence item. The marker disappears for every officer.
Read the evidence
Each Evidence item records the type, the weapon (casings), the DNA (blood), the time and the location (x, y).
Analyse blood at the lab
At the forensics lab, press E to see the evidence you carry. Press Analyze on a blood sample: after 4 seconds the DNA is matched to the character's name, whether that player is online or not, or to No match. The result is written on the item (Analysis result: John Doe). Casings already show the weapon and can't be analysed.
Store it
Put the bagged evidence in the evidence locker so the next shift can use it.
Every player with the job police receives each alert as a red notification (6 seconds) and a flashing red blip on the map for 60 seconds, named after the alert.
Alert
Sent when
Shots fired
Each shot has a 25 % chance of alerting police at the shooter's real position, at most once every 15 seconds per shooter.
Vehicle break-in reported
A player fails to hotwire a vehicle with a lockpick (qs-corevehiclekeys), at most once every 8 seconds per player.
Your own alerts
Any server script calls the Alert export.
exports['qs-police']:Alert(coords, label)
Server-side. Sends a dispatch alert to every online player whose job is police. label is optional and defaults to Shots fired.
lua
-- server side, e.g. in your store robbery scriptlocalfunctionalertPolice(source, text)if GetResourceState('qs-police') ~= 'started'thenreturnendlocal c = GetEntityCoords(GetPlayerPed(source))
exports['qs-police']:Alert({ x = c.x, y = c.y, z = c.z }, text)
end
alertPolice(source, 'Store robbery in progress')
coords must be a plain table with x, y and z. A vector3 (what GetEntityCoords returns) is ignored, so always copy the values into { x = …, y = …, z = … } as above.
Player(source).state.cuffed
Replicated state bag, true while the player is cuffed. Read it on the server with Player(source).state.cuffed or on the client with LocalPlayer.state.cuffed, for example to block your own phone or emote menu while someone is cuffed.
qs-ambulance is the FiveM EMS / ambulance job of Quasar Framework. Every hit you take becomes an injury on a body part: bleeding, bruising or burns, from Light to Critical. Medics diagnose patients, treat each injury with the right item, revive downed players (and get paid for it), carry patients on a stretcher into the ambulance, and get alerts whenever someone goes down. Players without a medic around can pay for treatment at the hospital.
The job is ambulance (label EMS). Every grade can use every feature. Grades set the salary, from Trainee ($500) to Chief ($2,000). Hire medics with /setjob <id> ambulance <grade>.
Death is handled by qs-core (see Characters & Players). When your health runs out you go down: you lie on the ground and can only look around and use the chat.
Key
When
What it does
G
Any time while down (30 s cooldown)
Calls EMS. Every medic gets EMS CALL: <name> needs a paramedic! and a blip at your position.
E
After 20 seconds
Respawn at the nearest hospital: Pillbox Hill vec4(298.6, -584.6, 43.26) or Paleto Bay vec4(-247.6, 6331.4, 32.4).
Admins can revive with /revive [id], the admin menu or the txAdmin menu's Heal. The timer, hospitals and cooldown are in Config.Death in [core]/qs-core/shared/config.lua.
Every time you take damage, the body part that was hit gets one level of an injury type.
Body region
Covers
Head
Head and neck
Upper Body
Spine, chest and pelvis. Any hit that can't be placed counts here.
Left Arm / Right Arm
Upper arm, forearm, hand and fingers
Left Leg / Right Leg
Thigh, calf and foot
What hurt you
Injury type (shown as)
Treated with
Falling
Bruising (Beat)
Ice Pack
Being on fire
Burning (Burn)
Burn Cream
Someone holding fists or a blunt weapon: unarmed, bat, crowbar, golf club, hammer, knuckle duster, nightstick, wrench, pool cue, flashlight
Bruising (Beat)
Ice Pack
Someone holding a molotov, flare, petrol can or flare gun
Burning (Burn)
Burn Cream
Being hit or run over by a vehicle
Bruising (Beat)
Ice Pack
Guns, knives and everything else
Bleeding (Bleeding)
Bandage
Each hit adds +1 level of that type on that region, up to 4: 1 Light, 2 Moderate, 3 Severe, 4 Critical. One region can carry several types at once, for example a bleeding arm that is also bruised.
Injuries have effects while you are up and about, checked every 5 seconds:
Injury
Effect
Bleeding (any region)
You slowly lose health, faster at higher levels. Bleeding alone never puts you down.
Bruising on a leg
You move more slowly. At Severe or worse you also walk with an injured limp.
Burns on the head or upper body
At Moderate or worse your screen is blurred.
Injuries stay until they are treated. Respawning or an admin revive brings your health back but does not clear injuries. A medic, a bandage (for bleeding) or the hospital check-in does. Injuries are cleared when you disconnect.
Takes 3.5 s. Lowers your worst bleeding by one level and heals +25 HP.
Hospital check-in
At the doctor in Pillbox Hill hospital (vec4(308.2, -595.4, 43.28), public Hospital blip): Press E to receive treatment ($250).
5 seconds, then $250 cash is taken. Restores full health and clears all injuries and blood. Without the cash: You need $250 in cash. Works for anyone, whatever their job.
Next to a downed player (within 4 m) you see Press E to treat the patient. For anyone else, or for yourself when nobody is near, type /diagnose. The camera frames the patient and the Treat Patient report opens.
Read the report
For each body region the report shows the most urgent injury and its severity, in the order bleeding, then bruising, then burns. A downed patient with no recorded injuries is given Moderate bleeding on a random region, so every downed patient needs at least one bandage.
Drag the right item onto the region
Your bandages, ice packs and burn cream are listed with their counts. Drag one onto the injured body part. Treating takes 6 seconds (X cancels) and uses one item. If the item matches an injury on that region, that injury type is cleared completely on that region (Injury treated), and if the region had another type, it now shows. The wrong item gives That is not the right treatment for this injury and uses nothing.
Repeat until the patient is stable
When the last injury on a downed patient is treated, they are revived with full health (A medic has treated your wounds). You see Patient stabilized! and receive a $250 cash payout (Service payout: $250). There is no payout for treating yourself.
The report closes if you move more than 6 m away or the patient leaves. Patients who are not down can be treated the same way, without a revive or a payout.
Supply cabinet (3, free), Medical Supplies ($25), 24/7 and LTD stores ($25), Ammu-Nation ($25), police armory
icepack
Ice Pack
0.35 kg
Bruising
Supply cabinet (2, free), Medical Supplies ($40)
burn_cream
Burn Cream
0.3 kg
Burning
Supply cabinet (2, free), Medical Supplies ($45)
Point
Location
Who
What it does
Supply cabinet
vec4(306.9, -601.3, 43.28) (no blip)
ambulance
Press E to grab medical supplies: 3 bandages, 2 ice packs and 2 burn creams for free. Once a minute per medic (The supply cabinet is being restocked, wait a moment).
Medics carry downed patients on a hospital bed and load it into the ambulance.
Action
How
Deploy
/stretcher spawns your stretcher in front of you and you start carrying it. Each medic can have one. Type /stretcher again to remove yours.
Carry
While carrying you can't jump, attack, aim, melee or get into vehicles. Press E to put it down.
Next to a stretcher (2.2 m)
The on-screen buttons show your options: E move, G load or unload a patient, H into the ambulance or store.
Load a patient
G puts the nearest downed player within 4 m on the stretcher. G again unloads them.
Into the ambulance
With an ambulance within 6 m, H opens the rear doors and locks the stretcher, patient included, in the back. To take it out, stand next to it and press E to carry it again.
Store
With no ambulance near, H removes the stretcher. Only its owner can.
Patient
When the patient is revived, they are taken off the stretcher automatically.
Any medic can move or load any stretcher. A stretcher disappears when its owner leaves the server, and its patient is released.
At vec4(295.51, -606.76, 43.33), next to the hospital (EMS Garage blip for medics): on foot, Press E to take out an ambulance spawns an ambulance at vec4(281.83, -604.14, 43.13) with a full tank, unless the spot is blocked. Drive back onto the point and press E from the driver's seat to store it.
Open the injury report for the nearest person, or for yourself.
/stretcher
—
ambulance
Deploy your stretcher, or remove it.
Treat patient
E
ambulance
Next to a downed player.
Stretcher
E / G / H
ambulance
Move or put down / load or unload / into the ambulance or store.
Call EMS
G
Anyone who is down
Pages every medic (30 s cooldown).
Respawn
E
Anyone who is down
After 20 s, at the nearest hospital.
Page EMS from your own client script
TriggerEvent('qs:client:emsCall') sends an EMS CALL with the caller's name and position to every medic. For example, use it from a phone app's "Call 911 (EMS)" button.
Revive a player from your own server script
exports['qs-core']:SetPlayerDead(source, false) revives a player, and true puts them down. Players also send EMS ALERT to medics when they go down this way.
point vec4(295.51, -606.76, 43.33), spawn vec4(281.83, -604.14, 43.13), model = 'ambulance'
EMS garage.
Config.ReviveReward
250
Cash paid to a medic for stabilising a downed patient. 0 turns it off.
Config.Stretcher.model
v_med_bed1
Stretcher prop (a hospital bed).
Config.Stretcher.keys
{ action = 38, patient = 47, store = 74 }
E move / put down / get off, G load / unload, H into ambulance / store.
Config.Stretcher.vehicleOffsets
ambulance → { coords, rotation }
Vehicle models that take a stretcher, and where it sits inside. Add an entry to make another ambulance model work.
To let another ambulance model carry the stretcher, add it to vehicleOffsets with its own position inside the vehicle (tune coords and rotation in game):
FiveM drugs: weed, cocaine and meth (qs-coredrugs)#
qs-coredrugs is the FiveM drugs script of Quasar Framework: weed, cocaine and meth, each with its own field, lab and multi-step processing, sold to street dealers for dirty cash (black_money). It is open to everyone: there is no job requirement and every field, lab and dealer has a public blip. Drug activity doesn't alert police by itself, but gunfire around it does, through the police evidence system.
At a field or supply point, walk up to a plant or barrel (within 2 m): Press E to harvest Marijuana. Your character works for a few seconds (X cancels) and you get the raw material. Each gather point has 8 plants or barrels scattered around it, and they never run out.
Process
At the lab, walk up to the table: Press E to process …. You need the full batch of raw material (You need 3x Weed Leaf). Processing runs through several stages: trimming, cutting or cooking, then weighing and packaging. Each stage has its own animation and prop. Cancel any stage and you get nothing, but you keep your materials.
Package
When the last stage finishes, the raw material is turned into one packaged bag.
Sell to a dealer
Talk to a dealer (Press E to talk to the dealer). The dealer window shows the price for each drug on this visit, how many bags you have and your dirty cash. Sell some or Sell all. The money goes into your black_money account (Sold 10x for $1200 dirty cash).
vec4(114.26, -1961.07, 21.33, 21.78), near Grove Street
Dealer 2
vec4(1214.39, -1644.12, 48.65, 30.35), East Los Santos
Prices roll per visit. When you open the dealer window, the dealer rolls one price per drug within its range. That price holds until you close the window.
25 bags per visit. A dealer buys at most 25 bags each time you open the window (Config.SellLimitPerVisit). After that you see The dealer won't buy any more right now. Closing and reopening the window starts a new visit with new prices.
Dirty cash. Sales pay into black_money (Config.SellAccount), shown as Dirty Cash in the dealer window. See Economy & Banking.
Reach to plants, barrels and lab tables. Dealers get 1 m more.
Config.SellAccount
'black_money'
Account dealer sales pay into.
Config.SellLimitPerVisit
25
Maximum bags a dealer buys per window.
Config.HarvestPerZone
8
Plants or barrels spawned at each gather point.
Config.HarvestSpread
3.5
Radius (m) they are scattered in.
Config.Drugs.<key>.label
Marijuana, Cocaine…
Name used in prompts and progress text.
Config.Drugs.<key>.gather
per drug
item, min, max, time (ms), weight and label (to register the raw item), prop, anim, blip (false hides it), locations (vec3).
Config.Drugs.<key>.process
per drug
input, inputAmount, output, outputAmount, time, weight and label (to register the bag), prop (lab table model), anim (used when there are no stages), stages, blip, locations (vec4).
Config.Drugs.<key>.process.stages
3 per drug
Each stage: label (a language key), time, anim = { dict, clip }, prop = { model, bone, pos, rot } held in the hand, optional ptfx = { asset, name, bone, offset, scale }.
Config.Drugs.<key>.sell
per drug
{ item, min, max }: dealer price range per bag.
Config.Dealer
ped g_m_y_mexgoon_01, 2 locations
Dealer ped, scenario, blip (false hides it) and locations.
You can add a drug in config alone. The example adds a premium weed strain that reuses the weed props and animations.
Pick your locations
Stand at each field point, at the lab table and wherever you want new dealers, and run /coords (admin) to get vec4(x, y, z, h). The lab table is placed exactly at the coordinate you give, so use the floor height: about 1 m below the z that /coords prints.
A stage label is a key from qs-coredrugs' language files: stage_trim, stage_cut, stage_cook, stage_weigh or stage_pack. For new text, add the key to every file in [addons]/qs-coredrugs/locales/, for example stage_dry = 'Drying the buds...'.
Restart qs-coredrugs
The raw item and the bag are registered from gather.label/gather.weight and process.label/process.weight, the props and blips appear, and every dealer starts buying the new drug.
To add a dealer, add another vec4 to Config.Dealer.locations. Every dealer buys every drug.
That point belongs to a different job. Apply for the job at the Job Center, or have an admin run /setjob. Job blips also only appear for the job you hold.
My new job doesn't show up at the Job Center
It must be in [core]/qs-core/shared/jobs.luaand in Config.Center.jobs in [addons]/qs-jobs/config.lua, with exactly the same name. Restart the server after editing.
"You are not a police officer" / "You are not a medic"
The commands and station points check the job name, police or ambulance. Set it with /setjob <id> police <grade> or /setjob <id> ambulance <grade>.
The hospital doctor or EMS garage is floating in an empty space
The hospital_map interior isn't loaded. Make sure [maps]/hospital_map exists and ensure [maps] is in server.cfg.
"The spawn point is blocked"
Another vehicle is parked on the garage spawn (police or EMS). Move it, or store it from the driver's seat on the garage point.
exports['qs-police']:Alert does nothing
Pass a plain table { x = c.x, y = c.y, z = c.z }, not a vector3, and check that qs-police is started.
Bandages heal only 20 HP or body armor stops working after a restart
qs-coreinventory has its own simple bandage. If you restart qs-coreinventory on a running server, also restart qs-ambulance and qs-police afterwards so their bandage and body armor handlers are registered again.
Driving it from your own scripts? Every command, key and export of these jobs, together with qs-core's SetJob, GetJobs, RegisterJob and SetPlayerDead, is listed in Commands and Exports.
On the server, QBCore.Shared.Jobs contains every qs-core job in QBCore shape (grades['0'] = { name, payment, isboss }).
QBCore:Server:OnJobUpdate (source, job) and QBCore:Client:OnJobUpdate (job) fire on every job change.
Player.Functions.SetJob(name, grade) writes to qs-core. Unknown jobs are created from QBCore.Shared.Jobs if you defined them there, otherwise with grades 0–4.
Jobs you put in [bridge]/qb-core/shared/jobs.lua (QBCore format) are registered in qs-core when the server starts. That makes it easy to paste the jobs a QBCore script ships with.