macro_rules! impl_shared_transformer_methods {
(@let_before ArcStatefulTransformer, $name:ident, $value:expr) => {
let mut $name = $value;
};
(@let_before RcStatefulTransformer, $name:ident, $value:expr) => {
let mut $name = $value;
};
(@let_before ArcStatefulBiTransformer, $name:ident, $value:expr) => {
let mut $name = $value;
};
(@let_before RcStatefulBiTransformer, $name:ident, $value:expr) => {
let mut $name = $value;
};
(@let_before $struct_name:ident, $name:ident, $value:expr) => {
let $name = $value;
};
(@let_after StatefulTransformer, $name:ident, $value:expr) => {
let mut $name = $value;
};
(@let_after $transformer_trait:ident, $name:ident, $value:expr) => {
let $name = $value;
};
(
$struct_name:ident < $t:ident, $r:ident >,
$conditional_type:ident,
$predicate_type:ident,
$chained_transformer_trait:ident,
predicate_bounds = ($($predicate_bounds:tt)+),
chained_bounds = ($($chained_bounds:tt)+)
) => {
#[inline]
pub fn when<P>(&self, predicate: P) -> $conditional_type<$t, $r>
where
$t: 'static,
$r: 'static,
P: Predicate<$t> + $($predicate_bounds)+,
{
$conditional_type {
transformer: self.clone(),
predicate: $crate::$predicate_type::new(predicate),
}
}
#[inline]
pub fn and_then<S, F>(&self, after: F) -> $struct_name<$t, S>
where
$t: 'static,
$r: 'static,
S: 'static,
F: $chained_transformer_trait<$r, S> + $($chained_bounds)+,
{
impl_shared_transformer_methods!(@let_before $struct_name, before, self.clone());
impl_shared_transformer_methods!(@let_after $chained_transformer_trait, after, after);
$struct_name::new(move |t| {
let r = before.apply(t);
after.apply(r)
})
}
};
(
$struct_name:ident < $t:ident, $u:ident, $r:ident >,
$conditional_type:ident,
$predicate_type:ident,
$chained_transformer_trait:ident,
predicate_bounds = ($($predicate_bounds:tt)+),
chained_bounds = ($($chained_bounds:tt)+)
) => {
#[inline]
pub fn when<P>(&self, predicate: P) -> $conditional_type<$t, $u, $r>
where
$t: 'static,
$u: 'static,
$r: 'static,
P: BiPredicate<$t, $u> + $($predicate_bounds)+,
{
$conditional_type {
transformer: self.clone(),
predicate: $crate::$predicate_type::new(predicate),
}
}
#[inline]
pub fn and_then<S, F>(&self, after: F) -> $struct_name<$t, $u, S>
where
$t: 'static,
$u: 'static,
$r: 'static,
S: 'static,
F: $chained_transformer_trait<$r, S> + $($chained_bounds)+,
{
impl_shared_transformer_methods!(@let_before $struct_name, before, self.clone());
impl_shared_transformer_methods!(@let_after $chained_transformer_trait, after, after);
$struct_name::new(move |t, u| {
let r = before.apply(t, u);
after.apply(r)
})
}
};
}
pub(crate) use impl_shared_transformer_methods;