bms_rs/bms/model/
stop.rs

1//! This module introduces struct [`StopObjects`], which manages definitions and events of scroll stop.
2
3use std::collections::{BTreeMap, HashMap, HashSet};
4
5use crate::bms::prelude::*;
6
7#[derive(Debug, Default, Clone, PartialEq, Eq)]
8#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
9/// This aggregate manages definitions and events of scroll stop.
10pub struct StopObjects {
11    /// Stop definitions, indexed by [`ObjId`]. `#STOP[01-ZZ]`
12    pub stop_defs: HashMap<ObjId, Decimal>,
13    /// Stop lengths by stop object id.
14    pub stops: BTreeMap<ObjTime, StopObj>,
15    /// Record of used STOP ids from `#STOPxx` messages, for validity checks.
16    pub stop_ids_used: HashSet<ObjId>,
17    /// bemaniaDX STP events, indexed by [`ObjTime`]. `#STP`
18    pub stp_events: BTreeMap<ObjTime, StpEvent>,
19}
20
21impl StopObjects {
22    /// Gets the time of the last STOP object.
23    #[must_use]
24    pub fn last_obj_time(&self) -> Option<ObjTime> {
25        self.stops.last_key_value().map(|(&time, _)| time)
26    }
27}
28
29impl StopObjects {
30    /// Adds a new stop object to the notes.
31    pub fn push_stop(&mut self, stop: StopObj) {
32        self.stops
33            .entry(stop.time)
34            .and_modify(|existing| {
35                existing.duration = &existing.duration + &stop.duration;
36            })
37            .or_insert_with(|| stop);
38    }
39}