Skip to main content

topcoat_runtime/surrogate/
signal.rs

1use ref_cast::RefCast;
2use serde::Serialize;
3
4use crate::{Signal, Surrogated, impl_surrogate, impl_surrogate_mut, impl_surrogate_ref};
5
6#[derive(RefCast)]
7#[repr(transparent)]
8pub struct SignalSurrogate<T>(Signal<T>);
9
10impl<T> SignalSurrogate<T> {
11    #[inline]
12    pub(crate) const fn new(v: Signal<T>) -> Self {
13        Self(v)
14    }
15}
16
17impl<T> SignalSurrogate<T>
18where
19    for<'b> &'b T: Surrogated,
20{
21    pub fn read(&self) -> <&T as Surrogated>::Surrogate {
22        self.0.read().into_surrogate()
23    }
24}
25
26impl<T> SignalSurrogate<T>
27where
28    T: Surrogated + Clone,
29{
30    pub fn get(&self) -> <T as Surrogated>::Surrogate {
31        self.0.get().into_surrogate()
32    }
33}
34
35impl<T> SignalSurrogate<T>
36where
37    T: Surrogated,
38{
39    /// Writes a new value to the signal.
40    ///
41    /// # Panics
42    ///
43    /// Always panics; signal writes can only occur in client-side expressions.
44    pub fn set(&self, _v: T::Surrogate) {
45        panic!("expressions in which a signal is written to cannot be run server-side");
46    }
47}
48
49impl_surrogate!({T} Signal<T>, SignalSurrogate<T>);
50impl_surrogate_ref!({T} Signal<T>, SignalSurrogate<T>);
51impl_surrogate_mut!({T} Signal<T>, SignalSurrogate<T>);
52
53impl<T> Serialize for SignalSurrogate<T> {
54    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
55    where
56        S: serde::Serializer,
57    {
58        #[derive(Serialize)]
59        struct TaggedSignal {
60            t: &'static str,
61            id: std::string::String,
62        }
63
64        TaggedSignal {
65            t: "Signal",
66            id: self.0.id().to_string(),
67        }
68        .serialize(serializer)
69    }
70}