Skip to main content

rill_core_model/macros/
element.rs

1/// Generate a single WDF element struct implementing `WdfElement`.
2///
3/// Defines port resistance, scattering, state update, and reset behaviour
4/// via closures provided at the macro call site.
5#[macro_export]
6macro_rules! wdf_element {
7    (
8        name: $name:ident<T>,
9        params: { $($pname:ident: $ptype:ty),* },
10        state: { $($sname:ident: $stype:ty),* },
11        port_resistance: |$pr_self:ident| $pr:expr,
12        scattering: |$p:ident, $a:ident| $scatter:expr,
13        update: |$u:ident| $update:expr,
14        reset: |$r:ident| $reset:expr,
15    ) => {
16        /// A single WDF element.
17        ///
18        /// `params` fields are element parameters (e.g. resistance, capacitance);
19        /// `state` fields hold per-sample state. `voltage` and `current` are
20        /// computed by the WDF traversal.
21        #[derive(Debug, Clone, Copy)]
22        pub struct $name<T> {
23            $($pname: $ptype,)*
24            $($sname: $stype,)*
25            voltage: T,
26            current: T,
27        }
28
29        impl<T: $crate::Transcendental> $name<T> {
30            /// Create a new element with the given parameters and zeroed state.
31            pub fn new($($pname: $ptype),*) -> Self {
32                Self { $($pname,)* $($sname: T::ZERO,)* voltage: T::ZERO, current: T::ZERO }
33            }
34        }
35
36        impl<T: $crate::Transcendental> $crate::WdfElement<T> for $name<T> {
37            fn port_resistance(&self) -> T { let $pr_self = self; $pr }
38            fn process_incident(&mut self, a: T) -> T { let $p = self; let $a = a; $scatter }
39            fn update_state(&mut self) { let $u = self; $update }
40            fn voltage(&self) -> T { self.voltage }
41            fn current(&self) -> T { self.current }
42            fn reset(&mut self) { let $r = self; $reset }
43        }
44    };
45}