File: Noise.hs

package info (click to toggle)
haskell-netwire 5.0.3-6
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 184 kB
  • sloc: haskell: 1,326; makefile: 2
file content (98 lines) | stat: -rw-r--r-- 2,685 bytes parent folder | download | duplicates (6)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
-- |
-- Module:     FRP.Netwire.Noise
-- Copyright:  (c) 2013 Ertugrul Soeylemez
-- License:    BSD3
-- Maintainer: Ertugrul Soeylemez <es@ertes.de>

module FRP.Netwire.Noise
    ( -- * Noise generators
      noise,
      noiseR,
      wackelkontakt,

      -- * Convenience
      stdNoise,
      stdNoiseR,
      stdWackelkontakt
    )
    where

import Control.Wire
import Prelude hiding ((.), id)
import System.Random


-- | Noise events with the given distance between events.  Use 'hold' or
-- 'holdFor' to generate a staircase.

noise ::
    (HasTime t s, Random b, RandomGen g)
    => t  -- ^ Time period.
    -> g  -- ^ Random number generator.
    -> Wire s e m a (Event b)
noise int | int <= 0 = error "noise: Non-positive interval"
noise int = periodicList int . randoms


-- | Noise events with the given distance between events.  Noise will be
-- in the given range.  Use 'hold' or 'holdFor' to generate a staircase.

noiseR ::
    (HasTime t s, Random b, RandomGen g)
    => t       -- ^ Step duration.
    -> (b, b)  -- ^ Noise range.
    -> g       -- ^ Random number generator.
    -> Wire s e m a (Event b)
noiseR int _ | int <= 0 = error "noiseR: Non-positive interval"
noiseR int r = periodicList int . randomRs r


-- | Convenience interface to 'noise' for 'StdGen'.

stdNoise ::
    (HasTime t s, Random b)
    => t    -- ^ Step duration.
    -> Int  -- ^ 'StdGen' seed.
    -> Wire s e m a (Event b)
stdNoise int = noise int . mkStdGen


-- | Convenience interface to 'noiseR' for 'StdGen'.

stdNoiseR ::
    (HasTime t s, Monad m, Random b)
    => t       -- ^ Step duration.
    -> (b, b)  -- ^ Noise range.
    -> Int     -- ^ 'StdGen' seed.
    -> Wire s e m a (Event b)
stdNoiseR int r = noiseR int r . mkStdGen


-- | Convenience interface to 'wackelkontakt' for 'StdGen'.

stdWackelkontakt ::
    (HasTime t s, Monad m, Monoid e)
    => t    -- ^ Step duration.
    -> Double    -- ^ Probability to produce.
    -> Int  -- ^ 'StdGen' seed.
    -> Wire s e m a a
stdWackelkontakt int p = wackelkontakt int p . mkStdGen


-- | Randomly produce or inhibit with the given probability, each time
-- for the given duration.
--
-- The name /Wackelkontakt/ (German for /slack joint/) is a Netwire
-- running gag.  It makes sure that you revisit the documentation from
-- time to time. =)
--
-- * Depends: now.

wackelkontakt ::
    (HasTime t s, Monad m, Monoid e, RandomGen g)
    => t  -- ^ Duration.
    -> Double  -- ^ Probability to produce.
    -> g  -- ^ Random number generator.
    -> Wire s e m a a
wackelkontakt int _ _ | int <= 0 = error "wackelkontakt: Non-positive duration"
wackelkontakt int p g = fmap snd $ when (< p) . hold . noise int g &&& id