聊天重做前缓存
This commit is contained in:
160
TrainerUI.lua
160
TrainerUI.lua
@@ -61,10 +61,11 @@ local currentFilter = "all"
|
||||
local displayList = {}
|
||||
local rowButtons = {}
|
||||
local collapsedCats = {}
|
||||
local isTradeskillTrainerCached = false -- Cache to avoid repeated API calls
|
||||
local isTradeskillTrainerCached = false
|
||||
local function HideBlizzardTrainer()
|
||||
if not ClassTrainerFrame then return end
|
||||
ClassTrainerFrame:SetScript("OnHide", function() end)
|
||||
ClassTrainerFrame:UnregisterAllEvents()
|
||||
if ClassTrainerFrame:IsVisible() then
|
||||
if HideUIPanel then
|
||||
pcall(HideUIPanel, ClassTrainerFrame)
|
||||
@@ -161,123 +162,20 @@ end
|
||||
local function GetVerifiedCategory(index)
|
||||
local name, _, category = GetTrainerServiceInfo(index)
|
||||
if not name then return nil end
|
||||
|
||||
-- "used" is always reliable - player already knows this skill
|
||||
if category == "used" then
|
||||
return "used"
|
||||
if category == "available" or category == "unavailable" or category == "used" then
|
||||
return category
|
||||
end
|
||||
|
||||
-- "unavailable" from API should be trusted - it considers:
|
||||
-- - Level requirements
|
||||
-- - Skill rank prerequisites (e.g., need Fireball Rank 1 before Rank 2)
|
||||
-- - Profession skill requirements
|
||||
if category == "unavailable" then
|
||||
return "unavailable"
|
||||
end
|
||||
|
||||
-- For "available", do extra verification only for tradeskill trainers
|
||||
-- Class trainers' "available" is already accurate
|
||||
if category == "available" then
|
||||
-- Additional check for tradeskill trainers (use cached value)
|
||||
if isTradeskillTrainerCached then
|
||||
local playerLevel = UnitLevel("player") or 1
|
||||
|
||||
-- Check level requirement
|
||||
if GetTrainerServiceLevelReq then
|
||||
local ok, levelReq = pcall(GetTrainerServiceLevelReq, index)
|
||||
if ok and levelReq and levelReq > 0 and playerLevel < levelReq then
|
||||
return "unavailable"
|
||||
end
|
||||
end
|
||||
|
||||
-- Check skill requirement
|
||||
if GetTrainerServiceSkillReq then
|
||||
local ok, skillName, skillRank, hasReq = pcall(GetTrainerServiceSkillReq, index)
|
||||
if ok and skillName and skillName ~= "" and not hasReq then
|
||||
return "unavailable"
|
||||
end
|
||||
end
|
||||
end
|
||||
return "available"
|
||||
end
|
||||
|
||||
-- Fallback: unknown category, treat as unavailable
|
||||
return category or "unavailable"
|
||||
return "unavailable"
|
||||
end
|
||||
|
||||
local scanTip = nil
|
||||
|
||||
local function GetServiceTooltipInfo(index)
|
||||
if not scanTip then
|
||||
scanTip = CreateFrame("GameTooltip", "SFramesTrainerScanTip", nil, "GameTooltipTemplate")
|
||||
end
|
||||
scanTip:SetOwner(WorldFrame, "ANCHOR_NONE")
|
||||
scanTip:ClearLines()
|
||||
local ok = pcall(scanTip.SetTrainerService, scanTip, index)
|
||||
if not ok then return "", "" end
|
||||
|
||||
local infoLines = {}
|
||||
local descLines = {}
|
||||
local numLines = scanTip:NumLines()
|
||||
local foundDesc = false
|
||||
|
||||
for i = 2, numLines do
|
||||
local leftFS = _G["SFramesTrainerScanTipTextLeft" .. i]
|
||||
local rightFS = _G["SFramesTrainerScanTipTextRight" .. i]
|
||||
local leftText = leftFS and leftFS:GetText() or ""
|
||||
local rightText = rightFS and rightFS:GetText() or ""
|
||||
|
||||
if leftText == "" and rightText == "" then
|
||||
if not foundDesc and table.getn(infoLines) > 0 then
|
||||
foundDesc = true
|
||||
end
|
||||
else
|
||||
local line
|
||||
if rightText ~= "" and leftText ~= "" then
|
||||
line = leftText .. " " .. rightText
|
||||
elseif leftText ~= "" then
|
||||
line = leftText
|
||||
else
|
||||
line = rightText
|
||||
end
|
||||
|
||||
local isYellow = leftFS and leftFS.GetTextColor and true
|
||||
local r, g, b
|
||||
if leftFS and leftFS.GetTextColor then
|
||||
r, g, b = leftFS:GetTextColor()
|
||||
end
|
||||
local isWhiteOrYellow = r and (r > 0.9 and g > 0.75)
|
||||
|
||||
if not foundDesc and rightText ~= "" then
|
||||
table.insert(infoLines, line)
|
||||
elseif not foundDesc and not isWhiteOrYellow and string.len(leftText) < 30 then
|
||||
table.insert(infoLines, line)
|
||||
else
|
||||
foundDesc = true
|
||||
table.insert(descLines, line)
|
||||
end
|
||||
end
|
||||
end
|
||||
scanTip:Hide()
|
||||
return table.concat(infoLines, "\n"), table.concat(descLines, "\n")
|
||||
return "", ""
|
||||
end
|
||||
|
||||
local function GetServiceQuality(index)
|
||||
if not scanTip then
|
||||
scanTip = CreateFrame("GameTooltip", "SFramesTrainerScanTip", nil, "GameTooltipTemplate")
|
||||
end
|
||||
scanTip:SetOwner(WorldFrame, "ANCHOR_NONE")
|
||||
scanTip:ClearLines()
|
||||
local ok = pcall(scanTip.SetTrainerService, scanTip, index)
|
||||
if not ok then scanTip:Hide() return nil end
|
||||
local firstLine = _G["SFramesTrainerScanTipTextLeft1"]
|
||||
if not firstLine or not firstLine.GetTextColor then
|
||||
scanTip:Hide()
|
||||
return nil
|
||||
end
|
||||
local r, g, b = firstLine:GetTextColor()
|
||||
scanTip:Hide()
|
||||
return ColorToQuality(r, g, b)
|
||||
return nil
|
||||
end
|
||||
|
||||
--------------------------------------------------------------------------------
|
||||
@@ -392,10 +290,7 @@ end
|
||||
local qualityCache = {}
|
||||
|
||||
local function GetCachedServiceQuality(index)
|
||||
if qualityCache[index] ~= nil then return qualityCache[index] end
|
||||
local q = GetServiceQuality(index)
|
||||
qualityCache[index] = q or false
|
||||
return q
|
||||
return nil
|
||||
end
|
||||
|
||||
--------------------------------------------------------------------------------
|
||||
@@ -604,22 +499,8 @@ local function CreateListRow(parent, idx)
|
||||
self.icon:SetVertexColor(T.passive[1], T.passive[2], T.passive[3])
|
||||
end
|
||||
|
||||
-- Skip quality scan for tradeskill trainers (performance optimization)
|
||||
if not isTradeskillTrainerCached then
|
||||
local quality = GetCachedServiceQuality(svc.index)
|
||||
local qc = QUALITY_COLORS[quality]
|
||||
if qc and quality and quality >= 2 then
|
||||
self.qualGlow:SetVertexColor(qc[1], qc[2], qc[3])
|
||||
self.qualGlow:Show()
|
||||
self.iconFrame:SetBackdropBorderColor(qc[1], qc[2], qc[3], 1)
|
||||
else
|
||||
self.qualGlow:Hide()
|
||||
self.iconFrame:SetBackdropBorderColor(T.slotBorder[1], T.slotBorder[2], T.slotBorder[3], T.slotBorder[4])
|
||||
end
|
||||
else
|
||||
self.qualGlow:Hide()
|
||||
self.iconFrame:SetBackdropBorderColor(T.slotBorder[1], T.slotBorder[2], T.slotBorder[3], T.slotBorder[4])
|
||||
end
|
||||
self.qualGlow:Hide()
|
||||
self.iconFrame:SetBackdropBorderColor(T.slotBorder[1], T.slotBorder[2], T.slotBorder[3], T.slotBorder[4])
|
||||
|
||||
local ok, cost = pcall(GetTrainerServiceCost, svc.index)
|
||||
if ok and cost and cost > 0 then
|
||||
@@ -838,13 +719,7 @@ local function UpdateDetail()
|
||||
detail.icon:SetTexture(iconTex)
|
||||
detail.iconFrame:Show()
|
||||
|
||||
local quality = GetServiceQuality(selectedIndex)
|
||||
local qc = QUALITY_COLORS[quality]
|
||||
if qc and quality and quality >= 2 then
|
||||
detail.iconFrame:SetBackdropBorderColor(qc[1], qc[2], qc[3], 1)
|
||||
else
|
||||
detail.iconFrame:SetBackdropBorderColor(T.slotBorder[1], T.slotBorder[2], T.slotBorder[3], T.slotBorder[4])
|
||||
end
|
||||
detail.iconFrame:SetBackdropBorderColor(T.slotBorder[1], T.slotBorder[2], T.slotBorder[3], T.slotBorder[4])
|
||||
|
||||
detail.nameFS:SetText(name or "")
|
||||
|
||||
@@ -873,13 +748,10 @@ local function UpdateDetail()
|
||||
end
|
||||
detail.reqFS:SetText(table.concat(reqParts, " "))
|
||||
|
||||
local spellInfo, descText = GetServiceTooltipInfo(selectedIndex)
|
||||
detail.infoFS:SetText(spellInfo)
|
||||
detail.descFS:SetText(descText)
|
||||
detail.descDivider:Show()
|
||||
|
||||
local textH = detail.descFS:GetHeight() or 40
|
||||
detail.descScroll:GetScrollChild():SetHeight(math.max(1, textH))
|
||||
detail.infoFS:SetText("")
|
||||
detail.descFS:SetText("")
|
||||
detail.descDivider:Hide()
|
||||
detail.descScroll:GetScrollChild():SetHeight(1)
|
||||
detail.descScroll:SetVerticalScroll(0)
|
||||
|
||||
local canTrain = (category == "available") and cost and (GetMoney() >= cost)
|
||||
@@ -1342,6 +1214,7 @@ function TUI:Initialize()
|
||||
local function CleanupBlizzardTrainer()
|
||||
if not ClassTrainerFrame then return end
|
||||
ClassTrainerFrame:SetScript("OnHide", function() end)
|
||||
ClassTrainerFrame:UnregisterAllEvents()
|
||||
if HideUIPanel then pcall(HideUIPanel, ClassTrainerFrame) end
|
||||
if ClassTrainerFrame:IsVisible() then ClassTrainerFrame:Hide() end
|
||||
ClassTrainerFrame:SetAlpha(0)
|
||||
@@ -1361,6 +1234,7 @@ function TUI:Initialize()
|
||||
if event == "TRAINER_SHOW" then
|
||||
if ClassTrainerFrame then
|
||||
ClassTrainerFrame:SetScript("OnHide", function() end)
|
||||
ClassTrainerFrame:UnregisterAllEvents()
|
||||
ClassTrainerFrame:SetAlpha(0)
|
||||
ClassTrainerFrame:EnableMouse(false)
|
||||
end
|
||||
|
||||
Reference in New Issue
Block a user