From 3895f23349d1c7096fcde6faff7b753ec49241e4 Mon Sep 17 00:00:00 2001 From: Rasmus Kromann-Larsen Date: Wed, 9 Sep 2026 13:14:22 +0200 Subject: [PATCH 1/2] Iterate flasks and charms in slot order env.flasks and env.charms are keyed by item table, so pairs() walks them in memory-address order, which differs between processes. That order reaches the modDB and, for charms, the limit loop stops early, so it also decided which charms applied. CalcSetup now records each slotted item's slot number in env.itemSlotIndex, and mergeFlasks/mergeCharms iterate in that order with item.id as the tiebreak. --- src/Modules/CalcPerform.lua | 26 ++++++++++++++++++++++++++ src/Modules/CalcSetup.lua | 4 ++++ 2 files changed, 30 insertions(+) diff --git a/src/Modules/CalcPerform.lua b/src/Modules/CalcPerform.lua index eb0b3e18dc..b2f044f345 100644 --- a/src/Modules/CalcPerform.lua +++ b/src/Modules/CalcPerform.lua @@ -1707,7 +1707,20 @@ function calcs.perform(env, skipEHP) local flaskBuffsNonPlayer = {} local flaskBuffsPerBaseNonPlayer = {} + local slotIndex = env.itemSlotIndex or { } + local orderedFlasks = { } for item in pairs(flasks) do + t_insert(orderedFlasks, item) + end + table.sort(orderedFlasks, function(a, b) + local posA = slotIndex[a] or 0 + local posB = slotIndex[b] or 0 + if posA ~= posB then + return posA < posB + end + return (a.id or 0) < (b.id or 0) + end) + for _, item in ipairs(orderedFlasks) do flaskBuffsPerBase[item.baseName] = flaskBuffsPerBase[item.baseName] or {} flaskBuffsPerBaseNonPlayer[item.baseName] = flaskBuffsPerBaseNonPlayer[item.baseName] or {} flaskConditions["UsingFlask"] = true @@ -1810,7 +1823,20 @@ function calcs.perform(env, skipEHP) local charmConditions = {} local charmBuffsPerBase = {} + local slotIndex = env.itemSlotIndex or { } + local orderedCharms = { } for item in pairs(charms) do + t_insert(orderedCharms, item) + end + table.sort(orderedCharms, function(a, b) + local posA = slotIndex[a] or 0 + local posB = slotIndex[b] or 0 + if posA ~= posB then + return posA < posB + end + return (a.id or 0) < (b.id or 0) + end) + for _, item in ipairs(orderedCharms) do if charmLimit <= 0 then break end diff --git a/src/Modules/CalcSetup.lua b/src/Modules/CalcSetup.lua index 2922ef02f6..c06cac0a45 100644 --- a/src/Modules/CalcSetup.lua +++ b/src/Modules/CalcSetup.lua @@ -1267,10 +1267,14 @@ function calcs.initEnv(build, mode, override, specEnv) end end + env.itemSlotIndex = { } for _, slot in pairs(build.itemsTab.orderedSlots) do local slotName = slot.slotName local item = items[slotName] local node = slot.nodeId and env.spec.nodes[slot.nodeId] + if item then + env.itemSlotIndex[item] = tonumber(slotName:match("%d+")) or 0 + end if item and item.type == "Flask" then if slot.active then env.flasks[item] = true From f28a33bc3d188ca50afacb6d8004137741c67930 Mon Sep 17 00:00:00 2001 From: LocalIdentity Date: Thu, 10 Sep 2026 12:25:12 +1000 Subject: [PATCH 2/2] Fix duplicate charms changing slot order --- src/Modules/CalcSetup.lua | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/src/Modules/CalcSetup.lua b/src/Modules/CalcSetup.lua index c06cac0a45..164e2d71ff 100644 --- a/src/Modules/CalcSetup.lua +++ b/src/Modules/CalcSetup.lua @@ -1273,7 +1273,13 @@ function calcs.initEnv(build, mode, override, specEnv) local item = items[slotName] local node = slot.nodeId and env.spec.nodes[slot.nodeId] if item then - env.itemSlotIndex[item] = tonumber(slotName:match("%d+")) or 0 + local slotIndex = tonumber(slotName:match("%d+")) or 0 + -- Repeated flasks/charms keep their earliest active slot. + if not (env.flasks[item] or env.charms[item]) then + env.itemSlotIndex[item] = slotIndex + elseif slot.active then + env.itemSlotIndex[item] = m_min(env.itemSlotIndex[item], slotIndex) + end end if item and item.type == "Flask" then if slot.active then