bevy_utils/
once.rs

1use bevy_platform::sync::atomic::{AtomicBool, Ordering};
2
3/// Wrapper around an [`AtomicBool`], abstracting the backing implementation and
4/// ordering considerations.
5#[doc(hidden)]
6pub struct OnceFlag(AtomicBool);
7
8impl OnceFlag {
9    /// Create a new flag in the unset state.
10    pub const fn new() -> Self {
11        Self(AtomicBool::new(true))
12    }
13
14    /// Sets this flag. Will return `true` if this flag hasn't been set before.
15    pub fn set(&self) -> bool {
16        self.0.swap(false, Ordering::Relaxed)
17    }
18}
19
20impl Default for OnceFlag {
21    fn default() -> Self {
22        Self::new()
23    }
24}
25
26/// Call some expression only once per call site.
27#[macro_export]
28macro_rules! once {
29    ($expression:expr) => {{
30        static SHOULD_FIRE: $crate::OnceFlag = $crate::OnceFlag::new();
31        if SHOULD_FIRE.set() {
32            $expression;
33        }
34    }};
35}