From e3add266417e2bfbfaa51a9e0682166289e185db Mon Sep 17 00:00:00 2001 From: aratama <16192627+aratama@users.noreply.github.com> Date: Sun, 17 Nov 2024 04:24:58 +0900 Subject: [PATCH] homing --- .github/workflows/release.yaml | 14 ++------- src/cast.rs | 7 +++++ src/controller/remote.rs | 4 +++ src/enemy/basic.rs | 1 + src/entity/actor.rs | 1 + src/entity/bullet.rs | 33 ++++++++++++++++++++- src/entity/witch.rs | 52 ++++------------------------------ src/spell.rs | 1 + src/spell_props.rs | 18 +++++++++--- src/ui/inventory.rs | 7 ++--- src/world.rs | 51 ++++++++++++++++++++++++++++++++- 11 files changed, 119 insertions(+), 70 deletions(-) diff --git a/.github/workflows/release.yaml b/.github/workflows/release.yaml index 281aa789..afe12af5 100644 --- a/.github/workflows/release.yaml +++ b/.github/workflows/release.yaml @@ -7,13 +7,6 @@ on: branches: ["main"] env: - # update with the name of the main binary - # binary: bevy_github_ci_template - # add_binaries_to_github_release: true - #itch_target: / - - # Before enabling LFS, please take a look at GitHub's documentation for costs and quota limits: - # https://docs.github.com/en/repositories/working-with-files/managing-large-files/about-storage-and-bandwidth-usage use_git_lfs: false jobs: @@ -24,16 +17,13 @@ jobs: steps: - uses: olegtarasov/get-tag@v2.1.2 id: get_version + - uses: actions/checkout@v4 - with: - lfs: ${{ env.use_git_lfs }} + - uses: dtolnay/rust-toolchain@stable with: targets: wasm32-unknown-unknown - - name: install target wasm - run: rustup target add wasm32-unknown-unknown - - name: install trunk run: cargo install --locked trunk diff --git a/src/cast.rs b/src/cast.rs index ac326ab0..7f6e7a1a 100644 --- a/src/cast.rs +++ b/src/cast.rs @@ -89,9 +89,11 @@ pub fn cast_spell( light_intensity, light_radius, light_color_hlsa, + homing: actor.homing, }, ); actor.bullet_speed_buff_factor = 0.0; + actor.homing = 0.0; wand.shift(); return props.cast_delay as i32; @@ -133,6 +135,11 @@ pub fn cast_spell( } return delay; } + SpellCast::Homing => { + wand.shift(); + actor.homing = (actor.homing + 0.01).max(-0.1).min(0.1); + return props.cast_delay as i32; + } } } else { wand.shift(); diff --git a/src/controller/remote.rs b/src/controller/remote.rs index 78e89203..606622b4 100644 --- a/src/controller/remote.rs +++ b/src/controller/remote.rs @@ -79,6 +79,7 @@ pub enum RemoteMessage { light_intensity: f32, light_radius: f32, light_color_hlsa: [f32; 4], + homing: f32, }, // ダメージを受けたことを通知します Hit { @@ -257,6 +258,7 @@ fn receive_events( 3.0, &audio, false, + [None, None, None, None], ); info!("Remote player spawned: {}", uuid); } @@ -276,6 +278,7 @@ fn receive_events( light_intensity, light_radius, light_color_hlsa, + homing, } => { spawn_bullet( &mut commands, @@ -295,6 +298,7 @@ fn receive_events( light_intensity, light_radius, light_color_hlsa, + homing, }, ); } diff --git a/src/enemy/basic.rs b/src/enemy/basic.rs index 4e0c333e..aa3418fc 100644 --- a/src/enemy/basic.rs +++ b/src/enemy/basic.rs @@ -47,6 +47,7 @@ pub fn spawn_basic_enemy( filter: ENTITY_GROUP | WALL_GROUP | WITCH_GROUP, current_wand: 0, bullet_speed_buff_factor: 0.0, + homing: 0.0, wands: [ Some(Wand { wand_type: WandType::CypressWand, diff --git a/src/entity/actor.rs b/src/entity/actor.rs index d8eb039d..bba4e32a 100644 --- a/src/entity/actor.rs +++ b/src/entity/actor.rs @@ -57,6 +57,7 @@ pub struct Actor { pub bullet_speed_buff_factor: f32, // マルチキャストで待機中の弾丸 // pub multicasts: Vec, + pub homing: f32, } impl Actor { diff --git a/src/entity/bullet.rs b/src/entity/bullet.rs index c4457b10..f52046fb 100644 --- a/src/entity/bullet.rs +++ b/src/entity/bullet.rs @@ -1,5 +1,6 @@ use crate::asset::GameAssets; use crate::command::GameCommand; +use crate::controller::enemy::Enemy; use crate::controller::remote::{RemoteMessage, RemotePlayer}; use crate::entity::actor::Actor; use crate::entity::breakable::Breakable; @@ -33,6 +34,7 @@ pub struct Bullet { damage: i32, impulse: f32, owner: Option, + homing: f32, } #[derive(Bundle)] @@ -73,6 +75,7 @@ pub fn spawn_bullets( light_intensity: props.light_intensity, light_radius: props.light_radius, light_color_hlsa: props.light_color_hlsa, + homing: props.homing, }) .unwrap(); writer.send(ClientMessage::Binary(serialized)); @@ -93,6 +96,7 @@ pub struct SpawnBulletProps { pub light_intensity: f32, pub light_radius: f32, pub light_color_hlsa: [f32; 4], + pub homing: f32, } /// 指定された位置、方向、弾丸種別などから実際にエンティティを生成します @@ -112,6 +116,7 @@ pub fn spawn_bullet( damage: spawning.damage, impulse: spawning.impulse, owner: spawning.owner, + homing: spawning.homing, }, EntityDepth, AsepriteSliceBundle { @@ -178,6 +183,32 @@ fn despawn_bullet_by_lifetime( } } +fn bullet_homing( + mut bullet_query: Query<(&mut Bullet, &mut Transform, &mut Velocity)>, + enemy_query: Query<&Transform, (With, Without)>, +) { + for (bullet, mut bullet_transform, mut velocity) in bullet_query.iter_mut() { + if 0.0 < bullet.homing { + let bullet_position = bullet_transform.translation.truncate(); + let mut enemies = Vec::from_iter(enemy_query.iter()); + enemies.sort_by(|a, b| { + let x = a.translation.truncate().distance(bullet_position); + let y = b.translation.truncate().distance(bullet_position); + x.total_cmp(&y) + }); + if let Some(nearest) = enemies.first() { + let bullet_angle = velocity.linvel.to_angle(); + let target_angle = (nearest.translation.truncate() - bullet_position).to_angle(); + let angle_diff = target_angle - bullet_angle; + let next_angle = angle_diff.signum() * angle_diff.abs().min(bullet.homing); + velocity.linvel = + Vec2::from_angle(bullet_angle + next_angle) * velocity.linvel.length(); + bullet_transform.rotation = Quat::from_rotation_z(velocity.linvel.to_angle()); + } + } + } +} + fn bullet_collision( mut commands: Commands, mut bullet_query: Query<(Entity, &mut Bullet, &Transform, &Velocity)>, @@ -333,7 +364,7 @@ impl Plugin for BulletPlugin { fn build(&self, app: &mut App) { app.add_systems( FixedUpdate, - (despawn_bullet_by_lifetime, bullet_collision) + (despawn_bullet_by_lifetime, bullet_collision, bullet_homing) .run_if(in_state(GameState::InGame)) .before(PhysicsSet::SyncBackend), ); diff --git a/src/entity/witch.rs b/src/entity/witch.rs index 3376cb07..80195921 100644 --- a/src/entity/witch.rs +++ b/src/entity/witch.rs @@ -5,9 +5,8 @@ use crate::entity::breakable::{Breakable, BreakableSprite}; use crate::entity::EntityDepth; use crate::hud::life_bar::{spawn_life_bar, LifeBarResource}; use crate::interaction_sensor::spawn_interaction_sensor; -use crate::spell::SpellType; use crate::states::GameState; -use crate::wand::{Wand, WandType}; +use crate::wand::Wand; use crate::wand_props::wand_to_props; use bevy::prelude::*; use bevy_aseprite_ultra::prelude::*; @@ -48,6 +47,8 @@ pub fn spawn_witch( footstep_audio: &Res