From fc678c6b428dc5279243175663054a1f153d5dc0 Mon Sep 17 00:00:00 2001 From: "Zed A. Shaw" Date: Sun, 31 Aug 2025 00:17:47 -0400 Subject: [PATCH] Pathing in either diagonal or simple motion works. --- Makefile | 4 ++-- pathing.cpp | 31 ++++++++++++++++++++++--------- tests/pathing.cpp | 19 ++++++++++--------- 3 files changed, 34 insertions(+), 20 deletions(-) diff --git a/Makefile b/Makefile index b764430..8d1605e 100644 --- a/Makefile +++ b/Makefile @@ -37,7 +37,7 @@ tracy_build: meson compile -j 10 -C builddir test: asset_build build - ./builddir/runtests -d yes "[pathing]" + ./builddir/runtests -d yes run: build test ifeq '$(OS)' 'Windows_NT' @@ -60,7 +60,7 @@ clean: meson compile --clean -C builddir debug_test: build - gdb --nx -x .gdbinit --ex run --ex bt --ex q --args builddir/runtests -e "[pathing]" + gdb --nx -x .gdbinit --ex run --ex bt --ex q --args builddir/runtests -e win_installer: powershell 'start "C:\Program Files (x86)\solicus\InstallForge\bin\ifbuilderenvx86.exe" scripts\win_installer.ifp' diff --git a/pathing.cpp b/pathing.cpp index 756206c..8805f20 100644 --- a/pathing.cpp +++ b/pathing.cpp @@ -76,29 +76,42 @@ void Pathing::clear_target(const Point &at) { PathingResult Pathing::find_path(Point &out, int direction, bool diag) { - (void)diag; - // get the current dijkstra number int cur = $paths[out.y][out.x]; int target = cur; bool found = false; - // go through all possible directions - for(matrix::box it{$paths, out.x, out.y, 1}; it.next();) { - target = $paths[it.y][it.x]; + // a lambda makes it easy to capture what we have to change + auto next_step = [&](size_t x, size_t y) -> bool { + target = $paths[y][x]; // don't go through walls - if(target == WALL_PATH_LIMIT) continue; + if(target == WALL_PATH_LIMIT) return false; int weight = cur - target; if(weight == direction) { - out = {(size_t)it.x, (size_t)it.y}; + out = {x, y}; found = true; - break; + return true; } else if(weight == 0) { - out = {(size_t)it.x, (size_t)it.y}; + out = {x, y}; found = true; } + + return false; + }; + + + if(diag) { + for(matrix::box it{$paths, out.x, out.y, 1}; it.next();) { + bool should_stop = next_step(it.x, it.y); + if(should_stop) break; + } + } else { + for(matrix::compass it{$paths, out.x, out.y}; it.next();) { + bool should_stop = next_step(it.x, it.y); + if(should_stop) break; + } } if(target == 0) { diff --git a/tests/pathing.cpp b/tests/pathing.cpp index 2b092b0..aa9c9cd 100644 --- a/tests/pathing.cpp +++ b/tests/pathing.cpp @@ -8,6 +8,7 @@ #include "game_level.hpp" #include #include +#include "rand.hpp" using namespace fmt; using namespace nlohmann; @@ -46,25 +47,25 @@ TEST_CASE("multiple targets can path", "[pathing]") { }); paths.compute_paths(walls_copy); + bool diag = Random::uniform(0, 1); auto pos = GameDB::player_position().location; - auto found = paths.find_path(pos, PATHING_TOWARD, false); + auto found = paths.find_path(pos, PATHING_TOWARD, diag); while(found == PathingResult::CONTINUE) { - fmt::println("\033[2J\033[1;1H"); - matrix::dump("failed paths", paths.$paths, pos.x, pos.y); + // fmt::println("\033[2J\033[1;1H"); + // matrix::dump(diag ? "diag" : "simple", paths.$paths, pos.x, pos.y); std::this_thread::sleep_for(200ms); - found = paths.find_path(pos, PATHING_TOWARD, false); + found = paths.find_path(pos, PATHING_TOWARD, diag); } - fmt::println("\033[2J\033[1;1H"); - matrix::dump("failed paths", paths.$paths, pos.x, pos.y); + // fmt::println("\033[2J\033[1;1H"); + // matrix::dump(diag ? "diag" : "simple", paths.$paths, pos.x, pos.y); if(found == PathingResult::FOUND) { fmt::println("FOUND!"); - } else if(found == PathingResult::FAIL) { - fmt::println("FAILED!"); - std::this_thread::sleep_for(20000ms); + } else if(found == PathingResult::FAIL && !diag) { + REQUIRE(found != PathingResult::FAIL); } }