metroviz/src/timer.rs

96 lines
3.2 KiB
Rust

use crate::SimulationTime;
use bevy::prelude::*;
/// Current simulation time (in [TIME_UNIT] after midnight).
#[derive(Resource)]
pub struct SimulationTimer {
time: SimulationTime,
timer: Timer,
}
impl SimulationTimer {
/// Returns `true` if the current simulation time is within the given start and end times.
pub fn covers(&self, start: SimulationTime, end: SimulationTime) -> bool {
self.time >= start && self.time <= end
}
}
/// Event that triggers when the [SimulationTimer] is updated.
#[derive(Default, Event)]
pub struct SimulationTimerUpdated(pub SimulationTime);
pub struct SimulationTimerPlugin;
impl Plugin for SimulationTimerPlugin {
fn build(&self, app: &mut App) {
app.insert_resource(SimulationTimer {
time: SimulationTime(0),
timer: Timer::from_seconds(1.0, TimerMode::Repeating),
})
.add_event::<SimulationTimerUpdated>()
.add_systems(Startup, initialize_ui)
.add_systems(Update, (update_simulation_timer, debug_simulation_timer));
}
}
fn initialize_ui(mut commands: Commands, asset_server: Res<AssetServer>) {
commands
.spawn(NodeBundle {
style: Style {
width: Val::Percent(100.0),
height: Val::Px(100.0),
position_type: PositionType::Absolute,
bottom: Val::Px(0.0),
align_items: AlignItems::Center,
justify_content: JustifyContent::Center,
..default()
},
background_color: BackgroundColor(Color::WHITE),
..default()
})
.with_children(|parent| {
parent
.spawn(ButtonBundle {
style: Style {
width: Val::Px(30.0),
height: Val::Px(30.0),
border: UiRect::all(Val::Px(2.0)),
justify_content: JustifyContent::Center,
align_items: AlignItems::Center,
..default()
},
border_color: BorderColor(Color::BLACK),
background_color: BackgroundColor(Color::GRAY),
..default()
})
.with_children(|parent| {
parent.spawn(TextBundle::from_section(
"\u{23f5}",
TextStyle {
font: asset_server.load("fonts/Symbola.ttf"),
font_size: 40.0,
color: Color::WHITE,
},
));
});
});
}
fn update_simulation_timer(
time: Res<Time>,
mut simulation_timer: ResMut<SimulationTimer>,
mut event_writer: EventWriter<SimulationTimerUpdated>,
) {
simulation_timer.timer.tick(time.delta());
if simulation_timer.timer.just_finished() {
simulation_timer.time += SimulationTime(1);
event_writer.send(SimulationTimerUpdated(simulation_timer.time))
}
}
fn debug_simulation_timer(mut timer_events: EventReader<SimulationTimerUpdated>) {
for ev in timer_events.iter() {
println!("{:?}", ev.0);
}
}