From f8f55976533ac3b77bb8d31697ba2f1e54a994c1 Mon Sep 17 00:00:00 2001 From: Star Rauchenberger Date: Sat, 8 Mar 2025 10:52:51 -0500 Subject: Made indicator updates more fine-grained --- src/ap_state.cpp | 93 ++++++++++++++++++++++++++++++++------------------------ 1 file changed, 54 insertions(+), 39 deletions(-) (limited to 'src/ap_state.cpp') diff --git a/src/ap_state.cpp b/src/ap_state.cpp index 29e649f..d01290b 100644 --- a/src/ap_state.cpp +++ b/src/ap_state.cpp @@ -243,7 +243,7 @@ struct APState { checked_paintings.count(painting_mapping.at(painting_id))); } - std::string GetItemName(int id) { return apclient->get_item_name(id); } + std::string GetItemName(int id) { return apclient->get_item_name(id, "Lingo"); } void RevealPaintings() { std::lock_guard state_guard(state_mutex); @@ -369,7 +369,7 @@ struct APState { } } - RefreshTracker(false); + RefreshTracker(StateUpdate{.cleared_locations = true}); } void OnSlotDisconnected() { @@ -391,51 +391,53 @@ struct APState { } void OnItemsReceived(const std::list& items) { + std::vector item_states; + { std::lock_guard state_guard(state_mutex); + std::map index_by_item; + for (const APClient::NetworkItem& item : items) { inventory[item.item]++; TrackerLog(fmt::format("Item: {}", item.item)); + + index_by_item[item.item] = item.index; + } + + for (const auto& [item_id, item_index] : index_by_item) { + item_states.push_back(ItemState{.name = GetItemName(item_id), + .amount = inventory[item_id], + .index = item_index}); } } - RefreshTracker(false); + RefreshTracker(StateUpdate{.items = item_states}); } void OnRetrieved(const std::map& data) { + StateUpdate state_update; + { std::lock_guard state_guard(state_mutex); for (const auto& [key, value] : data) { - HandleDataStorage(key, value); + HandleDataStorage(key, value, state_update); } } - RefreshTracker(false); + RefreshTracker(state_update); } void OnSetReply(const std::string& key, const nlohmann::json& value) { - bool should_refresh = false; - bool should_redraw_position = false; + StateUpdate state_update; + { std::lock_guard state_guard(state_mutex); - HandleDataStorage(key, value); - - if (key.ends_with("PlayerPos")) - { - should_redraw_position = true; - } else { - should_refresh = true; - } + HandleDataStorage(key, value, state_update); } - if (should_refresh) - { - RefreshTracker(false); - } else if (should_redraw_position) { - tracker_frame->RedrawPosition(); - } + RefreshTracker(state_update); } void OnSlotConnected(std::string player, std::string server, @@ -531,7 +533,7 @@ struct APState { } ResetReachabilityRequirements(); - RefreshTracker(true); + RefreshTracker(std::nullopt); } void OnSlotRefused(const std::list& errors) { @@ -574,11 +576,15 @@ struct APState { } // Assumes state mutex is locked. - void HandleDataStorage(const std::string& key, const nlohmann::json& value) { + void HandleDataStorage(const std::string& key, const nlohmann::json& value, StateUpdate& state_update) { if (value.is_boolean()) { data_storage[key] = value.get(); TrackerLog(fmt::format("Data storage {} retrieved as {}", key, (value.get() ? "true" : "false"))); + + if (key.find("Achievement|") != std::string::npos) { + state_update.achievements = true; + } } else if (value.is_number()) { data_storage[key] = value.get(); TrackerLog(fmt::format("Data storage {} retrieved as {}", key, @@ -587,6 +593,7 @@ struct APState { if (key.ends_with("PlayerPos")) { auto map_value = value.get>(); player_pos = std::tuple(map_value["x"], map_value["z"]); + state_update.player_position = true; } else { data_storage[key] = value.get>(); } @@ -595,6 +602,7 @@ struct APState { } else if (value.is_null()) { if (key.ends_with("PlayerPos")) { player_pos = std::nullopt; + state_update.player_position = true; } else { data_storage.erase(key); } @@ -606,6 +614,8 @@ struct APState { if (key.ends_with("Paintings")) { data_storage[key] = std::set(list_value.begin(), list_value.end()); + state_update.paintings = + std::vector(list_value.begin(), list_value.end()); } else { data_storage[key] = list_value; } @@ -616,29 +626,34 @@ struct APState { } // State mutex should NOT be locked. - void RefreshTracker(bool reset) { + // nullopt state_update indicates a reset. + void RefreshTracker(std::optional state_update) { TrackerLog("Refreshing display..."); - std::string prev_msg; - { - std::lock_guard state_guard(state_mutex); + if (!state_update || !state_update->items.empty() || + !state_update->paintings.empty()) { + std::string prev_msg; + { + std::lock_guard state_guard(state_mutex); - prev_msg = status_message; - SetStatusMessage(fmt::format("{} Recalculating...", status_message)); - } + prev_msg = status_message; + SetStatusMessage(fmt::format("{} Recalculating...", status_message)); + } - RecalculateReachability(); + RecalculateReachability(); - if (reset) { - tracker_frame->ResetIndicators(); - } else { - tracker_frame->UpdateIndicators(); - } + { + std::lock_guard state_guard(state_mutex); - { - std::lock_guard state_guard(state_mutex); + SetStatusMessage(prev_msg); + } + } + - SetStatusMessage(prev_msg); + if (!state_update) { + tracker_frame->ResetIndicators(); + } else { + tracker_frame->UpdateIndicators(*state_update); } } -- cgit 1.4.1