Mercurial > wow > wowdb-profiler
comparison Main.lua @ 420:bd7a7162cc0f
Added new kill count system for raid encounters based on saved instances/LFRs.
author | MMOSimca <MMOSimca@gmail.com> |
---|---|
date | Wed, 07 Jan 2015 04:59:49 -0500 |
parents | df4820871122 |
children | b2cfa966277f |
comparison
equal
deleted
inserted
replaced
419:9c964e2d6971 | 420:bd7a7162cc0f |
---|---|
98 CHAT_MSG_MONSTER_YELL = "RecordQuote", | 98 CHAT_MSG_MONSTER_YELL = "RecordQuote", |
99 CHAT_MSG_SYSTEM = true, | 99 CHAT_MSG_SYSTEM = true, |
100 COMBAT_LOG_EVENT_UNFILTERED = true, | 100 COMBAT_LOG_EVENT_UNFILTERED = true, |
101 COMBAT_TEXT_UPDATE = true, | 101 COMBAT_TEXT_UPDATE = true, |
102 CURSOR_UPDATE = true, | 102 CURSOR_UPDATE = true, |
103 ENCOUNTER_END = true, | |
103 FORGE_MASTER_OPENED = true, | 104 FORGE_MASTER_OPENED = true, |
104 GARRISON_MISSION_BONUS_ROLL_COMPLETE = "HandleBadChatLootData", | 105 GARRISON_MISSION_BONUS_ROLL_COMPLETE = "HandleBadChatLootData", |
105 GARRISON_MISSION_COMPLETE_RESPONSE = "HandleBadChatLootData", | 106 GARRISON_MISSION_COMPLETE_RESPONSE = "HandleBadChatLootData", |
106 GOSSIP_SHOW = true, | 107 GOSSIP_SHOW = true, |
107 GROUP_ROSTER_UPDATE = true, | 108 GROUP_ROSTER_UPDATE = true, |
115 MERCHANT_CLOSED = true, | 116 MERCHANT_CLOSED = true, |
116 MERCHANT_SHOW = "UpdateMerchantItems", | 117 MERCHANT_SHOW = "UpdateMerchantItems", |
117 MERCHANT_UPDATE = "UpdateMerchantItems", | 118 MERCHANT_UPDATE = "UpdateMerchantItems", |
118 PET_BAR_UPDATE = true, | 119 PET_BAR_UPDATE = true, |
119 --PET_JOURNAL_LIST_UPDATE = true, | 120 --PET_JOURNAL_LIST_UPDATE = true, |
121 PLAYER_LOGOUT = true, | |
120 PLAYER_REGEN_DISABLED = true, | 122 PLAYER_REGEN_DISABLED = true, |
121 PLAYER_REGEN_ENABLED = true, | 123 PLAYER_REGEN_ENABLED = true, |
122 PLAYER_TARGET_CHANGED = true, | 124 PLAYER_TARGET_CHANGED = true, |
123 QUEST_COMPLETE = true, | 125 QUEST_COMPLETE = true, |
124 QUEST_DETAIL = true, | 126 QUEST_DETAIL = true, |
175 local chat_loot_data | 177 local chat_loot_data |
176 local chat_loot_timer_handle | 178 local chat_loot_timer_handle |
177 local current_target_id | 179 local current_target_id |
178 local current_area_id | 180 local current_area_id |
179 local current_loot | 181 local current_loot |
182 local saved_raid_encounter_data | |
183 local update_raid_encounter_timer_handle | |
184 local saved_difficulty_token | |
180 | 185 |
181 | 186 |
182 -- Data for our current action. Including possible values as a reference. | 187 -- Data for our current action. Including possible values as a reference. |
183 local current_action = { | 188 local current_action = { |
184 identifier = nil, | 189 identifier = nil, |
918 table.wipe(chat_loot_data) | 923 table.wipe(chat_loot_data) |
919 end | 924 end |
920 end | 925 end |
921 | 926 |
922 | 927 |
928 -- This wipes a timer as well | |
929 local UpdateRaidEncounterInfo | |
930 do | |
931 local fresh_raid_encounter_data = {} | |
932 | |
933 function UpdateRaidEncounterInfo() | |
934 -- Clear timer info | |
935 if update_raid_encounter_timer_handle then | |
936 update_raid_encounter_timer_handle:Cancel() | |
937 update_raid_encounter_timer_handle = nil | |
938 end | |
939 table.wipe(fresh_raid_encounter_data) | |
940 | |
941 -- Collect encounter data for LFR difficulty via RF functions | |
942 for i = 1, _G.GetNumRFDungeons() do | |
943 local dungeon_ID = _G.GetRFDungeonInfo(i) | |
944 fresh_raid_encounter_data[dungeon_ID] = fresh_raid_encounter_data[dungeon_ID] or {} | |
945 for j = 1, _G.GetLFGDungeonNumEncounters(dungeon_ID) do | |
946 local boss_name, _, is_killed = _G.GetLFGDungeonEncounterInfo(dungeon_ID, j) | |
947 fresh_raid_encounter_data[dungeon_ID][boss_name] = is_killed | |
948 end | |
949 end | |
950 | |
951 -- Collect encounter data for Normal/Heroic/Mythic difficulty via saved instance functions | |
952 for i = 1, _G.GetNumSavedInstances() do | |
953 local _, dungeon_ID, _, _, _, _, _, _, _, _, num_encounters = _G.GetSavedInstanceInfo(i) | |
954 fresh_raid_encounter_data[dungeon_ID] = fresh_raid_encounter_data[dungeon_ID] or {} | |
955 for j = 1, num_encounters do | |
956 local boss_name, _, is_killed = _G.GetSavedInstanceEncounterInfo(i, j) | |
957 fresh_raid_encounter_data[dungeon_ID][boss_name] = is_killed | |
958 end | |
959 end | |
960 | |
961 Debug("UpdateRaidEncounterInfo: Collected fresh raid encounter data.") | |
962 if saved_raid_encounter_data then | |
963 -- Compare old data vs new table to find changes | |
964 for dungeon_ID, sub_table in next, saved_raid_encounter_data do | |
965 for boss_name, is_killed in next, saved_raid_encounter_data[dungeon_ID] do | |
966 if private.RAID_ENCOUNTER_NAME_TO_NPC_ID_MAP[boss_name] and saved_raid_encounter_data[dungeon_ID][boss_name] == false and fresh_raid_encounter_data[dungeon_ID] and fresh_raid_encounter_data[dungeon_ID][boss_name] == true then | |
967 Debug("UpdateRaidEncounterInfo: Incrementing kill count for boss %s with ID %d.", boss_name, private.RAID_ENCOUNTER_NAME_TO_NPC_ID_MAP[boss_name]) | |
968 -- Increment kill count for NPC IDs with detected changes | |
969 local npc = NPCEntry(private.RAID_ENCOUNTER_NAME_TO_NPC_ID_MAP[boss_name]) | |
970 if npc then | |
971 local encounter_data = npc:EncounterData(saved_difficulty_token) | |
972 encounter_data["drops"] = encounter_data["drops"] or {} | |
973 encounter_data.loot_counts = encounter_data.loot_counts or {} | |
974 encounter_data.loot_counts["drops"] = (encounter_data.loot_counts["drops"] or 0) + 1 | |
975 end | |
976 end | |
977 end | |
978 end | |
979 end | |
980 | |
981 -- Assign new table over old one | |
982 saved_raid_encounter_data = fresh_raid_encounter_data | |
983 saved_difficulty_token = nil | |
984 end | |
985 end | |
986 | |
987 | |
923 -- METHODS ------------------------------------------------------------ | 988 -- METHODS ------------------------------------------------------------ |
924 | 989 |
925 function WDP:OnInitialize() | 990 function WDP:OnInitialize() |
926 local db = LibStub("AceDB-3.0"):New("WoWDBProfilerData", DATABASE_DEFAULTS, "Default") | 991 local db = LibStub("AceDB-3.0"):New("WoWDBProfilerData", DATABASE_DEFAULTS, "Default") |
927 private.db = db | 992 private.db = db |
987 end, 100000) | 1052 end, 100000) |
988 target_location_timer_handle = C_Timer.NewTicker(0.5, function() | 1053 target_location_timer_handle = C_Timer.NewTicker(0.5, function() |
989 target_location_timer_handle._remainingIterations = 100000 | 1054 target_location_timer_handle._remainingIterations = 100000 |
990 WDP:UpdateTargetLocation() | 1055 WDP:UpdateTargetLocation() |
991 end, 100000) | 1056 end, 100000) |
1057 | |
1058 if ALLOWED_LOCALES[CLIENT_LOCALE] then | |
1059 update_raid_encounter_timer_handle = C_Timer.NewTimer(10, UpdateRaidEncounterInfo) | |
1060 end | |
992 | 1061 |
993 _G.hooksecurefunc("UseContainerItem", function(bag_index, slot_index, target_unit) | 1062 _G.hooksecurefunc("UseContainerItem", function(bag_index, slot_index, target_unit) |
994 if target_unit then | 1063 if target_unit then |
995 return | 1064 return |
996 end | 1065 end |
1285 function WDP:HandleBadChatLootData(...) | 1354 function WDP:HandleBadChatLootData(...) |
1286 ClearChatLootData() | 1355 ClearChatLootData() |
1287 end | 1356 end |
1288 | 1357 |
1289 | 1358 |
1359 -- EVENT HANDLERS ----------------------------------------------------- | |
1360 | |
1361 function WDP:ENCOUNTER_END(event_name) | |
1362 local loot_method = _G.GetLootMethod() | |
1363 -- This will only work for english clients due to questionable API design choices | |
1364 -- Currently only testing this method of kill count recording for personal loot. | |
1365 -- Master looting has too many edge cases, such as chest objects and multiple NPCs with split loot. | |
1366 if loot_method ~= "personalloot" or not ALLOWED_LOCALES[CLIENT_LOCALE] then | |
1367 return | |
1368 end | |
1369 | |
1370 saved_difficulty_token = InstanceDifficultyToken() | |
1371 update_raid_encounter_timer_handle = C_Timer.NewTimer(30, UpdateRaidEncounterInfo) | |
1372 end | |
1373 | |
1374 | |
1375 function WDP:PLAYER_LOGOUT(event_name) | |
1376 if update_raid_encounter_timer_handle then | |
1377 UpdateRaidEncounterInfo() | |
1378 end | |
1379 end | |
1380 | |
1290 -- For now, bonus roll data only pollutes the true drop percentages. We still want to capture the data from SPELL_CONFIRMATION_PROMPT because of legendary quest items though. | 1381 -- For now, bonus roll data only pollutes the true drop percentages. We still want to capture the data from SPELL_CONFIRMATION_PROMPT because of legendary quest items though. |
1291 function WDP:BONUS_ROLL_RESULT(event_name) | 1382 function WDP:BONUS_ROLL_RESULT(event_name) |
1292 Debug("%s: Bonus roll detected; stopping loot recording for this boss to avoid recording bonus loot.", event_name) | 1383 Debug("%s: Bonus roll detected; stopping loot recording for this boss to avoid recording bonus loot.", event_name) |
1293 ClearKilledBossID() | 1384 ClearKilledBossID() |
1294 ClearLootToastContainerID() | 1385 ClearLootToastContainerID() |
1382 end | 1473 end |
1383 else | 1474 else |
1384 Debug("%s: Currency texture is nil, from currency link %s", event_name, item_link) | 1475 Debug("%s: Currency texture is nil, from currency link %s", event_name, item_link) |
1385 end | 1476 end |
1386 elseif raid_boss_id then | 1477 elseif raid_boss_id then |
1478 local loot_method = _G.GetLootMethod() | |
1387 -- Slightly messy hack to workaround duplicate world bosses | 1479 -- Slightly messy hack to workaround duplicate world bosses |
1388 local upper_limit = 0 | 1480 local upper_limit = 0 |
1389 if DUPLICATE_WORLD_BOSS_IDS[raid_boss_id] then | 1481 if DUPLICATE_WORLD_BOSS_IDS[raid_boss_id] then |
1390 upper_limit = #DUPLICATE_WORLD_BOSS_IDS[raid_boss_id] | 1482 upper_limit = #DUPLICATE_WORLD_BOSS_IDS[raid_boss_id] |
1391 end | 1483 end |
1426 return | 1518 return |
1427 end | 1519 end |
1428 end | 1520 end |
1429 | 1521 |
1430 if not boss_loot_toasting[temp_npc_id] then | 1522 if not boss_loot_toasting[temp_npc_id] then |
1431 encounter_data.loot_counts[loot_label] = (encounter_data.loot_counts[loot_label] or 0) + 1 | 1523 -- In some situations, we will increment kill count by watching what the player is saved to |
1524 if not update_raid_encounter_timer_handle or not private.RAID_ENCOUNTER_NPC_ID_LIST[temp_npc_id] or loot_method ~= "personalloot" then | |
1525 encounter_data.loot_counts[loot_label] = (encounter_data.loot_counts[loot_label] or 0) + 1 | |
1526 else | |
1527 Debug("%s: Skipping incrementing kill count for NPC ID %d.", event_name, temp_npc_id) | |
1528 end | |
1432 boss_loot_toasting[temp_npc_id] = true -- Do not count further loots until timer expires or another boss is killed | 1529 boss_loot_toasting[temp_npc_id] = true -- Do not count further loots until timer expires or another boss is killed |
1433 end | 1530 end |
1434 end | 1531 end |
1435 end | 1532 end |
1436 elseif loot_toast_container_id then | 1533 elseif loot_toast_container_id then |
2004 local LOOT_OPENED_UPDATE_FUNCS = { | 2101 local LOOT_OPENED_UPDATE_FUNCS = { |
2005 [AF.ITEM] = function() | 2102 [AF.ITEM] = function() |
2006 GenericLootUpdate("items") | 2103 GenericLootUpdate("items") |
2007 end, | 2104 end, |
2008 [AF.NPC] = function() | 2105 [AF.NPC] = function() |
2106 local loot_method = _G.GetLootMethod() | |
2009 local difficulty_token = InstanceDifficultyToken() | 2107 local difficulty_token = InstanceDifficultyToken() |
2010 local loot_label = current_loot.label | 2108 local loot_label = current_loot.label |
2011 local source_list = {} | 2109 local source_list = {} |
2012 | 2110 |
2013 for source_guid, loot_data in pairs(current_loot.sources) do | 2111 for source_guid, loot_data in pairs(current_loot.sources) do |
2018 local encounter_data = npc:EncounterData(difficulty_token) | 2116 local encounter_data = npc:EncounterData(difficulty_token) |
2019 encounter_data[loot_label] = encounter_data[loot_label] or {} | 2117 encounter_data[loot_label] = encounter_data[loot_label] or {} |
2020 | 2118 |
2021 if not source_list[source_guid] then | 2119 if not source_list[source_guid] then |
2022 encounter_data.loot_counts = encounter_data.loot_counts or {} | 2120 encounter_data.loot_counts = encounter_data.loot_counts or {} |
2023 encounter_data.loot_counts[loot_label] = (encounter_data.loot_counts[loot_label] or 0) + 1 | 2121 -- In some situations, we will increment kill count by watching what the player is saved to |
2122 if not update_raid_encounter_timer_handle or not private.RAID_ENCOUNTER_NPC_ID_LIST[source_id] or loot_method ~= "personalloot" then | |
2123 encounter_data.loot_counts[loot_label] = (encounter_data.loot_counts[loot_label] or 0) + 1 | |
2124 else | |
2125 | |
2126 end | |
2024 source_list[source_guid] = true | 2127 source_list[source_guid] = true |
2025 end | 2128 end |
2026 | 2129 |
2027 for loot_token, quantity in pairs(loot_data) do | 2130 for loot_token, quantity in pairs(loot_data) do |
2028 local loot_type, currency_texture = (":"):split(loot_token) | 2131 local loot_type, currency_texture = (":"):split(loot_token) |