diff options
Diffstat (limited to 'src/player.odin')
| -rw-r--r-- | src/player.odin | 61 |
1 files changed, 55 insertions, 6 deletions
diff --git a/src/player.odin b/src/player.odin index 7233278..c758f31 100644 --- a/src/player.odin +++ b/src/player.odin @@ -1,6 +1,10 @@ package demonchime import "core:math" +import "core:math/linalg" +import "core:log" + +import rl "vendor:raylib" import "phys" @@ -16,6 +20,9 @@ PLAYER_DASH_SPEED :: 500 PLAYER_DASH_TIME :: 0.15 PLAYER_DASH_COOLDOWN :: 0.3 +PLAYER_GUN_HEIGHT :: 7 +PLAYER_GUN_DIST :: 5 // how far out to hold the gun + Player_State :: enum { DEFAULT, DASH, @@ -25,6 +32,7 @@ Player_State :: enum { player: struct { body_handle: phys.Body_Handle, sprite: Sprite, + gun_sprite: Sprite, jump_buffer: f32, coyote_time: f32, dash_cooldown: f32, @@ -35,7 +43,11 @@ player: struct { } init_player :: proc() { - handle, body := phys.make_body(phys.Rect{{-4, 17}, {8, 16}}) + handle, body := phys.make_body( + phys.Rect{{-4, -16}, {8, 16}}, + layers = {.PLAYER}, + mask = {.DEFAULT} + ) player.body_handle = handle phys.set_body_position(handle, Vec2{50, 100}) @@ -44,14 +56,19 @@ init_player :: proc() { player.sprite.offset = Vec2 { math.floor(f32(player.sprite.width / 2)), - -f32(player.sprite.height), + f32(player.sprite.height), + } + + init_sprite(&player.gun_sprite, .PISTOL) + + player.gun_sprite.offset = Vec2 { + -PLAYER_GUN_DIST, + math.round(f32(player.gun_sprite.height / 2)), } } -delete_player :: proc() { +deinit_player :: proc() { phys.remove_body(player.body_handle) - - destroy_sprite(player.sprite) } @(private = "file") @@ -74,7 +91,6 @@ _default_state :: proc(dt: f32) { if input != 0 { set_sprite_active_tag(&player.sprite, "run") - player.sprite.scale.x = math.sign(input) } else { set_sprite_active_tag(&player.sprite, "idle") } @@ -104,6 +120,27 @@ _default_state :: proc(dt: f32) { } } + rel_mouse_pos := get_mouse_pos() - body.pos + + if is_keybind_just_down(actions.shoot) { + mouse_dir := linalg.normalize0(rel_mouse_pos) + + bullet_pos := body.pos + bullet_pos.y -= PLAYER_GUN_HEIGHT + bullet_pos += mouse_dir * PLAYER_GUN_DIST + + make_bullet( + bullet_pos, + mouse_dir * 200, + ) + + // `make_bullet()` adds a new physics body, which could invalidate the + // pointer to our body when the body array reallocs + body = phys.get_body(player.body_handle) + } + + player.sprite.scale.x = math.sign(rel_mouse_pos.x) + if player.jump_buffer > 0 { if player.coyote_time > 0 { body.vel.y = -PLAYER_JUMP_FORCE @@ -184,6 +221,7 @@ _change_rooms :: proc() { new_room_pos := Vec2{f32(current_room.x), f32(current_room.y)} diff := prev_room_pos - new_room_pos + body = phys.get_body(player.body_handle) new_pos := body.pos + diff - {0, 0} phys.set_body_position(player.body_handle, new_pos) } @@ -201,6 +239,16 @@ update_player :: proc(dt: f32) { player.sprite.pos = body.pos update_sprite(&player.sprite, dt) + player.gun_sprite.pos = body.pos - Vec2{0, PLAYER_GUN_HEIGHT} + + mouse_dir := get_mouse_pos() - player.gun_sprite.pos + player.gun_sprite.rotation = math.atan2( + mouse_dir.y, + mouse_dir.x, + ) * math.DEG_PER_RAD + + player.gun_sprite.scale.y = -1 if mouse_dir.x < 0 else 1 + player.dash_cooldown -= dt player.jump_buffer -= dt player.coyote_time -= dt @@ -210,6 +258,7 @@ update_player :: proc(dt: f32) { draw_player :: proc() { draw_sprite(player.sprite) + draw_sprite(player.gun_sprite) } @(private = "file") |
