GKSHOP
GKSPHONE V2Configuration

Dispatch Integration

Built-in dispatch — native auto-alerts, third-party bridges, and sending calls from your own scripts.

Calls land in the MDT Dispatch tab, the overlay (O) and as map blips. There are three ways one gets there:

SourceUse when
Auto-alertsYou want the tablet to detect crimes itself — no other dispatch resource
BridgesYou already run a third-party dispatch and want its calls mirrored
ExportYour own script raises the call
config/config.lua
Config.Dispatch = {
    Enabled             = true,   -- master switch
    OverlayVisible      = true,   -- side panel and floating alerts outside the MDT
    BlipsEnabled        = true,
    SoundsEnabled       = true,
    BlipDurationMinutes = 5,
}

Run auto-alerts or bridges, not both. If an external dispatch resource already detects crimes and you leave AutoAlerts.Enabled = true, every incident arrives twice.

Auto-alerts

Native detection, on by default. Each alert type can be switched independently:

Config.Dispatch.AutoAlerts.Alerts = {
    Shooting = true,   Melee = true,        Autotheft = true,
    SeenCarStolen = true, Explosion = true, PlayerDowned = true,
    Speeding = true,   PedRunOver = true,   CarCrash = true,
    Fire = true,       VehicleFire = true,
    Armed = false,     InjuredPerson = false, ZoneChance = false,
}

Behaviour

SettingDefaultDoes
EnabledtrueMaster switch for native detection
CooldownSeconds5Minimum gap between alerts in the same group
Chance100Percentage chance any alert fires. ChancePerAlert overrides per type
SkipForPolicetrueOfficers don't trigger alerts
SkipForAmbulancefalseMedics do
SimpleColorNamestrue"Graceful Red" rather than "Metallic Graceful Red" in the vehicle colour field
SpeedMinKmh80Speeding threshold
ExplosionLocalRadius50.0How close a ped must be for ExplosionRequireLocalPed

The speeding threshold is not fixed: each check uses SpeedMinKmh + math.random(0, 20), so at the default a driver is reported somewhere between 80 and 100 km/h. That is deliberate — a hard line makes it trivial to sit just under it.

Cooldown groups

Alerts share a cooldown with others of the same kind, so one incident doesn't produce five calls:

CooldownGroups = {
    gun         = { 'shooting', 'vehicleshots', 'hunting', 'armed' },
    theft       = { 'carjack', 'vehicletheft', 'copcarstolen' },
    violence    = { 'fight', 'pedrunover' },
    destruction = { 'explosion', 'fire', 'vehiclefire' },
    traffic     = { 'speeding', 'carcrash' },
    medical     = { 'playerdowned', 'officerdown', 'emsdown', 'civdown' },
}

Witness requirement

Off by default. Turn it on and a nearby ambient NPC has to see the crime and call it in before dispatch fires:

Witness = {
    Enabled = false,
    MaxDistance = 100.0,
    MinWitnessDistance = 5.0,
    CallPolice = true,
}

Zones

-- Gunfire inside the radius is reported as Hunting instead of Shots Fired
HuntingZones = {
    { label = 'Hunting Zone', radius = 650.0, coords = vector3(-938.61, 4823.99, 313.92) },
}

-- Nothing is dispatched from inside these rotated boxes
NoDispatchZones = {
    { label = 'Ammunation', coords = vector3(13.53, -1097.92, 29.8),
      length = 14.0, width = 5.0, heading = 70, minZ = 28.8, maxZ = 32.8 },
}

A hunting zone doesn't silence the call — it swaps the preset, so officers see "Hunting Activity" rather than "Shots Fired". Use NoDispatchZones when you want silence, e.g. inside a gun shop.

Ignored weapons

IgnoredWeapons and IgnoredWeaponGroups are exclusion lists, not whitelists. Anything listed never raises Shooting or Armed alerts — grenades, molotovs, snowballs, fire extinguishers, stun guns, and the melee and unarmed groups.

Presets

Every alert draws its title, radio code, priority, target job and blip from AutoAlerts.Presets:

Presets = {
    shooting = {
        title       = 'Shots Fired',
        description = 'Reports of gunfire in the area',
        code        = '10-11',
        priority    = 'medium',
        job         = 'police',
        blip        = { sprite = 110, color = 1 },
    },
    -- ...
}

17 presets ship: shooting, vehicleshots, hunting, fight, carjack, vehicletheft, explosion, officerdown, emsdown, civdown, speeding, pedrunover, carcrash, fire, vehiclefire, copcarstolen, armed. Edit one to change how that call reads and where it goes — fire targets ambulance, vehiclefire targets police.

Bridges

Mirror calls from a dispatch resource you already run. No changes needed in your robbery or heist scripts.

Config.Dispatch.Bridges = {
    ["0r_dispatch"]     = true,
    ps_dispatch         = true,
    qs_dispatch         = true,
    cd_dispatch         = true,
    rcore_dispatch      = true,
    qb_police_alert     = true,
    qb_ambulance_alert  = true,
    emergencydispatch   = true,
    wasabi_ambulance_v2 = true,
}

Set one to false to drop it without turning dispatch off.

Writing your own

Add a file under server/dispatch/:

server/dispatch/my_dispatch.lua
if not DispatchBridge.IsBridgeEnabled("my_dispatch") then return end

local BRIDGE = "my_dispatch"

AddEventHandler("my-dispatch:server:alert", function(data)
    if type(data) ~= "table" then return end

    DispatchBridge.ForwardDispatch({
        title       = data.title or "Dispatch Call",
        description = data.message or "",
        code        = data.code or "10-00",
        priority    = DispatchBridge.MapPriority(data.priority),
        coords      = DispatchBridge.NormalizeCoords(data.coords),
        job         = DispatchBridge.ResolveJobTarget(data.jobs, BRIDGE),
        blip        = data.blip and DispatchBridge.MapBlip(data.blip),
    }, BRIDGE)
end)

Then add my_dispatch = true to Config.Dispatch.Bridges, and "server/dispatch/my_dispatch.lua" to fxmanifest.lua after server/dispatch/init.lua — that folder is listed file by file, not globbed.

Nine implementations sit next to it to copy from.

Sending a call yourself

From any server script:

exports['gks-tablet']:createDispatch({
    title    = "Store Robbery",
    message  = "Armed suspect at 24/7",
    coords   = vector3(-47.0, -1757.0, 29.0),
    code     = "10-90",
    priority = "high",       -- "high" | "medium" | "low"
    job      = "police",     -- "police" | "ambulance"
    location = "Grove St",
    blip     = { sprite = 161, color = 1 },
    fields   = {
        { icon = "fas fa-car", label = "Plate", value = "ABC 123" },
    },
})
FieldRequired
titleyesCall title in the MDT
message / descriptionyesCall details
coordsyesvector3 or { x, y, z }
jobnopolice (default) or ambulance
prioritynohigh, medium, low (default low)
codenoRadio code, e.g. 10-90
locationnoStreet or area label
blipno{ sprite, color, size, label }
fieldsnoExtra rows, { icon, label, value }, up to 8

Troubleshooting

SymptomCause
No call appearsConfig.Dispatch.Enabled is false, or job doesn't match a job in Config.Jobs
Every incident arrives twiceAuto-alerts and an external dispatch are both detecting. Turn one off
Bridge does nothingBridges.<name> is false, or the file is missing from fxmanifest.lua
Speeding never firesThe threshold is randomised up to +20 km/h above SpeedMinKmh
Nothing fires anywhereAutoAlerts.Chance below 100, or the spot is inside a NoDispatchZones box

On this page