-- | The unit-generator graph structure implemented by the SuperCollider synthesis server.
module Sound.Sc3.Server.Synthdef where

import qualified Data.ByteString.Lazy as L {- bytestring -}

import qualified Sound.Sc3.Ugen.Graph as Graph {- hsc3 -}
import qualified Sound.Sc3.Ugen.Help.Graph as Help.Graph {- hsc3 -}
import qualified Sound.Sc3.Ugen.Ugen as Ugen {- hsc3 -}

import qualified Sound.Sc3.Server.Graphdef as Graphdef {- hsc3 -}
import qualified Sound.Sc3.Server.Graphdef.Binary as Graphdef.Binary {- hsc3 -}
import qualified Sound.Sc3.Server.Graphdef.Graph as Graphdef.Graph {- hsc3 -}
import qualified Sound.Sc3.Server.Param as Param {- hsc3 -}

-- | A named unit generator graph.
data Synthdef =
  Synthdef
  {Synthdef -> String
synthdefName :: String
  ,Synthdef -> Ugen
synthdefUgen :: Ugen.Ugen}
  deriving (Synthdef -> Synthdef -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: Synthdef -> Synthdef -> Bool
$c/= :: Synthdef -> Synthdef -> Bool
== :: Synthdef -> Synthdef -> Bool
$c== :: Synthdef -> Synthdef -> Bool
Eq,Int -> Synthdef -> ShowS
[Synthdef] -> ShowS
Synthdef -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [Synthdef] -> ShowS
$cshowList :: [Synthdef] -> ShowS
show :: Synthdef -> String
$cshow :: Synthdef -> String
showsPrec :: Int -> Synthdef -> ShowS
$cshowsPrec :: Int -> Synthdef -> ShowS
Show)

-- | Alias for 'Synthdef'.
synthdef :: String -> Ugen.Ugen -> Synthdef
synthdef :: String -> Ugen -> Synthdef
synthdef = String -> Ugen -> Synthdef
Synthdef

{- | The SC3 /default/ instrument 'Synthdef', see 'default_ugen_graph'.

> import Sound.Osc {- hosc -}
> import Sound.Sc3 {- hsc3 -}
> withSc3 (sendMessage (d_recv defaultSynthdef))
> audition defaultSynthdef
-}
defaultSynthdef :: Synthdef
defaultSynthdef :: Synthdef
defaultSynthdef = String -> Ugen -> Synthdef
synthdef String
"default" Ugen
Help.Graph.default_ugen_graph

{- | The SC3 /default/ sample (buffer) playback instrument 'Synthdef',
see 'default_sampler_ugen_graph'.

> withSc3 (sendMessage (d_recv (defaultSampler False)))
> audition (defaultSampler False)
-}
defaultSampler :: Bool -> Synthdef
defaultSampler :: Bool -> Synthdef
defaultSampler Bool
use_gate =
    let nm :: String
nm = String
"default-sampler-" forall a. [a] -> [a] -> [a]
++ if Bool
use_gate then String
"gate" else String
"fixed"
    in String -> Ugen -> Synthdef
synthdef String
nm (Bool -> Ugen
Help.Graph.default_sampler_ugen_graph Bool
use_gate)

-- | 'ugen_to_graph' of 'synthdefUgen'.
synthdefGraph :: Synthdef -> Graph.U_Graph
synthdefGraph :: Synthdef -> U_Graph
synthdefGraph = Ugen -> U_Graph
Graph.ugen_to_graph forall b c a. (b -> c) -> (a -> b) -> a -> c
. Synthdef -> Ugen
synthdefUgen

{- | Parameter names at 'Synthdef'.

> synthdefParam defaultSynthdef == [("amp",0.1),("pan",0),("gate",1),("freq",440),("out",0)]
-}
synthdefParam :: Synthdef -> Param.Param
synthdefParam :: Synthdef -> Param
synthdefParam =
  forall a b. (a -> b) -> [a] -> [b]
map (\U_Node
n -> (U_Node -> String
Graph.u_node_k_name U_Node
n, U_Node -> Sample
Graph.u_node_k_default U_Node
n)) forall b c a. (b -> c) -> (a -> b) -> a -> c
.
  U_Graph -> [U_Node]
Graph.ug_controls forall b c a. (b -> c) -> (a -> b) -> a -> c
.
  Synthdef -> U_Graph
synthdefGraph

-- | 'graph_to_graphdef' at 'Synthdef'.
synthdef_to_graphdef :: Synthdef -> Graphdef.Graphdef
synthdef_to_graphdef :: Synthdef -> Graphdef
synthdef_to_graphdef (Synthdef String
nm Ugen
u) = String -> U_Graph -> Graphdef
Graphdef.Graph.graph_to_graphdef String
nm (Ugen -> U_Graph
Graph.ugen_to_graph Ugen
u)

-- | 'graph_to_graphdef' at 'Synthdef'.
ugen_to_graphdef :: Ugen.Ugen -> Graphdef.Graphdef
ugen_to_graphdef :: Ugen -> Graphdef
ugen_to_graphdef = Synthdef -> Graphdef
synthdef_to_graphdef forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> Ugen -> Synthdef
Synthdef String
"anonymous"

-- | Encode 'Synthdef' as a binary data stream.
synthdefData :: Synthdef -> L.ByteString
synthdefData :: Synthdef -> ByteString
synthdefData = Graphdef -> ByteString
Graphdef.Binary.encode_graphdef forall b c a. (b -> c) -> (a -> b) -> a -> c
. Synthdef -> Graphdef
synthdef_to_graphdef

-- | Write 'Synthdef' to indicated file.
synthdefWrite :: FilePath -> Synthdef -> IO ()
synthdefWrite :: String -> Synthdef -> IO ()
synthdefWrite String
fn = String -> Graphdef -> IO ()
Graphdef.Binary.graphdefWrite String
fn forall b c a. (b -> c) -> (a -> b) -> a -> c
. Synthdef -> Graphdef
synthdef_to_graphdef

-- | Write 'Synthdef' to indicated directory.  The filename is the
-- 'synthdefName' with the appropriate extension (@scsyndef@).
synthdefWrite_dir :: FilePath -> Synthdef -> IO ()
synthdefWrite_dir :: String -> Synthdef -> IO ()
synthdefWrite_dir String
dir = String -> Graphdef -> IO ()
Graphdef.Binary.graphdefWrite_dir String
dir forall b c a. (b -> c) -> (a -> b) -> a -> c
. Synthdef -> Graphdef
synthdef_to_graphdef

-- | 'graph_stat_ln' of 'synth'.
synthstat_ln :: Ugen.Ugen -> [String]
synthstat_ln :: Ugen -> [String]
synthstat_ln = U_Graph -> [String]
Graph.ug_stat_ln forall b c a. (b -> c) -> (a -> b) -> a -> c
. Ugen -> U_Graph
Graph.ugen_to_graph

-- | 'unlines' of 'synthstat_ln'.
synthstat :: Ugen.Ugen -> String
synthstat :: Ugen -> String
synthstat = [String] -> String
unlines forall b c a. (b -> c) -> (a -> b) -> a -> c
. Ugen -> [String]
synthstat_ln

{- | 'putStrLn' of 'synthstat'.

> synthstat_wr Sound.Sc3.Ugen.Help.Graph.default_ugen_graph
-}
synthstat_wr :: Ugen.Ugen -> IO ()
synthstat_wr :: Ugen -> IO ()
synthstat_wr = String -> IO ()
putStrLn forall b c a. (b -> c) -> (a -> b) -> a -> c
. Ugen -> String
synthstat

{- | Variant without Ugen sequence.

> putStrLn $ synthstat_concise (default_sampler_ugen_graph True)
-}
synthstat_concise :: Ugen.Ugen -> String
synthstat_concise :: Ugen -> String
synthstat_concise = [String] -> String
unlines forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. [a] -> [a]
reverse forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. Int -> [a] -> [a]
drop Int
1 forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. [a] -> [a]
reverse forall b c a. (b -> c) -> (a -> b) -> a -> c
. Ugen -> [String]
synthstat_ln

-- | 'graphdef_dump_ugens' of 'ugen_to_graphdef'
ugen_dump_ugens :: Ugen.Ugen -> IO ()
ugen_dump_ugens :: Ugen -> IO ()
ugen_dump_ugens = Graphdef -> IO ()
Graphdef.graphdef_dump_ugens forall b c a. (b -> c) -> (a -> b) -> a -> c
. Ugen -> Graphdef
ugen_to_graphdef