comparison Gear.lua @ 149:cfdb5e5c828e v70

Tweak to azerite gear matching.
author yellowfive
date Wed, 02 Jan 2019 18:29:51 -0800
parents df1596b1a744
children bdf1b0c98882
comparison
equal deleted inserted replaced
148:72366681175d 149:cfdb5e5c828e
27 return 0 27 return 0
28 end 28 end
29 29
30 -- one nil and other not, or different id, totally different 30 -- one nil and other not, or different id, totally different
31 if (not item1 and item2) or (item1 and not item2) or item1.id ~= item2.id then 31 if (not item1 and item2) or (item1 and not item2) or item1.id ~= item2.id then
32 return 10000 32 return 100000
33 end 33 end
34 34
35 -- different versions of same item (id + bonus ids + suffix + drop level, constitutes a different physical drop) 35 -- different versions of same item (id + bonus ids + suffix + drop level, constitutes a different physical drop)
36 if Amr.GetItemUniqueId(item1, true, true) ~= Amr.GetItemUniqueId(item2, true, true) then 36 if Amr.GetItemUniqueId(item1, true, true) ~= Amr.GetItemUniqueId(item2, true, true) then
37 return 1000 37 return 10000
38 end 38 end
39 39
40 -- different upgrade levels of the same item 40 -- different upgrade levels of the same item
41 if item1.upgradeId ~= item2.upgradeId then 41 if item1.upgradeId ~= item2.upgradeId then
42 return 100 42 return 1000
43 end 43 end
44 44
45 -- different azerite powers 45 -- a change that requires reforging is considered more different than a change that does not;
46 local aztDiffs = 0 46 -- it is assumed that item1 is how we want the item to be in the end, and item2 is how it currently is
47 if item1.azerite or item2.azerite then 47 local aztReforges = 0
48 local aztSelects = 0
49
50 if item1.id == item2.id and (item1.azerite or item2.azerite) then
51 -- azerite that needs to be reforged
52 if item2.azerite and not item1.azerite then
53 -- kind of a dumb case... but we would need to blank all azerite on item2 to match item1
54 aztReforges = #item2.azerite * 100
55 elseif item2.azerite then
56 -- count up azerite on item2 but not on item1, these would need to be reforged
57 for i = 1, #item2.azerite do
58 local missing = true
59 for j = 1, #item1.azerite do
60 if item1.azerite[j] == item2.azerite[i] then
61 missing = false
62 end
63 end
64 if missing then
65 aztReforges = aztReforges + 100
66 end
67 end
68 end
69
70 -- azerite that needs to be selected
48 if item1.azerite and not item2.azerite then 71 if item1.azerite and not item2.azerite then
49 aztDiffs = #item1.azerite * 10 72 -- item2 is blank, so just need to choose all the right ones
50 elseif item2.azerite and not item1.azerite then 73 aztSelects = #item1.azerite * 10
51 aztDiffs = #item2.azerite * 10 74 elseif item1.azerite then
52 else 75 -- count up azerite on item1 but not on item2, these would need to be selected
53 -- count up number in item1 but missing from item2
54 for i = 1, #item1.azerite do 76 for i = 1, #item1.azerite do
55 local missing = true 77 local missing = true
56 for j = 1, #item2.azerite do 78 for j = 1, #item2.azerite do
57 if item2.azerite[j] == item1.azerite[i] then 79 if item2.azerite[j] == item1.azerite[i] then
58 missing = false 80 missing = false
59 end 81 end
60 end 82 end
61 if missing then 83 if missing then
62 aztDiffs = aztDiffs + 10 84 aztSelects = aztSelects + 10
63 end 85 end
64 end 86 end
65 -- count up number in item2 but missing from item1 87 end
66 for i = 1, #item2.azerite do
67 local missing = true
68 for j = 1, #item1.azerite do
69 if item1.azerite[j] == item2.azerite[i] then
70 missing = false
71 end
72 end
73 if missing then
74 aztDiffs = aztDiffs + 10
75 end
76 end
77 end
78 end 88 end
79 89
80 -- different gems 90 -- different gems
81 local gemDiffs = 0 91 local gemDiffs = 0
82 for i = 1, 3 do 92 for i = 1, 3 do
89 local enchantDiff = 0 99 local enchantDiff = 0
90 if item1.enchantId ~= item2.enchantId then 100 if item1.enchantId ~= item2.enchantId then
91 enchantDiff = 1 101 enchantDiff = 1
92 end 102 end
93 103
94 return aztDiffs + gemDiffs + enchantDiff 104 return aztReforges + aztSelects + gemDiffs + enchantDiff
95 end 105 end
96 106
97 -- given a table of items (keyed or indexed doesn't matter) find closest match to item, or nil if none are a match 107 -- given a table of items (keyed or indexed doesn't matter) find closest match to item, or nil if none are a match
98 local function findMatchingItemFromTable(item, list, bestItem, bestDiff, bestLoc, usedItems, tableType) 108 local function findMatchingItemFromTable(item, list, bestItem, bestDiff, bestLoc, usedItems, tableType)
99 if not list then return nil end 109 if not list then return nil end
128 bestItem, bestDiff, bestLoc = findMatchingItemFromTable(item, player.BagItems, bestItem, bestDiff, bestLoc, usedItems, "bag") 138 bestItem, bestDiff, bestLoc = findMatchingItemFromTable(item, player.BagItems, bestItem, bestDiff, bestLoc, usedItems, "bag")
129 if player.BankItems then 139 if player.BankItems then
130 bestItem, bestDiff, bestLoc = findMatchingItemFromTable(item, player.BankItems, bestItem, bestDiff, bestLoc, usedItems, "bank") 140 bestItem, bestDiff, bestLoc = findMatchingItemFromTable(item, player.BankItems, bestItem, bestDiff, bestLoc, usedItems, "bank")
131 end 141 end
132 142
133 if bestDiff >= 10000 then 143 if bestDiff >= 100000 then
134 return nil, 10000 144 return nil, 100000
135 else 145 else
136 usedItems[bestLoc] = true 146 usedItems[bestLoc] = true
137 return bestItem, bestDiff 147 return bestItem, bestDiff
138 end 148 end
139 end 149 end
289 local isEquipped = false 299 local isEquipped = false
290 if equippedItem and optimalItem and Amr.GetItemUniqueId(equippedItem, false, true) == Amr.GetItemUniqueId(optimalItem, false, true) then 300 if equippedItem and optimalItem and Amr.GetItemUniqueId(equippedItem, false, true) == Amr.GetItemUniqueId(optimalItem, false, true) then
291 301
292 if slotId == 1 or slotId == 3 or slotId == 5 then 302 if slotId == 1 or slotId == 3 or slotId == 5 then
293 -- show the item as not equipped if azerite doesn't match... might mean they have to switch to another version of same item 303 -- show the item as not equipped if azerite doesn't match... might mean they have to switch to another version of same item
294 local aztDiff = countItemDifferences(equippedItem, optimalItem) 304 local aztDiff = countItemDifferences(optimalItem, equippedItem)
295 if aztDiff == 0 then 305 if aztDiff == 0 then
296 isEquipped = true 306 isEquipped = true
297 end 307 end
298 else 308 else
299 isEquipped = true 309 isEquipped = true
612 end 622 end
613 623
614 -- scan a bag for the best matching item 624 -- scan a bag for the best matching item
615 local function scanBagForItem(item, bagId, bestItem, bestDiff, bestLink) 625 local function scanBagForItem(item, bagId, bestItem, bestDiff, bestLink)
616 local numSlots = GetContainerNumSlots(bagId) 626 local numSlots = GetContainerNumSlots(bagId)
627 local loc = ItemLocation.CreateEmpty()
617 for slotId = 1, numSlots do 628 for slotId = 1, numSlots do
618 local _, _, _, _, _, _, itemLink = GetContainerItemInfo(bagId, slotId) 629 local _, _, _, _, _, _, itemLink = GetContainerItemInfo(bagId, slotId)
619 -- we skip any stackable item, as far as we know, there is no equippable gear that can be stacked 630 -- we skip any stackable item, as far as we know, there is no equippable gear that can be stacked
620 if itemLink then 631 if itemLink then
621 local bagItem = Amr.ParseItemLink(itemLink) 632 local bagItem = Amr.ParseItemLink(itemLink)
622 if bagItem ~= nil then 633 if bagItem ~= nil then
634 -- see if this is an azerite item and read azerite power ids
635 loc:SetBagAndSlot(bagId, slotId)
636 if C_AzeriteEmpoweredItem.IsAzeriteEmpoweredItem(loc) then
637 local powers = Amr.ReadAzeritePowers(loc)
638 if powers then
639 bagItem.azerite = powers
640 end
641 end
642
623 local diff = countItemDifferences(item, bagItem) 643 local diff = countItemDifferences(item, bagItem)
624 if diff < bestDiff then 644 if diff < bestDiff then
625 bestItem = { bag = bagId, slot = slotId } 645 bestItem = { bag = bagId, slot = slotId }
626 bestDiff = diff 646 bestDiff = diff
627 bestLink = itemLink 647 bestLink = itemLink
1056 1076
1057 -- find the best matching item anywhere in the player's gear 1077 -- find the best matching item anywhere in the player's gear
1058 local bestItem, bestDiff = Amr:FindMatchingItem(new, player, usedItems) 1078 local bestItem, bestDiff = Amr:FindMatchingItem(new, player, usedItems)
1059 new = bestItem 1079 new = bestItem
1060 1080
1061 local diff = countItemDifferences(old, new) 1081 local diff = countItemDifferences(new, old)
1062 1082
1063 if diff > 0 then 1083 if diff > 0 then
1064 list[slotId] = new 1084 list[slotId] = new
1065 if list == itemsToEquip.mh or list == itemsToEquip.oh then 1085 if list == itemsToEquip.mh or list == itemsToEquip.oh then
1066 itemsToEquip.weapons[slotId] = {} 1086 itemsToEquip.weapons[slotId] = {}