From 66bdf9327afe6a03929f45d9ba367c4bcae09951 Mon Sep 17 00:00:00 2001 From: PoliEcho Date: Fri, 7 Aug 2026 16:36:56 +0200 Subject: [PATCH] add arc and alt --- Kconfig | 2 +- src/core/units.hpp | 6 +++++ src/hal/draw.hpp | 1 + src/hal/hal_linux.cpp | 43 ++++++++++++++++++++++++++++++ src/main.cpp | 61 ++++++++++++++++++++++++++++--------------- 5 files changed, 91 insertions(+), 22 deletions(-) diff --git a/Kconfig b/Kconfig index efc6c8c..4e4666f 100644 --- a/Kconfig +++ b/Kconfig @@ -92,7 +92,7 @@ config METRIC bool "Use metric units" default y help - Show altitudes in meters instead of feet. + Show units in metric instead of aeronautical. comment "Platform dependent options" diff --git a/src/core/units.hpp b/src/core/units.hpp index 9174215..b70d64e 100644 --- a/src/core/units.hpp +++ b/src/core/units.hpp @@ -13,4 +13,10 @@ static inline T knot_to_km(T kt) { #define SPEED_UNIT "kmph" #else #define SPEED_UNIT "knot" +#endif + +#ifdef CONFIG_METRIC +#define ALTITUDE_UNIT "m" +#else +#define ALTITUDE_UNIT "ft" #endif \ No newline at end of file diff --git a/src/hal/draw.hpp b/src/hal/draw.hpp index 5ee7369..3d7acd1 100644 --- a/src/hal/draw.hpp +++ b/src/hal/draw.hpp @@ -20,4 +20,5 @@ struct rect_t { void circle(const uint16_t x_center, const uint16_t y_center,const uint16_t radius, const color_t color); void rhombus(const uint16_t x_center, const uint16_t y_center,const uint16_t radius, const color_t color); void line(const uint16_t x1,const uint16_t y1,const uint16_t x2,const uint16_t y2, const color_t color); + void arc(uint16_t start_x, uint16_t start_y, float start_angle, float speed /*in pps*/,float angular_speed, uint16_t duration, color_t color); } \ No newline at end of file diff --git a/src/hal/hal_linux.cpp b/src/hal/hal_linux.cpp index dd9de00..56759a3 100644 --- a/src/hal/hal_linux.cpp +++ b/src/hal/hal_linux.cpp @@ -25,6 +25,7 @@ #include #include #include +#include #include struct sdl_session { @@ -221,6 +222,48 @@ void line(const uint16_t x1, const uint16_t y1, const uint16_t x2, 0xff); SDL_RenderLine(main_sdl_session.renderer, x1, y1, x2, y2); } + +#ifdef CONFIG_VECTOR_FOLLOW_TRACK_RATE +void arc(uint16_t start_x, uint16_t start_y, float start_angle_rad, float speed /*in pps*/,float angular_speed_rads, uint16_t duration, color_t color) { + SDL_SetRenderDrawColor(main_sdl_session.renderer, color.r, color.g, color.b, + 0xff); + constexpr float DEG2RAD = std::numbers::pi / 180.0f; + + + // Handle straight line case + if (std::fabs(angular_speed_rads) < 1e-6f) { + uint16_t steps = static_cast(speed * duration); + for (uint16_t i = 0; i <= steps; ++i) { + float t = i / speed; + float x = start_x + std::cos(start_angle_rad) * speed * t; + float y = start_y + std::sin(start_angle_rad) * speed * t; + SDL_RenderPoint(main_sdl_session.renderer,static_cast(std::round(x)), static_cast(std::round(y))); + } + return; + } + + float r = speed / angular_speed_rads; + + // Center of circle: perpendicular to heading + float center_x = start_x - r * std::sin(start_angle_rad); + float center_y = start_y + r * std::cos(start_angle_rad); + + // Angle from center to start point + float radius_angle = std::atan2(start_y - center_y, start_x - center_x); + + // Step size in time — approx 1 pixel arc-length per step + float dt = 1.0f / std::max(std::fabs(speed), 1.0f); + uint16_t steps = static_cast(duration / dt); + + for (uint16_t i = 0; i <= steps; ++i) { + float t = i * dt; + float a = radius_angle + angular_speed_rads * t; + float x = center_x + std::fabs(r) * std::cos(a); + float y = center_y + std::fabs(r) * std::sin(a); + SDL_RenderPoint(main_sdl_session.renderer,static_cast(std::round(x)), static_cast(std::round(y))); + } +} +#endif } // namespace draw namespace net { diff --git a/src/main.cpp b/src/main.cpp index 6e42a2b..46875b9 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -111,22 +111,22 @@ int main() { " aircraft with no alt data detected!\n"; altitude = 0; } - #ifndef CONFIG_METRIC +#ifndef CONFIG_METRIC // aircraft ground speed in knots float speed_knot; - #endif +#endif // aircraft ground speed in km/h float speed; // aircraft track in degreees float track; try { - #ifdef CONFIG_METRIC +#ifdef CONFIG_METRIC speed = knot_to_km(craft["gs"].get()); - #else - speed_knot = craft["gs"].get(); - speed = knot_to_km(speed_knot); - #endif - +#else + speed_knot = craft["gs"].get(); + speed = knot_to_km(speed_knot); +#endif + track = craft["track"].get(); } catch (...) { std::clog << YELLOW @@ -164,11 +164,24 @@ int main() { const float track_rad = std::fmod((track - 90), 365.0f) * (static_cast(std::numbers::pi) / 180.0f); - - draw::line(x_center, y_center, - x_center + (vector_lenght * std::cos(track_rad)), - y_center + (vector_lenght * std::sin(track_rad)), - color); +#ifdef CONFIG_VECTOR_FOLLOW_TRACK_RATE +{ + float track_rate_rads; + try { + track_rate_rads = craft["track_rate"].get() * (static_cast(std::numbers::pi) / 180.0f); + } catch (...) { + std::clog << YELLOW + "[WARNING]" RESET + " aircraft with no track_rate data detected!\n"; + track_rate_rads = 0; + } + draw::arc(x_center, y_center,track_rad,speed_pph/3600,track_rate_rads,CONFIG_TIME_BASED_VECTOR_LENGHT*60,color); + } +#else + draw::line(x_center, y_center, + x_center + (vector_lenght * std::cos(track_rad)), + y_center + (vector_lenght * std::sin(track_rad)), color); +#endif draw::rhombus(x_center, y_center, 8 /*TODO: remove magic*/, color); @@ -182,14 +195,20 @@ int main() { callsign = CONFIG_NO_CALLSIGN_IDENTIFICATION; } // print some info - font::puts(callsign, x_center + 10 /*TODO: remove magic*/, y_center, color); + font::puts(callsign, x_center + 10 /*TODO: remove magic*/, + y_center, color); font::puts(std::to_string(static_cast( - #ifdef CONFIG_METRIC - speed - #else - speed_knot - #endif - )) + SPEED_UNIT, x_center + 10 /*TODO: remove magic*/, y_center + FONT_HEIGHT +CONFIG_CHARACTER_SPACING, color); +#ifdef CONFIG_METRIC + speed +#else + speed_knot +#endif + )) + + SPEED_UNIT, + x_center + 10 /*TODO: remove magic*/, + y_center + FONT_HEIGHT + CONFIG_CHARACTER_SPACING, + color); + font::puts(std::to_string(altitude) + ALTITUDE_UNIT, x_center + 10 /*TODO: remove magic*/, y_center + (FONT_HEIGHT + CONFIG_CHARACTER_SPACING)*2,color); } } catch (...) { std::clog << YELLOW "[WARNING]" RESET @@ -197,7 +216,7 @@ int main() { } } } else { - // TODO draw vizual error + // TODO draw visual error std::cerr << RED "[ERROR]" RESET " failed to get aircraft\n"; } }