From 9d16048c8dda0cd0f1d977f2f5d5cfdc0a669aae Mon Sep 17 00:00:00 2001 From: GreenComfyTea Date: Fri, 11 Aug 2023 16:10:19 +0300 Subject: [PATCH] Move logic out from REF D2D loop callback --- reframework/autorun/MHR_Overlay.lua | 129 +++++- .../autorun/MHR_Overlay/Buffs/buffs.lua | 3 +- .../MHR_Overlay/Monsters/large_monster.lua | 11 +- .../MHR_Overlay/UI/Modules/buff_UI.lua | 68 +-- .../UI/Modules/env_creature_UI.lua | 49 ++- .../UI/Modules/large_monster_UI.lua | 396 +++++++++++------- .../UI/Modules/small_monster_UI.lua | 82 ++-- 7 files changed, 461 insertions(+), 277 deletions(-) diff --git a/reframework/autorun/MHR_Overlay.lua b/reframework/autorun/MHR_Overlay.lua index 1c41ed2..f1e6eef 100644 --- a/reframework/autorun/MHR_Overlay.lua +++ b/reframework/autorun/MHR_Overlay.lua @@ -249,11 +249,47 @@ log.info("[MHR Overlay] Loaded."); ----------------------------LOOP----------------------------- -- #region +local function update_modules(module_visibility_config, flow_state_name) + if module_visibility_config.small_monster_UI and config.current_config.small_monster_UI.enabled then + local success = pcall(small_monster_UI.update); + if not success then + error_handler.report("MHR_Overlay.update_modules", string.format("[%s] Small Monster UI Update Function threw an Exception", flow_state_name)); + end + end + + local large_monster_UI_config = config.current_config.large_monster_UI; + + local dynamic_enabled = large_monster_UI_config.dynamic.enabled and module_visibility_config.large_monster_dynamic_UI; + local static_enabled = large_monster_UI_config.static.enabled and module_visibility_config.large_monster_static_UI; + local highlighted_enabled = large_monster_UI_config.highlighted.enabled and module_visibility_config.large_monster_highlighted_UI; + + if dynamic_enabled or static_enabled or highlighted_enabled then + local success = pcall(large_monster_UI.update, dynamic_enabled, static_enabled, highlighted_enabled); + if not success then + error_handler.report("MHR_Overlay.update_modules", string.format("[%s] Large Monster UI Update Function threw an Exception", flow_state_name)); + end + end + + if config.current_config.endemic_life_UI.enabled and module_visibility_config.endemic_life_UI then + local success = pcall(env_creature_UI.update); + if not success then + error_handler.report("MHR_Overlay.update_modules", string.format("[%s] Endemic Life UI Update Function threw an Exception", flow_state_name)); + end + end + + if config.current_config.buff_UI.enabled and module_visibility_config.buff_UI then + local success = pcall(buff_UI.update); + if not success then + error_handler.report("MHR_Overlay.update_modules", string.format("[%s] Buff UI Update Function threw an Exception", flow_state_name)); + end + end +end + local function draw_modules(module_visibility_config, flow_state_name) if module_visibility_config.small_monster_UI and config.current_config.small_monster_UI.enabled then local success = pcall(small_monster_UI.draw); if not success then - error_handler.report("MHR_Overlay.draw_modules", string.format("[%s] Small Monster UI Drawing Function threw an Exception", flow_state_name)); + error_handler.report("MHR_Overlay.draw_modules", string.format("[%s] Small Monster UI Draw Function threw an Exception", flow_state_name)); end end @@ -266,42 +302,94 @@ local function draw_modules(module_visibility_config, flow_state_name) if dynamic_enabled or static_enabled or highlighted_enabled then local success = pcall(large_monster_UI.draw, dynamic_enabled, static_enabled, highlighted_enabled); if not success then - error_handler.report("MHR_Overlay.draw_modules", string.format("[%s] Large Monster UI Drawing Function threw an Exception", flow_state_name)); + error_handler.report("MHR_Overlay.draw_modules", string.format("[%s] Large Monster UI Draw Function threw an Exception", flow_state_name)); end end if config.current_config.time_UI.enabled and module_visibility_config.time_UI then local success = pcall(time_UI.draw); if not success then - error_handler.report("MHR_Overlay.draw_modules", string.format("[%s] Time UI Drawing Function threw an Exception", flow_state_name)); + error_handler.report("MHR_Overlay.draw_modules", string.format("[%s] Time UI Draw Function threw an Exception", flow_state_name)); end end if config.current_config.damage_meter_UI.enabled and module_visibility_config.damage_meter_UI then local success = pcall(damage_meter_UI.draw); if not success then - error_handler.report("MHR_Overlay.draw_modules", string.format("[%s] Damage Meter UI Drawing Function threw an Exception", flow_state_name)); + error_handler.report("MHR_Overlay.draw_modules", string.format("[%s] Damage Meter UI Draw Function threw an Exception", flow_state_name)); end end if config.current_config.endemic_life_UI.enabled and module_visibility_config.endemic_life_UI then local success = pcall(env_creature_UI.draw); if not success then - error_handler.report("MHR_Overlay.draw_modules", string.format("[%s] Endemic Life UI Drawing Function threw an Exception", flow_state_name)); + error_handler.report("MHR_Overlay.draw_modules", string.format("[%s] Endemic Life UI Draw Function threw an Exception", flow_state_name)); end end if config.current_config.buff_UI.enabled and module_visibility_config.buff_UI then local success = pcall(buff_UI.draw); if not success then - error_handler.report("MHR_Overlay.draw_modules", string.format("[%s] Buff UI Drawing Function threw an Exception", flow_state_name)); + error_handler.report("MHR_Overlay.draw_modules", string.format("[%s] Buff UI Draw Function threw an Exception", flow_state_name)); end end end -local function main_loop() - time.update_timers(); +local function update_UI() + if quest_status.flow_state == quest_status.flow_states.IN_TRAINING_AREA then + local large_monster_UI_config = config.current_config.large_monster_UI; + local module_visibility_config = config.current_config.global_settings.module_visibility.in_training_area; + + local dynamic_enabled = large_monster_UI_config.dynamic.enabled and module_visibility_config.large_monster_dynamic_UI; + local static_enabled = large_monster_UI_config.static.enabled and module_visibility_config.large_monster_static_UI; + local highlighted_enabled = large_monster_UI_config.highlighted.enabled and module_visibility_config.large_monster_highlighted_UI; + + if dynamic_enabled or static_enabled or highlighted_enabled then + local success = pcall(large_monster_UI.update, dynamic_enabled, static_enabled, highlighted_enabled); + if not success then + error_handler.report("MHR_Overlay.update_loop", "[In Training Area] Large Monster UI Update Function threw an Exception"); + end + end + + if config.current_config.endemic_life_UI.enabled and module_visibility_config.endemic_life_UI then + local success = pcall(env_creature_UI.update); + if not success then + error_handler.report("MHR_Overlay.update_loop", "[In Training Area] Endemic Life UI Update Function threw an Exception"); + end + end + + if config.current_config.buff_UI.enabled and module_visibility_config.buff_UI then + local success = pcall(buff_UI.update); + if not success then + error_handler.report("MHR_Overlay.update_loop", "[In Training Area] Buff UI Update Function threw an Exception"); + end + end + + elseif quest_status.flow_state == quest_status.flow_states.CUTSCENE then + update_modules(config.current_config.global_settings.module_visibility.cutscene, "Cutscene"); + elseif quest_status.flow_state == quest_status.flow_states.LOADING_QUEST then + update_modules(config.current_config.global_settings.module_visibility.loading_quest, "Loading Quest"); + elseif quest_status.flow_state == quest_status.flow_states.QUEST_START_ANIMATION then + update_modules(config.current_config.global_settings.module_visibility.quest_start_animation, "Quest Start Animation"); + elseif quest_status.flow_state >= quest_status.flow_states.PLAYING_QUEST and quest_status.flow_state <= quest_status.flow_states.WYVERN_RIDING_START_ANIMATION then + update_modules(config.current_config.global_settings.module_visibility.playing_quest, "Playing Quest"); + elseif quest_status.flow_state == quest_status.flow_states.KILLCAM then + update_modules(config.current_config.global_settings.module_visibility.killcam, "Killcam"); + elseif quest_status.flow_state == quest_status.flow_states.QUEST_END_TIMER then + update_modules(config.current_config.global_settings.module_visibility.quest_end_timer, "Quest End Timer"); + elseif quest_status.flow_state == quest_status.flow_states.QUEST_END_ANIMATION then + update_modules(config.current_config.global_settings.module_visibility.quest_end_animation, "Quest End Animation"); + elseif quest_status.flow_state == quest_status.flow_states.QUEST_END_SCREEN then + update_modules(config.current_config.global_settings.module_visibility.quest_end_screen, "Quest End Screen"); + elseif quest_status.flow_state == quest_status.flow_states.REWARD_SCREEN then + update_modules(config.current_config.global_settings.module_visibility.reward_screen, "Reward Screen"); + elseif quest_status.flow_state == quest_status.flow_states.SUMMARY_SCREEN then + update_modules(config.current_config.global_settings.module_visibility.summary_screen, "Summary Screen"); + end +end + +local function draw_loop() if quest_status.flow_state == quest_status.flow_states.IN_TRAINING_AREA then local large_monster_UI_config = config.current_config.large_monster_UI; @@ -314,28 +402,28 @@ local function main_loop() if dynamic_enabled or static_enabled or highlighted_enabled then local success = pcall(large_monster_UI.draw, dynamic_enabled, static_enabled, highlighted_enabled); if not success then - error_handler.report("MHR_Overlay.main_loop", "[In Training Area] Large Monster UI Drawing Function threw an Exception"); + error_handler.report("MHR_Overlay.main_loop", "[In Training Area] Large Monster UI Draw Function threw an Exception"); end end if config.current_config.damage_meter_UI.enabled and module_visibility_config.damage_meter_UI then local success = pcall(damage_meter_UI.draw); if not success then - error_handler.report("MHR_Overlay.main_loop", "[In Training Area] Damage Meter UI Drawing Function threw an Exception"); + error_handler.report("MHR_Overlay.main_loop", "[In Training Area] Damage Meter UI Draw Function threw an Exception"); end end if config.current_config.endemic_life_UI.enabled and module_visibility_config.endemic_life_UI then local success = pcall(env_creature_UI.draw); if not success then - error_handler.report("MHR_Overlay.main_loop", "[In Training Area] Endemic Life UI Drawing Function threw an Exception"); + error_handler.report("MHR_Overlay.main_loop", "[In Training Area] Endemic Life UI Draw Function threw an Exception"); end end if config.current_config.buff_UI.enabled and module_visibility_config.buff_UI then local success = pcall(buff_UI.draw); if not success then - error_handler.report("MHR_Overlay.main_loop", "[In Training Area] Buff UI Drawing Function threw an Exception"); + error_handler.report("MHR_Overlay.main_loop", "[In Training Area] Buff UI Draw Function threw an Exception"); end end @@ -380,32 +468,35 @@ re.on_frame(function() if reframework:is_drawing_ui() then pcall(customization_menu.draw); end - - keyboard.update(); end); -- #endregion --------------------------RE_IMGUI--------------------------- -----------------------------D2D------------------------------ +-----------------------Loop Callbacks------------------------ -- #region if d2d ~= nil then d2d.register(function() drawing.init_font(); end, function() if config.current_config.global_settings.renderer.use_d2d_if_available then - main_loop(); + draw_loop(); end end); end re.on_frame(function() + time.update_timers(); + keyboard.update(); + if d2d == nil or not config.current_config.global_settings.renderer.use_d2d_if_available then - main_loop(); + draw_loop(); end end); -- #endregion -----------------------------D2D------------------------------ +-----------------------Loop Callbacks------------------------ if imgui.begin_table == nil then re.msg(language.current_language.customization_menu.reframework_outdated); -end \ No newline at end of file +end + +time.new_timer(update_UI, 0.5); \ No newline at end of file diff --git a/reframework/autorun/MHR_Overlay/Buffs/buffs.lua b/reframework/autorun/MHR_Overlay/Buffs/buffs.lua index 8879735..32b47ce 100644 --- a/reframework/autorun/MHR_Overlay/Buffs/buffs.lua +++ b/reframework/autorun/MHR_Overlay/Buffs/buffs.lua @@ -151,7 +151,7 @@ function this.update() return; end - abnormal_statuses.update(master_player); + local master_player_data = get_player_data_method:call(master_player); if master_player_data ~= nil then @@ -159,6 +159,7 @@ function this.update() endemic_life_buffs.update(master_player_data); skills.update(master_player, master_player_data); dangos.update(master_player_data); + abnormal_statuses.update(master_player, master_player_data); else error_handler.report("buffs.update", "Failed to access Data: master_player_data"); end diff --git a/reframework/autorun/MHR_Overlay/Monsters/large_monster.lua b/reframework/autorun/MHR_Overlay/Monsters/large_monster.lua index 1dc6b1e..382347b 100644 --- a/reframework/autorun/MHR_Overlay/Monsters/large_monster.lua +++ b/reframework/autorun/MHR_Overlay/Monsters/large_monster.lua @@ -1171,15 +1171,7 @@ function this.update_highlighted_id() end function this.draw(monster, type, cached_config, position_on_screen, opacity_scale) - local monster_UI; - - if type == "dynamic" then - monster_UI = monster.dynamic_UI; - elseif type == "static" then - monster_UI = monster.static_UI; - else - monster_UI = monster.highlighted_UI; - end + local monster_UI = monster[type]; local global_scale_modifier = config.current_config.global_settings.modifiers.global_scale_modifier; @@ -1307,7 +1299,6 @@ function this.init_dependencies() end function this.init_module() - time.new_timer(this.update_highlighted_id, 1/30); end return this; \ No newline at end of file diff --git a/reframework/autorun/MHR_Overlay/UI/Modules/buff_UI.lua b/reframework/autorun/MHR_Overlay/UI/Modules/buff_UI.lua index 2055cc1..9db541d 100644 --- a/reframework/autorun/MHR_Overlay/UI/Modules/buff_UI.lua +++ b/reframework/autorun/MHR_Overlay/UI/Modules/buff_UI.lua @@ -45,11 +45,12 @@ local os = os; local ValueType = ValueType; local package = package; -function this.draw() - local cached_config = config.current_config.buff_UI; - local global_scale_modifier = config.current_config.global_settings.modifiers.global_scale_modifier; +local displayed_buffs = {}; - local displayed_buffs = {}; +function this.update() + local cached_config = config.current_config.buff_UI; + + local _displayed_buffs = {}; for key, consumable in pairs(consumables.list) do @@ -57,7 +58,7 @@ function this.draw() goto continue; end - table.insert(displayed_buffs, consumable); + table.insert(_displayed_buffs, consumable); ::continue:: end @@ -68,7 +69,7 @@ function this.draw() goto continue2; end - table.insert(displayed_buffs, melody_effect); + table.insert(_displayed_buffs, melody_effect); ::continue2:: end @@ -78,7 +79,7 @@ function this.draw() goto continue3; end - table.insert(displayed_buffs, endemic_life_buff); + table.insert(_displayed_buffs, endemic_life_buff); ::continue3:: end @@ -88,7 +89,7 @@ function this.draw() goto continue4; end - table.insert(displayed_buffs, skill); + table.insert(_displayed_buffs, skill); ::continue4:: end @@ -98,64 +99,71 @@ function this.draw() goto continue5; end - table.insert(displayed_buffs, dango_buff); + table.insert(_displayed_buffs, dango_buff); ::continue5:: end for key, abnormal_status in pairs(abnormal_statuses.list) do if not abnormal_status.is_active then - goto continue5; + goto continue6; end - table.insert(displayed_buffs, abnormal_status); + table.insert(_displayed_buffs, abnormal_status); - ::continue5:: + ::continue6:: end + displayed_buffs = this.sort_buffs(_displayed_buffs, cached_config); +end - -- sort - if cached_config.sorting.type == "Name" then - if cached_config.sorting.reversed_order then - table.sort(displayed_buffs, function(left, right) +function this.sort_buffs(_displayed_buffs, cached_config) + cached_config = cached_config.sorting; + + if cached_config.type == "Name" then + if cached_config.reversed_order then + table.sort(_displayed_buffs, function(left, right) return left.name > right.name; end); else - table.sort(displayed_buffs, function(left, right) + table.sort(_displayed_buffs, function(left, right) return left.name < right.name; end); end - elseif cached_config.sorting.type == "Timer" then - if cached_config.sorting.reversed_order then - table.sort(displayed_buffs, function(left, right) + elseif cached_config.type == "Timer" then + if cached_config.reversed_order then + table.sort(_displayed_buffs, function(left, right) return left.timer > right.timer; end); else - table.sort(displayed_buffs, function(left, right) + table.sort(_displayed_buffs, function(left, right) return left.timer < right.timer; end); end else - if cached_config.sorting.reversed_order then - table.sort(displayed_buffs, function(left, right) + if cached_config.reversed_order then + table.sort(_displayed_buffs, function(left, right) return left.duration > right.duration; end); else - table.sort(displayed_buffs, function(left, right) + table.sort(_displayed_buffs, function(left, right) return left.duration < right.duration; end); end end + return _displayed_buffs; +end + +function this.draw() + local cached_config = config.current_config.buff_UI; + + local global_scale_modifier = config.current_config.global_settings.modifiers.global_scale_modifier; + local position_on_screen = screen.calculate_absolute_coordinates(cached_config.position); -- draw for _, buff in ipairs(displayed_buffs) do - - if not buff.is_active then - goto continue3; - end - buffs.draw(buff, buff.buff_UI, position_on_screen, 1); if cached_config.settings.orientation == "Horizontal" then @@ -164,7 +172,7 @@ function this.draw() position_on_screen.y = position_on_screen.y + cached_config.spacing.y * global_scale_modifier; end - ::continue3:: + ::continue:: end end diff --git a/reframework/autorun/MHR_Overlay/UI/Modules/env_creature_UI.lua b/reframework/autorun/MHR_Overlay/UI/Modules/env_creature_UI.lua index 5cd33fc..e61e4a6 100644 --- a/reframework/autorun/MHR_Overlay/UI/Modules/env_creature_UI.lua +++ b/reframework/autorun/MHR_Overlay/UI/Modules/env_creature_UI.lua @@ -45,29 +45,45 @@ local os = os; local ValueType = ValueType; local package = package; -function this.draw() - if singletons.enemy_manager == nil then +local displayed_creatures = {}; + +function this.update() + local cached_config = config.current_config.endemic_life_UI; + + local _displayed_creatures = {}; + + if cached_config.settings.max_distance == 0 then + displayed_creatures = {}; return; end - local cached_config = config.current_config.endemic_life_UI; - local global_scale_modifier = config.current_config.global_settings.modifiers.global_scale_modifier; - for REcreature, creature in pairs(env_creature.list) do - if cached_config.settings.max_distance == 0 then - break; - end - if cached_config.settings.hide_inactive_creatures and creature.is_inactive then goto continue; end - local position_on_screen = {}; + creature.distance = (players.myself_position - creature.position):length(); + if creature.distance > cached_config.settings.max_distance then + goto continue; + end - local world_offset = Vector3f.new(cached_config.world_offset.x, cached_config.world_offset.y, - cached_config.world_offset.z); + table.insert(_displayed_creatures, creature); + ::continue:: + end +end - position_on_screen = draw.world_to_screen(creature.position + world_offset); +function this.draw() + local cached_config = config.current_config.endemic_life_UI; + local global_scale_modifier = config.current_config.global_settings.modifiers.global_scale_modifier; + + for i, creature in ipairs(displayed_creatures) do + local world_offset = Vector3f.new( + cached_config.world_offset.x, + cached_config.world_offset.y, + cached_config.world_offset.z + ); + + local position_on_screen = draw.world_to_screen(creature.position + world_offset); if position_on_screen == nil then goto continue; @@ -76,14 +92,9 @@ function this.draw() position_on_screen.x = position_on_screen.x + cached_config.viewport_offset.x * global_scale_modifier; position_on_screen.y = position_on_screen.y + cached_config.viewport_offset.y * global_scale_modifier; - creature.distance = (players.myself_position - creature.position):length(); - local opacity_scale = 1; - if creature.distance > cached_config.settings.max_distance then - goto continue; - end - if cached_config.settings.opacity_falloff then + creature.distance = (players.myself_position - creature.position):length(); opacity_scale = 1 - (creature.distance / cached_config.settings.max_distance); end diff --git a/reframework/autorun/MHR_Overlay/UI/Modules/large_monster_UI.lua b/reframework/autorun/MHR_Overlay/UI/Modules/large_monster_UI.lua index b23650b..ae82f5e 100644 --- a/reframework/autorun/MHR_Overlay/UI/Modules/large_monster_UI.lua +++ b/reframework/autorun/MHR_Overlay/UI/Modules/large_monster_UI.lua @@ -54,148 +54,287 @@ local get_tg_camera_method = gui_manager_type_def:get_method("get_refGuiHud_TgCa local tg_camera_type_def = get_tg_camera_method:get_return_type(); local get_targeting_enemy_index_field = tg_camera_type_def:get_field("OldTargetingEmIndex"); -function this.draw(dynamic_enabled, static_enabled, highlighted_enabled) +local displayed_dynamic_monsters = {}; +local displayed_static_monsters = {}; +local highlighted_monster = nil; + +function this.update(dynamic_enabled, static_enabled, highlighted_enabled) local cached_config = config.current_config.large_monster_UI; if singletons.enemy_manager == nil then + error_handler.report("large_monster_UI.update", "Failed to access Data: enemy_manager"); return; end - local displayed_monsters = {}; - - local update_distance = - dynamic_enabled or cached_config.static.sorting.type == "Distance" - or (cached_config.highlighted.auto_highlight.enabled - and (cached_config.highlighted.auto_highlight.mode == "Closest" or cached_config.highlighted.auto_highlight.mode == "Furthest") - ); - - local monster_id_shift = 0; - local highlighted_monster = nil; + local large_monster_list = {}; local enemy_count = get_boss_enemy_count_method:call(singletons.enemy_manager); if enemy_count == nil then - error_handler.report("large_monster_UI.draw", "Failed to access Data: enemy_count"); + error_handler.report("large_monster_UI.update", "Failed to access Data: enemy_count"); return; end + for i = 0, enemy_count - 1 do local enemy = get_boss_enemy_method:call(singletons.enemy_manager, i); if enemy == nil then - error_handler.report("large_monster_UI.draw", "Failed to access Data: enemy No. " .. tostring(i)); + error_handler.report("large_monster_UI.update", "Failed to access Data: enemy No. " .. tostring(i)); goto continue; end local monster = large_monster.get_monster(enemy); if monster == nil then - error_handler.report("large_monster_UI.draw", "Failed to create Large Monster Entry No. " .. tostring(i)); + error_handler.report("large_monster_UI.update", "Failed to create Large Monster Entry No. " .. tostring(i)); goto continue; end - if update_distance then - monster.distance = (players.myself_position - monster.position):length(); - end + monster.distance = (players.myself_position - monster.position):length(); - if cached_config.highlighted.auto_highlight.enabled then - if highlighted_monster == nil then - highlighted_monster = monster; + table.insert(large_monster_list, monster); - elseif cached_config.highlighted.auto_highlight.mode == "Farthest" then - if monster.distance > highlighted_monster.distance then - highlighted_monster = monster; - end - - elseif cached_config.highlighted.auto_highlight.mode == "Lowest Health" then - if monster.health < highlighted_monster.health then - highlighted_monster = monster; - end - - elseif cached_config.highlighted.auto_highlight.mode == "Highest Health" then - if monster.health > highlighted_monster.health then - highlighted_monster = monster; - end - - elseif cached_config.highlighted.auto_highlight.mode == "Lowest Health Percentage" then - if monster.health_percentage < highlighted_monster.health_percentage then - highlighted_monster = monster; - end - - elseif cached_config.highlighted.auto_highlight.mode == "Highest Health Percentage" then - if monster.health_percentage > highlighted_monster.health_percentage then - highlighted_monster = monster; - end - - else - if monster.distance < highlighted_monster.distance then - highlighted_monster = monster; - end - end - else - if monster.dead_or_captured or not monster.is_disp_icon_mini_map then - monster_id_shift = monster_id_shift + 1; - - elseif i == large_monster.highlighted_id + monster_id_shift then - highlighted_monster = monster; - end - end - table.insert(displayed_monsters, monster); ::continue:: end - if dynamic_enabled then - local success = pcall(this.draw_dynamic, displayed_monsters, highlighted_monster, cached_config); - if not success then - error_handler.report("large_monster_UI.draw", "Dynamic Large Monster drawing function threw an exception"); - end - end + this.update_highlighted_monster(large_monster_list, cached_config.highlighted.auto_highlight); - if highlighted_enabled then - local success = pcall(this.draw_highlighted, highlighted_monster, cached_config); - if not success then - error_handler.report("large_monster_UI.draw", "Highlighted Large Monster drawing function threw an exception"); - end + if dynamic_enabled then + this.update_dynamic_monsters(large_monster_list, cached_config); end if static_enabled then - local success = pcall(this.draw_static, displayed_monsters, highlighted_monster, cached_config); - if not success then - error_handler.report("large_monster_UI.draw", "Static Large Monster drawing function threw an exception"); - end + this.update_static_monsters(large_monster_list, cached_config); end end -function this.draw_dynamic(displayed_monsters, highlighted_monster, cached_config) - cached_config = cached_config.dynamic; - local global_scale_modifier = config.current_config.global_settings.modifiers.global_scale_modifier; +function this.update_dynamic_monsters(large_monster_list, cached_config) + if not cached_config.dynamic.enabled then + displayed_dynamic_monsters = {}; + return; + end - local i = 0; - for _, monster in ipairs(displayed_monsters) do - if cached_config.settings.max_distance == 0 then - break; + local dynamic_cached_config = cached_config.dynamic.settings; + + local _displayed_dynamic_monsters = {}; + + if dynamic_cached_config.max_distance == 0 then + displayed_dynamic_monsters = {}; + return; + end + + for i, monster in ipairs(large_monster_list) do + if monster.distance > dynamic_cached_config.max_distance then + goto continue; end if monster.is_stealth then goto continue; end - if monster.dead_or_captured and cached_config.settings.hide_dead_or_captured then + if monster.dead_or_captured and dynamic_cached_config.hide_dead_or_captured then goto continue; end if monster == highlighted_monster then - if not cached_config.settings.render_highlighted_monster then + if not dynamic_cached_config.render_highlighted_monster then goto continue; end else - if not cached_config.settings.render_not_highlighted_monsters then + if not dynamic_cached_config.render_not_highlighted_monsters then goto continue; end end - local position_on_screen = {}; + table.insert(_displayed_dynamic_monsters, monster); + ::continue:: + end + + displayed_dynamic_monsters = _displayed_dynamic_monsters; +end + +function this.update_static_monsters(large_monster_list, cached_config) + if not cached_config.static.enabled then + displayed_static_monsters = {}; + return; + end + + local static_cached_config = cached_config.static.settings; + + local _displayed_static_monsters = {}; + + for i, monster in ipairs(large_monster_list) do + if monster.is_stealth then + goto continue; + end + + if monster.dead_or_captured and static_cached_config.hide_dead_or_captured then + goto continue; + end + + if monster == highlighted_monster then + if not static_cached_config.render_highlighted_monster then + goto continue; + end + else + if not static_cached_config.render_not_highlighted_monsters then + goto continue; + end + end + + table.insert(_displayed_static_monsters, monster); + ::continue:: + end + + + displayed_static_monsters = this.sort_static_monsters(_displayed_static_monsters, cached_config); +end + +function this.sort_static_monsters(_displayed_static_monsters, cached_config) + cached_config = cached_config.static.sorting; + + -- sort here + if cached_config.type == "Normal" and cached_config.reversed_order then + local reversed_monsters = {}; + for i = #_displayed_static_monsters, 1, -1 do + table.insert(reversed_monsters, _displayed_static_monsters[i]); + end + + _displayed_static_monsters = reversed_monsters; + + elseif cached_config.type == "Health" then + if cached_config.reversed_order then + table.sort(_displayed_static_monsters, function(left, right) + return left.health > right.health; + end); + else + table.sort(_displayed_static_monsters, function(left, right) + return left.health < right.health; + end); + end + elseif cached_config.type == "Health Percentage" then + if cached_config.reversed_order then + table.sort(_displayed_static_monsters, function(left, right) + return left.health_percentage > right.health_percentage; + end); + else + table.sort(_displayed_static_monsters, function(left, right) + return left.health_percentage < right.health_percentage; + end); + end + elseif cached_config.type == "Distance" then + if cached_config.reversed_order then + table.sort(_displayed_static_monsters, function(left, right) + return left.distance > right.distance; + end); + else + table.sort(_displayed_static_monsters, function(left, right) + return left.distance < right.distance; + end); + end + end + + return _displayed_static_monsters; +end + +function this.update_highlighted_monster(large_monster_list, autohighlight_config) + local monster_id_shift = 0; + local _highlighted_monster = nil; + + large_monster.update_highlighted_id(); + + if large_monster.highlighted_id == -1 then + highlighted_monster = nil; + return; + end + + for i, monster in ipairs(large_monster_list) do + if monster.dead_or_captured or not monster.is_disp_icon_mini_map then + monster_id_shift = monster_id_shift + 1; + goto continue; + end + + if not autohighlight_config.enabled then + if i - 1 == large_monster.highlighted_id + monster_id_shift then + _highlighted_monster = monster; + goto continue; + end + + goto continue; + end + + if _highlighted_monster == nil then + _highlighted_monster = monster; + goto continue; + end + + if autohighlight_config.mode == "Farthest" and monster.distance > _highlighted_monster.distance then + _highlighted_monster = monster; + goto continue; + end + + if autohighlight_config.mode == "Lowest Health" and monster.health < _highlighted_monster.health then + _highlighted_monster = monster; + goto continue; + end + + if autohighlight_config.mode == "Highest Health" and monster.health > _highlighted_monster.health then + _highlighted_monster = monster; + goto continue; + end + + if autohighlight_config.mode == "Lowest Health Percentage" and monster.health_percentage < _highlighted_monster.health_percentage then + _highlighted_monster = monster; + goto continue; + end + + if autohighlight_config.mode == "Highest Health Percentage" and monster.health_percentage > _highlighted_monster.health_percentage then + _highlighted_monster = monster; + goto continue; + end + + if monster.distance < _highlighted_monster.distance then + _highlighted_monster = monster; + end + + ::continue:: + end + + highlighted_monster = _highlighted_monster; +end + +function this.draw(dynamic_enabled, static_enabled, highlighted_enabled) + local cached_config = config.current_config.large_monster_UI; + + if dynamic_enabled then + local success = pcall(this.draw_dynamic, cached_config); + if not success then + error_handler.report("large_monster_UI.draw", "Dynamic Large Monster drawing function threw an exception"); + end + end + + if highlighted_enabled then + local success = pcall(this.draw_highlighted, cached_config); + if not success then + error_handler.report("large_monster_UI.draw", "Highlighted Large Monster drawing function threw an exception"); + end + end + + if static_enabled then + local success = pcall(this.draw_static, cached_config); + if not success then + error_handler.report("large_monster_UI.draw", "Static Large Monster drawing function threw an exception"); + end + end +end + +function this.draw_dynamic(cached_config) + cached_config = cached_config.dynamic; + local global_scale_modifier = config.current_config.global_settings.modifiers.global_scale_modifier; + + local i = 0; + for _, monster in ipairs(displayed_dynamic_monsters) do local world_offset = Vector3f.new(cached_config.world_offset.x, cached_config.world_offset.y, cached_config.world_offset.z); - - position_on_screen = draw.world_to_screen(monster.position + world_offset); + local position_on_screen = draw.world_to_screen(monster.position + world_offset); if position_on_screen == nil then goto continue; @@ -205,84 +344,27 @@ function this.draw_dynamic(displayed_monsters, highlighted_monster, cached_confi position_on_screen.y = position_on_screen.y + cached_config.viewport_offset.y * global_scale_modifier; local opacity_scale = 1; - if monster.distance > cached_config.settings.max_distance then - goto continue; - end - + if cached_config.settings.opacity_falloff then + monster.distance = (players.myself_position - monster.position):length(); opacity_scale = 1 - (monster.distance / cached_config.settings.max_distance); end - large_monster.draw(monster, "dynamic", cached_config, position_on_screen, opacity_scale); + large_monster.draw(monster, "dynamic_UI", cached_config, position_on_screen, opacity_scale); i = i + 1; ::continue:: end end -function this.draw_static(displayed_monsters, highlighted_monster, cached_config) +function this.draw_static(cached_config) cached_config = cached_config.static; local global_scale_modifier = config.current_config.global_settings.modifiers.global_scale_modifier; - -- sort here - if cached_config.sorting.type == "Normal" and cached_config.sorting.reversed_order then - local reversed_monsters = {}; - for i = #displayed_monsters, 1, -1 do - table.insert(reversed_monsters, displayed_monsters[i]); - end - - displayed_monsters = reversed_monsters; - - elseif cached_config.sorting.type == "Health" then - if cached_config.sorting.reversed_order then - table.sort(displayed_monsters, function(left, right) - return left.health > right.health; - end); - else - table.sort(displayed_monsters, function(left, right) - return left.health < right.health; - end); - end - elseif cached_config.sorting.type == "Health Percentage" then - if cached_config.sorting.reversed_order then - table.sort(displayed_monsters, function(left, right) - return left.health_percentage > right.health_percentage; - end); - else - table.sort(displayed_monsters, function(left, right) - return left.health_percentage < right.health_percentage; - end); - end - elseif cached_config.sorting.type == "Distance" then - if cached_config.sorting.reversed_order then - table.sort(displayed_monsters, function(left, right) - return left.distance > right.distance; - end); - else - table.sort(displayed_monsters, function(left, right) - return left.distance < right.distance; - end); - end - end - local position_on_screen = screen.calculate_absolute_coordinates(cached_config.position); local i = 0; - for _, monster in ipairs(displayed_monsters) do - if monster.dead_or_captured and cached_config.settings.hide_dead_or_captured then - goto continue; - end - - if monster == highlighted_monster then - if not cached_config.settings.render_highlighted_monster then - goto continue; - end - else - if not cached_config.settings.render_not_highlighted_monsters then - goto continue; - end - end - + for _, monster in ipairs(displayed_static_monsters) do local monster_position_on_screen = { x = position_on_screen.x, y = position_on_screen.y @@ -294,27 +376,23 @@ function this.draw_static(displayed_monsters, highlighted_monster, cached_config monster_position_on_screen.y = monster_position_on_screen.y + cached_config.spacing.y * i * global_scale_modifier; end - large_monster.draw(monster, "static", cached_config, monster_position_on_screen, 1); + large_monster.draw(monster, "static_UI", cached_config, monster_position_on_screen, 1); i = i + 1; ::continue:: end end -function this.draw_highlighted(monster, cached_config) - cached_config = cached_config.highlighted; - - if monster == nil then +function this.draw_highlighted(cached_config) + if highlighted_monster == nil then return; end + cached_config = cached_config.highlighted; + local position_on_screen = screen.calculate_absolute_coordinates(cached_config.position); - if monster.dead_or_captured then - return; - end - - large_monster.draw(monster, "highlighted", cached_config, position_on_screen, 1); + large_monster.draw(highlighted_monster, "highlighted_UI", cached_config, position_on_screen, 1); end function this.init_dependencies() diff --git a/reframework/autorun/MHR_Overlay/UI/Modules/small_monster_UI.lua b/reframework/autorun/MHR_Overlay/UI/Modules/small_monster_UI.lua index a925291..12a17fc 100644 --- a/reframework/autorun/MHR_Overlay/UI/Modules/small_monster_UI.lua +++ b/reframework/autorun/MHR_Overlay/UI/Modules/small_monster_UI.lua @@ -47,82 +47,96 @@ local enemy_manager_type_def = sdk.find_type_definition("snow.enemy.EnemyManager local get_zako_enemy_count_method = enemy_manager_type_def:get_method("getZakoEnemyCount"); local get_zako_enemy_method = enemy_manager_type_def:get_method("getZakoEnemy"); -function this.draw() - if singletons.enemy_manager == nil then +local displayed_monsters = {}; + +function this.update() + local cached_config = config.current_config.small_monster_UI; + + if cached_config.dynamic_positioning.enabled and cached_config.dynamic_positioning.max_distance == 0 then + displayed_monsters = {}; return; end - local cached_config = config.current_config.small_monster_UI; - - local displayed_monsters = {}; + local _displayed_monsters = {}; for enemy, monster in pairs(small_monster.list) do + if monster.dead_or_captured and cached_config.settings.hide_dead_or_captured then goto continue; end; - table.insert(displayed_monsters, monster); + monster.distance = (players.myself_position - monster.position):length(); + if monster.distance > cached_config.dynamic_positioning.max_distance then + goto continue; + end + table.insert(_displayed_monsters, monster); ::continue:: end + + displayed_monsters = this.sort_monsters(_displayed_monsters, cached_config); +end - if cached_config.dynamic_positioning.enabled - or (not cached_config.dynamic_positioning.enabled and cached_config.static_sorting.type == "Distance") then - for _, monster in ipairs(displayed_monsters) do - monster.distance = (players.myself_position - monster.position):length(); - end - end - +function this.sort_monsters(_displayed_monsters, cached_config) if not cached_config.dynamic_positioning.enabled then - -- sort here if cached_config.static_sorting.type == "Normal" and cached_config.static_sorting.reversed_order then local reversed_monsters = {}; - for i = #displayed_monsters, 1, -1 do - table.insert(reversed_monsters, displayed_monsters[i]); + for i = #_displayed_monsters, 1, -1 do + table.insert(reversed_monsters, _displayed_monsters[i]); end - displayed_monsters = reversed_monsters; + _displayed_monsters = reversed_monsters; elseif cached_config.static_sorting.type == "Health" then if cached_config.static_sorting.reversed_order then - table.sort(displayed_monsters, function(left, right) + table.sort(_displayed_monsters, function(left, right) return left.health > right.health; end); else - table.sort(displayed_monsters, function(left, right) + table.sort(_displayed_monsters, function(left, right) return left.health < right.health; end); end elseif cached_config.static_sorting.type == "Health Percentage" then if cached_config.static_sorting.reversed_order then - table.sort(displayed_monsters, function(left, right) + table.sort(_displayed_monsters, function(left, right) return left.health_percentage > right.health_percentage; end); else - table.sort(displayed_monsters, function(left, right) + table.sort(_displayed_monsters, function(left, right) return left.health_percentage < right.health_percentage; end); end elseif cached_config.static_sorting.type == "Distance" then if cached_config.static_sorting.reversed_order then - table.sort(displayed_monsters, function(left, right) + table.sort(_displayed_monsters, function(left, right) return left.distance > right.distance; end); else - table.sort(displayed_monsters, function(left, right) + table.sort(_displayed_monsters, function(left, right) return left.distance < right.distance; end); end end end + return _displayed_monsters; +end + +function this.draw() + local cached_config = config.current_config.small_monster_UI; + + local is_dynamic_positioning_enabled = cached_config.dynamic_positioning.enabled; + local i = 0; for _, monster in ipairs(displayed_monsters) do local position_on_screen; - if cached_config.dynamic_positioning.enabled then - local world_offset = Vector3f.new(cached_config.dynamic_positioning.world_offset.x, + if is_dynamic_positioning_enabled then + local world_offset = Vector3f.new( + cached_config.dynamic_positioning.world_offset.x, cached_config.dynamic_positioning.world_offset.y, - cached_config.dynamic_positioning.world_offset.z); + cached_config.dynamic_positioning.world_offset.z + ); position_on_screen = draw.world_to_screen(monster.position + world_offset); @@ -136,25 +150,15 @@ function this.draw() position_on_screen = screen.calculate_absolute_coordinates(cached_config.static_position); if cached_config.settings.orientation == "Horizontal" then position_on_screen.x = position_on_screen.x + cached_config.static_spacing.x * i; - else position_on_screen.y = position_on_screen.y + cached_config.static_spacing.y * i; end end local opacity_scale = 1; - if cached_config.dynamic_positioning.enabled then - if cached_config.dynamic_positioning.max_distance == 0 then - return; - end - - if monster.distance > cached_config.dynamic_positioning.max_distance then - goto continue; - end - - if cached_config.dynamic_positioning.opacity_falloff then - opacity_scale = 1 - (monster.distance / cached_config.dynamic_positioning.max_distance); - end + if is_dynamic_positioning_enabled and cached_config.dynamic_positioning.opacity_falloff then + monster.distance = (players.myself_position - monster.position):length(); + opacity_scale = 1 - (monster.distance / cached_config.dynamic_positioning.max_distance); end small_monster.draw(monster, cached_config, position_on_screen, opacity_scale);