Add files via upload

This commit is contained in:
Relationship
2026-07-11 11:12:12 +01:00
committed by GitHub
parent 664fc36e0d
commit 04f87e5b42
3 changed files with 152 additions and 133 deletions
+13 -53
View File
@@ -6,7 +6,7 @@ RelationshipsAttune = RelationshipsAttune or {}
local RA = RelationshipsAttune
local L = RelationshipsAttune_L
RA.VERSION = "1.2.7"
RA.VERSION = "1.3.0"
RA.COMM_PREFIX = "RATTUNE"
RA.playerName = nil
@@ -73,14 +73,18 @@ end
-- ---------------------------------------------------------------
-- Quest log scan (vanilla API)
--
-- Note: vanilla 1.12's GetQuestLogTitle returns 6 values without a questId.
-- Turtle/Octo backported questId as the 8th return. We pcall + accept both
-- shapes so the addon degrades gracefully on stock 1.12.
-- ---------------------------------------------------------------
function RA:ScanQuestLog()
if not GetNumQuestLogEntries then return end
local numEntries = GetNumQuestLogEntries()
for i = 1, numEntries do
local title, level, tag, isHeader, _, isComplete, _, questId =
GetQuestLogTitle(i)
if (not isHeader) and questId then
local ok, title, level, tag, isHeader, _, isComplete, _, questId =
pcall(GetQuestLogTitle, i)
if ok and (not isHeader) and questId then
if isComplete and isComplete == 1 then
RelationshipsAttuneCharDB.quests[questId] = "complete"
else
@@ -112,11 +116,6 @@ local function rememberItemLink(link)
end
-- Resolve by name so a custom Turtle/Octo item whose live client id
-- differs from the id declared in Data.lua still gets credited.
-- Try GetItemInfo first (works when the item is cached), then fall back
-- to parsing the bracketed display name straight out of the link. On
-- 1.12 / Turtle / Octo, keyring items very often return a link but
-- GetItemInfo returns nil because the item is not cached client-side,
-- so the bracketed-name parse is what actually credits the item.
local resolvedName
if GetItemInfo then
local ok, n = pcall(GetItemInfo, link)
@@ -200,19 +199,10 @@ local function scanContainer(containerId)
end
end
-- Scan a keyring-like container. Uses every fallback we know of so that
-- keys register on vanilla 1.12, Turtle, and Octo regardless of which
-- bag id / API path actually works on that client build:
-- 1) GetContainerItemLink -> parse item id + bracketed name from link.
-- 2) SetBagItem tooltip -> read visible line as name.
-- 3) GetContainerItemInfo -> at minimum proves a slot is occupied so
-- we keep probing even when NumSlots lies.
local function scanKeyringContainer(bag)
if not GetContainerNumSlots then return end
local ok, slots = pcall(GetContainerNumSlots, bag)
if not ok or not slots then slots = 0 end
-- Some 1.12 clients report 0 slots for the keyring until it has been
-- opened at least once. Probe a reasonable upper bound in that case.
local probe = slots
if probe < 1 then probe = 32 end
@@ -224,13 +214,11 @@ local function scanKeyringContainer(bag)
local setOk = false
pcall(function() tip:SetBagItem(bag, slot); setOk = true end)
-- Path 1: link
local link
local okL, l = pcall(GetContainerItemLink, bag, slot)
if okL then link = l end
if link then rememberItemLink(link) end
-- Path 2: tooltip visible name (works even when link is nil).
if setOk then
local name = tipItemName()
if name and nameMap then
@@ -239,11 +227,6 @@ local function scanKeyringContainer(bag)
end
end
-- Path 3: GetContainerItemInfo. We can't get a name from it, but
-- if it returns a texture the slot is definitely occupied; that
-- lets us know it's worth continuing to probe even when the
-- earlier paths returned nothing on this build.
-- (No-op for identification, kept for future diagnostics.)
if GetContainerItemInfo then
pcall(GetContainerItemInfo, bag, slot)
end
@@ -251,11 +234,6 @@ local function scanKeyringContainer(bag)
pcall(function() tip:Hide() end)
end
-- Warm the client-side item cache for every item id we care about. On
-- vanilla 1.12 the first GetItemInfo(id) call for an uncached item kicks
-- off a server fetch and returns nil; a later call returns real data.
-- Doing this at load time (and again after a short delay) means that by
-- the time we parse a keyring link, GetItemInfo can actually resolve it.
function RA:WarmItemCache()
if not GetItemInfo or not RelationshipsAttune_Data then return end
for i = 1, table.getn(RelationshipsAttune_Data) do
@@ -278,10 +256,6 @@ function RA:ScanBags()
scanContainer(bag)
end
-- Keyring: try every index the various 1.12 forks use. Vanilla/Turtle/
-- Octo typically expose it as -2; a few builds use -1, -3, or define
-- KEYRING_CONTAINER to something else entirely. Scanning a bogus id
-- is harmless because scanKeyringContainer pcall-guards every call.
local seen = {}
local function tryBag(b)
if b == nil or seen[b] then return end
@@ -301,7 +275,6 @@ function RA:ScanBags()
end
end
-- Back-compat shim: older code paths may still call this.
function RA:ForceKeyringResolve()
scanKeyringContainer(-2)
end
@@ -357,11 +330,9 @@ function RA:EvaluateAttunement(att)
steps[i] = nil
end
end
-- Short-circuit: if the player already owns the final key/item (or a step
-- explicitly flagged final=true) then the entire attunement is done, even
-- if earlier bookkeeping steps (prereq quests, reputation) can no longer
-- be detected on this character. This handles the case where the key was
-- earned before the addon was installed.
-- Short-circuit: if the "final" step is complete, treat the whole
-- attunement as done. Prefer an explicit final=true step; fall back to
-- the last item step (key), then the last applicable step.
local finalIdx = nil
for i = numSteps, 1, -1 do
local step = att.steps[i]
@@ -371,7 +342,6 @@ function RA:EvaluateAttunement(att)
end
end
if not finalIdx then
-- Fall back to the last applicable item step (typically the key).
for i = numSteps, 1, -1 do
local step = att.steps[i]
if step.type == "item" and self:StepApplies(step) then
@@ -381,8 +351,6 @@ function RA:EvaluateAttunement(att)
end
end
if not finalIdx then
-- If there is no key/item step, the last applicable step is the final
-- proof we can see. This covers quest-only or reputation attunements.
for i = numSteps, 1, -1 do
local step = att.steps[i]
if self:StepApplies(step) then
@@ -444,10 +412,6 @@ function RA:_OnUpdate(elapsed)
and RelationshipsAttuneDB.options.autoScanSeconds) or 20
if interval < 5 then interval = 5 end
-- Delayed post-login retry passes. GetItemInfo populates async on
-- 1.12, and the keyring itself may not be populated at PLAYER_LOGIN,
-- so we re-warm the cache and rescan a couple of times shortly after
-- login to catch keys that weren't resolvable on the first pass.
if RA._retryAt and GetTime then
local now = GetTime()
local pending = {}
@@ -497,14 +461,12 @@ end
-- ---------------------------------------------------------------
local function slashHandler(msg)
msg = string.lower(msg or "")
-- trim
msg = string.gsub(msg, "^%s+", "")
msg = string.gsub(msg, "%s+$", "")
if msg == "show" then
if RA.UI then RA.UI:Show() end
elseif msg == "hide" then
-- If the window is open, /attune hide closes it; otherwise it hides the minimap button.
if RA.UI and RA.UI:IsShown() then
RA.UI:Hide()
elseif RA.Minimap then
@@ -563,7 +525,6 @@ local function slashHandler(msg)
end
end
pcall(function() tip:Hide() end)
print("Scarlet Key (7146) owned: " .. tostring(RelationshipsAttuneCharDB.items[7146] == true))
elseif msg == "help" or msg == "?" then
print("Relationships Attune - commands:")
print(" /attune - toggle the window")
@@ -596,6 +557,8 @@ ef:RegisterEvent("BAG_UPDATE")
ef:RegisterEvent("PLAYER_LEVEL_UP")
ef:RegisterEvent("UPDATE_FACTION")
ef:RegisterEvent("CHAT_MSG_ADDON")
-- These events don't exist on stock 1.12 but Turtle/Octo backports them.
-- pcall prevents a hard failure on builds that don't recognise them.
pcall(function() ef:RegisterEvent("QUEST_TURNED_IN") end)
pcall(function() ef:RegisterEvent("KEYRING_UPDATE") end)
@@ -610,9 +573,6 @@ ef:SetScript("OnEvent", function()
RA:BuildNameIndex()
RA:WarmItemCache()
RA:ScanQuestLog(); RA:ScanBags(); RA:RecomputeAll()
-- Retry pass: on 1.12 GetItemInfo populates async, and the
-- keyring is not always populated at PLAYER_LOGIN. Schedule two
-- delayed rescans so keys still get credited without user action.
RA._retryAt = { GetTime() + 3, GetTime() + 10 }
if RA.Comm and RA.Comm.Init then RA.Comm:Init() end
if RA.UI and RA.UI.Init then RA.UI:Init() end