def __init__(self,xmlfile=None,gui=None,ports=(7007,7008)): self.xmlfile = xmlfile self.library = Library(xmlfile) self.cur_clip = Clip('',[-1,-1],"no clip loaded") self.cur_song = None self.cur_rec = None self.cur_col = -1 self.search = SearchR(self.library.clips) self.osc_client = ControlR(self,port=ports[0]) self.osc_server = ServeR(gui,port=ports[1]) self.record = RecordR(self) self.last_save_file = None self.cur_time = RefObj("cur_time") self.cur_clip_pos = RefObj("cur_clip_pos",0.0) def update_time(_,msg): # this is the driving force behind the (audio) backend :o) try: self.cur_time.value = int(msg) except: pass def update_song_info(_,msg): if self.cur_song: self.cur_song.vars['total_len'] = int(msg) self.osc_server.map("/pyaud/pos/frame",update_time) self.osc_server.map("/pyaud/info/song_len",update_song_info) self.osc_server.map("/activeclip/video/position/values",self.cur_clip_pos.update_generator('float')) ### MIDI CONTROL # basically, here are the descriptions that map to functions # then in the midi config it reads the keys and figures out # what keys to set to which functions # which are then mapped thru the osc server to figure out # what to do with the note value (different types of notes) self.desc_to_fun = { 'clip_play' : self.osc_client.play , 'clip_pause' : self.osc_client.pause , 'clip_reverse' : self.osc_client.reverse , 'clip_random' : self.osc_client.random_play , 'clip_clear' : self.osc_client.clear , } # can also auto-gen some of these for cue select etc def gen_selector(i): index = i def fun_tor(): self.select_clip(self.library.clip_collections[self.cur_col][index]) return fun_tor for i in range(C.NO_Q): self.desc_to_fun['clip_{}'.format(i)] = gen_selector(i) # no clue how im going to add midi out.. for now self.midi_control = None
def load_composition(self,fname): if fname == self.xmlfile: # add any new clips self.library.update_from_xml(fname) print('updated library from',fname) else: self.xmlfile = fname self.library = Library(fname) self.cur_clip = Clip('',[-1,-1],"no clip loaded") self.cur_col = -1 print('loaded library from',fname) self.search = SearchR(self.library.clips)
class Backend: """ entire backend for sol """ def __init__(self,xmlfile=None,gui=None,ports=(7007,7008)): self.xmlfile = xmlfile self.library = Library(xmlfile) self.cur_clip = Clip('',[-1,-1],"no clip loaded") self.cur_song = None self.cur_rec = None self.cur_col = -1 self.search = SearchR(self.library.clips) self.osc_client = ControlR(self,port=ports[0]) self.osc_server = ServeR(gui,port=ports[1]) self.record = RecordR(self) self.last_save_file = None self.cur_time = RefObj("cur_time") self.cur_clip_pos = RefObj("cur_clip_pos",0.0) def update_time(_,msg): # this is the driving force behind the (audio) backend :o) try: self.cur_time.value = int(msg) except: pass def update_song_info(_,msg): if self.cur_song: self.cur_song.vars['total_len'] = int(msg) self.osc_server.map("/pyaud/pos/frame",update_time) self.osc_server.map("/pyaud/info/song_len",update_song_info) self.osc_server.map("/activeclip/video/position/values",self.cur_clip_pos.update_generator('float')) ### MIDI CONTROL # basically, here are the descriptions that map to functions # then in the midi config it reads the keys and figures out # what keys to set to which functions # which are then mapped thru the osc server to figure out # what to do with the note value (different types of notes) self.desc_to_fun = { 'clip_play' : self.osc_client.play , 'clip_pause' : self.osc_client.pause , 'clip_reverse' : self.osc_client.reverse , 'clip_random' : self.osc_client.random_play , 'clip_clear' : self.osc_client.clear , } # can also auto-gen some of these for cue select etc def gen_selector(i): index = i def fun_tor(): self.select_clip(self.library.clip_collections[self.cur_col][index]) return fun_tor for i in range(C.NO_Q): self.desc_to_fun['clip_{}'.format(i)] = gen_selector(i) # no clue how im going to add midi out.. for now self.midi_control = None #self.load_last() def setup_midi(self): self.midi_control = MidiControl(self) def save_data(self,savefile=None): if not os.path.exists('./savedata'): os.makedirs('./savedata') if not savefile: if not self.last_save_file: filename = os.path.splitext(self.xmlfile)[0] filename = filename.split('/')[-1] savefile = "./savedata/{}".format(filename) else: savefile = self.last_save_file ######## savedata = {'xmlfile':self.xmlfile,'library':self.library, 'current_clip':self.cur_clip,'current_collection':self.cur_col} ######## with open(savefile,'wb') as f: dill.dump(savedata,f) with open('./savedata/last_save','w') as last_save: last_save.write(savefile) print('successfully saved',savefile) self.last_save_file = savefile return savefile # success def load_data(self,savefile): if os.path.exists(savefile): with open(savefile,'rb') as save: savedata = dill.load(save) ######## loaddata = {'xmlfile':'self.xmlfile','library':'self.library', 'current_clip':'self.cur_clip','current_collection':'self.cur_col'} ######## for key in loaddata: if key in savedata: exec("{} = savedata[key]".format(loaddata[key])) self.search = SearchR(self.library.clips) print('successfully loaded',savefile) self.last_save_file = savefile def load_composition(self,fname): if fname == self.xmlfile: # add any new clips self.library.update_from_xml(fname) print('updated library from',fname) else: self.xmlfile = fname self.library = Library(fname) self.cur_clip = Clip('',[-1,-1],"no clip loaded") self.cur_col = -1 print('loaded library from',fname) self.search = SearchR(self.library.clips) def load_last(self): if os.path.exists('./savedata/last_save'): with open('./savedata/last_save') as last_save: fname = last_save.read() self.load_data(fname) if self.midi_control is not None: self.load_last_midi() #self.record.load_last() dangerous (have to implement dependency on audio track 2 do this) def load_last_midi(self): if os.path.exists('./savedata/last_midi'): with open('./savedata/last_midi','r') as last_midi: fname = last_midi.read() self.midi_control.map_midi(fname) def change_clip(self,newclip): if self.cur_clip is not None: self.cur_clip.last_pos = self.cur_clip_pos.value self.cur_clip = newclip self.osc_client.select_clip(newclip) def select_clip(self,newclip): # function to be overwritten : ) self.change_clip(newclip)