commit 0e9d36b4d1477c6c470d9602f17266d2fc9aacdf
parent 33fb14b033746c208b9acdc695ebc6722715f6e8
Author: Matsuda Kenji <info@mtkn.jp>
Date: Sun, 1 Jan 2023 13:21:40 +0900
add falling status
Diffstat:
3 files changed, 44 insertions(+), 11 deletions(-)
diff --git a/ex8/main.c b/ex8/main.c
@@ -116,7 +116,7 @@ game_play(void)
int fps_count = 0;
#endif
struct timespec ts;
- struct OH *blh[WORLD_WIDTH] = {0}; // block list header
+ struct OH *blh[WORLD_WIDTH]; // block list header
struct OL *blc;
for (int xi = 0; xi < WORLD_WIDTH; xi++)
@@ -141,8 +141,6 @@ game_play(void)
}
while (next_menu == GAME_PLAY){
- clock_gettime(CLOCK_MONOTONIC, &ts);
- t0 = ts.tv_nsec;
receive_events(key_state);
handle_inputs(key_state);
@@ -152,7 +150,7 @@ game_play(void)
for (int k = 0; k < SUB_TICK; k++) {
next_tick(player, 1e9 / FPS / SUB_TICK);
- // game over when fall out of the screen
+ // game over when fall out of the world
if (player->p.y > WORLD_HEIGHT * BLOCK_SIZE) {
next_menu = GAME_OVER;
break;
@@ -170,11 +168,15 @@ game_play(void)
struct OH *collidings;
collidings = create_ol();
+ player_is_falling = 1;
for (int xi = (int) player->p.x / BLOCK_SIZE;
xi <= (int) player->p.x / BLOCK_SIZE + 1 && xi < WORLD_WIDTH;
xi++) {
blc = blh[xi]->first;
while (blc != NULL) {
+ if (is_on_floor_before(player, blc->o)) {
+ player_is_falling = 0;
+ }
if (test_collision(player, blc->o))
append_ol(collidings, blc->o);
blc = blc->next;
@@ -188,6 +190,7 @@ game_play(void)
blc = blc->next;
}
}
+ free_ol(collidings);
}
// fix fps
@@ -230,7 +233,7 @@ game_play(void)
strlen(status_string));
}
for (int xi = 0; xi < WORLD_WIDTH; xi++)
- free_ol(blh[xi]);
+ free_obj_and_ol(blh[xi]);
}
void
@@ -322,13 +325,13 @@ handle_inputs(enum key_state key_state[])
next_menu = GAME_OVER;
return;
}
- if (key_state[KEY_D] == KEY_DOWN) {
+ if (key_state[KEY_D] == KEY_DOWN && key_state[KEY_A] == KEY_UP) {
if (player->v.x > 0) {
player->a.x = 500;
} else {
player->a.x = 1000;
}
- } else if (key_state[KEY_A] == KEY_DOWN) {
+ } else if (key_state[KEY_A] == KEY_DOWN && key_state[KEY_D] == KEY_UP) {
if (player->v.x > 0) {
player->a.x = -1000;
} else {
@@ -349,8 +352,9 @@ handle_inputs(enum key_state key_state[])
if (key_state[KEY_W] == KEY_DOWN)
player->v.y += -300;
*/
- if (!player_is_falling && key_state[KEY_SPACE] == KEY_DOWN)
+ if (!player_is_falling && key_state[KEY_SPACE] == KEY_DOWN) {
player->v.y = -450;
+ }
}
void
diff --git a/ex8/main.h b/ex8/main.h
@@ -46,7 +46,7 @@ struct OH {
};
/*
- * linked list which starts with OH and
+ * linked list which starts with OH and
* terminates with ->next == NULL
*/
struct OL {
@@ -55,6 +55,7 @@ struct OL {
};
struct OH *create_ol(void);
void free_ol(struct OH *);
+void free_obj_and_ol(struct OH *);
void append_ol(struct OH *, struct Object *);
void swap_ol(struct OL *, struct OL *);
void sort_ol(struct OH *, struct Object *);
@@ -84,6 +85,7 @@ void handle_collision_mf(struct Object *, struct Object *);
int object_is_falling(struct Object *o, struct Object *fb, int num_f);
struct Object *create_object(float, float, float, float, float, float,
int, int, int);
+int is_on_floor_before(struct Object *, struct Object *);
/*
* x.c
*/
diff --git a/ex8/util.c b/ex8/util.c
@@ -78,7 +78,7 @@ rect_next_tick(struct Object *o, long ndt)
if (o->shape != SRECTANGLE) {
fprintf(stderr, "rect_next_tick: invalid object shape\n");
return;
- }
+ }
o->pp.x = o->p.x;
o->pp.y = o->p.y;
o->v.x += o->a.x * ndt / 1e9;
@@ -176,7 +176,6 @@ free_ol(struct OH *oh)
ol0 = ol1 = oh->first;
while (ol1 != NULL) {
ol1 = ol0->next;
- free(ol0->o);
free(ol0);
ol0 = ol1;
}
@@ -184,6 +183,22 @@ free_ol(struct OH *oh)
}
void
+free_obj_and_ol(struct OH *oh)
+{
+ if (oh == NULL)
+ return;
+ struct OL *ol0, *ol1;
+ ol0 = ol1 = oh->first;
+ while (ol1 != NULL) {
+ ol1 = ol0->next;
+ free(ol0->o);
+ free(ol0);
+ ol0 = ol1;
+ }
+
+}
+
+void
append_ol(struct OH *oh, struct Object *o)
{
struct OL *cur;
@@ -231,3 +246,15 @@ object_dist(struct Object *o1, struct Object *o2)
return (o1->p.x - o2->p.x) * (o1->p.x - o2->p.x) +
(o1->p.y - o2->p.y) * (o1->p.y - o2->p.y);
}
+
+int
+is_on_floor_before(struct Object *player, struct Object *floor)
+{
+ struct Object o = *player;
+ o.p.x = o.pp.x; o.p.y = o.pp.y;
+ o.v.x = 0; o.v.y = 5;
+ o.a.x = 0; o.a.y = 0;
+ next_tick(&o, 1e9);
+ int col = test_collision(&o, floor);
+ return col;
+}