NullSect
Systems nominal

Scripts / jobs · v1.0.0

Ambulance Job

A complete EMS job on a server-side patient model: real vital signs, two bags, a cardiac monitor and the cause to treat.

  • Qbox
  • QBCore
  • ESX

Features

  1. 01

    A patient, not a health bar

    Wounds bleed in ml/s, blood volume drives heart rate, blood pressure, SpO₂ and consciousness. Collapse and cardiac arrest follow from it.

  2. 02

    Two bags, no item spam

    A BLS and an ALS bag hold every supply: dressings, tourniquet, chest seal, splint, airways, IV, drugs, needle decompression.

  3. 03

    Monitor, AED and CPR

    Live ECG, pleth and capnography from the real rhythm. VF, VT, SVT, AF, PEA, asystole; shock, SYNC cardioversion and CPR with feedback.

  4. 04

    Skill games that look real

    IV, tourniquet, wound packing, chest seal, splint, i-gel and BVM are drawn hands-on games. Mistakes hurt the patient.

  5. 05

    Tablet, call-outs, hospitals

    Triage board, PCR reports, boss panel, NPC call-outs, insurance, 26 hospital MLO presets and an in-game location editor.

  6. 06

    Death screen included

    Bleed-out timer from the model, recap, injuries, EMS call, respawn. Replaces qbx_medical and qbx_ambulancejob.

Requirements

Frameworks
Qbox, QBCore, ESX
Requires
oxmysql
Works with
ox_lib, ox_target, ox_inventory, qb-inventory, ps-dispatch, cd_dispatch, rcore_dispatch
Version
1.0.0

Recent changes

Read the docs →

1.0.0 — 2026-10-29

First stable release: everything from 0.1 to 0.11, plus:

  • Discord log (Config.Features.Logs, off by default; Config.Logs.events): knocked down / cardiac arrest with cause and place, revives / ROSC / hospital / respawn with the medic who did it, every admin command and the Revive / Heal exports, medic payouts and hospital / pharmacy / insurance charges, hire / fire / grade changes, security flags. The webhook is the server convar ns_ambulancejob_webhook (never in config.lua). Messages are batched (10 per request, one request every 2 s) to stay under Discord's rate limit.
  • Removed the default sandy hospital. Its coordinates were the Bolingbroke prison infirmary, so a player who died in Sandy Shores / Grapeseed could respawn inside the prison. The default config now has Pillbox Hill and Paleto Bay; with a Sandy Shores MLO use its preset (cfx_gn_clinic_sandy, prompts_hospital, prompts_hospital_2) or add it with /emseditor. A hospital:sandy row moved earlier in the editor is ignored.
  • README: Qbox is the tested framework; QBCore and ESX run through the bridge but are not tested in game yet.

0.11.0 — 2026-10-29

From paramedic feedback: more heart rhythms, cardioversion, chest injury protocols, and local epinephrine.

Rhythms

  • Pulseless VT (pvt): a share of sudden arrests start in it (Config.Physiology.pvtShare); it turns into VF after pvtSeconds of no flow. Shockable like VF: the AED now advises a shock on VF and pulseless VT, the manual defibrillator converts both. Bled out, hypoxic and tension arrests still start in PEA.
  • Tachyarrhythmias with a pulse (Config.Physiology.rhythms): VT, SVT and AF with a fast rate. Only while knocked down (an unstable patient: he cannot be woken until it is converted). They come from VF / pVT falling back after ROSC (postRoscVt), a bruised heart after a hard blunt chest hit (contusion), epinephrine given with a pulse (complications), and the new cardiac call-out. VT with a pulse left alone loses its pulse (vtArrest, then pulseless VT).
  • The monitor draws them all (VT broad and regular, SVT narrow and very fast without P waves, AF irregular with a fibrillating baseline); alarms VFIB, VTACH, AFIB. HR goes up to 220 on the monitor.

Synchronised cardioversion: a SYNC key on the monitor. With SYNC on, white markers sit on the R waves and the shock is timed on them: VT / SVT / AF convert by chance (rhythms.cardiovert: recommended energy per rhythm, half the chance below it). SYNC on a normal (sinus) rhythm: a chest burn and rarely VF (complications, syncSinusArrest). SYNC in cardiac arrest does not fire (care_err_sync_arrest), the charge stays. New default energies 50 and 100 J (Config.Care.defib.energies). Amiodarone is now the right drug for VT with a pulse: no complication, it may convert it (rhythms.amio).

Chest injuries (Config.Physiology.chest)

  • A gunshot / stab wound of the torso (severity 2+) or a hard blunt hit to it (severity 3+, high energy) collapses the lung on one side (pneumothorax). It builds up into a tension pneumothorax: slowly while the wound is open, at full speed once it is sealed. Tension lowers SpO₂ and blood pressure and raises heart and breathing rate; a conscious patient collapses, and at full tension the heart stops in PEA (obstructive arrest). In arrest the ROSC odds stay near zero until the chest is decompressed.
  • Breath sounds in the manual vitals: listen to both sides (clear / reduced / absent; late: the trachea shifts).
  • Needle decompression (ALS bag, new supply needle = 2): pick the right or left chest. On the tension side it relieves it at once and stays in. On a side without a pneumothorax it is wasted, and with complications that lung collapses (cx_needle_wrong). The needle shows on the chart (ND).
  • The chest is saved with the patient (relog).
  • Waking needs no tension pneumothorax (care_err_wake_chest).

Local epinephrine (epi_local, uses an epinephrine ampoule): on a bleeding wound, no IV, also on a conscious patient. That wound bleeds much less for drugs.localEpiSeconds (localEpiFactor; an artery, severity 4, only a little: localEpiSevere). Not on burns, closed fractures, a wound that does not bleed, or in arrest. Systemic epinephrine stays refused on a conscious patient.

Pocket guide: new chapters Chest injuries and Rhythms & cardioversion; AED / monitor steps mention pulseless VT; the live plan suggests SYNC + energy for VT / SVT / AF, SYNC off in arrest, listening to the chest, needle decompression on the silent side (both sides in traumatic arrest) and local epinephrine before TXA; two new Mistakes. Practice: /emspractice cardiac (VT with a pulse: SYNC cardioversion or amiodarone) and /emspractice chest (stab wound, tension builds up: listen, needle); arrest may start in pulseless VT. Call-outs: new scenarios chest (stab wound with tension) and cardiac (VT / SVT / AF).

Config added. An older config.lua without these keys still runs (no pulseless VT, no chest model, no needle in the bag); copy them in to get the features: Physiology.pvtShare, pvtSeconds, rhythms, chest, rosc.shockPvt, rosc.cprBase.pvt, rosc.cprEpi.pvt, drugs.localEpi*, complications.syncSinusArrest, complications.epiPulseVt, Kits.als.supplies.needle, Care.durations.lungs / epi_local / needle, Missions.scenarios.chest / cardiac.

0.10.0 — 2026-10-28

Four new skill games, drawn and played like the first three (Config.Minigames.actions, Config.Minigames.difficulty). A failed game applies and uses up nothing; try again.

  • Chest seal (chestseal = 'seal'): hold to wipe the blood off the skin, then press at the end of a breath out (the breathing trace shows the still pause in green). Sealed while breathing in, while air still comes out, or on skin that got wet again: missed.
  • SAM splint (splint = 'splint', arm or leg drawn by the selected limb): hold for in-line traction until the limb is straight and the distal pulse comes back, then three straps: let go when each is snug. Pulled past straight or a strap so tight the distal pulse goes: missed. A loose strap just slips, pull it again.
  • i-gel (igel = 'igel'): a section of the head and neck; hold to glide it along the palate, let go when it meets the resistance at the larynx (the bite block line at the teeth), then two breaths with the bag: the capnography shows CO₂. Pushed on past the resistance: missed.
  • Bag-valve-mask (bvm = 'bvm'): hold for head tilt / chin lift until the tongue comes off the back of the throat, then two breaths: squeeze about a second and let go in the green band of the tidal volume scale (chest rise). Too little does not count; too much (air into the stomach) or an over-extended neck: missed. The bag refills in about a second, so squeezing again too soon gives less air.
  • Handbook entries of these four items say how the game is played.
  • Airway games do not show the selected body part as their subtitle.

Visuals (all seven games): rendered instead of drawn (nui/games-gfx.js). Skin is lit pixel by pixel (pores, fine creases, mottled tone, freckles, hair, light scattering red into the shadow side), veins stand out under it; drapes, quilted underpads, denim and T-shirts have folds, fibres and frayed cut edges; blood is wet and glossy where thick, runs down in rivulets and soaks into the cloth; nitrile gloves are soft lit shapes. The airway section has tissue textures (brain folds, cerebellum, porous bone, muscle fibres, wet mucosa, cartilage) and bends with the head tilt. Devices (cannula, CAT, gauze, chest seal, SAM splint, i-gel, bag and mask) got real materials.

  • The picture is baked once when a game opens (~0.2-0.3 s, then cached per limb / zone: reopening is instant); frames only draw the baked layers and the moving parts.
  • The game's time limit now starts after that, so the baking never eats into the player's time.

Fixed: an awake call-out (NPC) patient with a leg wound was offered a walking aid (chart button and handbook hint) that the server then refused. NPCs no longer get the offer.

New stretcher model: ns_ambulance_stretcher comes with the resource (stream/, works on every game build): an ambulance cot with scissor legs, loading wheels, side handles and straps (yellow frame, black mattress, orange straps), backrest flat for the patient, with collision. It is first in Config.Equipment.stretcher.models; the game's gurney and the hospital bed stay as fallbacks. The model is CC BY 4.0 (credited in the README) and stays outside the escrow (escrow_ignore: stream/*). A parked stretcher / wheelchair is held in place (brakes on) until it is pushed again.

Fixed (stretcher / wheelchair)

  • X only parks it. Pressing X again no longer grabs it back at once; walk to it and use its target option (ALT) to push it again. That option is now a small target zone around the parked device, so it also works on a streamed model without collision (the target ray went through it and never locked on).
  • Taking one from an EMS vehicle failed now and then ("could not be spawned") because the server looked for the new object before it had reached the server; it now waits up to 1.5 s for it.
  • It appears in front of the medic and is pushed right away, wherever they stand around the vehicle. Before, it was put 4.2 m behind the vehicle's centre: from the side or the front the server refused it as "not next to you" (and flagged a spoof), or it was left standing there unpushed.

Config: add the four lines to Config.Minigames.actions in an existing config to get the games (remove any of them to keep the plain timer for that step).

Related

Cart

Your cart is empty.