Differences From Artifact [8e359b2146853023]:
- Executable file
cfg.py
- 2010-11-16 18:37:14 - part of checkin [9bd31df856] on branch ply - Now prints csound code, both notes and chords, replicating the functionality of the original Minimaly Functional Version (user: spiffytech@gmail.com) [annotate]
To Artifact [f6edc4689fdace88]:
- Executable file
cfg.py
- 2010-11-17 00:07:43 - part of checkin [7c7ce6adb8] on branch tld - Added support for top-down composition (user: spiffytech@gmail.com) [annotate]
5 import sys 5 import sys
6 import time 6 import time
7 random.seed(time.time()) 7 random.seed(time.time())
8 import parse 8 import parse
9 9
10 def main(): 10 def main():
11 key = "A" 11 key = "A"
12 note_grammars = { <
> 12
> 13 composition = {
> 14 "a": { # Movement block 'a' for reuse throughout the piece
> 15 "melody": { # Instrument 'melody'
> 16 "csound_parameters": {
> 17 "instrument": 1,
> 18 },
> 19 "grammars": { # Notes for this instrument to use in this piece
13 "u": ["I V V V I I IV u u", "I IV u u", "I VII IV u u" , "e"], | 20 "u": ["I V V V I I IV u u", "I IV u u", "I VII IV u u" , "e
14 "e": [""], | 21 "e": [""],
15 } | 22 },
> 23 "score": "u u u",
> 24 },
> 25 "rhythm": {
> 26 "csound_parameters": {
> 27 "instrument": 1,
> 28 },
16 chord_grammars = { | 29 "grammars": {
17 "u": ['"I" "IV" "V" "IV" "I" u u', '"I" "VII" "IV" u u', '"I" "V" "IV" u | 30 "u": ['"I" "IV"/2 "V"2 "IV" "I" u u', '"I" "VII" "IV" u u',
18 "e": [""] | 31 "e": [""]
19 } | 32 },
20 compose_piece(key, note_grammars) <
21 compose_piece(key, chord_grammars, chords=True) <
> 33 "score": "u u u",
> 34 },
> 35 },
> 36 "b": {
> 37 "melody": { # Instrument 'melody'
> 38 "csound_parameters": {
> 39 "instrument": 1,
> 40 },
> 41 "grammars": { # Notes for this instrument to use in this piece
> 42 "u": ["I V I I/2 IV/2 u u", "I4 IV u u", "I IV IV VI V u u"
> 43 "e": [""],
> 44 },
> 45 "score": "u u u",
> 46 },
> 47 "rhythm": {
> 48 "csound_parameters": {
> 49 "instrument": 1,
> 50 },
> 51 "grammars": {
> 52 "u": ['"I" "IV"/2 "V"2 "IV" "I" u u', '"I" "VII" "IV" u u',
> 53 "e": [""]
> 54 },
> 55 "score": "u u u",
> 56 },
> 57 },
22 | 58 }
23 def compose_piece(key, grammars, chords=False): <
24 score = "" <
25 while len(score.split()) < 10: <
26 score = "u u u" <
27 score = generate_score(score, grammars) <
> 59
> 60 for comp_name, comp in composition.iteritems():
> 61 for instr_name, instr in comp.iteritems():
> 62 generated_score = generate_score(instr["score"], instr["grammars"])
> 63 # composition[comp_name][instr_name][grammar]["score"] = parse.pa
28 score = parse.parse(score) | 64 score = parse.parse(generated_score) # Return Node/Chord objects
29 score = transliterate_score(score, key, chords) <
30 score = generate_csound_score(score) <
> 65
> 66 # Generate timestamps for the notes
> 67 t = 0
> 68 for note in range(len(score)):
> 69 score[note].time = t
> 70 t += score[note].duration
> 71 composition[comp_name][instr_name]["score"] = score
> 72
> 73 # Must be done after all note times keyed in, else you c,an't coordinate mel
> 74 for comp_name, comp in composition.iteritems():
> 75 for instr_name, instr in comp.iteritems():
> 76 composition[comp_name][instr_name]["score"] = transliterate_score(co
> 77 # print "\nMovement %s instrument %s" % (comp_name, instr_name)
> 78 # print composition[comp_name][instr_name]["score"]
31 print "f1 0 256 10 1 0 3 ; sine wave function table" | 79 print "f1 0 256 10 1 0 3 ; sine wave function table"
> 80 final_score = generate_csound_score(composition[comp_name][instr_nam
32 for line in score: | 81 for line in final_score:
33 print line | 82 print line
34 | 83
35 84
36 def make_scale(key): 85 def make_scale(key):
37 notes = ["A", "A#", "B", "C", "C#", "D", "D#", "E", "F", "F#", "G", "G#"] 86 notes = ["A", "A#", "B", "C", "C#", "D", "D#", "E", "F", "F#", "G", "G#"]
38 scale = [key] 87 scale = [key]
39 pos = notes.index(key) 88 pos = notes.index(key)
40 progression = [2,2,1,2,2,2,1] 89 progression = [2,2,1,2,2,2,1]
41 for p in progression: 90 for p in progression:
................................................................................................................................................................................
48 while 1: 97 while 1:
49 found_substitution = False 98 found_substitution = False
50 for key,value in grammars.iteritems(): 99 for key,value in grammars.iteritems():
51 if score.find(key) != -1: 100 if score.find(key) != -1:
52 found_substitution = True 101 found_substitution = True
53 while score.find(key) != -1: 102 while score.find(key) != -1:
54 score = score.replace(key, random.choice(grammars[key]), 1) 103 score = score.replace(key, random.choice(grammars[key]), 1)
55 if len(score) > 200: | 104 if len(score.split()) > 200:
56 score = score.replace("u", "") 105 score = score.replace("u", "")
57 score = score.replace("e", "") 106 score = score.replace("e", "")
58 return score 107 return score
59 if found_substitution is False: 108 if found_substitution is False:
60 break 109 break
61 return score 110 return score
62 111
63 def transliterate_score(score, key, chords=False): | 112 def transliterate_score(score, key):
64 scale = make_scale(key) 113 scale = make_scale(key)
65 scale_conversion = { 114 scale_conversion = {
66 "I": 1, 115 "I": 1,
67 "II": 2, 116 "II": 2,
68 "III": 3, 117 "III": 3,
69 "IV": 4, 118 "IV": 4,
70 "V": 5, 119 "V": 5,
71 "VI": 6, 120 "VI": 6,
72 "VII": 7, 121 "VII": 7,
73 "VIII": 8, 122 "VIII": 8,
74 } 123 }
75 keyed_score = [] 124 keyed_score = []
76 if chords is False: <
77 for i in range(len(score)): | 125 for i in range(len(score)):
> 126 if isinstance(score[i], parse.Note):
78 score[i].value = scale[scale_conversion[score[i].value]-1] 127 score[i].value = scale[scale_conversion[score[i].value]-1]
79 else: | 128 else:
80 for i in range(len(score)): <
81 chord = [] 129 chord = []
82 root_note_index = scale.index(key) + scale_conversion[score[i].value 130 root_note_index = scale.index(key) + scale_conversion[score[i].value
83 chord.append(scale[root_note_index]) 131 chord.append(scale[root_note_index])
84 chord.append(scale[(root_note_index+3) % 8]) 132 chord.append(scale[(root_note_index+3) % 8])
85 chord.append(scale[(root_note_index+5) % 8]) 133 chord.append(scale[(root_note_index+5) % 8])
86 score[i].chord = chord 134 score[i].chord = chord
87 return score 135 return score