Count number of times a repeating Timer wraps around in a tick (#1112)
Added just_finished_count() function
This commit is contained in:
parent
1e8060a5a2
commit
ac7d2de67c
@ -13,8 +13,8 @@ pub struct Timer {
|
|||||||
elapsed: f32,
|
elapsed: f32,
|
||||||
duration: f32,
|
duration: f32,
|
||||||
finished: bool,
|
finished: bool,
|
||||||
/// Will only be true on the tick `duration` is reached or exceeded.
|
/// Will only be non-zero on the tick `duration` is reached or exceeded.
|
||||||
just_finished: bool,
|
just_finished_count: u32,
|
||||||
paused: bool,
|
paused: bool,
|
||||||
repeating: bool,
|
repeating: bool,
|
||||||
}
|
}
|
||||||
@ -51,7 +51,8 @@ impl Timer {
|
|||||||
self.paused
|
self.paused
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Returns the time elapsed on the timer. Guaranteed to be between 0.0 and `duration`, inclusive.
|
/// Returns the time elapsed on the timer. Guaranteed to be between 0.0 and `duration`.
|
||||||
|
/// Will only equal `duration` when the timer is finished and non repeating.
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn elapsed(&self) -> f32 {
|
pub fn elapsed(&self) -> f32 {
|
||||||
self.elapsed
|
self.elapsed
|
||||||
@ -74,8 +75,9 @@ impl Timer {
|
|||||||
|
|
||||||
/// Returns the finished state of the timer.
|
/// Returns the finished state of the timer.
|
||||||
///
|
///
|
||||||
/// Non repeating timers will stop tracking and stay in the finished state until reset.
|
/// Non-repeating timers will stop tracking and stay in the finished state until reset.
|
||||||
/// Repeating timers will only be in the finished state on each tick `duration` is reached or exceeded, and can still be reset at any given point.
|
/// Repeating timers will only be in the finished state on each tick `duration` is reached or exceeded, so in that case
|
||||||
|
/// this function is equivalent to `just_finished`.
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn finished(&self) -> bool {
|
pub fn finished(&self) -> bool {
|
||||||
self.finished
|
self.finished
|
||||||
@ -84,7 +86,16 @@ impl Timer {
|
|||||||
/// Will only be true on the tick the timer's duration is reached or exceeded.
|
/// Will only be true on the tick the timer's duration is reached or exceeded.
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn just_finished(&self) -> bool {
|
pub fn just_finished(&self) -> bool {
|
||||||
self.just_finished
|
self.just_finished_count > 0
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Returns the total number of times the timer finished during this tick.
|
||||||
|
///
|
||||||
|
/// This value can be used to ensure no completions of a repeating timer are skipped over due to a tick with an unexpectedly
|
||||||
|
/// long delta time. For non repeating timers, the value will only ever be 0 or 1.
|
||||||
|
#[inline]
|
||||||
|
pub fn just_finished_count(&self) -> u32 {
|
||||||
|
self.just_finished_count
|
||||||
}
|
}
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
@ -92,8 +103,11 @@ impl Timer {
|
|||||||
self.repeating
|
self.repeating
|
||||||
}
|
}
|
||||||
|
|
||||||
#[inline]
|
|
||||||
pub fn set_repeating(&mut self, repeating: bool) {
|
pub fn set_repeating(&mut self, repeating: bool) {
|
||||||
|
if !self.repeating && repeating && self.finished {
|
||||||
|
self.elapsed = 0.0;
|
||||||
|
self.finished = self.just_finished();
|
||||||
|
}
|
||||||
self.repeating = repeating
|
self.repeating = repeating
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -102,20 +116,24 @@ impl Timer {
|
|||||||
if self.paused {
|
if self.paused {
|
||||||
return self;
|
return self;
|
||||||
}
|
}
|
||||||
|
|
||||||
let prev_finished = self.finished;
|
let prev_finished = self.finished;
|
||||||
self.elapsed += delta;
|
self.elapsed += delta;
|
||||||
|
|
||||||
self.finished = self.elapsed >= self.duration;
|
self.finished = self.elapsed >= self.duration;
|
||||||
self.just_finished = !prev_finished && self.finished;
|
|
||||||
|
|
||||||
if self.finished {
|
if self.finished {
|
||||||
if self.repeating {
|
if self.repeating {
|
||||||
|
// Count the number of times the timer will wrap around from this tick
|
||||||
|
self.just_finished_count = (self.elapsed / self.duration) as u32;
|
||||||
// Repeating timers wrap around
|
// Repeating timers wrap around
|
||||||
self.elapsed %= self.duration;
|
self.elapsed %= self.duration;
|
||||||
} else {
|
} else {
|
||||||
|
self.just_finished_count = if prev_finished { 0 } else { 1 };
|
||||||
// Non-repeating timers clamp to duration
|
// Non-repeating timers clamp to duration
|
||||||
self.elapsed = self.duration;
|
self.elapsed = self.duration;
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
self.just_finished_count = 0;
|
||||||
}
|
}
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
@ -123,7 +141,7 @@ impl Timer {
|
|||||||
#[inline]
|
#[inline]
|
||||||
pub fn reset(&mut self) {
|
pub fn reset(&mut self) {
|
||||||
self.finished = false;
|
self.finished = false;
|
||||||
self.just_finished = false;
|
self.just_finished_count = 0;
|
||||||
self.elapsed = 0.0;
|
self.elapsed = 0.0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -151,6 +169,7 @@ mod tests {
|
|||||||
assert_eq!(t.duration(), 10.0);
|
assert_eq!(t.duration(), 10.0);
|
||||||
assert_eq!(t.finished(), false);
|
assert_eq!(t.finished(), false);
|
||||||
assert_eq!(t.just_finished(), false);
|
assert_eq!(t.just_finished(), false);
|
||||||
|
assert_eq!(t.just_finished_count(), 0);
|
||||||
assert_eq!(t.repeating(), false);
|
assert_eq!(t.repeating(), false);
|
||||||
assert_eq!(t.percent(), 0.025);
|
assert_eq!(t.percent(), 0.025);
|
||||||
assert_eq!(t.percent_left(), 0.975);
|
assert_eq!(t.percent_left(), 0.975);
|
||||||
@ -161,6 +180,7 @@ mod tests {
|
|||||||
assert_eq!(t.duration(), 10.0);
|
assert_eq!(t.duration(), 10.0);
|
||||||
assert_eq!(t.finished(), false);
|
assert_eq!(t.finished(), false);
|
||||||
assert_eq!(t.just_finished(), false);
|
assert_eq!(t.just_finished(), false);
|
||||||
|
assert_eq!(t.just_finished_count(), 0);
|
||||||
assert_eq!(t.repeating(), false);
|
assert_eq!(t.repeating(), false);
|
||||||
assert_eq!(t.percent(), 0.025);
|
assert_eq!(t.percent(), 0.025);
|
||||||
assert_eq!(t.percent_left(), 0.975);
|
assert_eq!(t.percent_left(), 0.975);
|
||||||
@ -170,6 +190,7 @@ mod tests {
|
|||||||
assert_eq!(t.elapsed(), 10.0);
|
assert_eq!(t.elapsed(), 10.0);
|
||||||
assert_eq!(t.finished(), true);
|
assert_eq!(t.finished(), true);
|
||||||
assert_eq!(t.just_finished(), true);
|
assert_eq!(t.just_finished(), true);
|
||||||
|
assert_eq!(t.just_finished_count(), 1);
|
||||||
assert_eq!(t.percent(), 1.0);
|
assert_eq!(t.percent(), 1.0);
|
||||||
assert_eq!(t.percent_left(), 0.0);
|
assert_eq!(t.percent_left(), 0.0);
|
||||||
// Continuing to tick when finished should only change just_finished
|
// Continuing to tick when finished should only change just_finished
|
||||||
@ -177,6 +198,7 @@ mod tests {
|
|||||||
assert_eq!(t.elapsed(), 10.0);
|
assert_eq!(t.elapsed(), 10.0);
|
||||||
assert_eq!(t.finished(), true);
|
assert_eq!(t.finished(), true);
|
||||||
assert_eq!(t.just_finished(), false);
|
assert_eq!(t.just_finished(), false);
|
||||||
|
assert_eq!(t.just_finished_count(), 0);
|
||||||
assert_eq!(t.percent(), 1.0);
|
assert_eq!(t.percent(), 1.0);
|
||||||
assert_eq!(t.percent_left(), 0.0);
|
assert_eq!(t.percent_left(), 0.0);
|
||||||
}
|
}
|
||||||
@ -190,14 +212,16 @@ mod tests {
|
|||||||
assert_eq!(t.duration(), 2.0);
|
assert_eq!(t.duration(), 2.0);
|
||||||
assert_eq!(t.finished(), false);
|
assert_eq!(t.finished(), false);
|
||||||
assert_eq!(t.just_finished(), false);
|
assert_eq!(t.just_finished(), false);
|
||||||
|
assert_eq!(t.just_finished_count(), 0);
|
||||||
assert_eq!(t.repeating(), true);
|
assert_eq!(t.repeating(), true);
|
||||||
assert_eq!(t.percent(), 0.375);
|
assert_eq!(t.percent(), 0.375);
|
||||||
assert_eq!(t.percent_left(), 0.625);
|
assert_eq!(t.percent_left(), 0.625);
|
||||||
// Tick past the end and make sure elapsed wraps
|
// Tick past the end and make sure elapsed wraps
|
||||||
t.tick(1.5);
|
t.tick(3.5);
|
||||||
assert_eq!(t.elapsed(), 0.25);
|
assert_eq!(t.elapsed(), 0.25);
|
||||||
assert_eq!(t.finished(), true);
|
assert_eq!(t.finished(), true);
|
||||||
assert_eq!(t.just_finished(), true);
|
assert_eq!(t.just_finished(), true);
|
||||||
|
assert_eq!(t.just_finished_count(), 2);
|
||||||
assert_eq!(t.percent(), 0.125);
|
assert_eq!(t.percent(), 0.125);
|
||||||
assert_eq!(t.percent_left(), 0.875);
|
assert_eq!(t.percent_left(), 0.875);
|
||||||
// Continuing to tick should turn off both finished & just_finished for repeating timers
|
// Continuing to tick should turn off both finished & just_finished for repeating timers
|
||||||
@ -205,6 +229,7 @@ mod tests {
|
|||||||
assert_eq!(t.elapsed(), 1.25);
|
assert_eq!(t.elapsed(), 1.25);
|
||||||
assert_eq!(t.finished(), false);
|
assert_eq!(t.finished(), false);
|
||||||
assert_eq!(t.just_finished(), false);
|
assert_eq!(t.just_finished(), false);
|
||||||
|
assert_eq!(t.just_finished_count(), 0);
|
||||||
assert_eq!(t.percent(), 0.625);
|
assert_eq!(t.percent(), 0.625);
|
||||||
assert_eq!(t.percent_left(), 0.375);
|
assert_eq!(t.percent_left(), 0.375);
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user