summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/Entities/Player.cpp32
1 files changed, 15 insertions, 17 deletions
diff --git a/src/Entities/Player.cpp b/src/Entities/Player.cpp
index fd22247..7a415ec 100644
--- a/src/Entities/Player.cpp
+++ b/src/Entities/Player.cpp
@@ -1,5 +1,7 @@
 #include "Player.hpp"
 
+#include <unordered_set>
+
 namespace MC::Entities {
 
 void Player::update(const Time& time, GFX::Window& window, GFX::Camera& camera, World::World& world) {
@@ -91,7 +93,7 @@ std::vector<AABB> Player::terrain_collision_domain(
     // Make the box a bit bigger so we don't clip through blocks.
     auto domain_box = bounding_box_for_position(from)
         .unite(bounding_box_for_position(to))
-        .unite(AABB{{1, 1, 1}});
+        .sum(AABB{{1, 1, 1}});
 
     std::vector<AABB> colliding_blocks;
 
@@ -100,25 +102,21 @@ std::vector<AABB> Player::terrain_collision_domain(
     // This will be more efficient and actually accurate,
     // since right now if you're fast enough you can clip
     // through whole chunks.
-    auto add_colliding = [&](Position::World chunk_pos, Position::BlockLocal pos, World::Chunk::BlockData& b) {
-        if (!b.type.is_solid()) return;
-        auto block_bounds = World::Chunk::block_bounds(pos).offset(chunk_pos);
-        if (domain_box.collides(block_bounds)) colliding_blocks.push_back(block_bounds);
-    };
 
-    auto chunk_from = world.chunks().find(to);
-    if (chunk_from.chunk.has_value()) {
-        auto position = chunk_from.chunk.value().position();
-        chunk_from.chunk->for_each([&](auto p, auto b) { add_colliding(position, p, b); });
+    std::unordered_set<World::ChunkIndex> chunks_to_check;
+    for (auto corner : domain_box.corners()) {
+        chunks_to_check.insert(World::ChunkIndex::from_position(corner));
     }
 
-    if (World::ChunkIndex::from_position(to) == World::ChunkIndex::from_position(from))
-        return colliding_blocks;
-
-    auto chunk_to = world.chunks().find(to);
-    if (chunk_to.chunk.has_value()) {
-        auto position = chunk_to.chunk.value().position();
-        chunk_to.chunk->for_each([&](auto p, auto b) { add_colliding(position, p, b); });
+    for (auto chunk_index : chunks_to_check) {
+        auto chunk = world.chunks().get(chunk_index);
+        if (!chunk.chunk.has_value()) continue;
+        auto chunk_position = chunk.chunk.value().position();
+        chunk.chunk->for_each([&](auto p, auto b) {
+            if (!b.type.is_solid()) return;
+            auto block_bounds = World::Chunk::block_bounds(p).offset(chunk_position);
+            if (domain_box.collides(block_bounds)) colliding_blocks.push_back(block_bounds);
+        });
     }
 
     return colliding_blocks;