2 Copyright (C) 2016 Robin Gareus <robin@gareus.org
3 Copyright (C) 2009-2012 Paul Davis
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
28 #include "pbd/file_utils.h"
30 #include <gtkmm/box.h>
31 #include <gtkmm/notebook.h>
32 #include <gtkmm/table.h>
33 #include <gtkmm/label.h>
34 #include <gtkmm/button.h>
35 #include <gtkmm/spinbutton.h>
36 #include <gtkmm/comboboxtext.h>
38 #include "gtkmm2ext/gtk_ui.h"
39 #include "gtkmm2ext/gui_thread.h"
40 #include "gtkmm2ext/utils.h"
42 #include "ardour/filesystem_paths.h"
50 using namespace ARDOUR;
52 using namespace Gtkmm2ext;
53 using namespace ArdourSurface;
55 OSC_GUI::OSC_GUI (OSC& p)
58 int n = 0; // table row
59 Table* table = manage (new Table);
61 table->set_row_spacings (16);
62 table->set_col_spacings (6);
63 table->set_border_width (12);
68 label = manage (new Gtk::Label(_("Connection:")));
69 label->set_alignment(1, .5);
70 table->attach (*label, 0, 1, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
71 label = manage (new Gtk::Label(cp.get_server_url()));
72 table->attach (*label, 1, 2, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
75 // show and set port to auto (default) or manual (one surface only)
76 label = manage (new Gtk::Label(_("Port Mode:")));
77 label->set_alignment(1, .5);
78 table->attach (*label, 0, 1, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
79 table->attach (portmode_combo, 1, 2, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
80 std::vector<std::string> portmode_options;
81 portmode_options.push_back (_("Auto - Reply to Originating Port"));
82 portmode_options.push_back (_("Manual - Specify Below"));
84 set_popdown_strings (portmode_combo, portmode_options);
85 portmode_combo.set_active ((int)cp.get_portmode());
89 label = manage (new Gtk::Label(_("Reply Manual Port:")));
90 label->set_alignment(1, .5);
91 table->attach (*label, 0, 1, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
92 table->attach (port_entry, 1, 2, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
93 port_entry.set_range(1024, 0xffff);
94 port_entry.set_increments (1, 100);
95 port_entry.set_text(cp.get_remote_port().c_str());
96 if (!cp.get_portmode()) {
97 port_entry.set_sensitive (false);
101 // default banksize setting
102 label = manage (new Gtk::Label(_("Bank Size:")));
103 label->set_alignment(1, .5);
104 table->attach (*label, 0, 1, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
105 table->attach (bank_entry, 1, 2, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
106 bank_entry.set_range (0, 0xffff);
107 bank_entry.set_increments (1, 8);
108 bank_entry.set_value (cp.get_banksize());
112 // default send page setting
113 label = manage (new Gtk::Label(_("Send Page Size:")));
114 label->set_alignment(1, .5);
115 table->attach (*label, 0, 1, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
116 table->attach (send_page_entry, 1, 2, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
117 send_page_entry.set_range (0, 0xffff);
118 send_page_entry.set_increments (1, 8);
119 send_page_entry.set_value (cp.get_send_size());
123 // default plugin page setting
124 label = manage (new Gtk::Label(_("Plugin Page Size:")));
125 label->set_alignment(1, .5);
126 table->attach (*label, 0, 1, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
127 table->attach (plugin_page_entry, 1, 2, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
128 plugin_page_entry.set_range (0, 0xffff);
129 plugin_page_entry.set_increments (1, 8);
130 plugin_page_entry.set_value (cp.get_send_size());
135 label = manage (new Gtk::Label(_("Gain Mode:")));
136 label->set_alignment(1, .5);
137 table->attach (*label, 0, 1, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
138 table->attach (gainmode_combo, 1, 2, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
139 std::vector<std::string> gainmode_options;
140 gainmode_options.push_back (_("/strip/gain (dB)"));
141 gainmode_options.push_back (_("/strip/fader (Position) and dB in control name"));
142 gainmode_options.push_back (_("/strip/fader (Position) and /strip/gain (dB)"));
143 gainmode_options.push_back (_("/strip/fader (Position)"));
145 set_popdown_strings (gainmode_combo, gainmode_options);
146 gainmode_combo.set_active ((int)cp.get_gainmode());
150 label = manage (new Gtk::Label(_("Debug:")));
151 label->set_alignment(1, .5);
152 table->attach (*label, 0, 1, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
153 table->attach (debug_combo, 1, 2, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
155 std::vector<std::string> debug_options;
156 debug_options.push_back (_("Off"));
157 debug_options.push_back (_("Log invalid messages"));
158 debug_options.push_back (_("Log all messages"));
159 debug_options.push_back (_("Print surface information to Log window"));
161 set_popdown_strings (debug_combo, debug_options);
162 debug_combo.set_active ((int)cp.get_debug_mode());
165 // Preset loader combo
166 label = manage (new Gtk::Label(_("Preset:")));
167 label->set_alignment(1, .5);
168 table->attach (*label, 0, 1, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
169 table->attach (preset_combo, 1, 2, n, n+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
171 preset_files.clear();
172 // no files for these two
173 preset_options.push_back (_("Last Loaded Session"));
174 preset_options.push_back (_("Ardour Factory Setting"));
175 // user is special it appears in menu even if no file is present
176 preset_options.push_back ("User");
177 preset_files["User"] = "";
178 // scan for OSC .preset files
179 scan_preset_files ();
181 set_popdown_strings (preset_combo, preset_options);
182 preset_combo.set_active (0);
183 preset_combo.signal_changed().connect (sigc::mem_fun (*this, &OSC_GUI::preset_changed));
187 append_page (*table, _("OSC Setup"));
189 debug_combo.signal_changed().connect (sigc::mem_fun (*this, &OSC_GUI::debug_changed));
190 portmode_combo.signal_changed().connect (sigc::mem_fun (*this, &OSC_GUI::portmode_changed));
191 gainmode_combo.signal_changed().connect (sigc::mem_fun (*this, &OSC_GUI::gainmode_changed));
192 port_entry.signal_changed().connect (sigc::mem_fun (*this, &OSC_GUI::port_changed));
193 port_entry.signal_focus_out_event().connect (sigc::mem_fun (*this, &OSC_GUI::port_focus_out));
194 bank_entry.signal_changed().connect (sigc::mem_fun (*this, &OSC_GUI::bank_changed));
195 send_page_entry.signal_changed().connect (sigc::mem_fun (*this, &OSC_GUI::send_page_changed));
196 plugin_page_entry.signal_changed().connect (sigc::mem_fun (*this, &OSC_GUI::plugin_page_changed));
198 // Strip Types Calculate Page
199 int stn = 0; // table row
200 Table* sttable = manage (new Table);
201 sttable->set_row_spacings (8);
202 sttable->set_col_spacings (6);
203 sttable->set_border_width (25);
206 label = manage (new Gtk::Label(_("Select Desired Types of Tracks")));
207 sttable->attach (*label, 0, 2, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
210 label = manage (new Gtk::Label(_("Strip Types Value:")));
211 label->set_alignment(1, .5);
212 sttable->attach (*label, 0, 1, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 15);
213 calculate_strip_types ();
214 current_strip_types.set_width_chars(10);
215 sttable->attach (current_strip_types, 1, 2, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 15);
218 label = manage (new Gtk::Label(_("Audio Tracks:")));
219 label->set_alignment(1, .5);
220 sttable->attach (*label, 0, 1, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
221 sttable->attach (audio_tracks, 1, 2, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
224 label = manage (new Gtk::Label(_("Midi Tracks:")));
225 label->set_alignment(1, .5);
226 sttable->attach (*label, 0, 1, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
227 sttable->attach (midi_tracks, 1, 2, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
230 label = manage (new Gtk::Label(_("Audio Busses:")));
231 label->set_alignment(1, .5);
232 sttable->attach (*label, 0, 1, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
233 sttable->attach (audio_buses, 1, 2, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
236 label = manage (new Gtk::Label(_("Audio Auxes:")));
237 label->set_alignment(1, .5);
238 sttable->attach (*label, 0, 1, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
239 sttable->attach (audio_auxes, 1, 2, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
242 label = manage (new Gtk::Label(_("Midi Busses:")));
243 label->set_alignment(1, .5);
244 sttable->attach (*label, 0, 1, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
245 sttable->attach (midi_buses, 1, 2, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
248 label = manage (new Gtk::Label(_("Control Masters:")));
249 label->set_alignment(1, .5);
250 sttable->attach (*label, 0, 1, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
251 sttable->attach (control_masters, 1, 2, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
254 label = manage (new Gtk::Label(_("Master (use /master instead):")));
255 label->set_alignment(1, .5);
256 sttable->attach (*label, 0, 1, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
257 sttable->attach (master_type, 1, 2, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
260 label = manage (new Gtk::Label(_("Monitor (use /monitor instead):")));
261 label->set_alignment(1, .5);
262 sttable->attach (*label, 0, 1, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
263 sttable->attach (monitor_type, 1, 2, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
266 label = manage (new Gtk::Label(_("Selected Tracks (use for selected tracks only):")));
267 label->set_alignment(1, .5);
268 sttable->attach (*label, 0, 1, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
269 sttable->attach (selected_tracks, 1, 2, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
272 label = manage (new Gtk::Label(_("Hidden Tracks:")));
273 label->set_alignment(1, .5);
274 sttable->attach (*label, 0, 1, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
275 sttable->attach (hidden_tracks, 1, 2, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
278 label = manage (new Gtk::Label(_("Use Groups:")));
279 label->set_alignment(1, .5);
280 sttable->attach (*label, 0, 1, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
281 sttable->attach (usegroups, 1, 2, stn, stn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
285 sttable->show_all ();
286 append_page (*sttable, _("Default Strip Types"));
289 // Feedback Calculate Page
290 int fn = 0; // table row
291 Table* fbtable = manage (new Table);
292 fbtable->set_row_spacings (4);
293 fbtable->set_col_spacings (6);
294 fbtable->set_border_width (12);
296 label = manage (new Gtk::Label(_("Select Desired Types of Feedback")));
297 fbtable->attach (*label, 0, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
300 label = manage (new Gtk::Label(_("Feedback Value:")));
301 label->set_alignment(1, .5);
302 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 15);
303 calculate_feedback ();
304 current_feedback.set_width_chars(10);
305 fbtable->attach (current_feedback, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 15);
308 label = manage (new Gtk::Label(_("Strip Buttons:")));
309 label->set_alignment(1, .5);
310 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
311 fbtable->attach (strip_buttons_button, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
314 label = manage (new Gtk::Label(_("Strip Controls:")));
315 label->set_alignment(1, .5);
316 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
317 fbtable->attach (strip_control_button, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
320 label = manage (new Gtk::Label(_("Use SSID as Path Extension:")));
321 label->set_alignment(1, .5);
322 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
323 fbtable->attach (ssid_as_path, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
326 label = manage (new Gtk::Label(_("Use Heart Beat:")));
327 label->set_alignment(1, .5);
328 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
329 fbtable->attach (heart_beat, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
332 label = manage (new Gtk::Label(_("Master Section:")));
333 label->set_alignment(1, .5);
334 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
335 fbtable->attach (master_fb, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
338 label = manage (new Gtk::Label(_("Play Head Position as Bar and Beat:")));
339 label->set_alignment(1, .5);
340 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
341 fbtable->attach (bar_and_beat, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
344 label = manage (new Gtk::Label(_("Play Head Position as SMPTE Time:")));
345 label->set_alignment(1, .5);
346 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
347 fbtable->attach (smpte, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
350 label = manage (new Gtk::Label(_("Metering as a Float:")));
351 label->set_alignment(1, .5);
352 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
353 fbtable->attach (meter_float, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
356 label = manage (new Gtk::Label(_("Metering as a LED Strip:")));
357 label->set_alignment(1, .5);
358 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
359 fbtable->attach (meter_led, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
362 label = manage (new Gtk::Label(_("Signal Present:")));
363 label->set_alignment(1, .5);
364 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
365 fbtable->attach (signal_present, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
368 label = manage (new Gtk::Label(_("Play Head Position as Samples:")));
369 label->set_alignment(1, .5);
370 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
371 fbtable->attach (hp_samples, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
374 label = manage (new Gtk::Label(_("Playhead Position as Minutes Seconds:")));
375 label->set_alignment(1, .5);
376 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
377 fbtable->attach (hp_min_sec, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
380 label = manage (new Gtk::Label(_("Playhead Position as per GUI Clock:")));
381 label->set_alignment(1, .5);
382 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
383 fbtable->attach (hp_gui, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
384 hp_gui.set_sensitive (false); // we don't have this yet (Mixbus wants)
387 label = manage (new Gtk::Label(_("Extra Select Only Feedback:")));
388 label->set_alignment(1, .5);
389 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
390 fbtable->attach (select_fb, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
393 label = manage (new Gtk::Label(_("Use /reply instead of #reply:")));
394 label->set_alignment(1, .5);
395 fbtable->attach (*label, 0, 1, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0));
396 fbtable->attach (use_osc10, 1, 2, fn, fn+1, AttachOptions(FILL|EXPAND), AttachOptions(0), 0, 0);
399 fbtable->show_all ();
400 append_page (*fbtable, _("Default Feedback"));
401 // set strips and feedback from loaded default values
404 audio_tracks.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
405 midi_tracks.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
406 audio_buses.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
407 audio_auxes.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
408 midi_buses.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
409 control_masters.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
410 master_type.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
411 monitor_type.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
412 selected_tracks.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
413 hidden_tracks.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
414 usegroups.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
415 strip_buttons_button.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
416 strip_control_button.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
417 ssid_as_path.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
418 heart_beat.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
419 master_fb.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
420 bar_and_beat.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
421 smpte.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
422 meter_float.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
423 meter_led.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
424 signal_present.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
425 hp_samples.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
426 hp_min_sec.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
427 hp_gui.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
428 select_fb.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
429 use_osc10.signal_clicked().connect (sigc::mem_fun (*this, &OSC_GUI::set_bitsets));
438 // static directory and file handling stuff
440 preset_search_path ()
442 bool preset_path_defined = false;
443 std::string spath_env (Glib::getenv (preset_env_variable_name, preset_path_defined));
445 if (preset_path_defined) {
449 Searchpath spath (ardour_data_search_path());
450 spath.add_subdirectory_to_paths(preset_dir_name);
456 user_preset_directory ()
458 return Glib::build_filename (user_config_directory(), preset_dir_name);
462 preset_filter (const std::string &str, void* /*arg*/)
464 return (str.length() > strlen(preset_suffix) &&
465 str.find (preset_suffix) == (str.length() - strlen (preset_suffix)));
469 legalize_for_path (const std::string& str)
471 std::string::size_type pos;
472 std::string illegal_chars = "/\\"; /* DOS, POSIX. Yes, we're going to ignore HFS */
478 while ((pos = legal.find_first_of (illegal_chars, pos)) != std::string::npos) {
479 legal.replace (pos, 1, "_");
483 return std::string (legal);
486 // end of static functions
489 OSC_GUI::debug_changed ()
491 std::string str = debug_combo.get_active_text ();
492 if (str == _("Off")) {
493 cp.set_debug_mode (OSC::Off);
495 else if (str == _("Log invalid messages")) {
496 cp.set_debug_mode (OSC::Unhandled);
498 else if (str == _("Log all messages")) {
499 cp.set_debug_mode (OSC::All);
501 else if (str == _("Print surface information to Log window")) {
503 debug_combo.set_active ((int)cp.get_debug_mode());
506 std::cerr << "Invalid OSC Debug Mode\n";
512 OSC_GUI::portmode_changed ()
514 int pm = portmode_combo.get_active_row_number ();
515 cp.set_portmode (pm);
517 port_entry.set_sensitive (true);
519 port_entry.set_sensitive (false);
525 OSC_GUI::port_changed ()
527 std::string str = port_entry.get_text ();
528 int prt = atoi (str.c_str());
529 if (prt == 3819 || prt < 1024) {
530 // indicate non-valid text
531 port_entry.set_progress_fraction (1.0);
533 port_entry.set_progress_fraction (0.0);
534 cp.set_remote_port (string_compose ("%1", prt));
540 OSC_GUI::port_focus_out (GdkEventFocus* )
542 std::string str = port_entry.get_text ();
543 int prt = atoi (str.c_str());
544 if (prt == 3819 || prt < 1024) {
545 port_entry.set_text(cp.get_remote_port().c_str());
546 port_entry.set_progress_fraction (0.0);
552 OSC_GUI::bank_changed ()
554 uint32_t bsize = atoi(bank_entry.get_text ());
555 bank_entry.set_text (string_compose ("%1", bsize));
556 cp.set_banksize (bsize);
562 OSC_GUI::send_page_changed ()
564 uint32_t ssize = atoi (send_page_entry.get_text ());
565 send_page_entry.set_text (string_compose ("%1", ssize));
566 cp.set_send_size (ssize);
572 OSC_GUI::plugin_page_changed ()
574 uint32_t psize = atoi (plugin_page_entry.get_text ());
575 plugin_page_entry.set_text (string_compose ("%1", psize));
576 cp.set_plugin_size (psize);
582 OSC_GUI::gainmode_changed ()
584 std::string str = gainmode_combo.get_active_text ();
585 if (str == _("/strip/gain (dB)")) {
588 else if (str == _("/strip/fader (Position) and dB in control name")) {
591 else if (str == _("/strip/fader (Position) and /strip/gain (dB)")) {
594 else if (str == _("/strip/fader (Position)")) {
598 std::cerr << "Invalid OSC Gain Mode\n";
605 OSC_GUI::clear_device ()
611 OSC_GUI::preset_changed ()
614 std::string str = preset_combo.get_active_text ();
615 if (str == "Last Loaded Session") {
616 restore_sesn_values ();
618 else if (str == "Ardour Factory Setting") {
621 else if (str == "User") {
622 load_preset ("User");
632 OSC_GUI::factory_reset ()
635 bank_entry.set_text ("0");
636 cp.set_send_size (0);
637 send_page_entry.set_text ("0");
638 cp.set_plugin_size (0);
639 plugin_page_entry.set_text ("0");
640 cp.set_defaultstrip (31);
641 cp.set_defaultfeedback (0);
644 gainmode_combo.set_active (0);
646 portmode_combo.set_active (1);
647 cp.set_remote_port ("8000");
648 port_entry.set_text ("8000");
654 OSC_GUI::reshow_values ()
656 def_strip = cp.get_defaultstrip();
657 audio_tracks.set_active(def_strip & 1);
658 midi_tracks.set_active(def_strip & 2);
659 audio_buses.set_active(def_strip & 4);
660 midi_buses.set_active(def_strip & 8);
661 control_masters.set_active(def_strip & 16);
662 master_type.set_active(def_strip & 32);
663 monitor_type.set_active(def_strip & 64);
664 audio_auxes.set_active(def_strip & 128);
665 selected_tracks.set_active(def_strip & 256);
666 hidden_tracks.set_active(def_strip & 512);
667 usegroups.set_active(def_strip & 1024);
668 def_feedback = cp.get_defaultfeedback();
669 strip_buttons_button.set_active(def_feedback & 1);
670 strip_control_button.set_active(def_feedback & 2);
671 ssid_as_path.set_active(def_feedback & 4);
672 heart_beat.set_active(def_feedback & 8);
673 master_fb.set_active(def_feedback & 16);
674 bar_and_beat.set_active(def_feedback & 32);
675 smpte.set_active(def_feedback & 64);
676 meter_float.set_active(def_feedback & 128);
677 meter_led.set_active(def_feedback & 256);
678 signal_present.set_active(def_feedback & 512);
679 hp_samples.set_active(def_feedback & 1024);
680 hp_min_sec.set_active (def_feedback & 2048);
681 //hp_gui.set_active (false); // we don't have this yet (Mixbus wants)
682 select_fb.set_active(def_feedback & 8192);
683 use_osc10.set_active(def_feedback & 16384);
685 calculate_strip_types ();
686 calculate_feedback ();
690 OSC_GUI::calculate_feedback ()
693 if (strip_buttons_button.get_active()) {
696 if (strip_control_button.get_active()) {
699 if (ssid_as_path.get_active()) {
702 if (heart_beat.get_active()) {
705 if (master_fb.get_active()) {
708 if (bar_and_beat.get_active()) {
711 if (smpte.get_active()) {
714 if (meter_float.get_active()) {
717 if (meter_led.get_active()) {
720 if (signal_present.get_active()) {
723 if (hp_samples.get_active()) {
726 if (hp_min_sec.get_active()) {
729 if (hp_gui.get_active()) {
732 if (select_fb.get_active()) {
735 if (use_osc10.get_active()) {
739 current_feedback.set_text(string_compose("%1", fbvalue));
743 OSC_GUI::calculate_strip_types ()
746 if (audio_tracks.get_active()) {
749 if (midi_tracks.get_active()) {
752 if (audio_buses.get_active()) {
755 if (midi_buses.get_active()) {
758 if (control_masters.get_active()) {
761 if (master_type.get_active()) {
764 if (monitor_type.get_active()) {
767 if (audio_auxes.get_active()) {
770 if (selected_tracks.get_active()) {
773 if (hidden_tracks.get_active()) {
776 if (usegroups.get_active()) {
780 current_strip_types.set_text(string_compose("%1", stvalue));
784 OSC_GUI::set_bitsets ()
789 calculate_strip_types ();
790 calculate_feedback ();
791 cp.set_defaultstrip (stvalue);
792 cp.set_defaultfeedback (fbvalue);
797 OSC_GUI::scan_preset_files ()
799 std::vector<std::string> presets;
800 Searchpath spath (preset_search_path());
802 find_files_matching_filter (presets, spath, preset_filter, 0, false, true);
803 //device_profiles.clear ();preset_list.clear // first two entries already there
805 if (presets.empty()) {
806 error << "No OSC preset files found using " << spath.to_string() << endmsg;
810 for (std::vector<std::string>::iterator i = presets.begin(); i != presets.end(); ++i) {
811 std::string fullpath = *i;
812 //DeviceProfile dp; // has to be initial every loop or info from last added.
816 if (!tree.read (fullpath.c_str())) {
820 XMLNode* root = tree.root ();
824 const XMLProperty* prop;
825 const XMLNode* child;
827 if (root->name() != "OSCPreset") {
831 if ((child = root->child ("Name")) == 0 || (prop = child->property ("value")) == 0) {
834 if (prop->value() == "User") {
835 // We already added user but no file name
836 preset_files[prop->value()] = fullpath;
837 } else if (preset_files.find(prop->value()) == preset_files.end()) {
838 preset_options.push_back (prop->value());
839 preset_files[prop->value()] = fullpath;
847 OSC_GUI::save_user ()
852 std::string fullpath = user_preset_directory();
854 if (g_mkdir_with_parents (fullpath.c_str(), 0755) < 0) {
855 error << string_compose(_("Session: cannot create user OSC profile folder \"%1\" (%2)"), fullpath, strerror (errno)) << endmsg;
859 fullpath = Glib::build_filename (fullpath, string_compose ("%1%2", legalize_for_path ("user"), preset_suffix));
861 XMLNode* node = new XMLNode ("OSCPreset");
862 XMLNode* child = new XMLNode ("Name");
864 child->set_property ("value", "User");
865 node->add_child_nocopy (*child);
867 child = new XMLNode ("PortMode");
868 child->set_property ("value", cp.get_portmode());
869 node->add_child_nocopy (*child);
871 child = new XMLNode ("Remote-Port");
872 child->set_property ("value", cp.get_remote_port());
873 node->add_child_nocopy (*child);
875 child = new XMLNode ("Bank-Size");
876 child->set_property ("value", cp.get_banksize());
877 node->add_child_nocopy (*child);
879 child = new XMLNode ("Send-Size");
880 child->set_property ("value", cp.get_send_size());
881 node->add_child_nocopy (*child);
883 child = new XMLNode ("Plugin-Size");
884 child->set_property ("value", cp.get_plugin_size());
885 node->add_child_nocopy (*child);
887 child = new XMLNode ("Strip-Types");
888 child->set_property ("value", cp.get_defaultstrip());
889 node->add_child_nocopy (*child);
891 child = new XMLNode ("Feedback");
892 child->set_property ("value", cp.get_defaultfeedback());
893 node->add_child_nocopy (*child);
895 child = new XMLNode ("Gain-Mode");
896 child->set_property ("value", cp.get_gainmode());
897 node->add_child_nocopy (*child);
900 tree.set_root (node);
902 if (!tree.write (fullpath)) {
903 error << string_compose ("OSC profile not saved to %1", fullpath) << endmsg;
905 preset_combo.set_active (2);
912 OSC_GUI::load_preset (std::string preset)
914 if (preset == "User" && preset_files["User"] == "") {
915 restore_sesn_values ();
916 } else if (preset_files.find(preset) != preset_files.end()) {
919 if (!tree.read (preset_files[preset])) {
920 std::cerr << "preset file not found " << preset_files[preset] << "\n";
924 XMLNode* root = tree.root ();
926 std::cerr << "invalid preset file " << preset_files[preset] << "\n";
929 const XMLProperty* prop;
930 const XMLNode* child;
932 if (root->name() != "OSCPreset") {
933 std::cerr << "invalid preset file " << preset_files[preset] << "\n";
937 if ((child = root->child ("Name")) == 0 || (prop = child->property ("value")) == 0) {
938 std::cerr << "preset file missing Name " << preset_files[preset] << "\n";
941 if ((child = root->child ("PortMode")) == 0 || (prop = child->property ("value")) == 0) {
942 cp.set_portmode (sesn_portmode);
943 portmode_combo.set_active (sesn_portmode);
945 cp.set_portmode (atoi (prop->value().c_str()));
946 portmode_combo.set_active (atoi (prop->value().c_str()));
948 if ((child = root->child ("Remote-Port")) == 0 || (prop = child->property ("value")) == 0) {
949 cp.set_remote_port (sesn_port);
950 port_entry.set_text (sesn_port);
952 cp.set_remote_port (prop->value());
953 port_entry.set_text (prop->value());
955 if ((child = root->child ("Bank-Size")) == 0 || (prop = child->property ("value")) == 0) {
956 cp.set_banksize (sesn_bank);
957 bank_entry.set_text (string_compose("%1", sesn_bank));
959 cp.set_banksize (atoi (prop->value().c_str()));
960 bank_entry.set_text (prop->value().c_str());
962 if ((child = root->child ("Send-Size")) == 0 || (prop = child->property ("value")) == 0) {
963 cp.set_send_size (sesn_send);
964 send_page_entry.set_text (string_compose("%1", sesn_send));
966 cp.set_send_size (atoi (prop->value().c_str()));
967 send_page_entry.set_text (prop->value().c_str());
969 if ((child = root->child ("Plugin-Size")) == 0 || (prop = child->property ("value")) == 0) {
970 cp.set_plugin_size (sesn_plugin);
971 plugin_page_entry.set_text (string_compose("%1", sesn_plugin));
973 cp.set_plugin_size (atoi (prop->value().c_str()));
974 plugin_page_entry.set_text (prop->value().c_str());
976 if ((child = root->child ("Strip-Types")) == 0 || (prop = child->property ("value")) == 0) {
977 cp.set_defaultstrip (sesn_strips);
979 cp.set_defaultstrip (atoi (prop->value().c_str()));
981 if ((child = root->child ("Feedback")) == 0 || (prop = child->property ("value")) == 0) {
982 cp.set_defaultfeedback (sesn_feedback);
984 cp.set_defaultfeedback (atoi (prop->value().c_str()));
986 reshow_values (); // show strip types and feed back in GUI
988 if ((child = root->child ("Gain-Mode")) == 0 || (prop = child->property ("value")) == 0) {
989 cp.set_gainmode (sesn_gainmode);
990 gainmode_combo.set_active (sesn_gainmode);
992 cp.set_gainmode (atoi (prop->value().c_str()));
993 gainmode_combo.set_active (atoi (prop->value().c_str()));
1002 OSC_GUI::get_session ()
1004 sesn_portmode = cp.get_portmode ();
1005 sesn_port = cp.get_remote_port ();
1006 sesn_bank = cp.get_banksize ();
1007 sesn_send = cp.get_send_size ();
1008 sesn_plugin = cp.get_plugin_size ();
1009 sesn_strips = cp.get_defaultstrip ();
1010 sesn_feedback = cp.get_defaultfeedback ();
1011 sesn_gainmode = cp.get_gainmode ();
1015 OSC_GUI::restore_sesn_values ()
1017 cp.set_portmode (sesn_portmode);
1018 portmode_combo.set_active (sesn_portmode);
1019 cp.set_remote_port (sesn_port);
1020 port_entry.set_text (sesn_port);
1021 cp.set_banksize (sesn_bank);
1022 bank_entry.set_text (string_compose ("%1", sesn_bank));
1023 cp.set_send_size (sesn_send);
1024 send_page_entry.set_text (string_compose ("%1", sesn_send));
1025 cp.set_plugin_size (sesn_plugin);
1026 plugin_page_entry.set_text (string_compose ("%1", sesn_plugin));
1027 cp.set_defaultstrip (sesn_strips);
1028 cp.set_defaultfeedback (sesn_feedback);
1030 cp.set_gainmode (sesn_gainmode);
1031 gainmode_combo.set_active (sesn_gainmode);