local globalevent = GlobalEvent("staminaRegeneration")
local STORAGE_KEY = 48474645
local REGENERATION_INTERVAL_LOW = 180 -- seconds (3 minutes) for stamina below 39 hours
local REGENERATION_INTERVAL_HIGH = 600 -- seconds (10 minutes) for stamina between 39 and 42 hours
local STAMINA_FULL = 42 * 60 -- full stamina in minutes (42 hours)
local STAMINA_THRESHOLD = 39 * 60 -- threshold in minutes (39 hours)
local PLAYER_BATCH_SIZE = 20 -- Number of players to process per interval
-- Store the list of players and track the processing state
local playersToProcess = {}
local playerIndex = 1 -- Keeps track of which player to process next
function globalevent.onThink()
-- Get all the players online
local players = Game.getPlayers()
local numPlayers = #players
-- Initialize playersToProcess list on the first run
if #playersToProcess == 0 then
-- Populate the list of all players
for i, player in ipairs(players) do
table.insert(playersToProcess, player)
end
end
-- Process the next batch of 20 players
local batchEndIndex = math.min(playerIndex + PLAYER_BATCH_SIZE - 1, numPlayers)
for i = playerIndex, batchEndIndex do
local player = playersToProcess[i]
-- Check if player is in a protection zone and stamina is below the maximum
if Tile(player:getPosition()):hasFlag(TILESTATE_PROTECTIONZONE) and player:getStamina() < STAMINA_FULL then
-- Increment storage by 60 (for 60-second interval)
local currentCount = player:getStorageValue(STORAGE_KEY)
if currentCount < 0 then
currentCount = 0
end
currentCount = currentCount + 60
player:setStorageValue(STORAGE_KEY, currentCount)
-- Determine regeneration interval based on player's current stamina
local playerStamina = player:getStamina()
local regenerationInterval = REGENERATION_INTERVAL_LOW -- Default to 3 minutes
if playerStamina >= STAMINA_THRESHOLD and playerStamina < STAMINA_FULL then
regenerationInterval = REGENERATION_INTERVAL_HIGH -- Set to 10 minutes
end
-- Check if the storage value has reached or exceeded the interval for stamina regeneration
if currentCount >= regenerationInterval then
-- Regenerate 1 minute of stamina
player:setStamina(playerStamina + 1)
-- Subtract the interval from the storage to carry over any extra time
player:setStorageValue(STORAGE_KEY, currentCount - regenerationInterval)
end
elseif player:getStorageValue(STORAGE_KEY) ~= 0 then
-- Reset storage to 0 if the player is not in a protection zone or has full stamina
player:setStorageValue(STORAGE_KEY, 0)
end
end
-- Update the index to process the next set of players in the next "think" event
playerIndex = playerIndex + PLAYER_BATCH_SIZE
-- If all players have been processed, reset the index and start over
if playerIndex > numPlayers then
playerIndex = 1
end
-- Schedule the next cycle of this function, ensuring each batch is processed over time
-- The next batch of 20 will be processed in the next "think" event (same 60-second cycle)
addEvent(globalevent.onThink, 100) -- Call the next `onThink()` immediately
end
globalevent:interval(60000) -- Executes every 60 seconds (1 minute)
globalevent:register()