def createMidiFileBuilder(self, txt): provided = {} provided['Builder'] =bbuilder.BMidiBuilder #reference to class provided['alert'] = midiscript_util.alert #reference to fn provided['status'] = self.status #reference to fn #run the code evaler = midiscript_util.Interpreter(provided) res = evaler.run_code(txt) if res!=True: midiscript_util.alert(res) return #we are most interested in what they set "result" to. if 'result' not in provided or not provided['result']: midiscript_util.alert('You must set "result" to something.') return res = provided['result'] #either a sequence or a value if isinstance(res, bbuilder.BMidiBuilder): #is a single instance mfileobject = bbuilder.build_midi([res]) else: mfileobject = bbuilder.build_midi(res) return mfileobject
def go(self, s): s = s.replace('\r\n', '\n') s = stripComments(s) #check for misplaced >>. they can only occur at the beginning of a line. found = re.findall(r'[^\n]>>', s) if found: raise InterpException( 'The characters >> can only be at start of line. This was not the case: "%s"' % found[0]) lines = s.split('\n') #create tracks self.trackObjs = [ bbuilder.BMidiBuilder() for i in range(Maxtracks) ] #eventually, will be assigned different channels, but not yet. self.state_octave = [4 for i in range(Maxtracks) ] #keeps track of current octave for each track self.state_currentBend = [ 0 for i in range(Maxtracks) ] #keeps track of current pitch-bend state for each track for trackobj in self.trackObjs: trackobj.tempo = 400 trackobj.addFasterTempo = True #secret undocumented un-understood event self.haveSeenNotes = False #have we seen any notes yet? for nline in range(len(lines)): line = lines[nline].strip() if not line: continue elif line.startswith('('): self.interpretControlString(line) elif line.startswith('>>'): self.haveSeenNotes = True parts = [line] nindex = nline while lines[nindex + 1].startswith('>>'): parts.append(lines[nindex + 1]) lines[nindex + 1] = '' #erase that one nindex += 1 if len(parts) > Maxtracks: raise InterpException("Exceeded maximum of %d tracks." % Maxtracks) #each track keeps track of its own currentTime. At the end, though, we have to sync them all back up. longestTimeSeen = -1 for i in range(len(parts)): if Debug: print('TRACK %d' % i) _, parts[i] = eatChars(parts[i], 2) #remove the >> characters self.interpretMusicString(parts[i], i) if self.trackObjs[i].currentTime > longestTimeSeen: longestTimeSeen = self.trackObjs[i].currentTime # restore track sync for all of the tracks. for trackobj in self.trackObjs: trackobj.currentTime = longestTimeSeen else: self.haveSeenNotes = True self.interpretMusicString(line, 0) # keep track sync for all of the tracks. lastTimeSeen = self.trackObjs[0].currentTime for trackobj in self.trackObjs: trackobj.currentTime = lastTimeSeen actualtracks = [ trackobj for trackobj in self.trackObjs if len(trackobj.notes) > 0 ] if len(actualtracks) == 0: #no notes found, so just stop return None # convert notes of pitch 0 to rests. for trackobj in actualtracks: trackobj.notes = [ note for note in trackobj.notes if not ( isinstance(note, bbuilder.SimpleNote) and note.pitch == 0) ] #join all of the tracks, returning a midifile mfile = bbuilder.build_midi(actualtracks) if Debug: print(mfile) return mfile
def go(self, s): s = s.replace('\r\n','\n') s = stripComments(s) #check for misplaced >>. they can only occur at the beginning of a line. found = re.findall(r'[^\n]>>', s) if found: raise InterpException('The characters >> can only be at start of line. This was not the case: "%s"'%found[0]) lines=s.split('\n') #create tracks self.trackObjs = [bbuilder.BMidiBuilder() for i in range(Maxtracks)] #eventually, will be assigned different channels, but not yet. self.state_octave = [4 for i in range(Maxtracks)] #keeps track of current octave for each track self.state_currentBend = [0 for i in range(Maxtracks)] #keeps track of current pitch-bend state for each track for trackobj in self.trackObjs: trackobj.tempo = 400; trackobj.addFasterTempo = True #secret undocumented un-understood event self.haveSeenNotes = False #have we seen any notes yet? for nline in range(len(lines)): line = lines[nline].strip() if not line: continue elif line.startswith('('): self.interpretControlString(line) elif line.startswith('>>'): self.haveSeenNotes = True parts = [line] nindex = nline while lines[nindex+1].startswith('>>'): parts.append(lines[nindex+1]) lines[nindex+1] = '' #erase that one nindex += 1 if len(parts)>Maxtracks: raise InterpException("Exceeded maximum of %d tracks."%Maxtracks) #each track keeps track of its own currentTime. At the end, though, we have to sync them all back up. longestTimeSeen = -1 for i in range(len(parts)): if Debug: print 'TRACK %d'%i _, parts[i] = eatChars(parts[i], 2) #remove the >> characters self.interpretMusicString(parts[i], i) if self.trackObjs[i].currentTime > longestTimeSeen: longestTimeSeen = self.trackObjs[i].currentTime # restore track sync for all of the tracks. for trackobj in self.trackObjs: trackobj.currentTime = longestTimeSeen else: self.haveSeenNotes = True self.interpretMusicString( line, 0 ) # keep track sync for all of the tracks. lastTimeSeen = self.trackObjs[0].currentTime for trackobj in self.trackObjs: trackobj.currentTime = lastTimeSeen actualtracks = [trackobj for trackobj in self.trackObjs if len(trackobj.notes) > 0] if len(actualtracks) == 0: #no notes found, so just stop return None # convert notes of pitch 0 to rests. for trackobj in actualtracks: trackobj.notes = [note for note in trackobj.notes if not (isinstance(note,bbuilder.SimpleNote) and note.pitch==0)] #join all of the tracks, returning a midifile mfile = bbuilder.build_midi(actualtracks) if Debug: print mfile return mfile