use crate::blood::handle_blood_grain;
use crate::bone::handle_bone_grain;
use crate::grid::{Grid, GridPosition};
use crate::utils::constants::{GAME_RESOLUTION_X, GAME_RESOLUTION_Y, WINDOW_SIZE};
use crate::utils::remap::remap_cursor_position;
use crate::utils::tick::TickCounter;
use bevy::prelude::*;
use bevy::sprite::Anchor;
use rand::Rng;
/*
🦀 Components. Learn more: https://bevy-cheatbook.github.io/programming/res.html
*/
#[derive(Component)]
pub struct Grain {
pub grain_type: GrainType,
pub velocity: Vec2, // Physics-based movement
pub mass: f32,
pub is_simulated: bool,
}
#[derive(Component)]
pub struct Lifetime(pub u32);
#[derive(Component, Clone, Copy, Debug, PartialEq)]
pub enum GrainType {
Bone,
Blood,
}
#[derive(Component, PartialEq)]
pub enum Direction {
Right,
Left,
None,
}
impl Default for Direction {
fn default() -> Self {
Direction::None
}
}
#[derive(Bundle)]
pub struct GrainBundle {
pub grain: Grain,
pub lifetime: Lifetime,
pub direction: Direction,
pub grid_position: GridPosition,
pub sprite_bundle: SpriteBundle,
}
impl GrainBundle {
pub fn new(
grain_type: GrainType,
x: i32,
y: i32,
color: Color,
size: Vec2,
) -> Self {
GrainBundle {
grain: Grain {
grain_type,
velocity: Vec2::ZERO,
mass: 1.0,
is_simulated: true,
},
lifetime: Lifetime(0),
direction: Direction::None,
grid_position: GridPosition::new(x, y),
sprite_bundle: SpriteBundle {
sprite: Sprite {
color,
custom_size: Some(size),
anchor: Anchor::Center,
..default()
},
transform: Transform::from_translation(Vec3::new(x as f32, y as f32, 0.0)),
..default()
},
}
}
}
pub fn spawn_grain(
mut commands: Commands,
mouse_button_input: Res>,
windows: Query<&Window>,
camera: Query<(&Camera, &GlobalTransform)>,
) {
if mouse_button_input.just_pressed(MouseButton::Left) {
let window = windows.single();
let (camera, camera_transform) = camera.single();
if let Some(cursor_position) = window.cursor_position() {
if let Some(world_position) = camera.viewport_to_world(camera_transform, cursor_position) {
let grid_pos = remap_cursor_position(world_position.origin.truncate());
commands.spawn(GrainBundle::new(
GrainType::Blood,
grid_pos.x,
grid_pos.y,
Color::RED,
Vec2::splat(1.0),
));
}
}
}
if mouse_button_input.just_pressed(MouseButton::Right) {
let window = windows.single();
let (camera, camera_transform) = camera.single();
if let Some(cursor_position) = window.cursor_position() {
if let Some(world_position) = camera.viewport_to_world(camera_transform, cursor_position) {
let grid_pos = remap_cursor_position(world_position.origin.truncate());
commands.spawn(GrainBundle::new(
GrainType::Bone,
grid_pos.x,
grid_pos.y,
Color::WHITE,
Vec2::splat(1.0),
));
}
}
}
}
pub fn update_grains(
mut query: Query<(&mut Transform, &mut GridPosition, &mut Grain, &mut Lifetime, &mut Direction)>,
mut grid: ResMut,
time: Res