300 lines
9.0 KiB
Lua
300 lines
9.0 KiB
Lua
ESX = nil
|
|
LR = {}
|
|
LR.__index = LR
|
|
|
|
function LR:Init()
|
|
local o = {}
|
|
setmetatable(o, LR)
|
|
o.PlayerData = {}
|
|
if ESX.IsPlayerLoaded() then
|
|
o.PlayerData = ESX.GetPlayerData()
|
|
end
|
|
o.InZone = false
|
|
o.CurZone = nil
|
|
o.Blips = {}
|
|
o.PulseBlip = nil
|
|
o.Busy = false
|
|
o.Capturing = false
|
|
o.Panel2Open = false
|
|
o.RemainCapture = 0
|
|
o.CanCapture = true
|
|
o.Cache = {}
|
|
ESX.TriggerServerCallback("lr_occ2:callback:getData", function(data)
|
|
o.Cache = data[1]
|
|
o.RemainCapture = data[2]
|
|
for k, v in pairs(o.Cache) do
|
|
Citizen.CreateThread(function()
|
|
local index = k
|
|
while o.Cache[index] ~= nil and o.Cache[index].remain > 0 do
|
|
Wait(1000)
|
|
o.Cache[index].remain = o.Cache[index].remain - 1
|
|
if o.Cache[index].remain <= 0 then
|
|
o.Cache[index] = nil
|
|
end
|
|
end
|
|
end)
|
|
end
|
|
end)
|
|
o:EventHandler()
|
|
o:PosThread()
|
|
o:Blip()
|
|
o:TimeThread()
|
|
print("LOADED LROCC")
|
|
return o
|
|
end
|
|
|
|
function LR:TimeThread()
|
|
Citizen.CreateThread(function()
|
|
while true do
|
|
Wait(1000)
|
|
if self.RemainCapture > 0 then
|
|
self.RemainCapture = self.RemainCapture - 1
|
|
self.CanCapture = false
|
|
else
|
|
self.CanCapture = true
|
|
end
|
|
end
|
|
end)
|
|
end
|
|
|
|
function LR:EventHandler()
|
|
RegisterNetEvent("esx:playerLoaded", function(xPlayer)
|
|
self.PlayerData = xPlayer
|
|
end)
|
|
RegisterNetEvent("lr_occ2:client:capture", function(index, playerName)
|
|
self:PulseBlip(index)
|
|
self:ShowNotification(("Khu vực %s đang bị chiếm bởi %s"):format(Config.Occ[index].Label, playerName))
|
|
self.Cache[index] = {
|
|
remain = Config.Occ[index].time,
|
|
name = playerName
|
|
}
|
|
Citizen.CreateThread(function()
|
|
local _index = index
|
|
while self.Cache[_index] ~= nil and self.Cache[_index].remain > 0 do
|
|
print(_index)
|
|
Wait(1000)
|
|
if self.Cache[_index] ~= nil then
|
|
self.Cache[_index].remain = self.Cache[_index].remain - 1
|
|
if self.Cache[index].remain <= 0 then
|
|
self.Cache[index] = nil
|
|
end
|
|
end
|
|
end
|
|
end)
|
|
end)
|
|
RegisterNetEvent("lr_occ2:client:captured", function(index, playerName)
|
|
self:UnPulse()
|
|
self.Cache[index] = nil
|
|
self.RemainCapture = Config.Delay
|
|
self:ShowNotification(("%s đã chiếm thành công khu vực %s"):format(playerName, Config.Occ[index].Label))
|
|
end)
|
|
RegisterNetEvent("lr_occ2:client:cancel", function(index, playerName)
|
|
self:UnPulse()
|
|
self.Cache[index] = nil
|
|
self:ShowNotification(("%s đã hủy chiếm %s"):format(playerName, Config.Occ[index].Label))
|
|
end)
|
|
RegisterNetEvent("lr_occ2:client:showNotification", function(msg)
|
|
self:ShowNotification(msg)
|
|
end)
|
|
end
|
|
|
|
function LR:Blip()
|
|
for k, v in pairs(Config.Occ) do
|
|
local blip = AddBlipForCoord(v.Pos.x, v.Pos.y, v.Pos.z)
|
|
SetBlipSprite(blip, 420)
|
|
SetBlipDisplay(blip, 2)
|
|
SetBlipScale(blip, 1.2)
|
|
SetBlipColour(blip, 1)
|
|
SetBlipAsShortRange(blip, true)
|
|
SetBlipHighDetail(blip, true)
|
|
BeginTextCommandSetBlipName("STRING")
|
|
AddTextComponentString(("Khu Vực Chiếm Đóng [%s]"):format(k))
|
|
EndTextCommandSetBlipName(blip)
|
|
self.Blips[k] = blip
|
|
end
|
|
--self:PulseBlip("main")
|
|
print("LOADED BLIPS")
|
|
end
|
|
|
|
function LR:PulseBlip(index)
|
|
local zoneCoords = Config.Occ[index].Pos
|
|
local Pblip = AddBlipForCoord(zoneCoords.x, zoneCoords.y, zoneCoords.z)
|
|
SetBlipSprite(Pblip, 161)
|
|
SetBlipScale(Pblip, 2.0)
|
|
SetBlipColour(Pblip, 1)
|
|
PulseBlip(Pblip)
|
|
self.PulseBlip = Pblip
|
|
end
|
|
|
|
function LR:UnPulse()
|
|
RemoveBlip(self.PulseBlip)
|
|
self.PulseBlip = nil
|
|
end
|
|
|
|
function LR:PosThread()
|
|
Citizen.CreateThread(function()
|
|
while true do
|
|
coroutine.yield(0)
|
|
self.ped = PlayerPedId()
|
|
self.pedCoords = GetEntityCoords(self.ped, true)
|
|
self.CurZone = self:CheckPos()
|
|
if self.CurZone ~= nil then
|
|
local zoneCoords = Config.Occ[self.CurZone].Pos
|
|
local distance = #(self.pedCoords - zoneCoords)
|
|
DrawMarker(1, zoneCoords.x, zoneCoords.y, zoneCoords.z - 100.100, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0,
|
|
Config.Occ[self.CurZone].Radius * 2, Config.Occ[self.CurZone].Radius * 2, 200.0, 255, 0, 0, 100,
|
|
false, true, 2, nil, nil, false)
|
|
DrawMarker(1, zoneCoords.x, zoneCoords.y, zoneCoords.z - 1.100, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 2.0, 2.0,
|
|
2.0, 255, 0, 0, 100, false, true, 2, nil, nil, false)
|
|
if distance <= 1.5 and not self.Busy and not self.Capturing then
|
|
DisplayText("Nhấn [E] để chiếm khu vực này")
|
|
if IsControlJustPressed(0, 38) then
|
|
self.Busy = true
|
|
ESX.TriggerServerCallback("lr_occ2:callback:canCapture", function(result)
|
|
self.Busy = false
|
|
if result == true then
|
|
self.Capturing = true
|
|
self:StartCapture(self.CurZone)
|
|
end
|
|
end, self.CurZone)
|
|
end
|
|
end
|
|
if (IsPedInAnyVehicle(self.ped, false) or IsPlayerFreeAiming(PlayerId())) and self.Panel2Open then
|
|
self:TogglePanel2(false)
|
|
elseif not self.Panel2Open and not IsPedInAnyVehicle(self.ped, false) and not IsPlayerFreeAiming(PlayerId()) then
|
|
self:TogglePanel2(true)
|
|
end
|
|
else
|
|
Wait(2000)
|
|
end
|
|
end
|
|
end)
|
|
end
|
|
|
|
function LR:StartCapture(index)
|
|
Citizen.CreateThread(function()
|
|
local time = Config.Occ[self.CurZone].time
|
|
while self.Capturing do
|
|
coroutine.yield(0)
|
|
print(time)
|
|
if self.CurZone ~= nil then
|
|
Wait(1000)
|
|
time = time - 1
|
|
if time <= 0 then
|
|
self.Capturing = false
|
|
end
|
|
if IsPlayerDead(PlayerId()) then
|
|
self.Capturing = false
|
|
TriggerServerEvent("lr_occ2:server:cancelCapture")
|
|
end
|
|
else
|
|
self.Capturing = false
|
|
TriggerServerEvent("lr_occ2:server:cancelCapture")
|
|
end
|
|
end
|
|
end)
|
|
end
|
|
|
|
function LR:StopCapture()
|
|
self.Capturing = false
|
|
end
|
|
|
|
function LR:ShowNotification(msg)
|
|
SendNUIMessage({
|
|
event = "notification",
|
|
data = msg
|
|
})
|
|
end
|
|
|
|
function LR:CheckPos()
|
|
for k, v in pairs(Config.Occ) do
|
|
local distance = #(self.pedCoords - v.Pos)
|
|
if distance <= v.Radius then
|
|
if not self.InZone then
|
|
self.InZone = true
|
|
self:TogglePanel2(true)
|
|
--self:TogglePanel3(true)
|
|
end
|
|
self:SetDataPanel2({
|
|
canCapture = self.CanCapture,
|
|
lastCapture = self.RemainCapture,
|
|
name = k,
|
|
point = v.point,
|
|
time = self.Cache[k] and self.Cache[k].remain or v.time,
|
|
capture = self.Cache[k] and self.Cache[k].name or nil
|
|
})
|
|
return k
|
|
end
|
|
end
|
|
if self.InZone then
|
|
self.InZone = false
|
|
self:TogglePanel2(false)
|
|
--self:TogglePanel3(false)
|
|
end
|
|
return nil
|
|
end
|
|
|
|
function LR:TogglePanel1(t)
|
|
SendNUIMessage({
|
|
event = "toggle-panel1",
|
|
data = t
|
|
})
|
|
end
|
|
|
|
function LR:SetDataPanel1(data)
|
|
SendNUIMessage({
|
|
event = "data-panel1",
|
|
data = data
|
|
})
|
|
end
|
|
|
|
function LR:TogglePanel2(t)
|
|
self.Panel2Open = t
|
|
SendNUIMessage({
|
|
event = "toggle-panel2",
|
|
data = t
|
|
})
|
|
end
|
|
|
|
function LR:SetDataPanel2(data)
|
|
SendNUIMessage({
|
|
event = "data-panel2",
|
|
data = data
|
|
})
|
|
end
|
|
|
|
function LR:TogglePanel3(t)
|
|
SendNUIMessage({
|
|
event = "toggle-panel3",
|
|
data = t
|
|
})
|
|
end
|
|
|
|
function LR:SetDataPanel3(data)
|
|
SendNUIMessage({
|
|
event = "data-panel3",
|
|
data = data
|
|
})
|
|
end
|
|
|
|
Citizen.CreateThread(function()
|
|
while ESX == nil do
|
|
Wait(0)
|
|
TriggerEvent("esx:getSharedObject", function(obj) ESX = obj end)
|
|
end
|
|
LR:Init()
|
|
end)
|
|
|
|
function DisplayText(text)
|
|
local width = string.len(text) + 0.0
|
|
DrawRect(1.0 - width / 200 / 2, 0.98, width / 200, 0.06, 245, 71, 72, 200)
|
|
SetTextScale(0.4, 0.4)
|
|
SetTextFont(ESX.FontId)
|
|
SetTextProportional(1)
|
|
SetTextColour(255, 255, 255, 255)
|
|
SetTextEntry("STRING")
|
|
SetTextCentre(1)
|
|
AddTextComponentString(text)
|
|
DrawText(1.0 - width / 200 / 2, 0.96)
|
|
end
|