local switch_map = {}
local MainButton = SL:Require("GUILayout\\2_TopLayout\\L_MainButton", true)
function switch_map:main()
-- 检查MainAssist是否初始化
if not MainAssist or not MainAssist._ui then
SL:Print("MainAssist未初始化")
return
看了你的代码,主要问题出在**循环调用和定时器管理**上。让我帮你分析:
## 主要问题:
1. **循环调用导致卡死**:
```lua
-- 在main()函数中直接调用MainButton:main()
MainButton:main() -- 如果MainButton也调用了switch_map:main(),就会形成循环
```
2. **定时器没有正确清理**:
```lua
-- 每次进入main()都会创建新定时器,但旧的可能没清理干净
switch_map._timer = SL:Schedule(function()
-- 更新逻辑
end, 1.0)
```
## 修复方案:
```lua
local switch_map = {}
local MainButton = SL:Require("GUILayout\\2_TopLayout\\L_MainButton", true)
-- 添加初始化标记,防止重复调用
switch_map._isInitialized = false
function switch_map:main()
-- 防止重复初始化
if switch_map._isInitialized then
return
end
-- 检查MainAssist是否初始化
if not MainAssist or not MainAssist._ui then
SL:Print("MainAssist未初始化")
return
end
local mainWin = MainAssist._ui["Panel_assist"]
if GUI:Win_IsNull(mainWin) then
SL:Print("mainWin为空")
return
end
local mapID = SL:GetMetaValue("MAP_ID")
if not mapID then
SL:Print("获取地图ID失败")
return
end
-- 【修复】先停止定时器再清理控件
self:cleanup()
SL:Print("进来了界面刷新")
-- 【修复】避免直接调用可能引起循环的模块
-- 如果MainButton需要初始化,应该在合适的地方调用
-- MainButton:main() -- 注释掉这行,避免循环
-- 判断是否是特殊地图
if mapID ~= "kf_wm" and mapID ~= "kf_nm" then
-- 正常地图逻辑
self:ShowAllMissions()
if BeStrongUp and BeStrongUp._ui and not GUI:Win_IsNull(BeStrongUp._ui["Button_up"]) then
GUI:setVisible(BeStrongUp._ui["Button_up"], true)
end
-- 清理任务节点
local taskNode = GUI:getChild(mainWin, "taskNode")
if not GUI:Win_IsNull(taskNode) then
GUI:removeAllChildren(taskNode)
end
else
-- 特殊地图逻辑
self:HideAllMissions()
if BeStrongUp and BeStrongUp._ui and not GUI:Win_IsNull(BeStrongUp._ui["Button_up"]) then
GUI:setVisible(BeStrongUp._ui["Button_up"], false)
end
-- 创建或更新特殊地图显示
local taskNode = GUI:getChild(mainWin, "taskNode")
if GUI:Win_IsNull(taskNode) then
taskNode = GUI:Node_Create(mainWin, "taskNode")
else
GUI:removeAllChildren(taskNode)
end
-- 检查Guild_value是否存在
if not self.Guild_value then
self.Guild_value = {}
end
local jifenValue = SL:GetMetaValue("MONEY", 25) or 0
local guildValue = "暂无归属"
if self.Guild_value and self.Guild_value.Shabak_guild_name then
local guildName = self.Guild_value.Shabak_guild_name
if guildName ~= "" and guildName ~= nil then
guildValue = guildName
end
end
local doorValue = "关闭"
if self.Guild_value and self.Guild_value.doorStatus == true then
doorValue = "开启"
end
local jiesuValue = "21:00"
local currentMode = SL:GetMetaValue("CURRENT_OPERMODE") or 1
local xPos = currentMode == 1 and 20 or 55
-- 创建显示内容
local guild_display = GUI:Text_Create(taskNode, "guild_text",
xPos, 160, 16, "#FFFC0404", "沙城归属:" .. guildValue)
local jifen_display = GUI:Text_Create(taskNode, "jifen_text",
xPos, 130, 16, "#FF05F35C", "跨服积分: " .. jifenValue)
local jiesu_time = GUI:Text_Create(taskNode, "jiesu_text",
xPos, 100, 16, "#FFFC0404", "结束时间:" .. jiesuValue)
local door_state = GUI:Text_Create(taskNode, "door_text",
xPos, 70, 16, "#FFFC0404", "内门状态:" .. doorValue)
local map_button = GUI:Button_Create(taskNode, "map_button",
xPos + (currentMode == 1 and 45 or 7), 15, "res/public/1900000662.png")
GUI:Button_setTitleText(map_button, "回到主城")
GUI:Button_setTitleColor(map_button, "#FFE7FC04")
GUI:addOnClickEvent(map_button, function()
SL:SendLuaNetMsg(1111, 11, 11, 11, "")
end)
-- 开启定时器前存储控件引用
self._displayWidgets = {
guild = guild_display,
jifen = jifen_display,
door = door_state
}
-- 【修复】使用ScheduleOnce避免循环
if self._updateTimer then
SL:UnSchedule(self._updateTimer)
end
self._updateTimer = SL:Schedule(function()
-- 检查控件引用和模块状态
if not self._displayWidgets or not self.Guild_value then
return
end
-- 获取数据
local jifenValue = SL:GetMetaValue("MONEY", 25) or 0
local guildValue = "暂无归属"
if self.Guild_value.Shabak_guild_name then
local guildName = self.Guild_value.Shabak_guild_name
if guildName ~= "" and guildName ~= nil then
guildValue = guildName
end
end
local doorValue = "关闭"
if self.Guild_value.doorStatus == true then
doorValue = "开启"
end
-- 更新文本内容
for key, widget in pairs(self._displayWidgets) do
if not GUI:Win_IsNull(widget) then
local text = ""
if key == "guild" then
text = "沙城归属:" .. tostring(guildValue)
elseif key == "jifen" then
text = "跨服积分:" .. tostring(jifenValue)
elseif key == "door" then
text = "内门状态:" .. tostring(doorValue)
end
GUI:Text_setString(widget, text)
end
end
end, 1.0)
end
-- 标记已初始化
switch_map._isInitialized = true
end
-- 添加清理函数
function switch_map:cleanup()
-- 停止定时器
if self._updateTimer then
SL:UnSchedule(self._updateTimer)
self._updateTimer = nil
end
-- 清理显示控件引用
if self._displayWidgets then
for key, widget in pairs(self._displayWidgets) do
if not GUI:Win_IsNull(widget) then
GUI:removeFromParent(widget)
end
end
self._displayWidgets = nil
end
self._isInitialized = false
end
-- 【修复】网络回调中避免直接调用main()
local function networkCB(msgID, p1, p2, p3, msgData)
if msgData then
switch_map.Guild_value = SL:JsonDecode(msgData)
else
switch_map.Guild_value = {}
end
-- 只更新数据,不重新初始化
if switch_map._updateTimer then
-- 定时器会自动更新显示
end
end
-- 【修复】地图切换时清理后重新初始化
SL:RegisterLUAEvent(LUA_EVENT_MAPINFOCHANGE, "MapRefreshUI", function()
switch_map:cleanup()
switch_map:main()
end)
SL:RegisterLuaNetMsg(1888, networkCB)
return switch_map
```
## 关键修改:
1. **移除了`MainButton:main()`的直接调用**,避免模块间循环
2. **添加了`_isInitialized`标记**防止重复初始化
3. **优化了定时器管理**,确保先清理再创建
4. **网络回调中不再调用main()**,只更新数据
这样修改后应该能解决卡死问题。如果还有问题,检查一下`MainButton`模块是否也调用了`switch_map:main()`。