1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
use std::cell::Ref;
use types::{Storage, SharedSignal, SharedImpl, MaybeOwned};
use signal::Signal;
#[macro_export]
macro_rules! signal_lift
{
($($sig:expr),+ => $f:expr) => ( signal_lift!($f, $($sig),+) );
($f:expr) => ($crate::Signal::from_fn($f));
($f:expr, $sig1:expr) => ( $crate::Signal::map(&$sig1, $f) );
($f:expr, $sig1:expr, $sig2:expr) =>
($crate::lift::lift2($f, $sig1, $sig2));
($f:expr, $sig1:expr, $sig2:expr, $sig3:expr) =>
($crate::lift::lift3($f, $sig1, $sig2, $sig3));
($f:expr, $sig1:expr, $sig2:expr, $sig3:expr, $sig4:expr) =>
($crate::lift::lift4($f, $sig1, $sig2, $sig3, $sig4));
($f:expr, $sig1:expr, $sig2:expr, $sig3:expr, $sig4:expr, $sig5:expr) =>
($crate::lift::lift5($f, $sig1, $sig2, $sig3, $sig4, $sig5));
($f:expr, $sig1:expr, $sig2:expr, $sig3:expr, $sig4:expr, $sig5:expr, $sig6:expr) =>
($crate::lift::lift6($f, $sig1, $sig2, $sig3, $sig4, $sig5, $sig6));
}
macro_rules! lift_impl
{
($fname:ident ( $($vname:ident : $tname:ident),+ ) $($idx:tt)+) => (
impl<T, $($tname,)+ F> SharedSignal<T> for SharedImpl<T, ($(Signal<$tname>),+), F>
where F: Fn($(MaybeOwned<$tname>),+) -> T + 'static,
$($tname: 'static),+
{
fn update(&self)
{
if !self.storage.must_update() && ($(self.source.$idx.has_changed())||+)
{
self.storage.inc_root();
}
}
fn has_changed(&self) -> bool
{
self.storage.must_update()
}
fn storage(&self) -> &Storage<T>
{
&self.storage
}
fn sample(&self) -> Ref<T>
{
if self.has_changed()
{
let val = sample_with!($(self.source.$idx),+; self.f);
self.storage.set_local(val);
}
self.storage.borrow()
}
}
pub fn $fname<T, F, $($tname),+>(f: F, $($vname: Signal<$tname>),+) -> Signal<T>
where F: Fn($(MaybeOwned<$tname>),+) -> T + 'static,
T: 'static, $($tname: 'static),+
{
Signal::shared(SharedImpl{
storage: Default::default(),
source: ($($vname),+),
f: f,
})
}
);
}
lift_impl!(lift2(s1: S1, s2: S2) 0 1);
lift_impl!(lift3(s1: S1, s2: S2, s3: S3) 0 1 2);
lift_impl!(lift4(s1: S1, s2: S2, s3: S3, s4: S4) 0 1 2 3);
lift_impl!(lift5(s1: S1, s2: S2, s3: S3, s4: S4, s5: S5) 0 1 2 3 4);
lift_impl!(lift6(s1: S1, s2: S2, s3: S3, s4: S4, s5: S5, s6: S6) 0 1 2 3 4 5);