commit e42269fa3745f6c6610263ee5bd8d58fcefd3ff0
parent 3418f76c8a1741b85df476212d4375f860c9c9bc
Author: amin <dev@aminmesbah.com>
Date: Fri, 26 Apr 2019 01:01:43 +0000
Move between two rooms
FossilOrigin-Name: 0187b03d62d68adcc2c345b422673cb3f107029d259327c8404f09de952c5a18
Diffstat:
3 files changed, 89 insertions(+), 6 deletions(-)
diff --git a/src/game.c b/src/game.c
@@ -4,6 +4,8 @@
// One tile is one square meter
#define TILE_SIZE 1.0f
+// TODO: delete
+#define NUM_ROOMS 2
#ifdef PLATFORM_HOTLOAD_GAME_CODE
void game_load_opengl_symbols(void)
@@ -16,8 +18,13 @@ internal void game_init(struct GameMemory *game_memory, v2u framebuffer)
{
struct GameState *game_state = game_memory->game_state;
+ game_state->player_pos_absolute = (struct AbsolutePos) {
+ .room_index = {0, 0},
+ .room_offset = {12.5f, 5.0f},
+ };
+
// init player
- game_state->player.pos = (v2) {12.5f, 5.0f};
+ game_state->player.pos = game_state->player_pos_absolute.room_offset;
// In Knytt, the player is 9 by 14 texels and a tile is 24 by 24 texels.
// These dimensions are relative to a square 'meter', one tile
@@ -85,6 +92,58 @@ internal void game_init(struct GameMemory *game_memory, v2u framebuffer)
}
}
+internal struct AbsolutePos pos_recanonicalize(struct AbsolutePos p)
+{
+ struct AbsolutePos p_final = p;
+ v2i room_index_delta = {0};
+
+ if (p.room_offset.x < 0.0f)
+ {
+ room_index_delta.x -= 1;
+ p_final.room_offset.x = glmth_wrap(p.room_offset.x, 0.0f, ROOM_TILE_DIM_X);
+ }
+ else if (p.room_offset.x > ROOM_TILE_DIM_X)
+ {
+ room_index_delta.x += 1;
+ p_final.room_offset.x = glmth_wrap(p.room_offset.x, 0.0f, ROOM_TILE_DIM_X);
+ }
+
+ if (p.room_offset.y < 0.0f)
+ {
+ room_index_delta.y -= 1;
+ p_final.room_offset.y = glmth_wrap(p.room_offset.y, 0.0f, ROOM_TILE_DIM_Y);
+ }
+ else if (p.room_offset.y > ROOM_TILE_DIM_Y)
+ {
+ room_index_delta.y += 1;
+ p_final.room_offset.y = glmth_wrap(p.room_offset.y, 0.0f, ROOM_TILE_DIM_Y);
+ }
+
+ p_final.room_index = glmth_v2i_a(p.room_index, room_index_delta);
+ return p_final;
+}
+
+struct RoomSearchResult
+{
+ bool room_found;
+ size_t room_array_index;
+};
+
+internal struct RoomSearchResult get_room_at_index(struct Room *rooms[NUM_ROOMS], u32 num_rooms, v2i room_i)
+{
+ struct RoomSearchResult result = {0};
+ for (size_t i = 0; i < num_rooms; i++)
+ {
+ struct Room *r = rooms[i];
+ if (r->index.x == room_i.x && r->index.y == room_i.y)
+ {
+ result.room_found = true;
+ result.room_array_index = i;
+ }
+ }
+ return result;
+}
+
struct WallCollision
{
bool collision_occurred;
@@ -320,8 +379,15 @@ void game_update_and_render(struct GameMemory *game_memory, struct GameInput *ga
},
};
- u32 *tiles = knytt_hanging_fly_village.tiles;
- tiles = collision_test_zone.tiles;
+ // TODO: This is, of course, just temporary. Delete it.
+ struct Room *rooms[NUM_ROOMS] = {&collision_test_zone, &knytt_hanging_fly_village};
+
+ v2i current_room_i = game_state->player_pos_absolute.room_index;
+ struct RoomSearchResult r = get_room_at_index(rooms, NUM_ROOMS, current_room_i);
+ assert(r.room_found);
+ struct Room *current_room = rooms[r.room_array_index];
+ assert(current_room);
+ u32 *tiles = current_room->tiles;
// render tiles
{
@@ -377,7 +443,8 @@ void game_update_and_render(struct GameMemory *game_memory, struct GameInput *ga
if (player_is_in_tile && solid)
{
color = (v3) {0.8f, 0.4f, 0.4f};
- assert(false);
+ // TODO: re-enable this
+ //assert(false);
}
}
@@ -610,8 +677,11 @@ void game_update_and_render(struct GameMemory *game_memory, struct GameInput *ga
}
}
#undef RENDER_COLLISION_DEBUG_QUAD
- glmth_clamp(&player->pos.x, 0.0f, ROOM_TILE_DIM_X);
- glmth_clamp(&player->pos.y, 0.0f, ROOM_TILE_DIM_Y);
+
+ game_state->player_pos_absolute.room_offset = player->pos;
+ struct AbsolutePos new_canonical_p = pos_recanonicalize(game_state->player_pos_absolute);
+ game_state->player_pos_absolute = new_canonical_p;
+ player->pos = game_state->player_pos_absolute.room_offset;
}
// render player
diff --git a/src/game.h b/src/game.h
@@ -39,10 +39,17 @@ struct Room
u32 tiles[ROOM_TILE_DIM_Y * ROOM_TILE_DIM_X];
};
+struct AbsolutePos
+{
+ v2i room_index;
+ v2 room_offset;
+};
+
struct GameState
{
struct RendererState renderer;
struct Entity player;
+ struct AbsolutePos player_pos_absolute;
};
internal void game_init(struct GameMemory *game_memory, v2u framebuffer);
diff --git a/src/glmth.h b/src/glmth.h
@@ -187,6 +187,12 @@ internal inline f32 glmth_v2_dot(v2 vec1, v2 vec2)
return dot_product;
}
+internal inline v2i glmth_v2i_a(v2i vec1, v2i vec2)
+{
+ v2i r = {vec1.x + vec2.x, vec1.y + vec2.y};
+ return r;
+}
+
internal inline v3 glmth_v3_cross(v3 vec1, v3 vec2)
{
// cross product, a.k.a. outer product or vector product