我正在尝试用 lua 和 love2d 制作一个主菜单,这是我第一次这样做,遗憾的是没有关于此事的教程,所以我自己尝试了一下。我一直遇到这个错误,我不知道如何修复它,请帮忙!
完整错误消息: 错误 main.lua:23: 尝试索引 upvalue 'Menu' ( bool 值) Traceback main.lua:23: 在函数 'load' 中 [C ]:在函数“xpcall”中 [C]:在函数“xpcall”中
菜单文件
local Menu = {}
local game_state = 'menu'
local menus = { 'Play', 'Quit' }
local selected_menu_item = 1
local window_width
local window_height
local font_height
local Map = require("map")
-- functions
local draw_menu
local menu_keypressed
local draw_game
local game_keypressed
function Menu:load()
-- get the width and height of the game window in order to center menu items
self.window_width, self.window_height = love.graphics.getDimensions()
-- use a big font for the menu
self.font = love.graphics.newFont("assets/bit.ttf", 36)
-- get the height of the font to help calculate vertical positions of menu items
self.font_height = font:getHeight()
end
function Menu:update(dt)
end
function Menu:draw()
local horizontal_center = self.window_width / 2
local vertical_center = self.window_height / 2
local start_y = vertical_center - (self.font_height * (#menus / 2))
-- draw guides to help check if menu items are centered, can remove later
-- love.graphics.setColor(1, 1, 1, 0.1)
-- love.graphics.line(horizontal_center, 0, horizontal_center, window_height)
-- love.graphics.line(0, vertical_center, window_width, vertical_center)
-- draw game title
love.graphics.setColor(1, 1, 1, 1)
love.graphics.printf("Breakout", 0, 150, window_width, 'center')
-- draw menu items
for i = 1, #menus do
-- currently selected menu item is yellow
if i == selected_menu_item then
love.graphics.setColor(1, 1, 0, 1)
-- other menu items are white
else
love.graphics.setColor(1, 1, 1, 1)
end
-- draw this menu item centered
love.graphics.printf(menus[i], 0, start_y + self.font_height * (i-1), self.window_width, 'center')
end
end
function Menu:keypressed(key)
-- pressing Esc on the main menu quits the game
if key == 'escape' then
love.event.quit()
-- pressing up selects the previous menu item, wrapping to the bottom if necessary
elseif key == 'up' then
selected_menu_item = selected_menu_item - 1
if selected_menu_item < 1 then
selected_menu_item = #menus
end
-- pressing down selects the next menu item, wrapping to the top if necessary
elseif key == 'down' then
selected_menu_item = selected_menu_item + 1
if selected_menu_item > #menus then
selected_menu_item = 1
end
-- pressing enter changes the game state (or quits the game)
elseif key == 'return' or key == 'kpenter' then
if menus[selected_menu_item] == 'Play' then
Map:load()
elseif menus[selected_menu_item] == 'Quit' then
love.event.quit()
end
end
end
主文件
love.graphics.setDefaultFilter("nearest", "nearest")
local Player = require("player")
local Coin = require("coin")
local GUI = require("gui")
local Spike = require("spike")
local Camera = require("camera")
local Stone = require("stone")
local Enemy = require("enemy")
local Map = require("map")
local Enemy2 = require("enemy2")
local Sound = require("sound")
local Menu = require("menu")
function love.load()
Sound:init("music", "sfx/music.wav", "static")
Sound:init("breeze", "sfx/breeze.mp3", "static")
Enemy.loadAssets()
Enemy2.loadAssets()
Map:load()
background = love.graphics.newImage("assets/background2.png")
Player:load()
GUI:load()
Menu:load()
end
function love.update(dt)
Sound:update()
World:update(dt)
Player:update(dt)
Coin.updateAll(dt)
Stone.updateAll(dt)
Enemy.updateAll(dt)
Enemy2.updateAll(dt)
GUI:load(dt)
Spike:updateAll(dt)
Camera:setPosition(Player.x, 0)
Map:update(dt)
Menu:load()
end
function love.draw()
love.graphics.draw(background)
Map.level:draw(-Camera.x, -Camera.y, Camera.scale, Camera.scale)
Menu:draw()
Camera:apply()
Player:draw()
Enemy.drawAll()
Enemy2.drawAll()
Coin.drawAll()
Spike.drawAll()
Stone.drawAll()
Camera:clear()
GUI:draw()
end
function love.playmusic()
loopingMusic = Sound:play("music", "sfx", 0.05, 1)
loopingMusic:setLooping(true)
end
function love.playBreeze()
loopingBreeze = Sound:play("breeze", "sfx", 0.3, 1)
loopingBreeze:setLooping(true)
end
function love.keypressed(key)
Player:jump(key)
Menu:keypressed(key)
if key == "m" then
Sound:stop("sfx")
end
end
function beginContact(a, b, collision)
if Coin.beginContact(a, b, collision) then
return
end
if Spike.beginContact(a, b, collision) then
return end
Enemy.beginContact(a, b, collision)
Enemy2.beginContact(a, b, collision)
Player:beginContact(a, b, collision)
end
function endContact(a, b, collision)
Player:endContact(a, b, collision)
end
function endGame()
love.event.quit()
end
最佳答案
您的menu.lua不会返回您的表格菜单。
因此 assiging menu = require("menu")
会导致 menu
引用 Menu
但引用 true
.
来自Lua manua升:
Once a loader is found, require calls the loader with a single argument, modname. If the loader returns any value, require assigns the returned value to package.loaded[modname]. If the loader returns no value and has not assigned any value to package.loaded[modname], then require assigns true to this entry. In any case, require returns the final value of package.loaded[modname].
因此,在 main.lua 的第 23 行中,您实际上是在尝试索引 true(一个 bool 值)。 菜单:load()
将return Menu
添加到menu.lua的末尾
关于user-interface - 错误 main.lua :23: attempt to index upvalue 'Menu' (a boolean value),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/70593608/