diff --git a/src/math.hpp b/src/math.hpp index 8104eb6..0f6a8f1 100644 --- a/src/math.hpp +++ b/src/math.hpp @@ -9,6 +9,7 @@ typedef struct vec2 { float x, y; } vec2; typedef struct vec2i { int x, y; } vec2i; +typedef struct polar_t { float angle, length; } polar_t; static const vec2 vec2_zero = { 0, 0 }; static const vec2 vec2_one = { 1, 1 }; @@ -102,8 +103,29 @@ static vec2 max2(vec2 const &a, vec2 const &b) static vec2 polar_to_vec2(const float angle, const float len) { + // 0 (north) up return { .x = len * sinf(angle), .y = len * cosf(angle) }; } + +static polar_t vec2_to_polar(const vec2 v) +{ + // 0 (north) up + if (v.x == 0) + return { + .angle = (v.y > 0) ? 0 : M_PIf, + .length = abs(v.y) + }; + + polar_t ret = { + .angle = atanf(v.x / v.y) + (v.y > 0 ? 0 : M_PIf), + .length = norm(v) + }; + + if (ret.angle < 0) + ret.angle += 2 * M_PIf; + + return ret; +} diff --git a/src/sim/af_spawner.cpp b/src/sim/af_spawner.cpp index 0ca6f1d..8254808 100644 --- a/src/sim/af_spawner.cpp +++ b/src/sim/af_spawner.cpp @@ -1,5 +1,7 @@ #include "af_spawner.hpp" +#include + void dxd::sim::AFSpawner::tick(float timestep, World *world) { (void)timestep; @@ -11,7 +13,7 @@ void dxd::sim::AFSpawner::tick(float timestep, World *world) //Pos should spawn in a grid, check if free, and offset random from grid coord to look natural vec2 pos = {(SDL_randf()-.5f)*2*60.0f, (SDL_randf()-.5f)*2*60.0f}; - Airfield *af = new Airfield(pos, _MIN_AF_TTL + SDL_rand(_MAX_AF_TTL)); + Airfield *af = new Airfield(pos, _MIN_AF_TTL + SDL_rand(_MAX_AF_TTL), SDL_randf()*2*M_PIf); world->add_obj(af); _airfields.push_back(af); } diff --git a/src/sim/aircraft.cpp b/src/sim/aircraft.cpp index 5b91b48..5d310a4 100644 --- a/src/sim/aircraft.cpp +++ b/src/sim/aircraft.cpp @@ -5,6 +5,16 @@ void dxd::sim::Aircraft::tick(float timestep, World *world) { (void)world; + float target_direction = vec2_to_polar(_target - _position).angle; + float target_deviation = target_direction - _direction; + //TODO: Fix this normalization mess + if (target_deviation > M_PIf) + { + target_deviation -= 2 * M_PIf; + } + printf("%0.2f %.2f %0.2f\n", target_direction, target_deviation, target_direction - _direction); + + _direction += SDL_clamp(target_deviation, -_MAX_TURN_RATE, _MAX_TURN_RATE) * timestep; _position = _position + polar_to_vec2(_direction, _speed) * timestep; if (--_trail_cooldown == 0) diff --git a/src/sim/aircraft.hpp b/src/sim/aircraft.hpp index a4fbba1..838b21c 100644 --- a/src/sim/aircraft.hpp +++ b/src/sim/aircraft.hpp @@ -12,14 +12,16 @@ private: vec2 _position; float _direction; float _speed; + vec2 _target; int _trail_cooldown; const int _TRAIL_DELAY = 60; const int _TRAIL_DURATION = 420; + const float _MAX_TURN_RATE = 0.5f; public: - Aircraft(vec2 position, float direction, float speed) - : _position(position), _direction(direction), _speed(speed) + Aircraft(vec2 position, float direction, float speed, vec2 target) + : _position(position), _direction(direction), _speed(speed), _target(target) { _trail_cooldown = _TRAIL_DELAY; } diff --git a/src/sim/airfield.cpp b/src/sim/airfield.cpp index 7bb1622..595eacb 100644 --- a/src/sim/airfield.cpp +++ b/src/sim/airfield.cpp @@ -13,9 +13,13 @@ void dxd::sim::Airfield::tick(float timestep, World *world) if (--_next_spawn == 0) { - Aircraft *af = new Aircraft(_position, SDL_randf() * 2 * M_PIf, 5.0f); + vec2 pos = _position + polar_to_vec2(_rw_heading, _WR_LENGTH+0.5); + //vec2 tgt = _position + polar_to_vec2(SDL_randf()*2*M_PIf, 30); + vec2 tgt = _position + polar_to_vec2(0, 80); + Aircraft *af = new Aircraft(pos, _rw_heading, 5.0f, tgt); world->add_obj(af); - _next_spawn = _MIN_TAKEOFF_DELAY + SDL_rand(_MAX_TAKEOFF_DELAY - _MIN_TAKEOFF_DELAY); + //_next_spawn = _MIN_TAKEOFF_DELAY + SDL_rand(_MAX_TAKEOFF_DELAY - _MIN_TAKEOFF_DELAY); + _next_spawn = 99999999; } } @@ -24,4 +28,9 @@ void dxd::sim::Airfield::draw(Renderer *rend) rend->color(127, 127, 127, 255); rend->rect(_position, 5); rend->diamond(_position, 5); + + rend->color(64, 64, 255, 255); + vec2 a = _position + polar_to_vec2(_rw_heading, +_WR_LENGTH); + vec2 b = _position + polar_to_vec2(_rw_heading, -_WR_LENGTH); + rend->line(a, b); } diff --git a/src/sim/airfield.hpp b/src/sim/airfield.hpp index 5a827f1..22607db 100644 --- a/src/sim/airfield.hpp +++ b/src/sim/airfield.hpp @@ -14,14 +14,17 @@ private: vec2 _position; int _ttl; int _next_spawn; + float _rw_heading; const int _MIN_TAKEOFF_DELAY = 240; const int _MAX_TAKEOFF_DELAY = 600; + const int _WR_LENGTH = 6; public: - Airfield(vec2 position, int ttl) : _position(position), _ttl(ttl) + Airfield(vec2 position, int ttl, float rw_heading) + : _position(position), _ttl(ttl), _rw_heading(rw_heading) { - _next_spawn = 30; + _next_spawn = _MIN_TAKEOFF_DELAY; } void tick(float timestep, World *world) override;