From 06d41e932bb6c671dd7eb784c99e268e7aa239e7 Mon Sep 17 00:00:00 2001 From: Lukas Krickl Date: Thu, 5 Mar 2026 05:11:40 +0100 Subject: [PATCH] math: added function to reverse isometric transformation. This function will of course lose some data if applied since we only work with integers, but in general it is close enough. --- src/tests/t_math.c | 33 +++++++++++++++++++++++++++++---- src/u_math.c | 2 +- 2 files changed, 30 insertions(+), 5 deletions(-) diff --git a/src/tests/t_math.c b/src/tests/t_math.c index 8323229..9593985 100644 --- a/src/tests/t_math.c +++ b/src/tests/t_math.c @@ -22,19 +22,44 @@ int t_test_tile_to_screen(void) { } int t_test_point_to_world_world_to_point(void) { - struct u_vec2 res = u_point_to_screen(1, 2); - T_ASSERT(res.x == -2 && res.y == 1, ("point to screen %d/%d\n", res.x, res.y)); + struct u_vec2 res; + i32 x, y; + const i32 check_max = 1024 * 8; + + /* 1 */ + res = u_point_to_screen(4, 2); + T_ASSERT(res.x == 0 && res.y == 2, ("point to screen %d/%d\n", res.x, res.y)); res = u_point_to_world(res.x, res.y); - T_ASSERT(res.x == 1 && res.y == 2, ("point to world %d/%d\n", res.x, res.y)); - + T_ASSERT(res.x == 4 && res.y == 2, ("point to world %d/%d\n", res.x, res.y)); + /* 2 */ res = u_point_to_screen(32, 64); T_ASSERT(res.x == -48 && res.y == 40, ("point to screen %d/%d\n", res.x, res.y)); res = u_point_to_world(res.x, res.y); T_ASSERT(res.x == 32 && res.y == 64, ("point to world %d/%d\n", res.x, res.y)); + /* 3 */ + res = u_point_to_screen(256, 128); + T_ASSERT(res.x == 0 && res.y == 128, ("point to screen %d/%d\n", res.x, res.y)); + + res = u_point_to_world(res.x, res.y); + T_ASSERT(res.x == 256 && res.y == 128, ("point to world %d/%d\n", res.x, res.y)); + + /* test all points + * tiles on the grid line should work fine + * all other tiles might lose data when transforming back + * because it is all integer coordinates + */ + for (x = -check_max; x < check_max; x += R_TILE_W) { + for (y = -check_max; y < check_max; y += R_TILE_H) { + res = u_point_to_screen(x, y); + res = u_point_to_world(res.x, res.y); + T_ASSERT(res.x == x && res.y == y, ("point to world from %d/%d to %d/%d\n", x, y, res.x, res.y)); + } + } + return 0; } diff --git a/src/u_math.c b/src/u_math.c index 4ddfb88..e266bcf 100644 --- a/src/u_math.c +++ b/src/u_math.c @@ -26,8 +26,8 @@ struct u_vec2 u_point_to_screen(i32 x, i32 y) { struct u_vec2 u_point_to_world(i32 x, i32 y) { struct u_vec2 r; - r.x = (y + x); r.y = (2 * y - x) / 2; + r.x = (x + 2 * y); return r; } -- 2.30.2