mirror of
https://github.com/doukutsu-rs/doukutsu-rs
synced 2024-11-16 10:52:44 +00:00
112 lines
3.2 KiB
Rust
112 lines
3.2 KiB
Rust
use crate::common::{Color, Rect};
|
|
use crate::entity::GameEntity;
|
|
use crate::framework::context::Context;
|
|
use crate::framework::error::GameResult;
|
|
use crate::framework::graphics;
|
|
use crate::game::frame::Frame;
|
|
use crate::game::shared_game_state::SharedGameState;
|
|
|
|
pub enum FlashState {
|
|
None,
|
|
Cross(i32, i32, u16),
|
|
Blink(u16),
|
|
}
|
|
|
|
pub struct Flash {
|
|
state: FlashState,
|
|
}
|
|
|
|
impl Flash {
|
|
pub fn new() -> Flash {
|
|
Flash {
|
|
state: FlashState::None
|
|
}
|
|
}
|
|
|
|
pub fn set_cross(&mut self, x: i32, y: i32) {
|
|
self.state = FlashState::Cross(x, y, 0);
|
|
}
|
|
|
|
pub fn set_blink(&mut self) {
|
|
self.state = FlashState::Blink(0);
|
|
}
|
|
|
|
pub fn stop(&mut self) {
|
|
self.state = FlashState::None;
|
|
}
|
|
}
|
|
|
|
impl GameEntity<()> for Flash {
|
|
fn tick(&mut self, _state: &mut SharedGameState, _custom: ()) -> GameResult<()> {
|
|
match self.state {
|
|
FlashState::None => {}
|
|
FlashState::Cross(x, y, tick) => {
|
|
self.state = if tick > 128 {
|
|
FlashState::None
|
|
} else {
|
|
FlashState::Cross(x, y, tick + 1)
|
|
};
|
|
}
|
|
FlashState::Blink(tick) => {
|
|
self.state = if tick > 20 {
|
|
FlashState::None
|
|
} else {
|
|
FlashState::Blink(tick + 1)
|
|
};
|
|
}
|
|
}
|
|
Ok(())
|
|
}
|
|
|
|
fn draw(&self, state: &mut SharedGameState, ctx: &mut Context, frame: &Frame) -> GameResult<()> {
|
|
const WHITE: Color = Color::new(1.0, 1.0, 1.0, 1.0);
|
|
|
|
match self.state {
|
|
FlashState::None => {}
|
|
FlashState::Cross(x, y, tick) => {
|
|
let tick = tick as f32 + state.frame_time as f32;
|
|
let frame_pos = frame.xy_interpolated(state.frame_time);
|
|
|
|
let (cen_x, cen_y) = (
|
|
(x as f32 / 512.0) - frame_pos.0,
|
|
(y as f32 / 512.0) - frame_pos.1
|
|
);
|
|
|
|
let width = if tick > 100.0 {
|
|
(1.0 - (tick - 100.0).max(0.0) / 28.0).powf(2.0) * state.canvas_size.0
|
|
} else {
|
|
(1.0 - (0.97f32).powf(tick)).max(0.0) * state.canvas_size.0
|
|
};
|
|
|
|
|
|
let mut rect = Rect {
|
|
left: 0,
|
|
top: ((cen_y - width) * state.scale) as isize,
|
|
right: (state.canvas_size.0 * state.scale) as isize,
|
|
bottom: ((cen_y + width) * state.scale) as isize,
|
|
};
|
|
|
|
graphics::draw_rect(ctx, rect, WHITE)?;
|
|
|
|
if tick <= 100.0 {
|
|
rect = Rect {
|
|
left: ((cen_x - width) * state.scale) as isize,
|
|
top: 0,
|
|
right: ((cen_x + width) * state.scale) as isize,
|
|
bottom: (state.canvas_size.1 * state.scale) as isize,
|
|
};
|
|
|
|
graphics::draw_rect(ctx, rect, WHITE)?;
|
|
}
|
|
}
|
|
FlashState::Blink(tick) => {
|
|
if tick / 2 % 2 != 0 {
|
|
graphics::clear(ctx, WHITE);
|
|
}
|
|
}
|
|
}
|
|
|
|
Ok(())
|
|
}
|
|
}
|