lines-lua/menu.lua
2025-10-22 15:21:56 +03:00

126 lines
2.7 KiB
Lua

require 'config'
require 'button'
-- Menu state class
---@class MenuState
---@field buttons Button[]
MenuState = {
buttons = {}
}
-- Factory function
---@param buttons Button[] | nil
---@return MenuState
function MenuState:new( buttons )
local state = {
buttons = buttons or MenuState.buttons
}
setmetatable( state, { __index = self } )
return state
end
-- Draw buttons
function MenuState:draw()
for _, button in ipairs(self.buttons) do
button:draw()
end
end
-- Update buttons
---@param dt number
---@param point Point
---@param pressed boolean
function MenuState:update( dt, point, pressed )
for _, button in pairs(self.buttons) do
button:update( dt, point, pressed )
end
end
---@enum MenuStateIndex
MenuStateIndex = {
start = 'start',
pause = 'pause',
levels = 'levels',
hidden = 'hidden'
}
local startButton = Button:new(
Point:new( 240, 120 ),
Point:new( 320, 80 ),
'Start',
nil,
nil,
function()
Menu.current_state = MenuStateIndex.hidden
GameGrid = LevelHandler:first()
Menu.updateCellSize()
end
)
local exitToMenuButton = Button:new(
Point:new( 240, 200 ),
Point:new( 320, 80 ),
'Return to menu',
nil,
nil,
function()
Menu.current_state = MenuStateIndex.start
end
)
local exitGameButton = Button:new(
Point:new( 240, 240 ),
Point:new( 320, 80 ),
'Exit',
nil,
nil,
function()
love.event.quit()
end
)
-- Menu handler
---@class Menu
---@field states MenuState[]
---@field current_state MenuStateIndex
Menu = {
states = {
-- Main menu
[MenuStateIndex.start] = MenuState:new({
startButton, exitGameButton
}),
-- Pause menu
[MenuStateIndex.pause] = MenuState:new({
exitToMenuButton
}),
-- Level selector
[MenuStateIndex.levels] = MenuState:new({
}),
-- Empty state
[MenuStateIndex.hidden] = MenuState:new()
},
current_state = MenuStateIndex.start
}
-- Draw current state
function Menu:draw()
self.states[self.current_state]:draw()
end
-- Update current state
---@param dt number
---@param point Point
---@param pressed boolean
function Menu:update( dt, point, pressed )
self.states[self.current_state]:update( dt, point, pressed )
end
function Menu.updateCellSize()
local width, height = love.graphics.getDimensions()
local gridX, gridY = GameGrid.size:coords();
local isWidthBased = (width / height) / (gridX / gridY)
Config.cellSize = math.floor(isWidthBased and height / gridY or width / gridX)
love.graphics.setLineWidth( Config.cellSize * Config.lineWidth )
end