player_entity.c 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122
  1. #include "player_entity.h"
  2. #include "../../engine/game_manager.h"
  3. #include "../../game.h"
  4. #include "level_game.h"
  5. #define PLAYER_SIZE 6
  6. #define PLAYER_SPEED 1
  7. #define PLAYER_INITIAL_X 64
  8. #define PLAYER_INITIAL_Y 32
  9. #define PLAYER_ANIMATION_DURATION 15.0f
  10. Entity*
  11. player_spawn(Level* level, GameManager* manager)
  12. {
  13. Entity* player = level_add_entity(level, &player_description);
  14. // Set position and collider rect
  15. entity_pos_set(player, (Vector){ PLAYER_INITIAL_X, PLAYER_INITIAL_Y });
  16. entity_collider_add_rect(player, PLAYER_SIZE, PLAYER_SIZE);
  17. // Load player sprite
  18. PlayerContext* player_context = entity_context_get(player);
  19. player_context->sprite = game_manager_sprite_load(manager, "player.fxbm");
  20. return player;
  21. }
  22. void
  23. player_respawn(Entity* player)
  24. {
  25. // Set player position.
  26. entity_pos_set(player, (Vector){ PLAYER_INITIAL_X, PLAYER_INITIAL_Y });
  27. // Reset animation
  28. PlayerContext* player_context = entity_context_get(player);
  29. player_context->time = 0.0f;
  30. }
  31. static void
  32. player_update(Entity* self, GameManager* manager, void* _entity_context)
  33. {
  34. // Check pause
  35. Level* level = game_manager_current_level_get(manager);
  36. GameLevelContext* level_context = level_context_get(level);
  37. if (level_context->is_paused) {
  38. return;
  39. }
  40. // Start level animation
  41. PlayerContext* player = _entity_context;
  42. if (player->time < PLAYER_ANIMATION_DURATION) {
  43. player->time += 1.0f;
  44. return;
  45. }
  46. InputState input = game_manager_input_get(manager);
  47. Vector pos = entity_pos_get(self);
  48. // Control player movement
  49. if (input.held & GameKeyUp)
  50. pos.y -= PLAYER_SPEED;
  51. if (input.held & GameKeyDown)
  52. pos.y += PLAYER_SPEED;
  53. if (input.held & GameKeyLeft)
  54. pos.x -= PLAYER_SPEED;
  55. if (input.held & GameKeyRight)
  56. pos.x += PLAYER_SPEED;
  57. // Clamp player position to screen bounds, and set it
  58. pos.x = CLAMP(pos.x, 125, 3);
  59. pos.y = CLAMP(pos.y, 61, 3);
  60. entity_pos_set(self, pos);
  61. // Control game pause
  62. if (input.pressed & GameKeyBack) {
  63. pause_game(level);
  64. }
  65. }
  66. static void
  67. player_render(Entity* self,
  68. GameManager* manager,
  69. Canvas* canvas,
  70. void* _entity_context)
  71. {
  72. PlayerContext* player = _entity_context;
  73. // Draw initial animation
  74. if (player->time < PLAYER_ANIMATION_DURATION) {
  75. float step = 61 / PLAYER_ANIMATION_DURATION;
  76. float left_x = player->time * step;
  77. float right_x = 122 - left_x;
  78. left_x = CLAMP(left_x, 61, 0);
  79. right_x = CLAMP(right_x, 122, 61);
  80. canvas_draw_sprite(canvas, player->sprite, left_x, 29);
  81. canvas_draw_sprite(canvas, player->sprite, right_x, 29);
  82. return;
  83. }
  84. // Draw player sprite
  85. Vector pos = entity_pos_get(self);
  86. canvas_draw_sprite(canvas, player->sprite, pos.x - 3, pos.y - 3);
  87. // Draw score
  88. GameContext* game_context = game_manager_game_context_get(manager);
  89. canvas_printf_aligned(
  90. canvas, 64, 0, AlignCenter, AlignTop, "%lu", game_context->score);
  91. }
  92. const EntityDescription player_description = {
  93. .start = NULL,
  94. .stop = NULL,
  95. .update = player_update,
  96. .render = player_render,
  97. .collision = NULL,
  98. .event = NULL,
  99. .context_size = sizeof(PlayerContext),
  100. };