Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
bevyengine
GitHub Repository: bevyengine/bevy
Path: blob/main/crates/bevy_ecs/src/resource.rs
6598 views
1
//! Resources are unique, singleton-like data types that can be accessed from systems and stored in the [`World`](crate::world::World).
2
3
// The derive macro for the `Resource` trait
4
pub use bevy_ecs_macros::Resource;
5
6
/// A type that can be inserted into a [`World`] as a singleton.
7
///
8
/// You can access resource data in systems using the [`Res`] and [`ResMut`] system parameters
9
///
10
/// Only one resource of each type can be stored in a [`World`] at any given time.
11
///
12
/// # Examples
13
///
14
/// ```
15
/// # let mut world = World::default();
16
/// # let mut schedule = Schedule::default();
17
/// # use bevy_ecs::prelude::*;
18
/// #[derive(Resource)]
19
/// struct MyResource { value: u32 }
20
///
21
/// world.insert_resource(MyResource { value: 42 });
22
///
23
/// fn read_resource_system(resource: Res<MyResource>) {
24
/// assert_eq!(resource.value, 42);
25
/// }
26
///
27
/// fn write_resource_system(mut resource: ResMut<MyResource>) {
28
/// assert_eq!(resource.value, 42);
29
/// resource.value = 0;
30
/// assert_eq!(resource.value, 0);
31
/// }
32
/// # schedule.add_systems((read_resource_system, write_resource_system).chain());
33
/// # schedule.run(&mut world);
34
/// ```
35
///
36
/// # `!Sync` Resources
37
/// A `!Sync` type cannot implement `Resource`. However, it is possible to wrap a `Send` but not `Sync`
38
/// type in [`SyncCell`] or the currently unstable [`Exclusive`] to make it `Sync`. This forces only
39
/// having mutable access (`&mut T` only, never `&T`), but makes it safe to reference across multiple
40
/// threads.
41
///
42
/// This will fail to compile since `RefCell` is `!Sync`.
43
/// ```compile_fail
44
/// # use std::cell::RefCell;
45
/// # use bevy_ecs::resource::Resource;
46
///
47
/// #[derive(Resource)]
48
/// struct NotSync {
49
/// counter: RefCell<usize>,
50
/// }
51
/// ```
52
///
53
/// This will compile since the `RefCell` is wrapped with `SyncCell`.
54
/// ```
55
/// # use std::cell::RefCell;
56
/// # use bevy_ecs::resource::Resource;
57
/// use bevy_platform::cell::SyncCell;
58
///
59
/// #[derive(Resource)]
60
/// struct ActuallySync {
61
/// counter: SyncCell<RefCell<usize>>,
62
/// }
63
/// ```
64
///
65
/// [`Exclusive`]: https://doc.rust-lang.org/nightly/std/sync/struct.Exclusive.html
66
/// [`World`]: crate::world::World
67
/// [`Res`]: crate::system::Res
68
/// [`ResMut`]: crate::system::ResMut
69
/// [`SyncCell`]: bevy_platform::cell::SyncCell
70
#[diagnostic::on_unimplemented(
71
message = "`{Self}` is not a `Resource`",
72
label = "invalid `Resource`",
73
note = "consider annotating `{Self}` with `#[derive(Resource)]`"
74
)]
75
pub trait Resource: Send + Sync + 'static {}
76
77