diff --git a/sonorancad/core/client.lua b/sonorancad/core/client.lua index f49b592..6daa1d0 100644 --- a/sonorancad/core/client.lua +++ b/sonorancad/core/client.lua @@ -422,3 +422,61 @@ CreateThread(function() end end end) + +RegisterCommand('time', function() + local hours = GetClockHours() + local minutes = GetClockMinutes() + TriggerEvent('chat:addMessage', { + args = { + 'SonoranCAD', + ('Current time: %s:%s'):format(hours, minutes) + } + }) +end) + +-- Jordan - Time Utils +local isSendingTime = false + +local function getFormattedGameTime() + -- Get in-game date and time + local year, month, day = GetClockYear(), GetClockMonth(), GetClockDayOfMonth() + local hour, minute, second = GetClockHours(), GetClockMinutes(), GetClockSeconds() + + -- Format the in-game time as "YYYY-MM-DD HH:MM:SS" + return string.format("%04d-%02d-%02d %02d:%02d:%02d", year, month, day, hour, minute, second) +end + +local function getSecondsPerInGameHour() + -- Get milliseconds per in-game minute + local msPerMinute = GetMillisecondsPerGameMinute() + + -- Convert to seconds per in-game hour + local secondsPerHour = (msPerMinute / 1000) * 60 + return secondsPerHour +end + +-- Event to start sending time to the server +RegisterNetEvent("SonoranCad:time:requestSendTime", function() + debugLog("You have been selected to send the time.") + isSendingTime = true + + Citizen.CreateThread(function() + while isSendingTime do + local inGameTime = getFormattedGameTime() + local secondsPerHour = getSecondsPerInGameHour() + local timeData = { + currentGame = inGameTime, + secondsPerHour = secondsPerHour + } + TriggerServerEvent("SonoranCad:time:sendTime", timeData) + debugLog("Time sent to server: " .. json.encode(timeData)) + Citizen.Wait(60000) -- Wait 60 seconds before sending again + end + end) +end) + +-- Event to stop sending time (optional cleanup) +RegisterNetEvent("SonoranCad:time:stopSendingTime", function() + debugLog("You are no longer required to send the time.") + isSendingTime = false +end) diff --git a/sonorancad/core/commands.lua b/sonorancad/core/commands.lua index 9d93cb1..0760eb2 100644 --- a/sonorancad/core/commands.lua +++ b/sonorancad/core/commands.lua @@ -21,6 +21,8 @@ function dumpInfo() local version = GetResourceMetadata(GetCurrentResourceName(), "version", 0) local pluginList, loadedPlugins, disabledPlugins = GetPluginLists() local pluginVersions = {} + local versionFile = LoadVersionFile() + local versions = json.decode(versionFile) local cadVariables = { ["netPort"] = GetConvar("netPort", "Unknown")} local variableList = "" for k, v in pairs(cadVariables) do @@ -28,7 +30,7 @@ function dumpInfo() end for k, v in pairs(pluginList) do if Config.plugins[v] then - table.insert(pluginVersions, ("%s [%s/%s]"):format(v, Config.plugins[v].version, Config.plugins[v].latestVersion)) + table.insert(pluginVersions, ("%s [%s/%s]"):format(v, Config.plugins[v].configVersion, versions.submoduleConfigs[v].version)) end end local coreConfig = {} diff --git a/sonorancad/core/plugin_loader.lua b/sonorancad/core/plugin_loader.lua index c03bbfb..4b33855 100644 --- a/sonorancad/core/plugin_loader.lua +++ b/sonorancad/core/plugin_loader.lua @@ -6,7 +6,7 @@ Provides logic for checking loaded plugins after startup ]] -local function LoadVersionFile() +function LoadVersionFile() local f = LoadResourceFile(GetCurrentResourceName(), ("version.json")) if f then return f diff --git a/sonorancad/core/server.lua b/sonorancad/core/server.lua index 581ad51..6dee03c 100644 --- a/sonorancad/core/server.lua +++ b/sonorancad/core/server.lua @@ -527,4 +527,81 @@ exports('setCallPostal', setCallPostal) exports('performLookup', performLookup) exports('checkCADSubscriptionType', checkCADSubscriptionType) exports('getDispatchStatus', getDispatchStatus) --- Jordan - CAD Utils \ No newline at end of file +-- Jordan - CAD Utils + +-- Jordan - Time Utils + +local currentTimeClient = nil -- Stores the Player ID of the current time reporter +local lastSendTime = nil -- Stores the last time the time was sent + +-- Function to select a new client +local function selectNewClient() + local players = GetPlayers() + if #players == 0 then + if currentTimeClient then + TriggerClientEvent("SonoranCad:time:stopSendingTime", currentTimeClient) + end + currentTimeClient = nil + debugLog("No players available to send time.") + return + end + local newClient = players[math.random(1, #players)] + -- Inform the previous client to stop sending time + if currentTimeClient and currentTimeClient ~= newClient then + TriggerClientEvent("SonoranCad:time:stopSendingTime", currentTimeClient) + end + currentTimeClient = newClient + debugLog("Selected client " .. currentTimeClient .. " to send time.") + TriggerClientEvent("SonoranCad:time:requestSendTime", currentTimeClient) +end + +-- Event to handle received time from the client +RegisterNetEvent("SonoranCad:time:sendTime", function(timeData) + local source = source + if tonumber(source) == tonumber(currentTimeClient) then + debugLog("Received time from client " .. source .. ": " .. json.encode(timeData)) + lastSendTime = os.time() + -- Send the time to the API + exports['sonorancad']:performApiRequest({ + { + ['serverId'] = GetConvar('sonoran_serverId', 1), + ['currentUtc'] = os.date("!%Y-%m-%d %H:%M:%S"), + ['currentGame'] = timeData.currentGame, + ['secondsPerHour'] = timeData.secondsPerHour + } + }, 'SET_CLOCK', function(_) + end) + else + debugLog("Unexpected client sent time. Ignored.") + end +end) + +-- Event when a player disconnects +AddEventHandler("playerDropped", function(reason) + local playerId = source + if tonumber(playerId) == tonumber(currentTimeClient) then + debugLog("Client " .. playerId .. " disconnected. Selecting a new client.") + selectNewClient() + end +end) + +-- Initial selection when server starts +AddEventHandler("onResourceStart", function(resourceName) + if resourceName == GetCurrentResourceName() then + selectNewClient() + end +end) + +Citizen.CreateThread(function() + while true do + Citizen.Wait(65000) + if currentTimeClient then + if lastSendTime and os.time() - lastSendTime > 70 then + debugLog("Client " .. currentTimeClient .. " failed to report time in 60 seconds.") + selectNewClient() + end + elseif not currentTimeClient and #GetPlayers() > 0 then + selectNewClient() + end + end +end) \ No newline at end of file diff --git a/sonorancad/fxmanifest.lua b/sonorancad/fxmanifest.lua index 06e1038..f987bca 100644 --- a/sonorancad/fxmanifest.lua +++ b/sonorancad/fxmanifest.lua @@ -3,7 +3,7 @@ games {'gta5'} author 'Sonoran CAD' description 'Sonoran CAD FiveM Integration' -version '3.0.9' +version '3.1.0' server_scripts { 'core/http.js' diff --git a/sonorancad/version.json b/sonorancad/version.json index 3a7f6c5..0bb4705 100644 --- a/sonorancad/version.json +++ b/sonorancad/version.json @@ -1,5 +1,5 @@ { - "resource": "3.0.9", + "resource": "3.1.0", "testedFxServerVersion": "5932", "submoduleConfigs": { "callcommands": {