diff options
author | Stanislaw Halik <sthalik@misaki.pl> | 2023-09-25 06:11:52 +0200 |
---|---|---|
committer | Stanislaw Halik <sthalik@misaki.pl> | 2023-09-25 06:11:52 +0200 |
commit | 18d1db7d8be97fd9aea67c352e78b376d7145f4b (patch) | |
tree | b28d9b272bf1a0e5bf971c4e162e8ef2bf44b037 /src | |
parent | 627dc90720e083b2e458ab7efb4dcca739b7a19a (diff) |
a
Diffstat (limited to 'src')
-rw-r--r-- | src/path-search.cpp | 50 | ||||
-rw-r--r-- | src/path-search.hpp | 9 | ||||
-rw-r--r-- | src/world.hpp | 2 |
3 files changed, 52 insertions, 9 deletions
diff --git a/src/path-search.cpp b/src/path-search.cpp index cf7d41d5..47ce6f61 100644 --- a/src/path-search.cpp +++ b/src/path-search.cpp @@ -176,10 +176,52 @@ auto path_search::make_neighbor_tile_bbox(Vector2i coord, Vector2ub own_size, ro return { Vector2(min + shift), Vector2(max + shift) }; } -Optional<path_search_result> -path_search::operator()(world& w, object_id own_id, - global_coords from, Vector2b from_offset, Vector2ub size, - global_coords to, Vector2b to_offset) +auto path_search::get_walkable_neighbor_tiles(world& w, global_coords coord, Vector2ub size, object_id own_id) -> neighbors +{ + auto ch = chunk_coords_{ coord.chunk(), coord.z() }; + auto pos = Vector2i(coord.local()); + + if (auto [min, max] = make_neighbor_tile_bbox(pos, size, rotation_COUNT); + !is_passable(w, ch, min, max, own_id)) + return {}; + + neighbors ns; + + using enum rotation; + constexpr struct { + Vector2i off; + rotation r = {}; + } nbs[] = { + { { 0, -1 }, N }, + { { 1, 0 }, E }, + { { 0, 1 }, S }, + { { -1, 0 }, W }, + }; + + for (auto [off, dir] : nbs) + { + auto [min, max] = make_neighbor_tile_bbox(pos, size, dir); + if (is_passable(w, ch, min, max, own_id)) + ns.neighbors[ns.size++] = coord + off; + } + + return ns; +} + +auto path_search::bbox_union(bbox bb, Vector2i coord, Vector2b offset, Vector2ub size) -> bbox +{ + auto center = coord * iTILE_SIZE2 + Vector2i(offset); + auto min = center - Vector2i(size / 2u); + auto max = center + Vector2i(size); + return { + .min = Math::min(bb.min, Vector2(min)), + .max = Math::max(bb.max, Vector2(max)), + }; +} + +Optional<path_search_result> path_search::operator()(world& w, object_id own_id, + global_coords from, Vector2b from_offset, Vector2ub size, + global_coords to, Vector2b to_offset) { if (from.z() != to.z()) [[unlikely]] return {}; diff --git a/src/path-search.hpp b/src/path-search.hpp index 68cf41a4..4d3c7d23 100644 --- a/src/path-search.hpp +++ b/src/path-search.hpp @@ -41,9 +41,9 @@ struct path_search_result final const global_coords* data() const; private: - mutable path_search_result* _next; + mutable path_search_result* _next = nullptr; std::unique_ptr<global_coords[]> _path; - size_t _size; + size_t _size = 0; }; class path_search final @@ -54,7 +54,7 @@ class path_search final auto end() const { return neighbors.data() + size; } std::array<global_coords, 4> neighbors; - uint8_t size; + uint8_t size = 0; }; struct chunk_tiles_cache @@ -91,7 +91,8 @@ public: static bool is_passable(world& w, global_coords coord, Vector2b offset, Vector2ub size, object_id own_id); static bbox make_neighbor_tile_bbox(Vector2i coord, Vector2ub own_size, rotation r); - static neighbors get_walkable_neighbor_tiles(world& w, global_coords pos, Vector2 size, object_id own_id); + static bbox bbox_union(bbox bb, Vector2i coord, Vector2b offset, Vector2ub size); + static neighbors get_walkable_neighbor_tiles(world& w, global_coords coord, Vector2ub size, object_id own_id); }; } // namespace floormat diff --git a/src/world.hpp b/src/world.hpp index bda8d3a4..9b776c5e 100644 --- a/src/world.hpp +++ b/src/world.hpp @@ -98,7 +98,7 @@ public: [[nodiscard]] object_id make_id() { return ++_object_counter; } void set_object_counter(object_id value); - struct neighbor_pair final { chunk* c; chunk_coords_ coord; }; + struct neighbor_pair final { chunk* c = nullptr; chunk_coords_ coord; }; std::array<neighbor_pair, 8> neighbors(chunk_coords_ coord); |