module Synthesizer.State.Control (
constant,
line,
linear, linearMultiscale, linearMultiscaleNeutral,
exponential, exponentialMultiscale, exponentialMultiscaleNeutral,
exponential2, exponential2Multiscale, exponential2MultiscaleNeutral,
exponentialFromTo, exponentialFromToMultiscale,
vectorExponential,
vectorExponential2,
cosine,
cubicHermite,
curveMultiscale,
curveMultiscaleNeutral,
) where
import qualified Synthesizer.Plain.Control as Ctrl
import qualified Synthesizer.State.Signal as Sig
import qualified Algebra.Module as Module
import qualified Algebra.Transcendental as Trans
import qualified Algebra.Field as Field
import qualified Algebra.Ring as Ring
import qualified Algebra.Additive as Additive
import NumericPrelude.Numeric
import NumericPrelude.Base
constant :: a -> Sig.T a
constant = Sig.repeat
linear :: Additive.C a =>
a
-> a
-> Sig.T a
linear d y0 = Sig.iterate (d+) y0
linearMultiscale :: Additive.C y =>
y
-> y
-> Sig.T y
linearMultiscale = curveMultiscale (+)
linearMultiscaleNeutral :: Additive.C y =>
y
-> Sig.T y
linearMultiscaleNeutral slope =
curveMultiscaleNeutral (+) slope zero
line :: Field.C y =>
Int
-> (y,y)
-> Sig.T y
line n (y0,y1) =
Sig.take n $ linear ((y1y0) / fromIntegral n) y0
exponential, exponentialMultiscale :: Trans.C a =>
a
-> a
-> Sig.T a
exponential time =
Sig.iterate (exp ( recip time) *)
exponentialMultiscale time = curveMultiscale (*) (exp ( recip time))
exponentialMultiscaleNeutral :: Trans.C y =>
y
-> Sig.T y
exponentialMultiscaleNeutral time =
curveMultiscaleNeutral (*) (exp ( recip time)) one
exponential2, exponential2Multiscale :: Trans.C a =>
a
-> a
-> Sig.T a
exponential2 halfLife =
Sig.iterate (((Ring.one+Ring.one) ** ( recip halfLife)) *)
exponential2Multiscale halfLife = curveMultiscale (*) (0.5 ** recip halfLife)
exponential2MultiscaleNeutral :: Trans.C y =>
y
-> Sig.T y
exponential2MultiscaleNeutral halfLife =
curveMultiscaleNeutral (*) (0.5 ** recip halfLife) one
exponentialFromTo, exponentialFromToMultiscale :: Trans.C y =>
y
-> y
-> y
-> Sig.T y
exponentialFromTo time y0 y1 =
Sig.iterate (* (y1/y0) ** recip time) y0
exponentialFromToMultiscale time y0 y1 =
curveMultiscale (*) ((y1/y0) ** recip time) y0
vectorExponential :: (Trans.C a, Module.C a v) =>
a
-> v
-> Sig.T v
vectorExponential time y0 =
Sig.iterate (exp (1/time) *>) y0
vectorExponential2 :: (Trans.C a, Module.C a v) =>
a
-> v
-> Sig.T v
vectorExponential2 halfLife y0 =
Sig.iterate (0.5**(1/halfLife) *>) y0
cosine :: Trans.C a =>
a
-> a
-> Sig.T a
cosine = Ctrl.cosineWithSlope $
\d x -> Sig.map cos (linear d x)
cubicHermite :: Field.C a => (a, (a,a)) -> (a, (a,a)) -> Sig.T a
cubicHermite node0 node1 =
Sig.map (Ctrl.cubicFunc node0 node1) (linear 1 0)
curveMultiscale :: (y -> y -> y) -> y -> y -> Sig.T y
curveMultiscale op d y0 =
Sig.cons y0 (Sig.map (op y0) (Sig.iterateAssociative op d))
curveMultiscaleNeutral :: (y -> y -> y) -> y -> y -> Sig.T y
curveMultiscaleNeutral op d neutral =
Sig.cons neutral (Sig.iterateAssociative op d)