use core::ops::{Add, Mul, Neg, Sub}; use crate::{primitives::ConstantClosure, Anim, Fun}; impl Add> for Anim where F: Fun, G: Fun, F::V: Add, { type Output = Anim>; fn add(self, rhs: Anim) -> Self::Output { Anim(AddClosure(self.0, rhs.0)) } } impl Add for Anim where W: Copy, F: Fun, F::V: Add, { type Output = Anim>>; fn add(self, rhs: W) -> Self::Output { Anim(AddClosure(self.0, ConstantClosure::from(rhs))) } } impl Sub> for Anim where F: Fun, G: Fun, F::V: Sub, { type Output = Anim>; fn sub(self, rhs: Anim) -> Self::Output { Anim(SubClosure(self.0, rhs.0)) } } impl Sub for Anim where W: Copy, F: Fun, F::T: Copy, F::V: Sub, { type Output = Anim>>; fn sub(self, rhs: W) -> Self::Output { Anim(SubClosure(self.0, ConstantClosure::from(rhs))) } } impl Mul> for Anim where F: Fun, G: Fun, F::T: Copy, F::V: Mul, { type Output = Anim>; fn mul(self, rhs: Anim) -> Self::Output { Anim(MulClosure(self.0, rhs.0)) } } impl Mul for Anim where W: Copy, F: Fun, F::T: Copy, F::V: Mul, { type Output = Anim>>; fn mul(self, rhs: W) -> Self::Output { Anim(MulClosure(self.0, ConstantClosure::from(rhs))) } } impl Neg for Anim where V: Copy, F: Fun, { type Output = Anim>; fn neg(self) -> Self::Output { Anim(NegClosure(self.0)) } } #[doc(hidden)] #[derive(Debug, Clone)] pub struct AddClosure(F, G); impl Fun for AddClosure where F: Fun, G: Fun, F::T: Clone, F::V: Add, { type T = F::T; type V = >::Output; fn eval(&self, t: F::T) -> Self::V { self.0.eval(t.clone()) + self.1.eval(t) } } #[doc(hidden)] #[derive(Debug, Clone)] pub struct SubClosure(F, G); impl Fun for SubClosure where F: Fun, G: Fun, F::T: Clone, F::V: Sub, { type T = F::T; type V = >::Output; fn eval(&self, t: F::T) -> Self::V { self.0.eval(t.clone()) - self.1.eval(t) } } #[doc(hidden)] #[derive(Debug, Clone)] pub struct MulClosure(F, G); impl Fun for MulClosure where F: Fun, G: Fun, F::T: Copy, F::V: Mul, { type T = F::T; type V = >::Output; fn eval(&self, t: F::T) -> Self::V { self.0.eval(t) * self.1.eval(t) } } #[doc(hidden)] pub struct NegClosure(F); impl Fun for NegClosure where F: Fun, F::V: Neg, { type T = F::T; type V = ::Output; fn eval(&self, t: F::T) -> Self::V { -self.0.eval(t) } }