pub struct SharedState<Data> { /* private fields */ }
Expand description

A type that allows you to share information across your application easily. Get immutable and mutable access to the data and subscribe to changes.

Panics

SharedState uses a RwLock internally. If you use Self::read() and Self::write() in the same scope your code might be stuck in a deadlock or panic.

Implementations§

Create a new SharedState variable.

The data will be initialized lazily on the first access.

Example
use relm4::SharedState;
static STATE: SharedState<MyData> = SharedState::new();
Examples found in repository?
examples/libadwaita/tab_game.rs (line 24)
24
static GAME_STATE: SharedState<GameState> = SharedState::new();

Subscribe to a shared state type. Any subscriber will be notified with a message every time you modify the shared state using Self::get_mut().

use relm4::SharedState;
static STATE: SharedState<u8> = SharedState::new();

let (sender, receiver) = relm4::channel();

// Every time we modify the data, we will receive
// the updated value as a message.
STATE.subscribe(&sender, |data| *data);

{
    let mut data = STATE.write();
    *data += 1;
}

assert_eq!(receiver.recv_sync().unwrap(), 1);
Examples found in repository?
examples/libadwaita/tab_game.rs (line 154)
153
154
155
156
    fn init_model(value: Self::Init, _index: &DynamicIndex, sender: FactorySender<Self>) -> Self {
        GAME_STATE.subscribe(sender.input_sender(), |_| CounterMsg::Update);
        Self { id: value }
    }

An alternative version of subscribe() that only send a message if the closure returns Some.

Get immutable access to the shared data.

Returns an RAII guard which will release this thread’s shared access once it is dropped.

The calling thread will be blocked until there are no more writers which hold the lock (see RwLock).

Panics

This function will panic if the internal RwLock is poisoned. An RwLock is poisoned whenever a writer panics while holding an exclusive lock. The failure will occur immediately after the lock has been acquired.

Also, this function might panic when called if the lock is already held by the current thread.

Examples found in repository?
examples/libadwaita/tab_game.rs (line 165)
158
159
160
161
162
163
164
165
166
167
168
    fn init_widgets(
        &mut self,
        index: &DynamicIndex,
        root: &Self::Root,
        returned_widget: &adw::TabPage,
        sender: FactorySender<Self>,
    ) -> Self::Widgets {
        let state = GAME_STATE.read();
        let widgets = view_output!();
        widgets
    }

Get mutable access to the shared data.

Returns an RAII guard which will notify all subscribers and release this thread’s shared access once it is dropped.

This function will not return while other writers or other readers currently have access to the internal lock (see RwLock).

Panics

This function will panic if the internal RwLock is poisoned. An RwLock is poisoned whenever a writer panics while holding an exclusive lock. The failure will occur immediately after the lock has been acquired.

Also, this function might panic when called if the lock is already held by the current thread.

Example
static STATE: SharedState<u8> = SharedState::new();

// Overwrite the current value with 1
*STATE.write() = 1;
Panic example
static STATE: SharedState<u8> = SharedState::new();

let read_guard = STATE.read();

// This is fine
let another_read_guard = STATE.read();

// This might panic or result in a dead lock
// because you cannot read and write at the same time.
// To solve this, drop all read guards on this thread first.
let another_write_guard = STATE.write();
Examples found in repository?
examples/libadwaita/tab_game.rs (line 259)
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
    fn update(&mut self, msg: Self::Input, sender: ComponentSender<Self>, _root: &Self::Root) {
        match msg {
            AppMsg::StartGame(index) => {
                self.start_index = Some(index);
                sender.command(|sender, _| async move {
                    for i in (1..4).rev() {
                        *GAME_STATE.write() = GameState::Countdown(i);
                        relm4::tokio::time::sleep(Duration::from_millis(1000)).await;
                    }
                    *GAME_STATE.write() = GameState::Running;
                    for _ in 0..20 {
                        relm4::tokio::time::sleep(Duration::from_millis(500)).await;
                        sender.send(false).unwrap();
                    }
                    relm4::tokio::time::sleep(Duration::from_millis(1000)).await;
                    sender.send(true).unwrap();
                });
            }
            AppMsg::StopGame => {
                *GAME_STATE.write() = GameState::Guessing;
            }
            AppMsg::SelectedGuess(index) => {
                *GAME_STATE.write() = GameState::End(index == self.start_index.take().unwrap());
            }
        }
    }

Get mutable access to the shared data. Since this call borrows the SharedState mutably, no actual locking needs to take place, but the mutable borrow statically guarantees no locks exist.

This method will not notify any subscribers!

Panics

This function will panic if the internal RwLock is poisoned. An RwLock is poisoned whenever a writer panics while holding an exclusive lock. The failure will occur immediately after the lock has been acquired.

Get immutable access to the shared data.

This method will not notify any subscribers!

Panics

This function will panic if the internal RwLock is poisoned. An RwLock is poisoned whenever a writer panics while holding an exclusive lock. The failure will occur immediately after the lock has been acquired.

Also, this function might panic when called if the lock is already held by the current thread.

Get mutable access to the shared data.

This method will not notify any subscribers!

Panics

This function will panic if the internal RwLock is poisoned. An RwLock is poisoned whenever a writer panics while holding an exclusive lock. The failure will occur immediately after the lock has been acquired.

Also, this function might panic when called if the lock is already held by the current thread.

Trait Implementations§

Formats the value using the given formatter. Read more

Auto Trait Implementations§

Blanket Implementations§

Gets the TypeId of self. Read more
Immutably borrows from an owned value. Read more
Mutably borrows from an owned value. Read more

Returns the argument unchanged.

Instruments this type with the provided Span, returning an Instrumented wrapper. Read more
Instruments this type with the current Span, returning an Instrumented wrapper. Read more

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Returns the position. Read more
The type returned in the event of a conversion error.
Performs the conversion.
The type returned in the event of a conversion error.
Performs the conversion.
Attaches the provided Subscriber to this type, returning a WithDispatch wrapper. Read more
Attaches the current default Subscriber to this type, returning a WithDispatch wrapper. Read more