1 #include <gtkmm/liststore.h>
2 #include <gtkmm/stock.h>
3 #include <gtkmm/scale.h>
4 #include <gtkmm2ext/utils.h>
5 #include <gtkmm2ext/slider_controller.h>
7 #include "midi++/manager.h"
8 #include "midi++/factory.h"
10 #include "ardour/rc_configuration.h"
11 #include "ardour/control_protocol_manager.h"
12 #include "control_protocol/control_protocol.h"
13 #include "rc_option_editor.h"
15 #include "midi_port_dialog.h"
22 using namespace Gtkmm2ext;
24 using namespace ARDOUR;
26 class MIDIPorts : public OptionEditorBox
29 MIDIPorts (RCConfiguration* c, list<ComboOption<string>* > const & o)
31 _add_port_button (Stock::ADD),
34 _store = ListStore::create (_model);
35 _view.set_model (_store);
36 _view.append_column (_("Name"), _model.name);
37 _view.get_column(0)->set_resizable (true);
38 _view.get_column(0)->set_expand (true);
39 _view.append_column_editable (_("Online"), _model.online);
40 _view.append_column_editable (_("Trace input"), _model.trace_input);
41 _view.append_column_editable (_("Trace output"), _model.trace_output);
43 HBox* h = manage (new HBox);
45 h->pack_start (_view, true, true);
47 VBox* v = manage (new VBox);
49 v->pack_start (_add_port_button, false, false);
50 h->pack_start (*v, false, false);
52 _box->pack_start (*h);
56 _store->signal_row_changed().connect (sigc::mem_fun (*this, &MIDIPorts::model_changed));
58 _add_port_button.signal_clicked().connect (sigc::mem_fun (*this, &MIDIPorts::add_port_clicked));
61 void parameter_changed (string const &) {}
62 void set_state_from_config () {}
66 void model_changed (TreeModel::Path const &, TreeModel::iterator const & i)
68 TreeModel::Row r = *i;
70 MIDI::Port* port = r[_model.port];
77 if (r[_model.online] == port->input()->offline()) {
78 port->input()->set_offline (!r[_model.online]);
81 if (r[_model.trace_input] != port->input()->tracing()) {
82 port->input()->trace (r[_model.trace_input], &cerr, string (port->name()) + _(" input: "));
88 if (r[_model.trace_output] != port->output()->tracing()) {
89 port->output()->trace (r[_model.trace_output], &cerr, string (port->name()) + _(" output: "));
95 void setup_ports_combo (ComboOption<string>* c)
98 MIDI::Manager::PortList const & ports = MIDI::Manager::instance()->get_midi_ports ();
99 for (MIDI::Manager::PortList::const_iterator i = ports.begin(); i != ports.end(); ++i) {
100 c->add ((*i)->name(), (*i)->name());
104 void ports_changed ()
106 /* XXX: why is this coming from here? */
107 MIDI::Manager::PortList const & ports = MIDI::Manager::instance()->get_midi_ports ();
110 port_connections.drop_connections ();
112 for (MIDI::Manager::PortList::const_iterator i = ports.begin(); i != ports.end(); ++i) {
114 TreeModel::Row r = *_store->append ();
116 r[_model.name] = (*i)->name();
119 r[_model.online] = !(*i)->input()->offline();
120 (*i)->input()->OfflineStatusChanged.connect (port_connections, boost::bind (&MIDIPorts::port_offline_changed, this, (*i)));
121 r[_model.trace_input] = (*i)->input()->tracing();
124 if ((*i)->output()) {
125 r[_model.trace_output] = (*i)->output()->tracing();
128 r[_model.port] = (*i);
131 for (list<ComboOption<string>* >::iterator i = _port_combos.begin(); i != _port_combos.end(); ++i) {
132 setup_ports_combo (*i);
136 void port_offline_changed (MIDI::Port* p)
142 for (TreeModel::Children::iterator i = _store->children().begin(); i != _store->children().end(); ++i) {
143 if ((*i)[_model.port] == p) {
144 (*i)[_model.online] = !p->input()->offline();
149 void add_port_clicked ()
151 MidiPortDialog dialog;
153 dialog.set_position (WIN_POS_MOUSE);
157 int const r = dialog.run ();
160 case RESPONSE_ACCEPT:
167 Glib::ustring const mode = dialog.port_mode_combo.get_active_text ();
170 if (mode == _("input")) {
172 } else if (mode == (_("output"))) {
178 XMLNode node (X_("MIDI-port"));
180 node.add_property ("tag", dialog.port_name.get_text());
181 node.add_property ("device", X_("ardour")); // XXX this can't be right for all types
182 node.add_property ("type", MIDI::PortFactory::default_port_type());
183 node.add_property ("mode", smod);
185 if (MIDI::Manager::instance()->add_port (node) != 0) {
186 cerr << " there are now " << MIDI::Manager::instance()->nports() << endl;
191 class MIDIModelColumns : public TreeModelColumnRecord
203 TreeModelColumn<string> name;
204 TreeModelColumn<bool> online;
205 TreeModelColumn<bool> trace_input;
206 TreeModelColumn<bool> trace_output;
207 TreeModelColumn<MIDI::Port*> port;
210 RCConfiguration* _rc_config;
211 Glib::RefPtr<ListStore> _store;
212 MIDIModelColumns _model;
214 Button _add_port_button;
215 ComboBoxText _mtc_combo;
216 ComboBoxText _midi_clock_combo;
217 ComboBoxText _mmc_combo;
218 ComboBoxText _mpc_combo;
219 list<ComboOption<string>* > _port_combos;
220 PBD::ScopedConnectionList port_connections;
224 class ClickOptions : public OptionEditorBox
227 ClickOptions (RCConfiguration* c, ArdourDialog* p)
231 Table* t = manage (new Table (2, 3));
234 Label* l = manage (new Label (_("Click audio file:")));
235 l->set_alignment (0, 0.5);
236 t->attach (*l, 0, 1, 0, 1, FILL);
237 t->attach (_click_path_entry, 1, 2, 0, 1, FILL);
238 Button* b = manage (new Button (_("Browse...")));
239 b->signal_clicked().connect (sigc::mem_fun (*this, &ClickOptions::click_browse_clicked));
240 t->attach (*b, 2, 3, 0, 1, FILL);
242 l = manage (new Label (_("Click emphasis audio file:")));
243 l->set_alignment (0, 0.5);
244 t->attach (*l, 0, 1, 1, 2, FILL);
245 t->attach (_click_emphasis_path_entry, 1, 2, 1, 2, FILL);
246 b = manage (new Button (_("Browse...")));
247 b->signal_clicked().connect (sigc::mem_fun (*this, &ClickOptions::click_emphasis_browse_clicked));
248 t->attach (*b, 2, 3, 1, 2, FILL);
250 _box->pack_start (*t, false, false);
253 void parameter_changed (string const & p)
255 if (p == "click-sound") {
256 _click_path_entry.set_text (_rc_config->get_click_sound());
257 } else if (p == "click-emphasis-sound") {
258 _click_emphasis_path_entry.set_text (_rc_config->get_click_emphasis_sound());
262 void set_state_from_config ()
264 parameter_changed ("click-sound");
265 parameter_changed ("click-emphasis-sound");
270 void click_browse_clicked ()
272 SoundFileChooser sfdb (*_parent, _("Choose Click"));
277 if (sfdb.run () == RESPONSE_OK) {
278 click_chosen (sfdb.get_filename());
282 void click_chosen (string const & path)
284 _click_path_entry.set_text (path);
285 _rc_config->set_click_sound (path);
288 void click_emphasis_browse_clicked ()
290 SoundFileChooser sfdb (*_parent, _("Choose Click Emphasis"));
295 if (sfdb.run () == RESPONSE_OK) {
296 click_emphasis_chosen (sfdb.get_filename());
300 void click_emphasis_chosen (string const & path)
302 _click_emphasis_path_entry.set_text (path);
303 _rc_config->set_click_emphasis_sound (path);
306 RCConfiguration* _rc_config;
307 ArdourDialog* _parent;
308 Entry _click_path_entry;
309 Entry _click_emphasis_path_entry;
312 class UndoOptions : public OptionEditorBox
315 UndoOptions (RCConfiguration* c) :
317 _limit_undo_button (_("Limit undo history to")),
318 _save_undo_button (_("Save undo history of"))
320 Table* t = new Table (2, 3);
323 t->attach (_limit_undo_button, 0, 1, 0, 1, FILL);
324 _limit_undo_spin.set_range (0, 512);
325 _limit_undo_spin.set_increments (1, 10);
326 t->attach (_limit_undo_spin, 1, 2, 0, 1, FILL | EXPAND);
327 Label* l = manage (new Label (_("commands")));
328 l->set_alignment (0, 0.5);
329 t->attach (*l, 2, 3, 0, 1);
331 t->attach (_save_undo_button, 0, 1, 1, 2, FILL);
332 _save_undo_spin.set_range (0, 512);
333 _save_undo_spin.set_increments (1, 10);
334 t->attach (_save_undo_spin, 1, 2, 1, 2, FILL | EXPAND);
335 l = manage (new Label (_("commands")));
336 l->set_alignment (0, 0.5);
337 t->attach (*l, 2, 3, 1, 2);
339 _box->pack_start (*t);
341 _limit_undo_button.signal_toggled().connect (sigc::mem_fun (*this, &UndoOptions::limit_undo_toggled));
342 _limit_undo_spin.signal_value_changed().connect (sigc::mem_fun (*this, &UndoOptions::limit_undo_changed));
343 _save_undo_button.signal_toggled().connect (sigc::mem_fun (*this, &UndoOptions::save_undo_toggled));
344 _save_undo_spin.signal_value_changed().connect (sigc::mem_fun (*this, &UndoOptions::save_undo_changed));
347 void parameter_changed (string const & p)
349 if (p == "history-depth") {
350 int32_t const d = _rc_config->get_history_depth();
351 _limit_undo_button.set_active (d != 0);
352 _limit_undo_spin.set_sensitive (d != 0);
353 _limit_undo_spin.set_value (d);
354 } else if (p == "save-history") {
355 bool const x = _rc_config->get_save_history ();
356 _save_undo_button.set_active (x);
357 _save_undo_spin.set_sensitive (x);
358 } else if (p == "save-history-depth") {
359 _save_undo_spin.set_value (_rc_config->get_saved_history_depth());
363 void set_state_from_config ()
365 parameter_changed ("save-history");
366 parameter_changed ("history-depth");
367 parameter_changed ("save-history-depth");
370 void limit_undo_toggled ()
372 bool const x = _limit_undo_button.get_active ();
373 _limit_undo_spin.set_sensitive (x);
374 int32_t const n = x ? 16 : 0;
375 _limit_undo_spin.set_value (n);
376 _rc_config->set_history_depth (n);
379 void limit_undo_changed ()
381 _rc_config->set_history_depth (_limit_undo_spin.get_value_as_int ());
384 void save_undo_toggled ()
386 bool const x = _save_undo_button.get_active ();
387 _rc_config->set_save_history (x);
390 void save_undo_changed ()
392 _rc_config->set_saved_history_depth (_save_undo_spin.get_value_as_int ());
396 RCConfiguration* _rc_config;
397 CheckButton _limit_undo_button;
398 SpinButton _limit_undo_spin;
399 CheckButton _save_undo_button;
400 SpinButton _save_undo_spin;
405 static const struct {
417 { "Shift", GDK_SHIFT_MASK },
418 { "Command", GDK_META_MASK },
419 { "Control", GDK_CONTROL_MASK },
420 { "Option", GDK_MOD1_MASK },
421 { "Command-Shift", GDK_MOD1_MASK|GDK_SHIFT_MASK },
422 { "Command-Option", GDK_MOD1_MASK|GDK_MOD5_MASK },
423 { "Shift-Option", GDK_SHIFT_MASK|GDK_MOD5_MASK },
424 { "Shift-Command-Option", GDK_MOD5_MASK|GDK_SHIFT_MASK|GDK_MOD1_MASK },
427 { "Shift", GDK_SHIFT_MASK },
428 { "Control", GDK_CONTROL_MASK },
429 { "Alt (Mod1)", GDK_MOD1_MASK },
430 { "Control-Shift", GDK_CONTROL_MASK|GDK_SHIFT_MASK },
431 { "Control-Alt", GDK_CONTROL_MASK|GDK_MOD1_MASK },
432 { "Shift-Alt", GDK_SHIFT_MASK|GDK_MOD1_MASK },
433 { "Control-Shift-Alt", GDK_CONTROL_MASK|GDK_SHIFT_MASK|GDK_MOD1_MASK },
434 { "Mod2", GDK_MOD2_MASK },
435 { "Mod3", GDK_MOD3_MASK },
436 { "Mod4", GDK_MOD4_MASK },
437 { "Mod5", GDK_MOD5_MASK },
443 class KeyboardOptions : public OptionEditorBox
447 _delete_button_adjustment (3, 1, 12),
448 _delete_button_spin (_delete_button_adjustment),
449 _edit_button_adjustment (3, 1, 5),
450 _edit_button_spin (_edit_button_adjustment)
453 /* internationalize and prepare for use with combos */
456 for (int i = 0; modifiers[i].name; ++i) {
457 dumb.push_back (_(modifiers[i].name));
460 set_popdown_strings (_edit_modifier_combo, dumb);
461 _edit_modifier_combo.signal_changed().connect (sigc::mem_fun(*this, &KeyboardOptions::edit_modifier_chosen));
463 for (int x = 0; modifiers[x].name; ++x) {
464 if (modifiers[x].modifier == Keyboard::edit_modifier ()) {
465 _edit_modifier_combo.set_active_text (_(modifiers[x].name));
470 Table* t = manage (new Table (4, 4));
473 Label* l = manage (new Label (_("Edit using:")));
474 l->set_name ("OptionsLabel");
475 l->set_alignment (0, 0.5);
477 t->attach (*l, 0, 1, 0, 1, FILL | EXPAND, FILL);
478 t->attach (_edit_modifier_combo, 1, 2, 0, 1, FILL | EXPAND, FILL);
480 l = manage (new Label (_("+ button")));
481 l->set_name ("OptionsLabel");
483 t->attach (*l, 3, 4, 0, 1, FILL | EXPAND, FILL);
484 t->attach (_edit_button_spin, 4, 5, 0, 1, FILL | EXPAND, FILL);
486 _edit_button_spin.set_name ("OptionsEntry");
487 _edit_button_adjustment.set_value (Keyboard::edit_button());
488 _edit_button_adjustment.signal_value_changed().connect (sigc::mem_fun(*this, &KeyboardOptions::edit_button_changed));
490 set_popdown_strings (_delete_modifier_combo, dumb);
491 _delete_modifier_combo.signal_changed().connect (sigc::mem_fun(*this, &KeyboardOptions::delete_modifier_chosen));
493 for (int x = 0; modifiers[x].name; ++x) {
494 if (modifiers[x].modifier == Keyboard::delete_modifier ()) {
495 _delete_modifier_combo.set_active_text (_(modifiers[x].name));
500 l = manage (new Label (_("Delete using:")));
501 l->set_name ("OptionsLabel");
502 l->set_alignment (0, 0.5);
504 t->attach (*l, 0, 1, 1, 2, FILL | EXPAND, FILL);
505 t->attach (_delete_modifier_combo, 1, 2, 1, 2, FILL | EXPAND, FILL);
507 l = manage (new Label (_("+ button")));
508 l->set_name ("OptionsLabel");
510 t->attach (*l, 3, 4, 1, 2, FILL | EXPAND, FILL);
511 t->attach (_delete_button_spin, 4, 5, 1, 2, FILL | EXPAND, FILL);
513 _delete_button_spin.set_name ("OptionsEntry");
514 _delete_button_adjustment.set_value (Keyboard::delete_button());
515 _delete_button_adjustment.signal_value_changed().connect (sigc::mem_fun(*this, &KeyboardOptions::delete_button_changed));
517 set_popdown_strings (_snap_modifier_combo, dumb);
518 _snap_modifier_combo.signal_changed().connect (sigc::mem_fun(*this, &KeyboardOptions::snap_modifier_chosen));
520 for (int x = 0; modifiers[x].name; ++x) {
521 if (modifiers[x].modifier == (guint) Keyboard::snap_modifier ()) {
522 _snap_modifier_combo.set_active_text (_(modifiers[x].name));
527 l = manage (new Label (_("Toggle snap using:")));
528 l->set_name ("OptionsLabel");
529 l->set_alignment (0, 0.5);
531 t->attach (*l, 0, 1, 2, 3, FILL | EXPAND, FILL);
532 t->attach (_snap_modifier_combo, 1, 2, 2, 3, FILL | EXPAND, FILL);
536 for (map<string,string>::iterator bf = Keyboard::binding_files.begin(); bf != Keyboard::binding_files.end(); ++bf) {
537 strs.push_back (bf->first);
540 set_popdown_strings (_keyboard_layout_selector, strs);
541 _keyboard_layout_selector.set_active_text (Keyboard::current_binding_name());
542 _keyboard_layout_selector.signal_changed().connect (sigc::mem_fun (*this, &KeyboardOptions::bindings_changed));
544 l = manage (new Label (_("Keyboard layout:")));
545 l->set_name ("OptionsLabel");
546 l->set_alignment (0, 0.5);
548 t->attach (*l, 0, 1, 3, 4, FILL | EXPAND, FILL);
549 t->attach (_keyboard_layout_selector, 1, 2, 3, 4, FILL | EXPAND, FILL);
551 _box->pack_start (*t, false, false);
554 void parameter_changed (string const &)
556 /* XXX: these aren't really config options... */
559 void set_state_from_config ()
561 /* XXX: these aren't really config options... */
566 void bindings_changed ()
568 string const txt = _keyboard_layout_selector.get_active_text();
570 /* XXX: config...? for all this keyboard stuff */
572 for (map<string,string>::iterator i = Keyboard::binding_files.begin(); i != Keyboard::binding_files.end(); ++i) {
573 if (txt == i->first) {
574 if (Keyboard::load_keybindings (i->second)) {
575 Keyboard::save_keybindings ();
581 void edit_modifier_chosen ()
583 string const txt = _edit_modifier_combo.get_active_text();
585 for (int i = 0; modifiers[i].name; ++i) {
586 if (txt == _(modifiers[i].name)) {
587 Keyboard::set_edit_modifier (modifiers[i].modifier);
593 void delete_modifier_chosen ()
595 string const txt = _delete_modifier_combo.get_active_text();
597 for (int i = 0; modifiers[i].name; ++i) {
598 if (txt == _(modifiers[i].name)) {
599 Keyboard::set_delete_modifier (modifiers[i].modifier);
605 void snap_modifier_chosen ()
607 string const txt = _snap_modifier_combo.get_active_text();
609 for (int i = 0; modifiers[i].name; ++i) {
610 if (txt == _(modifiers[i].name)) {
611 Keyboard::set_snap_modifier (modifiers[i].modifier);
617 void delete_button_changed ()
619 Keyboard::set_delete_button (_delete_button_spin.get_value_as_int());
622 void edit_button_changed ()
624 Keyboard::set_edit_button (_edit_button_spin.get_value_as_int());
627 ComboBoxText _keyboard_layout_selector;
628 ComboBoxText _edit_modifier_combo;
629 ComboBoxText _delete_modifier_combo;
630 ComboBoxText _snap_modifier_combo;
631 Adjustment _delete_button_adjustment;
632 SpinButton _delete_button_spin;
633 Adjustment _edit_button_adjustment;
634 SpinButton _edit_button_spin;
637 class FontScalingOptions : public OptionEditorBox
640 FontScalingOptions (RCConfiguration* c) :
642 _dpi_adjustment (50, 50, 250, 1, 10),
643 _dpi_slider (_dpi_adjustment)
645 _dpi_adjustment.set_value (_rc_config->get_font_scale () / 1024);
647 Label* l = manage (new Label (_("Font scaling:")));
648 l->set_name ("OptionsLabel");
650 _dpi_slider.set_update_policy (UPDATE_DISCONTINUOUS);
651 HBox* h = manage (new HBox);
653 h->pack_start (*l, false, false);
654 h->pack_start (_dpi_slider, true, true);
656 _box->pack_start (*h, false, false);
658 _dpi_adjustment.signal_value_changed().connect (sigc::mem_fun (*this, &FontScalingOptions::dpi_changed));
661 void parameter_changed (string const & p)
663 if (p == "font-scale") {
664 _dpi_adjustment.set_value (_rc_config->get_font_scale() / 1024);
668 void set_state_from_config ()
670 parameter_changed ("font-scale");
677 _rc_config->set_font_scale ((long) floor (_dpi_adjustment.get_value() * 1024));
678 /* XXX: should be triggered from the parameter changed signal */
682 RCConfiguration* _rc_config;
683 Adjustment _dpi_adjustment;
687 class SoloMuteOptions : public OptionEditorBox
690 SoloMuteOptions (RCConfiguration* c) :
692 // 0.781787 is the value needed for gain to be set to 0.
693 _db_adjustment (0.781787, 0.0, 1.0, 0.01, 0.1)
696 if ((pix = ::get_icon ("fader_belt_h")) == 0) {
697 throw failed_constructor();
700 _db_slider = manage (new HSliderController (pix,
706 parameter_changed ("solo-mute-gain");
708 Label* l = manage (new Label (_("Solo mute cut (dB):")));
709 l->set_name ("OptionsLabel");
711 HBox* h = manage (new HBox);
713 h->pack_start (*l, false, false);
714 h->pack_start (*_db_slider, false, false);
715 h->pack_start (_db_display, false, false);
717 set_size_request_to_display_given_text (_db_display, "-99.0", 12, 12);
719 _box->pack_start (*h, false, false);
721 _db_adjustment.signal_value_changed().connect (sigc::mem_fun (*this, &SoloMuteOptions::db_changed));
724 void parameter_changed (string const & p)
726 if (p == "solo-mute-gain") {
727 gain_t val = _rc_config->get_solo_mute_gain();
729 _db_adjustment.set_value (gain_to_slider_position (val));
734 snprintf (buf, sizeof (buf), "-inf");
736 snprintf (buf, sizeof (buf), "%.2f", accurate_coefficient_to_dB (val));
739 _db_display.set_text (buf);
743 void set_state_from_config ()
745 parameter_changed ("solo-mute-gain");
752 _rc_config->set_solo_mute_gain (slider_position_to_gain (_db_adjustment.get_value()));
755 RCConfiguration* _rc_config;
756 Adjustment _db_adjustment;
757 Gtkmm2ext::HSliderController* _db_slider;
758 Glib::RefPtr<Gdk::Pixbuf> pix;
763 class ControlSurfacesOptions : public OptionEditorBox
766 ControlSurfacesOptions ()
768 _store = ListStore::create (_model);
769 _view.set_model (_store);
770 _view.append_column (_("Name"), _model.name);
771 _view.get_column(0)->set_resizable (true);
772 _view.get_column(0)->set_expand (true);
773 _view.append_column_editable (_("Enabled"), _model.enabled);
774 _view.append_column_editable (_("Feedback"), _model.feedback);
776 _box->pack_start (_view, false, false);
778 _store->signal_row_changed().connect (sigc::mem_fun (*this, &ControlSurfacesOptions::model_changed));
781 void parameter_changed (std::string const &)
786 void set_state_from_config ()
790 ControlProtocolManager& m = ControlProtocolManager::instance ();
791 for (list<ControlProtocolInfo*>::iterator i = m.control_protocol_info.begin(); i != m.control_protocol_info.end(); ++i) {
793 if (!(*i)->mandatory) {
794 TreeModel::Row r = *_store->append ();
795 r[_model.name] = (*i)->name;
796 r[_model.enabled] = ((*i)->protocol || (*i)->requested);
797 r[_model.feedback] = ((*i)->protocol && (*i)->protocol->get_feedback ());
798 r[_model.protocol_info] = *i;
805 void model_changed (TreeModel::Path const &, TreeModel::iterator const & i)
807 TreeModel::Row r = *i;
809 ControlProtocolInfo* cpi = r[_model.protocol_info];
814 bool const was_enabled = (cpi->protocol != 0);
815 bool const is_enabled = r[_model.enabled];
817 if (was_enabled != is_enabled) {
819 ControlProtocolManager::instance().instantiate (*cpi);
821 ControlProtocolManager::instance().teardown (*cpi);
825 bool const was_feedback = (cpi->protocol && cpi->protocol->get_feedback ());
826 bool const is_feedback = r[_model.feedback];
828 if (was_feedback != is_feedback && cpi->protocol) {
829 cpi->protocol->set_feedback (is_feedback);
833 class ControlSurfacesModelColumns : public TreeModelColumnRecord
837 ControlSurfacesModelColumns ()
845 TreeModelColumn<string> name;
846 TreeModelColumn<bool> enabled;
847 TreeModelColumn<bool> feedback;
848 TreeModelColumn<ControlProtocolInfo*> protocol_info;
851 Glib::RefPtr<ListStore> _store;
852 ControlSurfacesModelColumns _model;
857 RCOptionEditor::RCOptionEditor ()
858 : OptionEditor (Config, _("Ardour Preferences")),
863 add_option (_("Misc"), new OptionEditorHeading (_("Metering")));
865 ComboOption<float>* mht = new ComboOption<float> (
867 _("Meter hold time"),
868 sigc::mem_fun (*_rc_config, &RCConfiguration::get_meter_hold),
869 sigc::mem_fun (*_rc_config, &RCConfiguration::set_meter_hold)
872 mht->add (MeterHoldOff, _("off"));
873 mht->add (MeterHoldShort, _("short"));
874 mht->add (MeterHoldMedium, _("medium"));
875 mht->add (MeterHoldLong, _("long"));
877 add_option (_("Misc"), mht);
879 ComboOption<float>* mfo = new ComboOption<float> (
882 sigc::mem_fun (*_rc_config, &RCConfiguration::get_meter_falloff),
883 sigc::mem_fun (*_rc_config, &RCConfiguration::set_meter_falloff)
886 mfo->add (METER_FALLOFF_OFF, _("off"));
887 mfo->add (METER_FALLOFF_SLOWEST, _("slowest"));
888 mfo->add (METER_FALLOFF_SLOW, _("slow"));
889 mfo->add (METER_FALLOFF_MEDIUM, _("medium"));
890 mfo->add (METER_FALLOFF_FAST, _("fast"));
891 mfo->add (METER_FALLOFF_FASTER, _("faster"));
892 mfo->add (METER_FALLOFF_FASTEST, _("fastest"));
894 add_option (_("Misc"), mfo);
896 add_option (_("Misc"), new OptionEditorHeading (_("Undo")));
898 add_option (_("Misc"), new UndoOptions (_rc_config));
900 add_option (_("Misc"), new OptionEditorHeading (_("Misc")));
903 /* font scaling does nothing with GDK/Quartz */
904 add_option (_("Misc"), new FontScalingOptions (_rc_config));
907 add_option (_("Misc"),
909 "verify-remove-last-capture",
910 _("Verify removal of last capture"),
911 sigc::mem_fun (*_rc_config, &RCConfiguration::get_verify_remove_last_capture),
912 sigc::mem_fun (*_rc_config, &RCConfiguration::set_verify_remove_last_capture)
915 add_option (_("Misc"),
917 "periodic-safety-backups",
918 _("Make periodic backups of the session file"),
919 sigc::mem_fun (*_rc_config, &RCConfiguration::get_periodic_safety_backups),
920 sigc::mem_fun (*_rc_config, &RCConfiguration::set_periodic_safety_backups)
923 add_option (_("Misc"),
925 "sync-all-route-ordering",
926 _("Syncronise editor and mixer track order"),
927 sigc::mem_fun (*_rc_config, &RCConfiguration::get_sync_all_route_ordering),
928 sigc::mem_fun (*_rc_config, &RCConfiguration::set_sync_all_route_ordering)
931 add_option (_("Misc"),
933 "only-copy-imported-files",
934 _("Always copy imported files"),
935 sigc::mem_fun (*_rc_config, &RCConfiguration::get_only_copy_imported_files),
936 sigc::mem_fun (*_rc_config, &RCConfiguration::set_only_copy_imported_files)
939 add_option (_("Misc"),
942 _("Use narrow mixer strips"),
943 sigc::mem_fun (*_rc_config, &RCConfiguration::get_default_narrow_ms),
944 sigc::mem_fun (*_rc_config, &RCConfiguration::set_default_narrow_ms)
947 add_option (_("Misc"),
950 _("Name new markers"),
951 sigc::mem_fun (*_rc_config, &RCConfiguration::get_name_new_markers),
952 sigc::mem_fun (*_rc_config, &RCConfiguration::set_name_new_markers)
957 add_option (_("Transport"),
959 "latched-record-enable",
960 _("Keep record-enable engaged on stop"),
961 sigc::mem_fun (*_rc_config, &RCConfiguration::get_latched_record_enable),
962 sigc::mem_fun (*_rc_config, &RCConfiguration::set_latched_record_enable)
965 add_option (_("Transport"),
967 "stop-recording-on-xrun",
968 _("Stop recording when an xrun occurs"),
969 sigc::mem_fun (*_rc_config, &RCConfiguration::get_stop_recording_on_xrun),
970 sigc::mem_fun (*_rc_config, &RCConfiguration::set_stop_recording_on_xrun)
973 add_option (_("Transport"),
975 "create-xrun-marker",
976 _("Create markers where xruns occur"),
977 sigc::mem_fun (*_rc_config, &RCConfiguration::get_create_xrun_marker),
978 sigc::mem_fun (*_rc_config, &RCConfiguration::set_create_xrun_marker)
981 add_option (_("Transport"),
983 "stop-at-session-end",
984 _("Stop at the end of the session"),
985 sigc::mem_fun (*_rc_config, &RCConfiguration::get_stop_at_session_end),
986 sigc::mem_fun (*_rc_config, &RCConfiguration::set_stop_at_session_end)
989 add_option (_("Transport"),
991 "primary-clock-delta-edit-cursor",
992 _("Primary clock delta to edit cursor"),
993 sigc::mem_fun (*_rc_config, &RCConfiguration::get_primary_clock_delta_edit_cursor),
994 sigc::mem_fun (*_rc_config, &RCConfiguration::set_primary_clock_delta_edit_cursor)
997 add_option (_("Transport"),
999 "secondary-clock-delta-edit-cursor",
1000 _("Secondary clock delta to edit cursor"),
1001 sigc::mem_fun (*_rc_config, &RCConfiguration::get_secondary_clock_delta_edit_cursor),
1002 sigc::mem_fun (*_rc_config, &RCConfiguration::set_secondary_clock_delta_edit_cursor)
1005 add_option (_("Transport"),
1007 "disable-disarm-during-roll",
1008 _("Disable per-track record disarm while rolling"),
1009 sigc::mem_fun (*_rc_config, &RCConfiguration::get_disable_disarm_during_roll),
1010 sigc::mem_fun (*_rc_config, &RCConfiguration::set_disable_disarm_during_roll)
1015 add_option (_("Editor"),
1017 "link-region-and-track-selection",
1018 _("Link selection of regions and tracks"),
1019 sigc::mem_fun (*_rc_config, &RCConfiguration::get_link_region_and_track_selection),
1020 sigc::mem_fun (*_rc_config, &RCConfiguration::set_link_region_and_track_selection)
1023 add_option (_("Editor"),
1025 "automation-follows-regions",
1026 _("Move relevant automation when regions are moved"),
1027 sigc::mem_fun (*_rc_config, &RCConfiguration::get_automation_follows_regions),
1028 sigc::mem_fun (*_rc_config, &RCConfiguration::set_automation_follows_regions)
1031 add_option (_("Editor"),
1033 "show-track-meters",
1034 _("Show meters on tracks in the editor"),
1035 sigc::mem_fun (*_rc_config, &RCConfiguration::get_show_track_meters),
1036 sigc::mem_fun (*_rc_config, &RCConfiguration::set_show_track_meters)
1039 add_option (_("Editor"),
1041 "use-overlap-equivalency",
1042 _("Use overlap equivalency for regions"),
1043 sigc::mem_fun (*_rc_config, &RCConfiguration::get_use_overlap_equivalency),
1044 sigc::mem_fun (*_rc_config, &RCConfiguration::set_use_overlap_equivalency)
1047 add_option (_("Editor"),
1049 "rubberbanding-snaps-to-grid",
1050 _("Make rubberband selection rectangle snap to the grid"),
1051 sigc::mem_fun (*_rc_config, &RCConfiguration::get_rubberbanding_snaps_to_grid),
1052 sigc::mem_fun (*_rc_config, &RCConfiguration::set_rubberbanding_snaps_to_grid)
1055 add_option (_("Editor"),
1058 _("Show waveforms in regions"),
1059 sigc::mem_fun (*_rc_config, &RCConfiguration::get_show_waveforms),
1060 sigc::mem_fun (*_rc_config, &RCConfiguration::set_show_waveforms)
1063 ComboOption<WaveformScale>* wfs = new ComboOption<WaveformScale> (
1065 _("Waveform scale"),
1066 sigc::mem_fun (*_rc_config, &RCConfiguration::get_waveform_scale),
1067 sigc::mem_fun (*_rc_config, &RCConfiguration::set_waveform_scale)
1070 wfs->add (Linear, _("linear"));
1071 wfs->add (Logarithmic, _("logarithmic"));
1073 add_option (_("Editor"), wfs);
1075 ComboOption<WaveformShape>* wfsh = new ComboOption<WaveformShape> (
1077 _("Waveform shape"),
1078 sigc::mem_fun (*_rc_config, &RCConfiguration::get_waveform_shape),
1079 sigc::mem_fun (*_rc_config, &RCConfiguration::set_waveform_shape)
1082 wfsh->add (Traditional, _("traditional"));
1083 wfsh->add (Rectified, _("rectified"));
1085 add_option (_("Editor"), wfsh);
1089 add_option (_("Audio"), new OptionEditorHeading (_("Solo")));
1092 add_option (_("Audio"),
1094 "solo-control-is-listen-control",
1095 _("Solo controls are Listen controls"),
1096 sigc::mem_fun (*_rc_config, &RCConfiguration::get_solo_control_is_listen_control),
1097 sigc::mem_fun (*_rc_config, &RCConfiguration::set_solo_control_is_listen_control)
1100 ComboOption<ListenPosition>* lp = new ComboOption<ListenPosition> (
1102 _("Listen Position"),
1103 sigc::mem_fun (*_rc_config, &RCConfiguration::get_listen_position),
1104 sigc::mem_fun (*_rc_config, &RCConfiguration::set_listen_position)
1107 lp->add (AfterFaderListen, _("after-fader listen"));
1108 lp->add (PreFaderListen, _("pre-fader listen"));
1110 add_option (_("Audio"), lp);
1111 add_option (_("Audio"), new SoloMuteOptions (_rc_config));
1113 add_option (_("Audio"),
1117 sigc::mem_fun (*_rc_config, &RCConfiguration::get_solo_latched),
1118 sigc::mem_fun (*_rc_config, &RCConfiguration::set_solo_latched)
1121 add_option (_("Audio"),
1124 _("Show solo muting"),
1125 sigc::mem_fun (*_rc_config, &RCConfiguration::get_show_solo_mutes),
1126 sigc::mem_fun (*_rc_config, &RCConfiguration::set_show_solo_mutes)
1129 add_option (_("Audio"),
1131 "solo-mute-override",
1132 _("Override muting"),
1133 sigc::mem_fun (*_rc_config, &RCConfiguration::get_solo_mute_override),
1134 sigc::mem_fun (*_rc_config, &RCConfiguration::set_solo_mute_override)
1137 add_option (_("Audio"), new OptionEditorHeading (_("Monitoring")));
1139 ComboOption<MonitorModel>* mm = new ComboOption<MonitorModel> (
1141 _("Monitoring handled by"),
1142 sigc::mem_fun (*_rc_config, &RCConfiguration::get_monitoring_model),
1143 sigc::mem_fun (*_rc_config, &RCConfiguration::set_monitoring_model)
1146 mm->add (HardwareMonitoring, _("JACK"));
1147 mm->add (SoftwareMonitoring, _("ardour"));
1148 mm->add (ExternalMonitoring, _("audio hardware"));
1150 add_option (_("Audio"), mm);
1152 add_option (_("Audio"),
1154 "tape-machine-mode",
1155 _("Tape machine mode"),
1156 sigc::mem_fun (*_rc_config, &RCConfiguration::get_tape_machine_mode),
1157 sigc::mem_fun (*_rc_config, &RCConfiguration::set_tape_machine_mode)
1160 add_option (_("Audio"), new OptionEditorHeading (_("Connection of tracks and busses")));
1162 add_option (_("Audio"),
1164 "auto-connect-standard-busses",
1165 _("Auto-connect master/monitor busses"),
1166 sigc::mem_fun (*_rc_config, &RCConfiguration::get_auto_connect_standard_busses),
1167 sigc::mem_fun (*_rc_config, &RCConfiguration::set_auto_connect_standard_busses)
1170 ComboOption<AutoConnectOption>* iac = new ComboOption<AutoConnectOption> (
1171 "input-auto-connect",
1172 _("Connect track and bus inputs"),
1173 sigc::mem_fun (*_rc_config, &RCConfiguration::get_input_auto_connect),
1174 sigc::mem_fun (*_rc_config, &RCConfiguration::set_input_auto_connect)
1177 iac->add (AutoConnectPhysical, _("automatically to physical inputs"));
1178 iac->add (ManualConnect, _("manually"));
1180 add_option (_("Audio"), iac);
1182 ComboOption<AutoConnectOption>* oac = new ComboOption<AutoConnectOption> (
1183 "output-auto-connect",
1184 _("Connect track and bus outputs"),
1185 sigc::mem_fun (*_rc_config, &RCConfiguration::get_output_auto_connect),
1186 sigc::mem_fun (*_rc_config, &RCConfiguration::set_output_auto_connect)
1189 oac->add (AutoConnectPhysical, _("automatically to physical outputs"));
1190 oac->add (AutoConnectMaster, _("automatically to master outputs"));
1191 oac->add (ManualConnect, _("manually"));
1193 add_option (_("Audio"), oac);
1195 add_option (_("Audio"), new OptionEditorHeading (_("Denormals")));
1197 add_option (_("Audio"),
1199 "denormal-protection",
1200 _("Use DC bias to protect against denormals"),
1201 sigc::mem_fun (*_rc_config, &RCConfiguration::get_denormal_protection),
1202 sigc::mem_fun (*_rc_config, &RCConfiguration::set_denormal_protection)
1205 ComboOption<DenormalModel>* dm = new ComboOption<DenormalModel> (
1207 _("Processor handling"),
1208 sigc::mem_fun (*_rc_config, &RCConfiguration::get_denormal_model),
1209 sigc::mem_fun (*_rc_config, &RCConfiguration::set_denormal_model)
1212 dm->add (DenormalNone, _("no processor handling"));
1216 if (fpu.has_flush_to_zero()) {
1217 dm->add (DenormalFTZ, _("use FlushToZero"));
1220 if (fpu.has_denormals_are_zero()) {
1221 dm->add (DenormalDAZ, _("use DenormalsAreZero"));
1224 if (fpu.has_flush_to_zero() && fpu.has_denormals_are_zero()) {
1225 dm->add (DenormalFTZDAZ, _("use FlushToZero and DenormalsAreZerO"));
1228 add_option (_("Audio"), dm);
1230 add_option (_("Audio"), new OptionEditorHeading (_("Plugins")));
1232 add_option (_("Audio"),
1234 "plugins-stop-with-transport",
1235 _("Stop plugins when the transport is stopped"),
1236 sigc::mem_fun (*_rc_config, &RCConfiguration::get_plugins_stop_with_transport),
1237 sigc::mem_fun (*_rc_config, &RCConfiguration::set_plugins_stop_with_transport)
1240 add_option (_("Audio"),
1242 "do-not-record-plugins",
1243 _("Disable plugins during recording"),
1244 sigc::mem_fun (*_rc_config, &RCConfiguration::get_do_not_record_plugins),
1245 sigc::mem_fun (*_rc_config, &RCConfiguration::set_do_not_record_plugins)
1248 add_option (_("Audio"),
1250 "new-plugins-active",
1251 _("Make new plugins active"),
1252 sigc::mem_fun (*_rc_config, &RCConfiguration::get_new_plugins_active),
1253 sigc::mem_fun (*_rc_config, &RCConfiguration::set_new_plugins_active)
1256 add_option (_("Audio"),
1258 "auto-analyse-audio",
1259 _("Enable automatic analysis of audio"),
1260 sigc::mem_fun (*_rc_config, &RCConfiguration::get_auto_analyse_audio),
1261 sigc::mem_fun (*_rc_config, &RCConfiguration::set_auto_analyse_audio)
1266 list<ComboOption<string>* > midi_combos;
1268 midi_combos.push_back (new ComboOption<string> (
1270 _("Send/Receive MTC via"),
1271 sigc::mem_fun (*_rc_config, &RCConfiguration::get_mtc_port_name),
1272 sigc::mem_fun (*_rc_config, &RCConfiguration::set_mtc_port_name)
1275 midi_combos.push_back (new ComboOption<string> (
1276 "midi-clock-port-name",
1277 _("Send/Receive MIDI clock via"),
1278 sigc::mem_fun (*_rc_config, &RCConfiguration::get_midi_clock_port_name),
1279 sigc::mem_fun (*_rc_config, &RCConfiguration::set_midi_clock_port_name)
1282 midi_combos.push_back (new ComboOption<string> (
1284 _("Send/Receive MMC via"),
1285 sigc::mem_fun (*_rc_config, &RCConfiguration::get_mmc_port_name),
1286 sigc::mem_fun (*_rc_config, &RCConfiguration::set_mmc_port_name)
1289 midi_combos.push_back (new ComboOption<string> (
1291 _("Send/Receive MIDI parameter control via"),
1292 sigc::mem_fun (*_rc_config, &RCConfiguration::get_midi_port_name),
1293 sigc::mem_fun (*_rc_config, &RCConfiguration::set_midi_port_name)
1296 add_option (_("MIDI control"), new MIDIPorts (_rc_config, midi_combos));
1298 for (list<ComboOption<string>* >::iterator i = midi_combos.begin(); i != midi_combos.end(); ++i) {
1299 add_option (_("MIDI control"), *i);
1302 add_option (_("MIDI control"),
1305 _("Obey MIDI Machine Control commands"),
1306 sigc::mem_fun (*_rc_config, &RCConfiguration::get_mmc_control),
1307 sigc::mem_fun (*_rc_config, &RCConfiguration::set_mmc_control)
1311 add_option (_("MIDI control"),
1314 _("Send MIDI Machine Control commands"),
1315 sigc::mem_fun (*_rc_config, &RCConfiguration::get_send_mmc),
1316 sigc::mem_fun (*_rc_config, &RCConfiguration::set_send_mmc)
1319 add_option (_("MIDI control"),
1322 _("Send MIDI control feedback"),
1323 sigc::mem_fun (*_rc_config, &RCConfiguration::get_midi_feedback),
1324 sigc::mem_fun (*_rc_config, &RCConfiguration::set_midi_feedback)
1327 add_option (_("MIDI control"),
1328 new SpinOption<uint8_t> (
1329 "mmc-receive-device-id",
1330 _("Inbound MMC device ID"),
1331 sigc::mem_fun (*_rc_config, &RCConfiguration::get_mmc_receive_device_id),
1332 sigc::mem_fun (*_rc_config, &RCConfiguration::set_mmc_receive_device_id),
1336 add_option (_("MIDI control"),
1337 new SpinOption<uint8_t> (
1338 "mmc-send-device-id",
1339 _("Outbound MMC device ID"),
1340 sigc::mem_fun (*_rc_config, &RCConfiguration::get_mmc_send_device_id),
1341 sigc::mem_fun (*_rc_config, &RCConfiguration::set_mmc_send_device_id),
1345 add_option (_("MIDI control"),
1346 new SpinOption<int32_t> (
1347 "initial-program-change",
1348 _("Initial program change"),
1349 sigc::mem_fun (*_rc_config, &RCConfiguration::get_initial_program_change),
1350 sigc::mem_fun (*_rc_config, &RCConfiguration::set_initial_program_change),
1354 /* CONTROL SURFACES */
1356 add_option (_("Control surfaces"), new ControlSurfacesOptions);
1358 ComboOption<RemoteModel>* rm = new ComboOption<RemoteModel> (
1360 _("Control surface remote ID"),
1361 sigc::mem_fun (*_rc_config, &RCConfiguration::get_remote_model),
1362 sigc::mem_fun (*_rc_config, &RCConfiguration::set_remote_model)
1365 rm->add (UserOrdered, _("assigned by user"));
1366 rm->add (MixerOrdered, _("follows order of mixer"));
1367 rm->add (EditorOrdered, _("follows order of editor"));
1369 add_option (_("Control surfaces"), rm);
1373 add_option (_("Click"), new ClickOptions (_rc_config, this));
1377 add_option (_("Keyboard"), new KeyboardOptions);