Hi I’m working on a game state manger for the server.
I’ve created a state machine to handle state transitions, inside of which, I stored state instances that store functions for each state.
I need for each of the state to be updated on heartbeat, however the current method I have is a little messy and feels unorganized.
What are your guys’ solution for state machines. Any advice appreciated,
(English is not my first language. sorry if i have any mistakes)
Current code
local rs = game:GetService("RunService")
local players = game:GetService("Players")
local gameStateManager = {
currentState = nil,
states = {},
statePrototype = {
name = "empty",
onEnter = function(self) end,
onExit = function(self) end,
},
addState = function(self, obj)
if not obj.name then
warn("must provide name for a new state")
return
end
local newState = obj or {}
setmetatable(newState, {__index = self.statePrototype})
self.states[obj.name] = newState
print("added state: "..obj.name)
end,
changeState = function(self, state)
if not self or not state then
print("invalid arguments for changeState()")
return
end
print("state changed: "..state)
if self.currentState then
self.states[self.currentState]:onExit()
end
self.currentState = state
self.states[self.currentState]:onEnter()
end,
}
gameStateManager:addState(
{
name = "intermission",
minPlayers = 1,
onEnter = function(self)
self.heartbeatConn = rs.Heartbeat:Connect(
function()
if #players:GetPlayers() >= self.minPlayers then
gameStateManager:changeState("nextState")
else
print("waiting for players")
end
end
)
end,
onExit = function(self)
if self.heartbeatConn then
self.heartbeatConn:Disconnect()
end
end,
}
)
gameStateManager:addState(
{
name = "nextState"
}
)
wait(3)
gameStateManager:changeState("intermission")
I have removed other states to make the code shorter