module Synthesizer.Dimensional.Amplitude.Cut (
unzip,
unzip3,
leftFromStereo, rightFromStereo,
span, dropWhile, takeWhile,
spanPrimitive, dropWhilePrimitive, takeWhilePrimitive,
concat, concatVolume, concatPrimitive,
append, appendVolume, appendPrimitive,
zip, zipVolume,
zip3, zip3Volume,
mergeStereo, mergeStereoVolume, mergeStereoPrimitive,
selectBool,
reverse,
) where
import qualified Synthesizer.Dimensional.Signal.Private as SigA
import Synthesizer.Dimensional.Signal.Private (toAmplitudeScalar, )
import qualified Synthesizer.Dimensional.Rate as Rate
import qualified Synthesizer.Dimensional.Amplitude as Amp
import qualified Synthesizer.Generic.Signal as SigG
import qualified Synthesizer.Generic.Cut as CutG
import qualified Synthesizer.State.Signal as Sig
import qualified Synthesizer.Frame.Stereo as Stereo
import qualified Number.DimensionTerm as DN
import qualified Algebra.DimensionTerm as Dim
import qualified Algebra.Module as Module
import qualified Algebra.Field as Field
import qualified Data.List as List
import NumericPrelude.Base (Ord, max, Bool, ($), (.), flip, )
import NumericPrelude.Numeric ((*>), )
import Prelude ()
unzip ::
(SigG.Transform sig (yv0, yv1),
SigG.Transform sig yv0,
SigG.Transform sig yv1) =>
SigA.T rate amp (sig (yv0, yv1)) ->
(SigA.T rate amp (sig yv0), SigA.T rate amp (sig yv1))
unzip x =
let (ss0,ss1) = SigG.unzip (SigA.body x)
in (SigA.replaceBody ss0 x, SigA.replaceBody ss1 x)
unzip3 ::
(SigG.Transform sig (yv0, yv1, yv2),
SigG.Transform sig yv0,
SigG.Transform sig yv1,
SigG.Transform sig yv2) =>
SigA.T rate amp (sig (yv0, yv1, yv2)) ->
(SigA.T rate amp (sig yv0), SigA.T rate amp (sig yv1), SigA.T rate amp (sig yv2))
unzip3 x =
let (ss0,ss1,ss2) = SigG.unzip3 (SigA.body x)
in (SigA.replaceBody ss0 x, SigA.replaceBody ss1 x, SigA.replaceBody ss2 x)
span ::
(SigG.Transform sig yv, Dim.C v, Field.C y, Module.C y yv) =>
DN.T v y ->
(yv -> Bool) ->
(SigA.T rate (Amp.Dimensional v y) (sig yv) ->
(SigA.T rate (Amp.Dimensional v y) (sig yv),
SigA.T rate (Amp.Dimensional v y) (sig yv)))
span v p x =
spanPrivate (p . (toAmplitudeScalar x v *>)) x
dropWhile ::
(SigG.Transform sig yv, Dim.C v, Field.C y, Module.C y yv) =>
DN.T v y ->
(yv -> Bool) ->
SigA.T rate (Amp.Dimensional v y) (sig yv) ->
SigA.T rate (Amp.Dimensional v y) (sig yv)
dropWhile v p x =
dropWhilePrivate (p . (toAmplitudeScalar x v *>)) x
takeWhile ::
(SigG.Transform sig yv, Dim.C v, Field.C y, Module.C y yv) =>
DN.T v y ->
(yv -> Bool) ->
SigA.T rate (Amp.Dimensional v y) (sig yv) ->
SigA.T rate (Amp.Dimensional v y) (sig yv)
takeWhile v p x =
takeWhilePrivate (p . (toAmplitudeScalar x v *>)) x
spanPrimitive ::
(SigG.Transform sig y, Amp.Primitive amp) =>
(y -> Bool) ->
(SigA.T rate amp (sig y) ->
(SigA.T rate amp (sig y),
SigA.T rate amp (sig y)))
spanPrimitive =
spanPrivate
dropWhilePrimitive ::
(SigG.Transform sig y, Amp.Primitive amp) =>
(y -> Bool) ->
SigA.T rate amp (sig y) ->
SigA.T rate amp (sig y)
dropWhilePrimitive =
dropWhilePrivate
takeWhilePrimitive ::
(SigG.Transform sig y, Amp.Primitive amp) =>
(y -> Bool) ->
SigA.T rate amp (sig y) ->
SigA.T rate amp (sig y)
takeWhilePrimitive =
takeWhilePrivate
spanPrivate ::
(SigG.Transform sig y) =>
(y -> Bool) ->
(SigA.T rate amp (sig y) ->
(SigA.T rate amp (sig y),
SigA.T rate amp (sig y)))
spanPrivate p x =
let (y,z) = SigG.span p $ SigA.body x
in (SigA.replaceBody y x,
SigA.replaceBody z x)
dropWhilePrivate ::
(SigG.Transform sig y) =>
(y -> Bool) ->
SigA.T rate amp (sig y) ->
SigA.T rate amp (sig y)
dropWhilePrivate p =
SigA.processBody (SigG.dropWhile p)
takeWhilePrivate ::
(SigG.Transform sig y) =>
(y -> Bool) ->
SigA.T rate amp (sig y) ->
SigA.T rate amp (sig y)
takeWhilePrivate p =
SigA.processBody (SigG.takeWhile p)
leftFromStereo :: (Dim.C u) =>
SigA.R s u y (Stereo.T yv) -> SigA.R s u y yv
leftFromStereo = SigA.processBody (Sig.map Stereo.left)
rightFromStereo :: (Dim.C u) =>
SigA.R s u y (Stereo.T yv) -> SigA.R s u y yv
rightFromStereo = SigA.processBody (Sig.map Stereo.right)
type Signal s u y sig yv =
SigA.T (Rate.Phantom s) (Amp.Dimensional u y) (sig yv)
concat ::
(Ord y, Field.C y, Dim.C u,
Module.C y yv,
SigG.Transform sig yv) =>
[Signal s u y sig yv] -> Signal s u y sig yv
concat xs =
concatVolume (List.maximum (List.map SigA.actualAmplitude xs)) xs
concatVolume ::
(Field.C y, Dim.C u,
Module.C y yv,
SigG.Transform sig yv) =>
DN.T u y ->
[Signal s u y sig yv] -> Signal s u y sig yv
concatVolume amp xs =
let smps = List.map (SigA.vectorSamples (toAmplitudeScalar z)) xs
z = SigA.fromBody amp (SigG.concat smps)
in z
concatPrimitive ::
(CutG.Transform sig, Amp.Primitive amp) =>
[SigA.T (Rate.Phantom s) amp sig] ->
SigA.T (Rate.Phantom s) amp sig
concatPrimitive =
SigA.primitiveFromBody . SigG.concat . List.map SigA.body
merge ::
(Ord y, Field.C y, Dim.C u,
Module.C y yv0, Module.C y yv1,
SigG.Transform sig0 yv0, SigG.Transform sig1 yv1) =>
(sig0 yv0 -> sig1 yv1 -> sig2 yv2) ->
Signal s u y sig0 yv0 -> Signal s u y sig1 yv1 -> Signal s u y sig2 yv2
merge f x0 x1 =
mergeVolume f (max (SigA.actualAmplitude x0) (SigA.actualAmplitude x1)) x0 x1
mergeVolume ::
(Field.C y, Dim.C u,
Module.C y yv0, Module.C y yv1,
SigG.Transform sig0 yv0, SigG.Transform sig1 yv1) =>
(sig0 yv0 -> sig1 yv1 -> sig2 yv2) ->
DN.T u y ->
Signal s u y sig0 yv0 -> Signal s u y sig1 yv1 -> Signal s u y sig2 yv2
mergeVolume f amp x y =
let sampX = SigA.vectorSamples (toAmplitudeScalar z) x
sampY = SigA.vectorSamples (toAmplitudeScalar z) y
z = SigA.fromBody amp (f sampX sampY)
in z
mergePrimitive ::
(Amp.Primitive amp) =>
(sig0 -> sig1 -> sig2) ->
SigA.T (Rate.Phantom s) amp sig0 ->
SigA.T (Rate.Phantom s) amp sig1 ->
SigA.T (Rate.Phantom s) amp sig2
mergePrimitive f x y =
SigA.Cons Rate.Phantom Amp.primitive $
f (SigA.body x) (SigA.body y)
append ::
(Ord y, Field.C y, Dim.C u,
Module.C y yv,
SigG.Transform sig yv) =>
Signal s u y sig yv -> Signal s u y sig yv -> Signal s u y sig yv
append = merge SigG.append
appendVolume ::
(Field.C y, Dim.C u,
Module.C y yv,
SigG.Transform sig yv) =>
DN.T u y ->
Signal s u y sig yv -> Signal s u y sig yv -> Signal s u y sig yv
appendVolume = mergeVolume SigG.append
appendPrimitive ::
(CutG.Transform sig, Amp.Primitive amp) =>
SigA.T (Rate.Phantom s) amp sig ->
SigA.T (Rate.Phantom s) amp sig ->
SigA.T (Rate.Phantom s) amp sig
appendPrimitive = mergePrimitive SigG.append
zip ::
(Ord y, Field.C y, Dim.C u,
Module.C y yv0, Module.C y yv1,
SigG.Read sig yv0, SigG.Transform sig yv1, SigG.Transform sig (yv0,yv1)) =>
Signal s u y sig yv0 -> Signal s u y sig yv1 -> Signal s u y sig (yv0,yv1)
zip =
merge (SigG.zipWithState (,)) . SigA.restore
zipVolume ::
(Field.C y, Dim.C u,
Module.C y yv0, Module.C y yv1,
SigG.Read sig yv0, SigG.Transform sig yv1, SigG.Transform sig (yv0,yv1)) =>
DN.T u y ->
Signal s u y sig yv0 -> Signal s u y sig yv1 -> Signal s u y sig (yv0,yv1)
zipVolume vol =
mergeVolume (SigG.zipWithState (,)) vol . SigA.restore
mergeStereo ::
(Ord y, Field.C y, Dim.C u,
Module.C y yv,
SigG.Transform sig yv, SigG.Transform sig (Stereo.T yv)) =>
Signal s u y sig yv -> Signal s u y sig yv -> Signal s u y sig (Stereo.T yv)
mergeStereo = merge (SigG.zipWith Stereo.cons)
mergeStereoVolume ::
(Field.C y, Dim.C u,
Module.C y yv,
SigG.Transform sig yv, SigG.Transform sig (Stereo.T yv)) =>
DN.T u y ->
Signal s u y sig yv -> Signal s u y sig yv -> Signal s u y sig (Stereo.T yv)
mergeStereoVolume = mergeVolume (SigG.zipWith Stereo.cons)
mergeStereoPrimitive ::
(Amp.Primitive amp, SigG.Transform sig y, SigG.Transform sig (Stereo.T y)) =>
SigA.T (Rate.Phantom s) amp (sig y) ->
SigA.T (Rate.Phantom s) amp (sig y) ->
SigA.T (Rate.Phantom s) amp (sig (Stereo.T y))
mergeStereoPrimitive =
mergePrimitive (SigG.zipWith Stereo.cons)
zip3 ::
(Ord y, Field.C y, Dim.C u,
Module.C y yv0, Module.C y yv1, Module.C y yv2,
SigG.Read sig yv0, SigG.Read sig yv1,
SigG.Transform sig yv2, SigG.Transform sig (yv0, yv1, yv2)) =>
Signal s u y sig yv0 -> Signal s u y sig yv1 -> Signal s u y sig yv2 ->
Signal s u y sig (yv0,yv1,yv2)
zip3 x0 x1 x2 =
zip3Volume
(SigA.actualAmplitude x0 `max` SigA.actualAmplitude x1 `max` SigA.actualAmplitude x2)
x0 x1 x2
zip3Volume ::
(Field.C y, Dim.C u,
Module.C y yv0, Module.C y yv1, Module.C y yv2,
SigG.Read sig yv0, SigG.Read sig yv1,
SigG.Transform sig yv2, SigG.Transform sig (yv0, yv1, yv2)) =>
DN.T u y ->
Signal s u y sig yv0 -> Signal s u y sig yv1 -> Signal s u y sig yv2 ->
Signal s u y sig (yv0,yv1,yv2)
zip3Volume amp x0 x1 x2 =
let sampX0 = SigA.vectorSamples (toAmplitudeScalar z) (SigA.restore x0)
sampX1 = SigA.vectorSamples (toAmplitudeScalar z) (SigA.restore x1)
sampX2 = SigA.vectorSamples (toAmplitudeScalar z) x2
z = SigA.fromBody amp (SigG.zipWithState3 (,,) sampX0 sampX1 sampX2)
in z
selectBool ::
(Ord y, Field.C y, Dim.C u,
Module.C y yv,
SigG.Read sig yv,
SigG.Transform sig Bool, SigG.Transform sig yv) =>
Signal s u y sig yv ->
Signal s u y sig yv ->
SigA.T (Rate.Phantom s) Amp.Abstract (sig Bool) ->
Signal s u y sig yv
selectBool xf xt cs =
SigA.processBody
(flip (SigG.zipWithState (\(xfi,xti) c -> if c then xti else xfi))
(SigA.body cs))
(zip
(SigA.restore xf)
(SigA.restore xt))
reverse ::
(SigG.Transform sig yv) =>
SigA.T rate amp (sig yv) ->
SigA.T rate amp (sig yv)
reverse =
SigA.processBody SigG.reverse