module JohnsonTrotter where
import Midi ;
import Pitch ;
import List (inits, tails) ;
import ListLive ;
main :: [ Event (Channel Message) ] ;
main =
channel 0 $ changeTempo timeUnit $ cycle $
concatMap (addBass . concatMap (note qn . makePitch)) $
johnsonTrotter indexes ;
addBass :: [Event Message] -> [Event Message] ;
addBass xs =
noteOn (makePitch 0) :
xs ++
noteOff (makePitch 0) :
[] ;
indexes :: [Integer] ;
indexes = [1,2,3,4] ;
makePitch :: Integer -> Pitch ;
makePitch 0 = c 2 ;
makePitch 1 = c 4 ;
makePitch 2 = e 4 ;
makePitch 3 = g 4 ;
makePitch _ = c 5 ;
johnsonTrotter :: [a] -> [[a]] ;
johnsonTrotter [] = [[]] ;
johnsonTrotter (x:xs) =
concat $
zipWith id
(cycle [walkRight x, walkLeft x])
(johnsonTrotter xs) ;
johnsonTrotterInt :: [Integer] -> [[Integer]] ;
johnsonTrotterInt [] = [[]] ;
johnsonTrotterInt (x:xs) =
concat $
applyStrictListList
(zipWith id
(cycle [walkRight x, walkLeft x]))
(johnsonTrotterInt xs) ;
walkLeft :: a -> [a] -> [[a]] ;
walkLeft x xs = reverse (walkRight x xs) ;
walkRight :: a -> [a] -> [[a]] ;
walkRight x xs =
zipWith (insert x) (inits xs) (tails xs) ;
insert :: a -> [a] -> [a] -> [a] ;
insert x prefix suffix = prefix ++ x : suffix ;
timeUnit :: Time ;
timeUnit = 150 ;
qn :: Integer ;
qn = 1 ;