From 836b42f42593ecc870d5f81b64a58d89fb699e99 Mon Sep 17 00:00:00 2001 From: Christoph Urlacher Date: Fri, 6 Mar 2026 03:30:31 +0100 Subject: [PATCH] color nodes based on target distance --- include/config.hpp | 10 +++--- include/state_manager.hpp | 1 + src/renderer.cpp | 64 ++++++++++++++++++++++++++++++++------- src/state_manager.cpp | 5 +++ 4 files changed, 65 insertions(+), 15 deletions(-) diff --git a/include/config.hpp b/include/config.hpp index 9a8f08e..32bb99e 100644 --- a/include/config.hpp +++ b/include/config.hpp @@ -72,14 +72,16 @@ constexpr float THETA = 0.8; // Barnes-Hut [0.5, 1.0] constexpr float SOFTENING = 0.01; // Barnes-Hut [0.01, 1.0] // Graph Drawing -constexpr Color EDGE_COLOR = DARKBLUE; -constexpr float VERTEX_SIZE = 0.5; +static const Color EDGE_COLOR = Fade(PURPLE, 0.75); +constexpr float VERTEX_SIZE = 0.75; static const Color VERTEX_COLOR = Fade(BLUE, 0.5); -constexpr Color VERTEX_VISITED_COLOR = DARKBLUE; +constexpr Color VERTEX_VISITED_COLOR = DARKPURPLE; constexpr Color VERTEX_PATH_COLOR = GREEN; constexpr Color VERTEX_TARGET_COLOR = RED; constexpr Color VERTEX_START_COLOR = ORANGE; -constexpr Color VERTEX_CURRENT_COLOR = PURPLE; +constexpr Color VERTEX_CURRENT_COLOR = DARKBLUE; +static const Color VERTEX_CLOSEST_COLOR = Fade(PINK, 0.85); +static const Color VERTEX_FARTHEST_COLOR = Fade(BLUE, 0.5); constexpr int DRAW_VERTICES_LIMIT = 1000000; // Klotski Drawing diff --git a/include/state_manager.hpp b/include/state_manager.hpp index 3069749..da015b6 100644 --- a/include/state_manager.hpp +++ b/include/state_manager.hpp @@ -141,6 +141,7 @@ public: [[nodiscard]] auto get_current_preset_comment() const -> const std::string&; [[nodiscard]] auto has_history() const -> bool; [[nodiscard]] auto has_distances() const -> bool; + [[nodiscard]] auto get_distances() const -> std::vector; [[nodiscard]] auto get_total_moves() const -> size_t; [[nodiscard]] auto was_edited() const -> bool; }; diff --git a/src/renderer.cpp b/src/renderer.cpp index 7613932..0da9964 100644 --- a/src/renderer.cpp +++ b/src/renderer.cpp @@ -63,6 +63,29 @@ auto renderer::draw_mass_springs(const std::vector& masses) -> void transforms.clear(); colors.clear(); + // Find max distance to interpolate colors in the given [0, max] range + int max_distance = 0; + for (const int distance : state.get_distances()) { + if (distance > max_distance) { + max_distance = distance; + } + } + + const auto lerp_color = [&](const Color from, const Color to, const int distance) + { + const float weight = 1.0 - static_cast(distance) / max_distance; + + Color result; + result.r = static_cast((1 - weight) * from.r + weight * to.r); + result.g = static_cast((1 - weight) * from.g + weight * to.g); + result.b = static_cast((1 - weight) * from.b + weight * to.b); + result.a = static_cast((1 - weight) * from.a + weight * to.a); + + return result; + }; + + const std::vector& distances = state.get_distances(); + size_t mass = 0; for (const auto& [x, y, z] : masses) { transforms.emplace_back(MatrixTranslate(x, y, z)); @@ -81,9 +104,13 @@ auto renderer::draw_mass_springs(const std::vector& masses) -> void } else if (state.get_visit_counts().at(mass) > 0) { // Visited vertex c = VERTEX_VISITED_COLOR; + } else if (distances.size() == masses.size()) { + c = lerp_color(VERTEX_FARTHEST_COLOR, + VERTEX_CLOSEST_COLOR, + static_cast(distances[mass])); } - // Current vertex is drawn as individual cube to increase its size + // Current vertex is drawn as individual cube to increase its size colors.emplace_back(c); ++mass; } @@ -181,32 +208,47 @@ auto renderer::draw_menu() const -> void EndTextureMode(); } -auto renderer::draw_textures(const int fps, const int ups, const size_t mass_count, +auto renderer::draw_textures(const int fps, + const int ups, + const size_t mass_count, const size_t spring_count) const -> void { BeginDrawing(); - DrawTextureRec(menu_target.texture, Rectangle(0, 0, menu_target.texture.width, -menu_target.texture.height), - Vector2(0, 0), WHITE); + DrawTextureRec(menu_target.texture, + Rectangle(0, 0, menu_target.texture.width, -menu_target.texture.height), + Vector2(0, 0), + WHITE); DrawTextureRec(klotski_target.texture, Rectangle(0, 0, klotski_target.texture.width, -klotski_target.texture.height), - Vector2(0, MENU_HEIGHT), WHITE); - DrawTextureRec(graph_target.texture, Rectangle(0, 0, graph_target.texture.width, -graph_target.texture.height), - Vector2(GetScreenWidth() / 2.0f, MENU_HEIGHT), WHITE); + Vector2(0, MENU_HEIGHT), + WHITE); + DrawTextureRec(graph_target.texture, + Rectangle(0, 0, graph_target.texture.width, -graph_target.texture.height), + Vector2(GetScreenWidth() / 2.0f, MENU_HEIGHT), + WHITE); // Draw borders DrawRectangleLinesEx(Rectangle(0, 0, GetScreenWidth(), MENU_HEIGHT), 1.0f, BLACK); - DrawRectangleLinesEx(Rectangle(0, MENU_HEIGHT, GetScreenWidth() / 2.0f, GetScreenHeight() - MENU_HEIGHT), 1.0f, + DrawRectangleLinesEx(Rectangle(0, MENU_HEIGHT, GetScreenWidth() / 2.0f, GetScreenHeight() - MENU_HEIGHT), + 1.0f, + BLACK); + DrawRectangleLinesEx(Rectangle(GetScreenWidth() / 2.0f, + MENU_HEIGHT, + GetScreenWidth() / 2.0f, + GetScreenHeight() - MENU_HEIGHT), + 1.0f, BLACK); - DrawRectangleLinesEx(Rectangle(GetScreenWidth() / 2.0f, MENU_HEIGHT, GetScreenWidth() / 2.0f, - GetScreenHeight() - MENU_HEIGHT), 1.0f, BLACK); gui.draw(fps, ups, mass_count, spring_count); EndDrawing(); } -auto renderer::render(const std::vector& masses, const int fps, const int ups, const size_t mass_count, +auto renderer::render(const std::vector& masses, + const int fps, + const int ups, + const size_t mass_count, const size_t spring_count) -> void { update_texture_sizes(); diff --git a/src/state_manager.cpp b/src/state_manager.cpp index b6ad5a5..b681bce 100644 --- a/src/state_manager.cpp +++ b/src/state_manager.cpp @@ -429,6 +429,11 @@ auto state_manager::has_distances() const -> bool return !node_target_distances.empty(); } +auto state_manager::get_distances() const -> std::vector +{ + return node_target_distances.distances; +} + auto state_manager::get_total_moves() const -> size_t { return total_moves;