Compare commits
3 commits
03b59593b7
...
48c13347fe
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
48c13347fe | ||
|
|
6b2d5d8af1 | ||
|
|
9f490974a4 |
2 changed files with 89 additions and 1 deletions
22
src/health/event.rs
Normal file
22
src/health/event.rs
Normal file
|
|
@ -0,0 +1,22 @@
|
||||||
|
use bevy::prelude::*;
|
||||||
|
|
||||||
|
use crate::health::Health;
|
||||||
|
|
||||||
|
/// Event that is called on entities when they should recieve damage
|
||||||
|
#[derive(EntityEvent)]
|
||||||
|
pub struct Damage {
|
||||||
|
entity: Entity,
|
||||||
|
damage: usize
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Marker-component that marks entity for an automatic damage handling
|
||||||
|
#[derive(Component)]
|
||||||
|
#[require(Health)]
|
||||||
|
pub struct Vulnerable;
|
||||||
|
|
||||||
|
/// Damages every vulnerable health components.
|
||||||
|
pub(super) fn damage_vulnerable_system(event: On<Damage>, mut health_query: Query<&mut Health,With<Vulnerable>>) {
|
||||||
|
if let Ok(mut health) = health_query.get_mut(event.entity) {
|
||||||
|
health.damage(event.damage);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -1,9 +1,75 @@
|
||||||
use bevy::prelude::*;
|
use bevy::prelude::*;
|
||||||
|
|
||||||
|
use event::damage_vulnerable_system;
|
||||||
|
|
||||||
|
pub use event::{Damage,Vulnerable};
|
||||||
|
|
||||||
|
pub mod event;
|
||||||
|
|
||||||
|
/// Health plugin provides systems to handle health modifications and events
|
||||||
pub struct HealthPlugin;
|
pub struct HealthPlugin;
|
||||||
|
|
||||||
impl Plugin for HealthPlugin {
|
impl Plugin for HealthPlugin {
|
||||||
fn build(&self, app: &mut App) {
|
fn build(&self, app: &mut App) {
|
||||||
//todo!()
|
app.add_systems(PostUpdate,cleanup_killed).add_observer(damage_vulnerable_system);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Component that holds health points and max health points of entity
|
||||||
|
#[derive(Component)]
|
||||||
|
pub struct Health {
|
||||||
|
health: usize,
|
||||||
|
max_health: usize,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Default for Health {
|
||||||
|
fn default() -> Self {
|
||||||
|
Self { health: 1, max_health: 1 }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Health {
|
||||||
|
/// Create new health component with set 'health' and 'max_health'.
|
||||||
|
pub fn new(health: usize, max_health: usize) -> Self {
|
||||||
|
Self {
|
||||||
|
health,
|
||||||
|
max_health
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/// Create new health component from max health.
|
||||||
|
pub fn from_max(max_health: usize) -> Self {
|
||||||
|
Self {
|
||||||
|
health: max_health,
|
||||||
|
max_health
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Substract 'damage' amount of health points from component with boundary check.
|
||||||
|
pub fn damage(&mut self, damage: usize) {
|
||||||
|
self.health = if damage > self.health {0} else {self.health - damage};
|
||||||
|
}
|
||||||
|
/// Add 'heal' amount of health points to component with max health as a boundary.
|
||||||
|
pub fn heal_no_overheal(&mut self, heal: usize) {
|
||||||
|
self.health = if self.health + heal > self.max_health {self.max_health} else {self.health + heal};
|
||||||
|
}
|
||||||
|
/// Add 'heal' amount of health points to component with usize::MAX as a boundary.
|
||||||
|
pub fn heal_with_overheal(&mut self, heal: usize) {
|
||||||
|
self.health = if usize::MAX-heal < self.health {usize::MAX} else {self.health + heal};
|
||||||
|
}
|
||||||
|
pub fn get_health(&self) -> usize {
|
||||||
|
self.health
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Marker component that marks entity to NOT be despawned at the end of frame when health reaches zero
|
||||||
|
#[derive(Component)]
|
||||||
|
#[require(Health)]
|
||||||
|
pub struct Unkillable;
|
||||||
|
|
||||||
|
fn cleanup_killed(mut commands: Commands, query: Query<(Entity, &Health), Without<Unkillable>>) {
|
||||||
|
for (entity, health) in query {
|
||||||
|
if health.health == 0 {
|
||||||
|
commands.entity(entity).despawn();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue