3 from gi
.repository
import GObject
, Gdk
, Gtk
6 sys
.path
= ["./py"] + sys
.path
9 from gui_tools
import *
13 import drum_pattern_editor
15 class SceneDialog(SelectObjectDialog
):
16 title
= "Select a scene"
17 def __init__(self
, parent
):
18 SelectObjectDialog
.__init
__(self
, parent
)
19 def update_model(self
, model
):
20 for s
in cbox
.Config
.sections("scene:"):
22 model
.append((s
.name
[6:], "Scene", s
.name
, title
))
23 for s
in cbox
.Config
.sections("instrument:"):
25 model
.append((s
.name
[11:], "Instrument", s
.name
, title
))
26 for s
in cbox
.Config
.sections("layer:"):
28 model
.append((s
.name
[6:], "Layer", s
.name
, title
))
30 class AddLayerDialog(SelectObjectDialog
):
32 def __init__(self
, parent
):
33 SelectObjectDialog
.__init
__(self
, parent
)
34 def update_model(self
, model
):
35 for s
in cbox
.Config
.sections("instrument:"):
37 model
.append((s
.name
[11:], "Instrument", s
.name
, title
))
38 for s
in cbox
.Config
.sections("layer:"):
40 model
.append((s
.name
[6:], "Layer", s
.name
, title
))
42 class PlayPatternDialog(SelectObjectDialog
):
43 title
= "Play a drum pattern"
44 def __init__(self
, parent
):
45 SelectObjectDialog
.__init
__(self
, parent
)
46 def update_model(self
, model
):
47 model
.append((None, "Stop", "", ""))
48 for s
in cbox
.Config
.sections("drumpattern:"):
50 model
.append((s
.name
[12:], "Pattern", s
.name
, title
))
51 for s
in cbox
.Config
.sections("drumtrack:"):
53 model
.append((s
.name
[10:], "Track", s
.name
, title
))
55 in_channels_ls
= Gtk
.ListStore(GObject
.TYPE_INT
, GObject
.TYPE_STRING
)
56 in_channels_ls
.append((0, "All"))
57 out_channels_ls
= Gtk
.ListStore(GObject
.TYPE_INT
, GObject
.TYPE_STRING
)
58 out_channels_ls
.append((0, "Same"))
59 for i
in range(1, 17):
60 in_channels_ls
.append((i
, str(i
)))
61 out_channels_ls
.append((i
, str(i
)))
62 notes_ls
= Gtk
.ListStore(GObject
.TYPE_INT
, GObject
.TYPE_STRING
)
63 opt_notes_ls
= Gtk
.ListStore(GObject
.TYPE_INT
, GObject
.TYPE_STRING
)
64 opt_notes_ls
.append((-1, "N/A"))
65 for i
in range(0, 128):
66 notes_ls
.append((i
, note_to_name(i
)))
67 opt_notes_ls
.append((i
, note_to_name(i
)))
68 transpose_ls
= Gtk
.ListStore(GObject
.TYPE_INT
, GObject
.TYPE_STRING
)
69 for i
in range(-60, 61):
70 transpose_ls
.append((i
, str(i
)))
72 class SceneLayersModel(Gtk
.ListStore
):
74 Gtk
.ListStore
.__init
__(self
, GObject
.TYPE_STRING
, GObject
.TYPE_BOOLEAN
,
75 GObject
.TYPE_INT
, GObject
.TYPE_INT
, GObject
.TYPE_BOOLEAN
,
76 GObject
.TYPE_INT
, GObject
.TYPE_INT
, GObject
.TYPE_INT
, GObject
.TYPE_INT
, GObject
.TYPE_STRING
)
77 #def make_row_item(self, opath, tree_path):
78 # return opath % self[(1 + int(tree_path))]
79 def make_row_item(self
, opath
, tree_path
):
80 return cbox
.Document
.uuid_cmd(self
[int(tree_path
)][-1], opath
)
81 def refresh(self
, scene_status
):
83 for layer
in scene_status
.layers
:
85 self
.append((ls
.instrument_name
, ls
.enable
!= 0, ls
.in_channel
, ls
.out_channel
, ls
.consume
!= 0, ls
.low_note
, ls
.high_note
, ls
.fixed_note
, ls
.transpose
, layer
.uuid
))
87 class SceneLayersView(Gtk
.TreeView
):
88 def __init__(self
, model
):
89 Gtk
.TreeView
.__init
__(self
, model
)
90 self
.enable_model_drag_source(Gdk
.ModifierType
.BUTTON1_MASK
, [("text/plain", 0, 1)], Gdk
.DragAction
.MOVE
)
91 self
.enable_model_drag_dest([("text/plain", Gtk
.TargetFlags
.SAME_APP | Gtk
.TargetFlags
.SAME_WIDGET
, 1)], Gdk
.DragAction
.MOVE
)
92 self
.connect('drag_data_get', self
.drag_data_get
)
93 self
.connect('drag_data_received', self
.drag_data_received
)
94 self
.insert_column_with_attributes(0, "On?", standard_toggle_renderer(model
, "/enable", 1), active
=1)
95 self
.insert_column_with_attributes(1, "Name", Gtk
.CellRendererText(), text
=0)
96 self
.insert_column_with_data_func(2, "In Ch#", standard_combo_renderer(model
, in_channels_ls
, "/in_channel", 2), lambda column
, cell
, model
, iter, data
: cell
.set_property('text', "%s" % model
[iter][2] if model
[iter][2] != 0 else 'All'), None)
97 self
.insert_column_with_data_func(3, "Out Ch#", standard_combo_renderer(model
, out_channels_ls
, "/out_channel", 3), lambda column
, cell
, model
, iter, data
: cell
.set_property('text', "%s" % model
[iter][3] if model
[iter][3] != 0 else 'Same'), None)
98 self
.insert_column_with_attributes(4, "Eat?", standard_toggle_renderer(model
, "/consume", 4), active
=4)
99 self
.insert_column_with_data_func(5, "Lo N#", standard_combo_renderer(model
, notes_ls
, "/low_note", 5), lambda column
, cell
, model
, iter, data
: cell
.set_property('text', note_to_name(model
[iter][5])), None)
100 self
.insert_column_with_data_func(6, "Hi N#", standard_combo_renderer(model
, notes_ls
, "/high_note", 6), lambda column
, cell
, model
, iter, data
: cell
.set_property('text', note_to_name(model
[iter][6])), None)
101 self
.insert_column_with_data_func(7, "Fix N#", standard_combo_renderer(model
, opt_notes_ls
, "/fixed_note", 7), lambda column
, cell
, model
, iter, data
: cell
.set_property('text', note_to_name(model
[iter][7])), None)
102 self
.insert_column_with_attributes(8, "Transpose", standard_combo_renderer(model
, transpose_ls
, "/transpose", 8), text
=8)
103 def drag_data_get(self
, treeview
, context
, selection
, target_id
, etime
):
104 cursor
= treeview
.get_cursor()
105 if cursor
is not None:
106 selection
.set('text/plain', 8, str(cursor
[0][0]))
107 def drag_data_received(self
, treeview
, context
, x
, y
, selection
, info
, etime
):
108 src_row
= int(selection
.data
)
109 dest_row_info
= treeview
.get_dest_row_at_pos(x
, y
)
110 if dest_row_info
is not None:
111 dest_row
= dest_row_info
[0][0]
112 #print src_row, dest_row, dest_row_info[1]
113 scene
= cbox
.Document
.get_scene()
114 scene
.move_layer(src_row
, dest_row
)
115 self
.get_model().refresh(scene
.status())
117 class SceneAuxBusesModel(Gtk
.ListStore
):
119 Gtk
.ListStore
.__init
__(self
, GObject
.TYPE_STRING
, GObject
.TYPE_STRING
)
120 def refresh(self
, scene_status
):
122 for aux_name
, aux_obj
in scene_status
.auxes
.items():
123 # XXXKF make slots more 1st class
124 slot
= aux_obj
.get_slot_status()
125 self
.append((slot
.insert_preset
, slot
.insert_engine
))
127 class SceneAuxBusesView(Gtk
.TreeView
):
128 def __init__(self
, model
):
129 Gtk
.TreeView
.__init
__(self
, model
)
130 self
.insert_column_with_attributes(0, "Name", Gtk
.CellRendererText(), text
=0)
131 self
.insert_column_with_attributes(1, "Engine", Gtk
.CellRendererText(), text
=1)
132 def get_current_row(self
):
133 if self
.get_cursor()[0] is None:
135 row
= self
.get_cursor()[0][0]
136 return row
+ 1, self
.get_model()[row
]
138 class StatusBar(Gtk
.Statusbar
):
140 Gtk
.Statusbar
.__init
__(self
)
141 self
.sample_rate_label
= Gtk
.Label("")
142 self
.pack_start(self
.sample_rate_label
, False, False, 2)
143 self
.status
= self
.get_context_id("Status")
144 self
.sample_rate
= self
.get_context_id("Sample rate")
145 self
.push(self
.status
, "")
146 self
.push(self
.sample_rate
, "-")
147 def update(self
, status
, sample_rate
):
148 self
.pop(self
.status
)
149 self
.push(self
.status
, status
)
150 self
.sample_rate_label
.set_text("%s Hz" % sample_rate
)
152 class MainWindow(Gtk
.Window
):
154 Gtk
.Window
.__init
__(self
, Gtk
.WindowType
.TOPLEVEL
)
155 self
.vbox
= Gtk
.VBox(spacing
= 5)
158 set_timer(self
, 30, self
.update
)
159 self
.drum_pattern_editor
= None
160 self
.drumkit_editor
= None
163 self
.menu_bar
= Gtk
.MenuBar()
165 self
.menu_bar
.append(create_menu("_Scene", [
166 ("_Load", self
.load_scene
),
167 ("_Quit", self
.quit
),
169 self
.menu_bar
.append(create_menu("_Layer", [
170 ("_Add", self
.layer_add
),
171 ("_Remove", self
.layer_remove
),
173 self
.menu_bar
.append(create_menu("_AuxBus", [
174 ("_Add", self
.aux_bus_add
),
175 ("_Edit", self
.aux_bus_edit
),
176 ("_Remove", self
.aux_bus_remove
),
178 self
.menu_bar
.append(create_menu("_Tools", [
179 ("_Drum Kit Editor", self
.tools_drumkit_editor
),
180 ("_Play Drum Pattern", self
.tools_play_drum_pattern
),
181 ("_Edit Drum Pattern", self
.tools_drum_pattern_editor
),
182 ("_Un-zombify", self
.tools_unzombify
),
183 ("_Object list", self
.tools_object_list
),
184 ("_Wave bank dump", self
.tools_wave_bank_dump
),
187 self
.vbox
.pack_start(self
.menu_bar
, False, False, 0)
188 rt
= cbox
.GetThings("/rt/status", ['audio_channels'], [])
189 scene
= cbox
.Document
.get_scene()
190 self
.nb
= Gtk
.Notebook()
191 self
.vbox
.add(self
.nb
)
192 self
.nb
.append_page(self
.create_master(scene
), Gtk
.Label("Master"))
193 self
.status_bar
= StatusBar()
194 self
.vbox
.pack_start(self
.status_bar
, False, False, 0)
195 self
.create_instrument_pages(scene
.status(), rt
)
197 def create_master(self
, scene
):
198 scene_status
= scene
.status()
199 self
.master_info
= left_label("")
200 self
.timesig_info
= left_label("")
203 t
.set_col_spacings(5)
204 t
.set_row_spacings(5)
206 t
.attach(bold_label("Scene"), 0, 1, 0, 1, Gtk
.AttachOptions
.SHRINK | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
207 self
.scene_label
= left_label(scene_status
.name
)
208 t
.attach(self
.scene_label
, 1, 3, 0, 1, Gtk
.AttachOptions
.SHRINK | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
210 self
.title_label
= left_label(scene_status
.title
)
211 t
.attach(bold_label("Title"), 0, 1, 1, 2, Gtk
.AttachOptions
.SHRINK | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
212 t
.attach(self
.title_label
, 1, 3, 1, 2, Gtk
.AttachOptions
.SHRINK | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
214 t
.attach(bold_label("Play pos"), 0, 1, 2, 3, Gtk
.AttachOptions
.SHRINK | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
215 t
.attach(self
.master_info
, 1, 3, 2, 3, Gtk
.AttachOptions
.EXPAND | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
217 t
.attach(bold_label("Time sig"), 0, 1, 3, 4, Gtk
.AttachOptions
.SHRINK | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
218 t
.attach(self
.timesig_info
, 1, 2, 3, 4, Gtk
.AttachOptions
.SHRINK | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
219 hb
= Gtk
.HButtonBox()
220 b
= Gtk
.Button("Play")
221 b
.connect('clicked', lambda w
: cbox
.Transport
.play())
222 hb
.pack_start(b
, False, False, 5)
223 b
= Gtk
.Button("Stop")
224 b
.connect('clicked', lambda w
: cbox
.Transport
.stop())
225 hb
.pack_start(b
, False, False, 5)
226 b
= Gtk
.Button("Rewind")
227 b
.connect('clicked', lambda w
: cbox
.Transport
.seek_ppqn(0))
228 hb
.pack_start(b
, False, False, 5)
229 b
= Gtk
.Button("Panic")
230 b
.connect('clicked', lambda w
: cbox
.Transport
.panic())
231 hb
.pack_start(b
, False, False, 5)
232 t
.attach(hb
, 2, 3, 3, 4, Gtk
.AttachOptions
.EXPAND
, Gtk
.AttachOptions
.SHRINK
)
234 t
.attach(bold_label("Tempo"), 0, 1, 4, 5, Gtk
.AttachOptions
.SHRINK | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
235 self
.tempo_adj
= Gtk
.Adjustment(40, 40, 300, 1, 5, 0)
236 self
.tempo_adj
.connect('value_changed', adjustment_changed_float
, cbox
.VarPath("/master/set_tempo"))
237 t
.attach(standard_hslider(self
.tempo_adj
), 1, 3, 4, 5, Gtk
.AttachOptions
.EXPAND | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
239 t
.attach(bold_label("Transpose"), 0, 1, 5, 6, Gtk
.AttachOptions
.SHRINK | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
240 self
.transpose_adj
= Gtk
.Adjustment(scene_status
.transpose
, -24, 24, 1, 5, 0)
241 self
.transpose_adj
.connect('value_changed', adjustment_changed_int
, cbox
.VarPath('/scene/transpose'))
242 t
.attach(standard_align(Gtk
.SpinButton(adjustment
= self
.transpose_adj
), 0, 0, 0, 0), 1, 3, 5, 6, Gtk
.AttachOptions
.EXPAND | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
244 self
.layers_model
= SceneLayersModel()
245 self
.layers_view
= SceneLayersView(self
.layers_model
)
246 t
.attach(standard_vscroll_window(-1, 160, self
.layers_view
), 0, 3, 6, 7, Gtk
.AttachOptions
.EXPAND | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
248 self
.auxes_model
= SceneAuxBusesModel()
249 self
.auxes_view
= SceneAuxBusesView(self
.auxes_model
)
250 t
.attach(standard_vscroll_window(-1, 120, self
.auxes_view
), 0, 3, 7, 8, Gtk
.AttachOptions
.EXPAND | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
252 self
.layers_model
.refresh(scene_status
)
253 self
.auxes_model
.refresh(scene_status
)
260 def load_scene(self
, w
):
261 d
= SceneDialog(self
)
264 if response
== Gtk
.ResponseType
.OK
:
265 scene
= cbox
.Document
.get_scene()
266 item_name
, item_type
, item_key
, item_label
= d
.get_selected_object()
267 if item_type
== 'Scene':
268 scene
.load(item_name
)
269 elif item_type
== 'Layer':
271 scene
.add_layer(item_name
)
272 elif item_type
== 'Instrument':
274 scene
.add_instrument_layer(item_name
)
275 scene_status
= scene
.status()
276 self
.scene_label
.set_text(scene_status
.name
)
277 self
.title_label
.set_text(scene_status
.title
)
278 self
.refresh_instrument_pages(scene_status
)
282 def layer_add(self
, w
):
283 d
= AddLayerDialog(self
)
286 if response
== Gtk
.ResponseType
.OK
:
287 scene
= cbox
.Document
.get_scene()
288 item_name
, item_type
, item_key
, item_label
= d
.get_selected_object()
289 if item_type
== 'Layer':
290 scene
.add_layer(item_name
)
291 elif item_type
== 'Instrument':
292 scene
.add_instrument_layer(item_name
)
293 self
.refresh_instrument_pages()
297 def layer_remove(self
, w
):
298 if self
.layers_view
.get_cursor()[0] is not None:
299 pos
= self
.layers_view
.get_cursor()[0][0]
300 cbox
.Document
.get_scene().delete_layer(pos
)
301 self
.refresh_instrument_pages()
303 def aux_bus_add(self
, w
):
304 d
= fx_gui
.LoadEffectDialog(self
)
307 cbox
.do_cmd("/scene/load_aux", None, [d
.get_selected_object()[0]])
308 self
.refresh_instrument_pages()
311 def aux_bus_remove(self
, w
):
312 rowid
, row
= self
.auxes_view
.get_current_row()
315 cbox
.do_cmd("/scene/delete_aux", None, [row
[0]])
316 self
.refresh_instrument_pages()
318 def aux_bus_edit(self
, w
):
319 rowid
, row
= self
.auxes_view
.get_current_row()
322 wclass
= fx_gui
.effect_window_map
[row
[1]]
323 popup
= wclass("Aux: %s" % row
[0], self
, "/scene/aux/%d/engine" % rowid
)
327 def tools_unzombify(self
, w
):
328 cbox
.do_cmd("/rt/cycle", None, [])
330 def tools_drumkit_editor(self
, w
):
331 if self
.drumkit_editor
is None:
332 self
.drumkit_editor
= drumkit_editor
.EditorDialog(self
)
333 self
.refresh_instrument_pages()
334 self
.drumkit_editor
.connect('destroy', self
.on_drumkit_editor_destroy
)
335 self
.drumkit_editor
.show_all()
336 self
.drumkit_editor
.present()
338 def on_drumkit_editor_destroy(self
, w
):
339 self
.drumkit_editor
= None
341 def tools_object_list(self
, w
):
344 def tools_wave_bank_dump(self
, w
):
345 waves
= cbox
.GetThings("/waves/list", ["*waveform"], [])
346 for w
in waves
.waveform
:
347 info
= cbox
.GetThings("/waves/info", ["filename", "name", "bytes", "loop"], [w
])
348 print("%s: %d bytes, loop = %s" % (info
.filename
, info
.bytes
, info
.loop
))
350 def tools_play_drum_pattern(self
, w
):
351 d
= PlayPatternDialog(self
)
354 if response
== Gtk
.ResponseType
.OK
:
355 row
= d
.get_selected_object()
356 if row
[1] == 'Pattern':
357 song
= cbox
.Document().get_song()
358 song
.loop_single_pattern(lambda: song
.load_drum_pattern(row
[0]))
359 elif row
[1] == 'Track':
360 song
= cbox
.Document().get_song()
361 song
.loop_single_pattern(lambda: song
.load_drum_track(row
[0]))
362 elif row
[1] == 'Stop':
363 song
= cbox
.Document().get_song()
365 song
.update_playback()
369 def tools_drum_pattern_editor(self
, w
):
370 if self
.drum_pattern_editor
is None:
371 length
= drum_pattern_editor
.PPQN
* 4
372 pat_data
= cbox
.Pattern
.get_pattern()
373 if pat_data
is not None:
374 pat_data
, length
= pat_data
375 self
.drum_pattern_editor
= drum_pattern_editor
.DrumSeqWindow(length
, pat_data
)
376 self
.drum_pattern_editor
.set_title("Drum pattern editor")
377 self
.drum_pattern_editor
.show_all()
378 self
.drum_pattern_editor
.connect('destroy', self
.on_drum_pattern_editor_destroy
)
379 self
.drum_pattern_editor
.pattern
.connect('changed', self
.on_drum_pattern_changed
)
380 self
.drum_pattern_editor
.pattern
.changed()
381 self
.drum_pattern_editor
.present()
383 def on_drum_pattern_changed(self
, pattern
):
385 for i
in pattern
.items():
387 data
+= cbox
.Pattern
.serialize_event(int(i
.pos
), 0x90 + ch
, int(i
.row
), int(i
.vel
))
389 data
+= cbox
.Pattern
.serialize_event(int(i
.pos
+ i
.len - 1), 0x80 + ch
, int(i
.row
), int(i
.vel
))
391 data
+= cbox
.Pattern
.serialize_event(int(i
.pos
+ 1), 0x80 + ch
, int(i
.row
), int(i
.vel
))
393 length
= pattern
.get_length()
395 song
= cbox
.Document().get_song()
396 song
.loop_single_pattern(lambda: song
.pattern_from_blob(data
, length
))
398 def on_drum_pattern_editor_destroy(self
, w
):
399 self
.drum_pattern_editor
= None
401 def refresh_instrument_pages(self
, scene_status
= None):
402 self
.delete_instrument_pages()
403 rt
= cbox
.GetThings("/rt/status", ['audio_channels'], [])
404 if scene_status
is None:
405 scene_status
= cbox
.Document
.get_scene().status()
406 self
.layers_model
.refresh(scene_status
)
407 self
.auxes_model
.refresh(scene_status
)
408 self
.create_instrument_pages(scene_status
, rt
)
410 self
.title_label
.set_text(scene_status
.title
)
412 def create_instrument_pages(self
, scene_status
, rt
):
413 self
.path_widgets
= {}
414 self
.path_popups
= {}
415 self
.fx_choosers
= {}
417 outputs_ls
= Gtk
.ListStore(GObject
.TYPE_STRING
, GObject
.TYPE_INT
)
418 for out
in range(0, rt
.audio_channels
[1]//2):
419 outputs_ls
.append(("Out %s/%s" % (out
* 2 + 1, out
* 2 + 2), out
))
421 auxbus_ls
= Gtk
.ListStore(GObject
.TYPE_STRING
, GObject
.TYPE_STRING
)
422 auxbus_ls
.append(("", ""))
423 for bus_name
in scene_status
.auxes
.keys():
424 auxbus_ls
.append(("Aux: %s" % bus_name
, bus_name
))
426 for iname
, (iengine
, iobj
) in scene_status
.instruments
.items():
427 ipath
= "/scene/instr/%s" % iname
428 idata
= iobj
.status()
429 #attribs = cbox.GetThings("/scene/instr_info", ['engine', 'name'], [i])
430 #markup += '<b>Instrument %d:</b> engine %s, name %s\n' % (i, attribs.engine, attribs.name)
431 b
= Gtk
.VBox(spacing
= 5)
432 b
.set_border_width(5)
433 b
.pack_start(Gtk
.Label("Engine: %s" % iengine
), False, False, 5)
434 b
.pack_start(Gtk
.HSeparator(), False, False, 5)
435 t
= Gtk
.Table(1 + idata
.outputs
, 7)
436 t
.set_col_spacings(5)
437 t
.attach(bold_label("Instr. output", 0.5), 0, 1, 0, 1, Gtk
.AttachOptions
.SHRINK
, Gtk
.AttachOptions
.SHRINK
)
438 t
.attach(bold_label("Send to", 0.5), 1, 2, 0, 1, Gtk
.AttachOptions
.SHRINK
, Gtk
.AttachOptions
.SHRINK
)
439 t
.attach(bold_label("Gain [dB]", 0.5), 2, 3, 0, 1, 0, Gtk
.AttachOptions
.SHRINK
)
440 t
.attach(bold_label("Effect", 0.5), 3, 4, 0, 1, 0, Gtk
.AttachOptions
.SHRINK
)
441 t
.attach(bold_label("Preset", 0.5), 4, 7, 0, 1, 0, Gtk
.AttachOptions
.SHRINK
)
442 b
.pack_start(t
, False, False, 5)
445 for o
in range(1, idata
.outputs
+ 1):
446 is_aux
= o
>= idata
.aux_offset
448 opath
= "%s/output/%s" % (ipath
, o
)
449 output_name
= "Out %s" % o
451 opath
= "%s/aux/%s" % (ipath
, o
- idata
.aux_offset
+ 1)
452 output_name
= "Aux %s" % (o
- idata
.aux_offset
+ 1)
453 odata
= cbox
.GetThings(opath
+ "/status", ['gain', 'output', 'bus', 'insert_engine', 'insert_preset', 'bypass'], [])
454 engine
= odata
.insert_engine
455 preset
= odata
.insert_preset
456 bypass
= odata
.bypass
458 t
.attach(Gtk
.Label(output_name
), 0, 1, y
, y
+ 1, Gtk
.AttachOptions
.SHRINK
, Gtk
.AttachOptions
.SHRINK
)
461 cb
= standard_combo(outputs_ls
, odata
.output
- 1)
462 cb
.connect('changed', combo_value_changed
, cbox
.VarPath(opath
+ '/output'), 1)
464 cb
= standard_combo(auxbus_ls
, ls_index(auxbus_ls
, odata
.bus
, 1))
465 cb
.connect('changed', combo_value_changed_use_column
, cbox
.VarPath(opath
+ '/bus'), 1)
466 t
.attach(cb
, 1, 2, y
, y
+ 1, Gtk
.AttachOptions
.SHRINK
, Gtk
.AttachOptions
.SHRINK
)
468 adj
= Gtk
.Adjustment(odata
.gain
, -96, 24, 1, 6, 0)
469 adj
.connect('value_changed', adjustment_changed_float
, cbox
.VarPath(opath
+ '/gain'))
470 t
.attach(standard_hslider(adj
), 2, 3, y
, y
+ 1, Gtk
.AttachOptions
.EXPAND | Gtk
.AttachOptions
.FILL
, Gtk
.AttachOptions
.SHRINK
)
472 chooser
= fx_gui
.InsertEffectChooser(opath
, "%s: %s" % (iname
, output_name
), engine
, preset
, bypass
, self
)
473 self
.fx_choosers
[opath
] = chooser
474 t
.attach(chooser
.fx_engine
, 3, 4, y
, y
+ 1, 0, Gtk
.AttachOptions
.SHRINK
)
475 t
.attach(chooser
.fx_preset
, 4, 5, y
, y
+ 1, 0, Gtk
.AttachOptions
.SHRINK
)
476 t
.attach(chooser
.fx_edit
, 5, 6, y
, y
+ 1, 0, Gtk
.AttachOptions
.SHRINK
)
477 t
.attach(chooser
.fx_bypass
, 6, 7, y
, y
+ 1, 0, Gtk
.AttachOptions
.SHRINK
)
479 if iengine
in instr_gui
.instrument_window_map
:
480 b
.pack_start(Gtk
.HSeparator(), False, False, 5)
481 b
.pack_start(instr_gui
.instrument_window_map
[iengine
](iname
, iobj
), True, True, 5)
482 self
.nb
.append_page(b
, Gtk
.Label(iname
))
485 def delete_instrument_pages(self
):
486 while self
.nb
.get_n_pages() > 1:
487 self
.nb
.remove_page(self
.nb
.get_n_pages() - 1)
491 master
= cbox
.GetThings("/master/status", ['pos', 'pos_ppqn', 'tempo', 'timesig', 'sample_rate'], [])
492 if master
.tempo
is not None:
493 self
.master_info
.set_markup('%s (%s)' % (master
.pos
, master
.pos_ppqn
))
494 self
.timesig_info
.set_markup("%s/%s" % tuple(master
.timesig
))
495 self
.tempo_adj
.set_value(master
.tempo
)
496 state
= cbox
.GetThings("/rt/status", ['state'], []).state
497 self
.status_bar
.update(state
[1], master
.sample_rate
)
506 w
.connect('destroy', do_quit
)