use core::{ops::Sub, time::Duration};
pub trait InstantProvider<D = Duration>
where
Self: Sub<Self, Output = D> + Clone,
{
fn now() -> Self;
fn elapsed(&self) -> D {
Self::now() - self.clone()
}
}
#[cfg(feature = "std")]
impl InstantProvider<std::time::Duration> for std::time::Instant {
fn now() -> Self {
std::time::Instant::now()
}
}
#[cfg(feature = "embassy")]
impl InstantProvider<embassy_time::Duration> for embassy_time::Instant {
fn now() -> Self {
embassy_time::Instant::now()
}
}
#[cfg(feature = "wasm")]
pub mod wasm {
use core::{ops::Sub, time::Duration};
use crate::InstantProvider;
#[derive(Clone, PartialEq)]
pub struct Instant(f64);
impl Sub for Instant {
type Output = Duration;
fn sub(self, rhs: Self) -> Self::Output {
let delta_ms = self.0 - rhs.0;
let millis = delta_ms.trunc() as u64;
let micros = (delta_ms.fract() * 1000.0) as u64;
Duration::from_millis(millis) + Duration::from_micros(micros)
}
}
impl InstantProvider<Duration> for Instant {
fn now() -> Self {
Instant(js_sys::Date::now())
}
}
}