diff --git a/README.md b/README.md index 019ba15d..bf319363 100644 --- a/README.md +++ b/README.md @@ -34,6 +34,24 @@ git clone https://github.com/ESX-Org/esx_jobs [esx]/esx_jobs start esx_jobs ``` +## iZone integreation (optional) +- You can use iZone with esx_jobs by creating polynomial zones with iZone. When you finish the zone creation, take the zone name and set a Zone field on the job like so: +``` +CloakRoom = { + Zone = "miner_room", -- HERE + Size = {x = 3.0, y = 3.0, z = 1.0}, + Color = {r = 204, g = 204, b = 0}, + Marker = 1, + Blip = true, + Name = _U("m_miner_locker"), + Type = "cloakroom", + Hint = _U("cloak_change"), + GPS = {x = 884.86, y = -2176.51, z = 29.51} +} +``` +- Note that this is just to have custom zone and avoid using radius. +### [How to install and use iZone](https://github.com/izio38/iZone) + # Legal ### License esx_jobs - jobs diff --git a/client/main.lua b/client/main.lua index 7f997a57..e3f9cf79 100644 --- a/client/main.lua +++ b/client/main.lua @@ -1,5 +1,33 @@ -local menuIsShowed, hintIsShowed, hintToDisplay, hasAlreadyEnteredMarker, isInMarker, vehicleObjInCaseofDrop, vehicleInCaseofDrop, vehicleMaxHealth -local PlayerData, Blips, JobBlips, myPlate, onDuty, spawner = {}, {}, {}, {}, false, 0 +local Keys = { + ["ESC"] = 322, ["F1"] = 288, ["F2"] = 289, ["F3"] = 170, ["F5"] = 166, ["F6"] = 167, ["F7"] = 168, ["F8"] = 169, ["F9"] = 56, ["F10"] = 57, + ["~"] = 243, ["1"] = 157, ["2"] = 158, ["3"] = 160, ["4"] = 164, ["5"] = 165, ["6"] = 159, ["7"] = 161, ["8"] = 162, ["9"] = 163, ["-"] = 84, ["="] = 83, ["BACKSPACE"] = 177, + ["TAB"] = 37, ["Q"] = 44, ["W"] = 32, ["E"] = 38, ["R"] = 45, ["T"] = 245, ["Y"] = 246, ["U"] = 303, ["P"] = 199, ["["] = 39, ["]"] = 40, ["ENTER"] = 18, + ["CAPS"] = 137, ["A"] = 34, ["S"] = 8, ["D"] = 9, ["F"] = 23, ["G"] = 47, ["H"] = 74, ["K"] = 311, ["L"] = 182, + ["LEFTSHIFT"] = 21, ["Z"] = 20, ["X"] = 73, ["C"] = 26, ["V"] = 0, ["B"] = 29, ["N"] = 249, ["M"] = 244, [","] = 82, ["."] = 81, + ["LEFTCTRL"] = 36, ["LEFTALT"] = 19, ["SPACE"] = 22, ["RIGHTCTRL"] = 70, + ["HOME"] = 213, ["PAGEUP"] = 10, ["PAGEDOWN"] = 11, ["DELETE"] = 178, + ["LEFT"] = 174, ["RIGHT"] = 175, ["TOP"] = 27, ["DOWN"] = 173, + ["NENTER"] = 201, ["N4"] = 108, ["N5"] = 60, ["N6"] = 107, ["N+"] = 96, ["N-"] = 97, ["N7"] = 117, ["N8"] = 61, ["N9"] = 118 +} + +local PlayerData = {} +local menuIsShowed = false +local hintIsShowed = false +local hasAlreadyEnteredMarker = false +local Blips = {} +local JobBlips = {} +local isInMarker = false +local isInPublicMarker = false + +local hintToDisplay = "no hint to display" +local onDuty = false +local spawner = 0 +local myPlate = {} + +local vehicleObjInCaseofDrop = nil +local vehicleInCaseofDrop = nil + +local vehicleMaxHealth = nil ESX = nil @@ -26,13 +54,14 @@ end) function OpenMenu() ESX.UI.Menu.CloseAll() - ESX.UI.Menu.Open('default', GetCurrentResourceName(), 'cloakroom', { + ESX.UI.Menu.Open('default', GetCurrentResourceName(), 'cloakroom', + { title = _U('cloakroom'), - align = 'top-left', elements = { {label = _U('job_wear'), value = 'job_wear'}, {label = _U('citizen_wear'), value = 'citizen_wear'} - }}, function(data, menu) + } + }, function(data, menu) if data.current.value == 'citizen_wear' then onDuty = false ESX.TriggerServerCallback('esx_skin:getPlayerSkin', function(skin) @@ -55,123 +84,138 @@ function OpenMenu() end) end -AddEventHandler('esx_jobs:action', function(job, zone, zoneIndex) +AddEventHandler('esx_jobs:action', function(job, zone) menuIsShowed = true - if zone.Type == 'cloakroom' then + if zone.Type == "cloakroom" then OpenMenu() - elseif zone.Type == 'work' then - hintToDisplay = nil + elseif zone.Type == "work" then + hintToDisplay = "no hint to display" hintIsShowed = false local playerPed = PlayerPedId() - if IsPedOnFoot(playerPed) then - TriggerServerEvent('esx_jobs:startWork', zoneIndex) - else + if IsPedInAnyVehicle(playerPed, false) then ESX.ShowNotification(_U('foot_work')) + else + TriggerServerEvent('esx_jobs:startWork', zone.Item) end - elseif zone.Type == 'vehspawner' then - local jobObject, spawnPoint, vehicle = Config.Jobs[PlayerData.job.name] + elseif zone.Type == "vehspawner" then + local spawnPoint = nil + local vehicle = nil - if jobObject then - for k,v in pairs(jobObject.Zones) do - if v.Type == 'vehspawnpt' and v.Spawner == zone.Spawner then - spawnPoint = v - spawner = v.Spawner - break + for k,v in pairs(Config.Jobs) do + if PlayerData.job.name == k then + for l,w in pairs(v.Zones) do + if w.Type == "vehspawnpt" and w.Spawner == zone.Spawner then + spawnPoint = w + spawner = w.Spawner + end end - end - for k,v in pairs(jobObject.Vehicles) do - if v.Spawner == zone.Spawner then - vehicle = v - break + for m,x in pairs(v.Vehicles) do + if x.Spawner == zone.Spawner then + vehicle = x + end end end end - if jobObject and spawnPoint and vehicle and ESX.Game.IsSpawnPointClear(spawnPoint.Pos, 5.0) then + if ESX.Game.IsSpawnPointClear(spawnPoint.Pos, 5.0) then spawnVehicle(spawnPoint, vehicle, zone.Caution) else ESX.ShowNotification(_U('spawn_blocked')) end - elseif zone.Type == 'vehdelete' then - local jobObject = Config.Jobs[PlayerData.job.name] + elseif zone.Type == "vehdelete" then + local looping = true - if jobObject then - for k,v in pairs(jobObject.Zones) do - if v.Type == 'vehdelete' and v.Spawner == zone.Spawner then - local playerPed = PlayerPedId() + for k,v in pairs(Config.Jobs) do + if PlayerData.job.name == k then + for l,w in pairs(v.Zones) do + if w.Type == "vehdelete" and w.Spawner == zone.Spawner then + local playerPed = PlayerPedId() - if IsPedInAnyVehicle(playerPed, false) then - local vehicle = GetVehiclePedIsIn(playerPed, false) - local plate = ESX.Math.Trim(GetVehicleNumberPlateText(vehicle)) - local driverPed = GetPedInVehicleSeat(vehicle, -1) + if IsPedInAnyVehicle(playerPed, false) then - if playerPed == driverPed then - if myPlate[plate] then - myPlate[plate] = nil + local vehicle = GetVehiclePedIsIn(playerPed, false) + local plate = GetVehicleNumberPlateText(vehicle) + plate = string.gsub(plate, " ", "") + local driverPed = GetPedInVehicleSeat(vehicle, -1) - local vehicleHealth = GetVehicleEngineHealth(vehicleInCaseofDrop) + if playerPed == driverPed then - -- fix for people using cheat engine to modify engine health - if vehicleHealth > vehicleMaxHealth then - vehicleHealth = vehicleMaxHealth + for i=1, #myPlate, 1 do + if myPlate[i] == plate then + + local vehicleHealth = GetVehicleEngineHealth(vehicleInCaseofDrop) + local giveBack = ESX.Math.Round(vehicleHealth / vehicleMaxHealth, 2) + + TriggerServerEvent('esx_jobs:caution', "give_back", giveBack, 0, 0) + DeleteVehicle(GetVehiclePedIsIn(playerPed, false)) + + if w.Teleport ~= 0 then + ESX.Game.Teleport(playerPed, w.Teleport) + end + + table.remove(myPlate, i) + + if vehicleObjInCaseofDrop.HasCaution then + vehicleInCaseofDrop = nil + vehicleObjInCaseofDrop = nil + vehicleMaxHealth = nil + end + + break + end end - local giveBack = ESX.Math.Round(vehicleHealth / vehicleMaxHealth, 2) - - TriggerServerEvent('esx_jobs:caution', 'give_back', giveBack, 0, 0) - DeleteVehicle(GetVehiclePedIsIn(playerPed, false)) - - if v.Teleport ~= 0 then - ESX.Game.Teleport(playerPed, v.Teleport) - end - - if vehicleObjInCaseofDrop.HasCaution then - vehicleInCaseofDrop, vehicleObjInCaseofDrop, vehicleMaxHealth = nil, nil, nil - end + else + ESX.ShowNotification(_U('not_your_vehicle')) end - else - ESX.ShowNotification(_U('not_your_vehicle')) + end + looping = false + break end - break + if looping == false then + break + end end end + if looping == false then + break + end end - elseif zone.Type == 'delivery' then - if Blips.delivery then - RemoveBlip(Blips.delivery) - Blips.delivery = nil + elseif zone.Type == "delivery" then + if Blips['delivery'] ~= nil then + RemoveBlip(Blips['delivery']) + Blips['delivery'] = nil end - hintToDisplay = nil + hintToDisplay = "no hint to display" hintIsShowed = false - TriggerServerEvent('esx_jobs:startWork', zoneIndex) + TriggerServerEvent('esx_jobs:startWork', zone.Item) end - --nextStep(zone.GPS) end) function nextStep(gps) if gps ~= 0 then - if Blips.delivery then - RemoveBlip(Blips.delivery) - Blips.delivery = nil + if Blips['delivery'] ~= nil then + RemoveBlip(Blips['delivery']) + Blips['delivery'] = nil end - Blips.delivery = AddBlipForCoord(gps.x, gps.y, gps.z) - SetBlipRoute(Blips.delivery, true) + Blips['delivery'] = AddBlipForCoord(gps.x, gps.y, gps.z) + SetBlipRoute(Blips['delivery'], true) ESX.ShowNotification(_U('next_point')) end end AddEventHandler('esx_jobs:hasExitedMarker', function(zone) TriggerServerEvent('esx_jobs:stopWork') - hintToDisplay = nil + hintToDisplay = "no hint to display" menuIsShowed = false hintIsShowed = false isInMarker = false @@ -188,32 +232,49 @@ AddEventHandler('esx:setJob', function(job) end) function deleteBlips() - for k,v in ipairs(JobBlips) do - RemoveBlip(v) - JobBlips[k] = nil + if JobBlips[1] ~= nil then + for i=1, #JobBlips, 1 do + RemoveBlip(JobBlips[i]) + JobBlips[i] = nil + end end end function refreshBlips() - if PlayerData.job then - local jobObject = Config.Jobs[PlayerData.job.name] + local zones = {} + local blipInfo = {} - if jobObject then - for k,v in pairs(jobObject.Zones) do - if v.Blip then - local blip = AddBlipForCoord(v.Pos.x, v.Pos.y, v.Pos.z) + if PlayerData.job ~= nil then + for jobKey,jobValues in pairs(Config.Jobs) do - SetBlipSprite (blip, jobObject.BlipInfos.Sprite) - SetBlipScale (blip, 1.2) - SetBlipCategory(blip, 3) - SetBlipColour (blip, jobObject.BlipInfos.Color) - SetBlipAsShortRange(blip, true) + if jobKey == PlayerData.job.name then + for zoneKey,zoneValues in pairs(jobValues.Zones) do - BeginTextCommandSetBlipName('STRING') - AddTextComponentSubstringPlayerName(v.Name) - EndTextCommandSetBlipName(blip) + if zoneValues.Blip then + local _Pos = {} + if (zoneValues.Zone) then + TriggerEvent("izone:getZoneCenter", zoneValues.Zone, function(_center) + if (_center) then + _Pos = _center + end + end) + else + _Pos = zoneValues.Pos + end + print(_Pos.x) + local blip = AddBlipForCoord(_Pos.x, _Pos.y, _Pos.z) + SetBlipSprite (blip, jobValues.BlipInfos.Sprite) + SetBlipDisplay (blip, 4) + SetBlipScale (blip, 1.2) + SetBlipCategory(blip, 3) + SetBlipColour (blip, jobValues.BlipInfos.Color) + SetBlipAsShortRange(blip, true) - table.insert(JobBlips, blip) + BeginTextCommandSetBlipName("STRING") + AddTextComponentString(zoneValues.Name) + EndTextCommandSetBlipName(blip) + table.insert(JobBlips, blip) + end end end end @@ -221,7 +282,7 @@ function refreshBlips() end function spawnVehicle(spawnPoint, vehicle, vehicleCaution) - hintToDisplay = nil + hintToDisplay = 'no hint to display' hintIsShowed = false TriggerServerEvent('esx_jobs:caution', 'take', vehicleCaution, spawnPoint, vehicle) end @@ -232,7 +293,7 @@ AddEventHandler('esx_jobs:spawnJobVehicle', function(spawnPoint, vehicle) ESX.Game.SpawnVehicle(vehicle.Hash, spawnPoint.Pos, spawnPoint.Heading, function(spawnedVehicle) - if vehicle.Trailer ~= 'none' then + if vehicle.Trailer ~= "none" then ESX.Game.SpawnVehicle(vehicle.Trailer, spawnPoint.Pos, spawnPoint.Heading, function(trailer) AttachVehicleToTrailer(spawnedVehicle, trailer, 1.1) end) @@ -241,12 +302,10 @@ AddEventHandler('esx_jobs:spawnJobVehicle', function(spawnPoint, vehicle) -- save & set plate local plate = 'WORK' .. math.random(100, 900) SetVehicleNumberPlateText(spawnedVehicle, plate) - myPlate[plate] = true + table.insert(myPlate, plate) + plate = string.gsub(plate, " ", "") TaskWarpPedIntoVehicle(playerPed, spawnedVehicle, -1) - Citizen.Wait(1) - SetVehicleFuelLevel(vehicle, 100.0) - DecorSetFloat(vehicle, "_FUEL_LEVEL", GetVehicleFuelLevel(vehicle)) if vehicle.HasCaution then vehicleInCaseofDrop = spawnedVehicle @@ -259,9 +318,9 @@ end) -- Show top left hint Citizen.CreateThread(function() while true do - Citizen.Wait(0) + Citizen.Wait(10) - if hintIsShowed and hintToDisplay then + if hintIsShowed then ESX.ShowHelpNotification(hintToDisplay) else Citizen.Wait(500) @@ -269,118 +328,215 @@ Citizen.CreateThread(function() end end) --- Draw markers (only if on duty and the player's job ones) +-- Display markers (only if on duty and the player's job ones) +Citizen.CreateThread(function() + while true do + Citizen.Wait(1) + local zones = {} + + if PlayerData.job ~= nil then + for k,v in pairs(Config.Jobs) do + if PlayerData.job.name == k then + zones = v.Zones + end + end + + local coords = GetEntityCoords(PlayerPedId()) + for k,v in pairs(zones) do + if onDuty or v.Type == "cloakroom" or PlayerData.job.name == "reporter" then + if (v.Zone) then + TriggerEvent("izone:getZoneCenter", v.Zone, function(center) + if (not(center == nil)) then + if(v.Marker ~= -1 and GetDistanceBetweenCoords(coords, center.x, center.y, center.z, true) < Config.DrawDistance) then + DrawMarker(v.Marker, center.x, center.y, center.z - 1, 0.0, 0.0, 0.0, 0, 0.0, 0.0, v.Size.x, v.Size.y, v.Size.z, v.Color.r, v.Color.g, v.Color.b, 100, false, true, 2, false, false, false, false) + end + end + end) + else + if(v.Marker ~= -1 and GetDistanceBetweenCoords(coords, v.Pos.x, v.Pos.y, v.Pos.z, true) < Config.DrawDistance) then + DrawMarker(v.Marker, v.Pos.x, v.Pos.y, v.Pos.z, 0.0, 0.0, 0.0, 0, 0.0, 0.0, v.Size.x, v.Size.y, v.Size.z, v.Color.r, v.Color.g, v.Color.b, 100, false, true, 2, false, false, false, false) + end + end + end + end + end + end +end) + +-- Display public markers Citizen.CreateThread(function() while true do Citizen.Wait(0) - local zones, currentZone, currentZoneIndex, isInMarker = {} - local letSleep, playerPed = true, PlayerPedId() - local playerCoords = GetEntityCoords(playerPed) - - if PlayerData.job then - if Config.Jobs[PlayerData.job.name] then - zones = Config.Jobs[PlayerData.job.name].Zones - end - - for k,v in pairs(zones) do - local distance = GetDistanceBetweenCoords(playerCoords, v.Pos.x, v.Pos.y, v.Pos.z, true) - - if onDuty or v.Type == 'cloakroom' or PlayerData.job.name == 'reporter' then - if(v.Marker ~= -1 and distance < Config.DrawDistance) then - letSleep = false - DrawMarker(v.Marker, v.Pos.x, v.Pos.y, v.Pos.z, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, v.Size.x, v.Size.y, v.Size.z, v.Color.r, v.Color.g, v.Color.b, 100, false, true, 2, false, nil, nil, false) - end - end - - if distance < v.Size.x then - letSleep, isInMarker, currentZone, currentZoneIndex = false, true, v, k - break - end - end - - if IsControlJustReleased(0, 38) and not menuIsShowed and isInMarker then - if onDuty or currentZone.Type == 'cloakroom' or PlayerData.job.name == 'reporter' then - TriggerEvent('esx_jobs:action', PlayerData.job.name, currentZone, currentZoneIndex) - end - end - - -- hide or show top left zone hints - if isInMarker and not menuIsShowed then - hintIsShowed = true - if (onDuty or currentZone.Type == 'cloakroom' or PlayerData.job.name == 'reporter') and currentZone.Type ~= 'vehdelete' then - hintToDisplay = currentZone.Hint - hintIsShowed = true - elseif currentZone.Type == 'vehdelete' and (onDuty or PlayerData.job.name == 'reporter') then - local playerPed = PlayerPedId() - - if IsPedInAnyVehicle(playerPed, false) then - local vehicle = GetVehiclePedIsIn(playerPed, false) - local driverPed = GetPedInVehicleSeat(vehicle, -1) - local plate = ESX.Math.Trim(GetVehicleNumberPlateText(vehicle)) - - if playerPed == driverPed then - if myPlate[plate] then - hintToDisplay = currentZone.Hint - end - else - hintToDisplay = _U('not_your_vehicle') - end - else - hintToDisplay = _U('in_vehicle') - end - hintIsShowed = true - elseif onDuty and currentZone.Spawner ~= spawner then - hintToDisplay = _U('wrong_point') - hintIsShowed = true - else - hintToDisplay = nil - hintIsShowed = false - end - end - - if isInMarker and not hasAlreadyEnteredMarker then - hasAlreadyEnteredMarker = true - end - - if not isInMarker and hasAlreadyEnteredMarker then - hasAlreadyEnteredMarker = false - TriggerEvent('esx_jobs:hasExitedMarker', currentZone) + local coords = GetEntityCoords(PlayerPedId()) + for k,v in pairs(Config.PublicZones) do + if(v.Marker ~= -1 and GetDistanceBetweenCoords(coords, v.Pos.x, v.Pos.y, v.Pos.z, true) < Config.DrawDistance) then + DrawMarker(v.Marker, v.Pos.x, v.Pos.y, v.Pos.z, 0.0, 0.0, 0.0, 0, 0.0, 0.0, v.Size.x, v.Size.y, v.Size.z, v.Color.r, v.Color.g, v.Color.b, 100, false, true, 2, false, false, false, false) end end + end +end) + +-- Activate public marker +Citizen.CreateThread(function() + while true do + Citizen.Wait(0) + local coords = GetEntityCoords(PlayerPedId()) + local position = nil + local zone = nil for k,v in pairs(Config.PublicZones) do - local distance = GetDistanceBetweenCoords(playerCoords, v.Pos.x, v.Pos.y, v.Pos.z, true) - - if v.Marker ~= -1 and distance < Config.DrawDistance then - DrawMarker(v.Marker, v.Pos.x, v.Pos.y, v.Pos.z, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, v.Size.x, v.Size.y, v.Size.z, v.Color.r, v.Color.g, v.Color.b, 100, false, true, 2, false, nil, nil, false) - letSleep = false - end - - if distance < v.Size.x / 2 then - letSleep, isInPublicMarker = false, true - ESX.ShowHelpNotification(v.Hint) - - if IsControlJustReleased(0, 38) then - ESX.Game.Teleport(playerPed, v.Teleport) - end + if GetDistanceBetweenCoords(coords, v.Pos.x, v.Pos.y, v.Pos.z, true) < v.Size.x/2 then + isInPublicMarker = true + position = v.Teleport + zone = v + break + else + isInPublicMarker = false end end - if letSleep then - Citizen.Wait(500) + if IsControlJustReleased(0, Keys['E']) and isInPublicMarker then + ESX.Game.Teleport(PlayerPedId(), position) + isInPublicMarker = false + end + + -- hide or show top left zone hints + if isInPublicMarker then + hintToDisplay = zone.Hint + hintIsShowed = true + else + if not isInMarker then + hintToDisplay = "no hint to display" + hintIsShowed = false + end + end + end +end) + +-- Activate menu when player is inside marker +Citizen.CreateThread(function() + while true do + + Citizen.Wait(1) + + if PlayerData.job ~= nil and PlayerData.job.name ~= 'unemployed' then + local zones = nil + local job = nil + + for k,v in pairs(Config.Jobs) do + if PlayerData.job.name == k then + job = v + zones = v.Zones + end + end + + if zones ~= nil then + local coords = GetEntityCoords(PlayerPedId()) + local currentZone = nil + local zone = nil + local lastZone = nil + + for k,v in pairs(zones) do + -- If we defined a zone from iZone + if v.Zone then + TriggerEvent("izone:isPlayerInZone", v.Zone, function(isIn) + if isIn then + isInMarker = true + currentZone = k + zone = v + return + else + isInMarker = false + end + end) + -- Because we were in a routine + if isInMarker then + break + end + -- Else use radius defined from center + else + if GetDistanceBetweenCoords(coords, v.Pos.x, v.Pos.y, v.Pos.z, true) < v.Size.x then + isInMarker = true + currentZone = k + zone = v + break + else + isInMarker = false + end + end + + end + + if IsControlJustReleased(0, Keys['E']) and not menuIsShowed and isInMarker then + if onDuty or zone.Type == "cloakroom" or PlayerData.job.name == "reporter" then + TriggerEvent('esx_jobs:action', job, zone) + end + end + + -- hide or show top left zone hints + if isInMarker and not menuIsShowed then + hintIsShowed = true + if (onDuty or zone.Type == "cloakroom" or PlayerData.job.name == "reporter") and zone.Type ~= "vehdelete" then + hintToDisplay = zone.Hint + hintIsShowed = true + elseif zone.Type == "vehdelete" and (onDuty or PlayerData.job.name == "reporter") then + local playerPed = PlayerPedId() + + if IsPedInAnyVehicle(playerPed, false) then + local vehicle = GetVehiclePedIsIn(playerPed, false) + local driverPed = GetPedInVehicleSeat(vehicle, -1) + local plate = GetVehicleNumberPlateText(vehicle) + plate = string.gsub(plate, " ", "") + + if playerPed == driverPed then + + for i=1, #myPlate, 1 do + if myPlate[i] == plate then + hintToDisplay = zone.Hint + break + end + end + + else + hintToDisplay = _U('not_your_vehicle') + end + else + hintToDisplay = _U('in_vehicle') + end + hintIsShowed = true + elseif onDuty and zone.Spawner ~= spawner then + hintToDisplay = _U('wrong_point') + hintIsShowed = true + else + if not isInPublicMarker then + hintToDisplay = "no hint to display" + hintIsShowed = false + end + end + end + + if isInMarker and not hasAlreadyEnteredMarker then + hasAlreadyEnteredMarker = true + end + + if not isInMarker and hasAlreadyEnteredMarker then + hasAlreadyEnteredMarker = false + TriggerEvent('esx_jobs:hasExitedMarker', zone) + end + end end end end) Citizen.CreateThread(function() -- Slaughterer - RemoveIpl('CS1_02_cf_offmission') - RequestIpl('CS1_02_cf_onmission1') - RequestIpl('CS1_02_cf_onmission2') - RequestIpl('CS1_02_cf_onmission3') - RequestIpl('CS1_02_cf_onmission4') + RemoveIpl("CS1_02_cf_offmission") + RequestIpl("CS1_02_cf_onmission1") + RequestIpl("CS1_02_cf_onmission2") + RequestIpl("CS1_02_cf_onmission3") + RequestIpl("CS1_02_cf_onmission4") -- Tailor - RequestIpl('id2_14_during_door') - RequestIpl('id2_14_during1') -end) + RequestIpl("id2_14_during_door") + RequestIpl("id2_14_during1") +end) \ No newline at end of file