; chord-sequence produces a set of elements (each of which is a set of chords) ; this is essentially a solution/creative response to assignment 2! (defun chord-sequence (sequence-list element-duration current-pitch current-time) (if (null sequence-list) nil (append (make-element (car sequence-list) (car sequence-list) element-duration current-pitch current-time) (chord-sequence (cdr sequence-list) element-duration (+ current-pitch (car sequence-list)) (+ current-time element-duration))))) ; make-element produces groups of chords (defun make-element (number-events remaining-events element-duration base-pitch base-time) (if (<= remaining-events 0) nil (let* ((chord-duration (/ element-duration number-events)) (next-time (+ base-time chord-duration))) (append (make-chord number-events chord-duration number-events base-pitch base-time) (make-element number-events (- remaining-events 1) element-duration (+ base-pitch 1) next-time))))) ; make-chord produces individual chords (defun make-chord (number-pitches chord-duration interval current-pitch current-time) (if (<= number-pitches 0) nil (cons (new midi :time current-time :duration chord-duration :keynum current-pitch :amplitude 0.9) (make-chord (- number-pitches 1) chord-duration interval (+ current-pitch interval) current-time)))) ; and here's the call which produces the whole thing.... ; (events (chord-sequence (list 1 2 3 5 8 13) 3.0 20 0) "test.mid") ; turning our attention to the use of random values in algorithms (a la Cage) ; definitions of gamuts for use in random selection ; (remember Cage's use of gamuts in works like Music of Changes) (defparameter pitch-gamut (list 0 1 3 4 6 7 9 10 11)) (defparameter register-gamut (list 36 60 72 84 96)) (defparameter onset-spacing-gamut (list 0 0.1 0.17 0.23 0.77 1.34 2.2 3.17)) (defparameter duration-gamut (list 0.05 0.08 0.15 0.35 0.89 2.3)) (defparameter amplitude-gamut (list 0.2 0.3 0.35 0.4 0.9)) ; function which picks a random element from a gamut (defun choose-from-gamut (gamut) (nth (random (length gamut)) gamut)) ; function which generates a single chord (choosing pitch and register from supplied gamuts) (defun generate-chord (number-pitches pitches registers start-time dur amp) (if (<= number-pitches 0) nil (cons (new midi :time start-time :keynum (+ (choose-from-gamut pitches) (choose-from-gamut registers)) :amplitude amp :duration dur) (generate-chord (- number-pitches 1) pitches registers start-time dur amp)))) ; function which produces a sequence of chords from gamuts (defun gamut-chords (number-chords pitches registers onsets durations amplitudes start-time) (if (<= number-chords 0) nil (let ((next-onset (+ start-time (choose-from-gamut onsets))) (dur (choose-from-gamut durations)) (amp (choose-from-gamut amplitudes))) (append (generate-chord 3 pitches registers start-time dur amp) (gamut-chords (- number-chords 1) pitches registers onsets durations amplitudes next-onset))))) #| (events (append (gamut-chords 20 pitch-gamut register-gamut onset-spacing-gamut duration-gamut amplitude-gamut 0.0) (gamut-chords 20 pitch-gamut register-gamut onset-spacing-gamut duration-gamut amplitude-gamut 0.0) (gamut-chords 20 pitch-gamut register-gamut onset-spacing-gamut duration-gamut amplitude-gamut 0.0)) "test.mid") |#