Merged with trunk R708
[ardour.git] / gtk2_ardour / ardour_ui.cc
1 /*
2     Copyright (C) 1999-2002 Paul Davis 
3
4     This program is free software; you can redistribute it and/or modify
5     it under the terms of the GNU General Public License as published by
6     the Free Software Foundation; either version 2 of the License, or
7     (at your option) any later version.
8
9     This program is distributed in the hope that it will be useful,
10     but WITHOUT ANY WARRANTY; without even the implied warranty of
11     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12     GNU General Public License for more details.
13
14     You should have received a copy of the GNU General Public License
15     along with this program; if not, write to the Free Software
16     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
17
18     $Id$
19 */
20
21 #include <algorithm>
22 #include <cmath>
23 #include <fcntl.h>
24 #include <signal.h>
25 #include <unistd.h>
26 #include <cerrno>
27 #include <fstream>
28
29 #include <iostream>
30
31 #include <gtkmm/messagedialog.h>
32 #include <gtkmm/accelmap.h>
33
34 #include <pbd/error.h>
35 #include <pbd/compose.h>
36 #include <pbd/pathscanner.h>
37 #include <pbd/failed_constructor.h>
38 #include <gtkmm2ext/gtk_ui.h>
39 #include <gtkmm2ext/utils.h>
40 #include <gtkmm2ext/click_box.h>
41 #include <gtkmm2ext/fastmeter.h>
42 #include <gtkmm2ext/stop_signal.h>
43 #include <gtkmm2ext/popup.h>
44
45 #include <midi++/port.h>
46 #include <midi++/mmc.h>
47
48 #include <ardour/ardour.h>
49 #include <ardour/port.h>
50 #include <ardour/audioengine.h>
51 #include <ardour/playlist.h>
52 #include <ardour/utils.h>
53 #include <ardour/audio_diskstream.h>
54 #include <ardour/audiofilesource.h>
55 #include <ardour/recent_sessions.h>
56 #include <ardour/session_route.h>
57 #include <ardour/port.h>
58 #include <ardour/audio_track.h>
59 #include <ardour/midi_track.h>
60
61 #include "actions.h"
62 #include "ardour_ui.h"
63 #include "public_editor.h"
64 #include "audio_clock.h"
65 #include "keyboard.h"
66 #include "mixer_ui.h"
67 #include "prompter.h"
68 #include "opts.h"
69 #include "keyboard_target.h"
70 #include "add_route_dialog.h"
71 #include "new_session_dialog.h"
72 #include "about.h"
73 #include "utils.h"
74 #include "gui_thread.h"
75 #include "color_manager.h"
76
77 #include "i18n.h"
78
79 using namespace ARDOUR;
80 using namespace PBD;
81 using namespace Gtkmm2ext;
82 using namespace Gtk;
83 using namespace sigc;
84
85 ARDOUR_UI *ARDOUR_UI::theArdourUI = 0;
86
87 sigc::signal<void,bool> ARDOUR_UI::Blink;
88 sigc::signal<void>      ARDOUR_UI::RapidScreenUpdate;
89 sigc::signal<void>      ARDOUR_UI::SuperRapidScreenUpdate;
90 sigc::signal<void,jack_nframes_t> ARDOUR_UI::Clock;
91
92 ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[], string rcfile)
93
94         : Gtkmm2ext::UI ("ardour", argcp, argvp, rcfile),
95           
96           primary_clock (X_("TransportClockDisplay"), true, false, true),
97           secondary_clock (X_("SecondaryClockDisplay"), true, false, true),
98           preroll_clock (X_("PreRollClock"), true, true),
99           postroll_clock (X_("PostRollClock"), true, true),
100
101           /* adjuster table */
102
103           adjuster_table (3, 3),
104
105           /* preroll stuff */
106
107           preroll_button (_("pre\nroll")),
108           postroll_button (_("post\nroll")),
109
110           /* big clock */
111
112           big_clock ("BigClockDisplay", true),
113
114           /* transport */
115
116           time_master_button (_("time\nmaster")),
117
118           shuttle_units_button (_("% ")),
119
120           punch_in_button (_("Punch In")),
121           punch_out_button (_("Punch Out")),
122           auto_return_button (_("Auto Return")),
123           auto_play_button (_("Autuo Play")),
124           auto_input_button (_("Auto Input")),
125           click_button (_("Click")),
126           auditioning_alert_button (_("AUDITION")),
127           solo_alert_button (_("SOLO")),
128           shown_flag (false)
129
130 {
131         using namespace Gtk::Menu_Helpers;
132
133         Gtkmm2ext::init();
134         
135         about = 0;
136
137         if (theArdourUI == 0) {
138                 theArdourUI = this;
139         }
140
141         ActionManager::init ();
142
143         /* load colors */
144
145         color_manager = new ColorManager();
146
147         std::string color_file = ARDOUR::find_config_file("ardour.colors");
148         
149         color_manager->load (color_file);
150
151         m_new_session_dialog = new NewSessionDialog();
152         editor = 0;
153         mixer = 0;
154         session = 0;
155         _session_is_new = false;
156         big_clock_window = 0;
157         session_selector_window = 0;
158         last_key_press_time = 0;
159         connection_editor = 0;
160         add_route_dialog = 0;
161         route_params = 0;
162         option_editor = 0;
163         location_ui = 0;
164         sfdb = 0;
165         open_session_selector = 0;
166         have_configure_timeout = false;
167         have_disk_overrun_displayed = false;
168         have_disk_underrun_displayed = false;
169         _will_create_new_session_automatically = false;
170         session_loaded = false;
171         last_speed_displayed = -1.0f;
172
173         last_configure_time.tv_sec = 0;
174         last_configure_time.tv_usec = 0;
175
176         shuttle_grabbed = false;
177         shuttle_fract = 0.0;
178         shuttle_max_speed = 8.0f;
179
180         set_shuttle_units (Percentage);
181         set_shuttle_behaviour (Sprung);
182
183         shuttle_style_menu = 0;
184         shuttle_unit_menu = 0;
185
186         gettimeofday (&last_peak_grab, 0);
187         gettimeofday (&last_shuttle_request, 0);
188
189         ARDOUR::AudioDiskstream::DeleteSources.connect (mem_fun(*this, &ARDOUR_UI::delete_sources_in_the_right_thread));
190         ARDOUR::AudioDiskstream::DiskOverrun.connect (mem_fun(*this, &ARDOUR_UI::disk_overrun_handler));
191         ARDOUR::AudioDiskstream::DiskUnderrun.connect (mem_fun(*this, &ARDOUR_UI::disk_underrun_handler));
192
193         /* handle pending state with a dialog */
194
195         ARDOUR::Session::AskAboutPendingState.connect (mem_fun(*this, &ARDOUR_UI::pending_state_dialog));
196
197         /* have to wait for AudioEngine and Configuration before proceeding */
198 }
199
200 void
201 ARDOUR_UI::set_engine (AudioEngine& e)
202 {
203         engine = &e;
204
205         engine->Stopped.connect (mem_fun(*this, &ARDOUR_UI::engine_stopped));
206         engine->Running.connect (mem_fun(*this, &ARDOUR_UI::engine_running));
207         engine->Halted.connect (mem_fun(*this, &ARDOUR_UI::engine_halted));
208         engine->SampleRateChanged.connect (mem_fun(*this, &ARDOUR_UI::update_sample_rate));
209
210         _tooltips.enable();
211
212         keyboard = new Keyboard;
213
214         if (setup_windows ()) {
215                 throw failed_constructor ();
216         }
217
218         if (GTK_ARDOUR::show_key_actions) {
219                 vector<string> names;
220                 vector<string> paths;
221                 vector<string> keys;
222                 vector<AccelKey> bindings;
223
224                 ActionManager::get_all_actions (names, paths, keys, bindings);
225
226                 vector<string>::iterator n;
227                 vector<string>::iterator k;
228                 for (n = names.begin(), k = keys.begin(); n != names.end(); ++n, ++k) {
229                         cerr << "Action: " << (*n) << " bound to " << (*k) << endl;
230                 }
231
232                 exit (0);
233         }
234
235         /* start with timecode, metering enabled
236         */
237         
238         blink_timeout_tag = -1;
239
240         /* the global configuration object is now valid */
241
242         use_config ();
243
244         /* this being a GUI and all, we want peakfiles */
245
246         AudioFileSource::set_build_peakfiles (true);
247         AudioFileSource::set_build_missing_peakfiles (true);
248
249         if (AudioSource::start_peak_thread ()) {
250                 throw failed_constructor();
251         }
252
253         /* start the time-of-day-clock */
254         
255         update_wall_clock ();
256         Glib::signal_timeout().connect (mem_fun(*this, &ARDOUR_UI::update_wall_clock), 60000);
257
258         update_disk_space ();
259         update_cpu_load ();
260         update_sample_rate (engine->frame_rate());
261
262         starting.connect (mem_fun(*this, &ARDOUR_UI::startup));
263         stopping.connect (mem_fun(*this, &ARDOUR_UI::shutdown));
264 }
265
266 ARDOUR_UI::~ARDOUR_UI ()
267 {
268         save_ardour_state ();
269
270         if (keyboard) {
271                 delete keyboard;
272         }
273
274         if (editor) {
275                 delete editor;
276         }
277
278         if (mixer) {
279                 delete mixer;
280         }
281
282         if (add_route_dialog) {
283                 delete add_route_dialog;
284         }
285
286         AudioSource::stop_peak_thread ();
287 }
288
289 gint
290 ARDOUR_UI::configure_timeout ()
291 {
292         struct timeval now;
293         struct timeval diff;
294
295         if (last_configure_time.tv_sec == 0 && last_configure_time.tv_usec == 0) {
296                 /* no configure events yet */
297                 return TRUE;
298         }
299
300         gettimeofday (&now, 0);
301         timersub (&now, &last_configure_time, &diff);
302
303         /* force a gap of 0.5 seconds since the last configure event
304          */
305
306         if (diff.tv_sec == 0 && diff.tv_usec < 500000) {
307                 return TRUE;
308         } else {
309                 have_configure_timeout = false;
310                 save_ardour_state ();
311                 return FALSE;
312         }
313 }
314
315 gboolean
316 ARDOUR_UI::configure_handler (GdkEventConfigure* conf)
317 {
318         if (have_configure_timeout) {
319                 gettimeofday (&last_configure_time, 0);
320         } else {
321                 Glib::signal_timeout().connect (mem_fun(*this, &ARDOUR_UI::configure_timeout), 100);
322                 have_configure_timeout = true;
323         }
324                 
325         return FALSE;
326 }
327
328 void
329 ARDOUR_UI::save_ardour_state ()
330 {
331         if (!keyboard || !mixer || !editor) {
332                 return;
333         }
334         
335         /* XXX this is all a bit dubious. add_extra_xml() uses
336            a different lifetime model from add_instant_xml().
337         */
338
339         XMLNode* node = new XMLNode (keyboard->get_state());
340         Config->add_extra_xml (*node);
341         Config->save_state();
342
343         XMLNode enode(static_cast<Stateful*>(editor)->get_state());
344         XMLNode mnode(mixer->get_state());
345
346         if (session) {
347                 session->add_instant_xml (enode, session->path());
348                 session->add_instant_xml (mnode, session->path());
349         } else {
350                 Config->add_instant_xml (enode, get_user_ardour_path());
351                 Config->add_instant_xml (mnode, get_user_ardour_path());
352         }
353
354         /* keybindings */
355
356         AccelMap::save ("ardour.saved_bindings");
357 }
358
359 void
360 ARDOUR_UI::startup ()
361 {
362         /* Once the UI is up and running, start the audio engine. Doing
363            this before the UI is up and running can cause problems
364            when not running with SCHED_FIFO, because the amount of
365            CPU and disk work needed to get the UI started can interfere
366            with the scheduling of the audio thread.
367         */
368
369         Glib::signal_idle().connect (mem_fun(*this, &ARDOUR_UI::start_engine));
370 }
371
372 void
373 ARDOUR_UI::finish()
374 {
375         if (session && session->dirty()) {
376                 switch (ask_about_saving_session(_("quit"))) {
377                 case -1:
378                         return;
379                         break;
380                 case 1:
381                         /* use the default name */
382                         if (save_state_canfail ("")) {
383                                 /* failed - don't quit */
384                                 MessageDialog msg (*editor, 
385                                                _("\
386 Ardour was unable to save your session.\n\n\
387 If you still wish to quit, please use the\n\n\
388 \"Just quit\" option."));
389                                 msg.run ();
390                                 return;
391                         }
392                         break;
393                 case 0:
394                         break;
395                 }
396         }
397         Config->save_state();
398         quit ();
399 }
400
401 int
402 ARDOUR_UI::ask_about_saving_session (const string & what)
403 {
404         ArdourDialog window (_("ardour: save session?"));
405         Gtk::HBox dhbox;  // the hbox for the image and text
406         Gtk::Label  prompt_label;
407         Gtk::Image* dimage = manage (new Gtk::Image(Stock::DIALOG_WARNING,  Gtk::ICON_SIZE_DIALOG));
408
409         string msg;
410
411         msg = string_compose(_("Don't %1"), what);
412         window.add_button (msg, RESPONSE_REJECT);
413         msg = string_compose(_("Just %1"), what);
414         window.add_button (msg, RESPONSE_APPLY);
415         msg = string_compose(_("Save and %1"), what);
416         window.add_button (msg, RESPONSE_ACCEPT);
417
418         window.set_default_response (RESPONSE_ACCEPT);
419
420         Gtk::Button noquit_button (msg);
421         noquit_button.set_name ("EditorGTKButton");
422
423         string prompt;
424         string type;
425
426         if (session->snap_name() == session->name()) {
427                 type = _("session");
428         } else {
429                 type = _("snapshot");
430         }
431         prompt = string_compose(_("The %1\"%2\"\nhas not been saved.\n\nAny changes made this time\nwill be lost unless you save it.\n\nWhat do you want to do?"), 
432                          type, session->snap_name());
433         
434         prompt_label.set_text (prompt);
435         prompt_label.set_name (X_("PrompterLabel"));
436         prompt_label.set_alignment(ALIGN_LEFT, ALIGN_TOP);
437
438         dimage->set_alignment(ALIGN_CENTER, ALIGN_TOP)
439 ;
440         dhbox.set_homogeneous (false);
441         dhbox.pack_start (*dimage, false, false, 5);
442         dhbox.pack_start (prompt_label, true, false, 5);
443         window.get_vbox()->pack_start (dhbox);
444
445         window.set_name (_("Prompter"));
446         window.set_position (Gtk::WIN_POS_MOUSE);
447         window.set_modal (true);
448         window.set_resizable (false);
449         window.show_all ();
450
451         save_the_session = 0;
452
453         editor->ensure_float (window);
454
455         ResponseType r = (ResponseType) window.run();
456
457         window.hide ();
458
459         switch (r) {
460         case RESPONSE_ACCEPT: // save and get out of here
461                 return 1;
462         case RESPONSE_APPLY:  // get out of here
463                 return 0;
464         default:
465                 break;
466         }
467
468         return -1;
469 }
470         
471 gint
472 ARDOUR_UI::every_second ()
473 {
474         update_cpu_load ();
475         update_buffer_load ();
476         update_disk_space ();
477         return TRUE;
478 }
479
480 gint
481 ARDOUR_UI::every_point_one_seconds ()
482 {
483         update_speed_display ();
484         RapidScreenUpdate(); /* EMIT_SIGNAL */
485         return TRUE;
486 }
487
488 gint
489 ARDOUR_UI::every_point_zero_one_seconds ()
490 {
491         SuperRapidScreenUpdate(); /* EMIT_SIGNAL */
492         return TRUE;
493 }
494
495 void
496 ARDOUR_UI::update_sample_rate (jack_nframes_t ignored)
497 {
498         char buf[32];
499
500         ENSURE_GUI_THREAD (bind (mem_fun(*this, &ARDOUR_UI::update_sample_rate), ignored));
501
502         if (!engine->connected()) {
503
504                 snprintf (buf, sizeof (buf), _("disconnected"));
505
506         } else {
507
508                 jack_nframes_t rate = engine->frame_rate();
509                 
510                 if (fmod (rate, 1000.0) != 0.0) {
511                         snprintf (buf, sizeof (buf), _("%.1f kHz / %4.1f msecs"), 
512                                   (float) rate/1000.0f,
513                                   (engine->frames_per_cycle() / (float) rate) * 1000.0f);
514                 } else {
515                         snprintf (buf, sizeof (buf), _("%u kHz / %4.1f msecs"), 
516                                   rate/1000,
517                                   (engine->frames_per_cycle() / (float) rate) * 1000.0f);
518                 }
519         }
520
521         sample_rate_label.set_text (buf);
522 }
523
524 void
525 ARDOUR_UI::update_cpu_load ()
526 {
527         char buf[32];
528         snprintf (buf, sizeof (buf), _("DSP: %.1f%%"), engine->get_cpu_load());
529         cpu_load_label.set_text (buf);
530 }
531
532 void
533 ARDOUR_UI::update_buffer_load ()
534 {
535         char buf[64];
536
537         if (session) {
538                 snprintf (buf, sizeof (buf), _("Buffers p:%" PRIu32 "%% c:%" PRIu32 "%%"), 
539                           session->playback_load(), session->capture_load());
540                 buffer_load_label.set_text (buf);
541         } else {
542                 buffer_load_label.set_text ("");
543         }
544 }
545
546 void
547 ARDOUR_UI::count_recenabled_diskstreams (Route& route)
548 {
549         Track* track = dynamic_cast<Track*>(&route);
550         if (track && track->diskstream().record_enabled()) {
551                 rec_enabled_diskstreams++;
552         }
553 }
554
555 void
556 ARDOUR_UI::update_disk_space()
557 {
558         if (session == 0) {
559                 return;
560         }
561
562         jack_nframes_t frames = session->available_capture_duration();
563         char buf[64];
564
565         if (frames == max_frames) {
566                 strcpy (buf, _("Disk: 24hrs+"));
567         } else {
568                 int hrs;
569                 int mins;
570                 int secs;
571                 jack_nframes_t fr = session->frame_rate();
572                 
573                 if (session->actively_recording()){
574                         
575                         rec_enabled_diskstreams = 0;
576                         session->foreach_route (this, &ARDOUR_UI::count_recenabled_diskstreams);
577                         
578                         if (rec_enabled_diskstreams) {
579                                 frames /= rec_enabled_diskstreams;
580                         }
581                         
582                 } else {
583                         
584                         /* hmmm. shall we divide by the route count? or the diskstream count?
585                            or what? for now, do nothing ...
586                         */
587                         
588                 }
589                 
590                 hrs  = frames / (fr * 3600);
591                 frames -= hrs * fr * 3600;
592                 mins = frames / (fr * 60);
593                 frames -= mins * fr * 60;
594                 secs = frames / fr;
595                 
596                 snprintf (buf, sizeof(buf), _("Disk: %02dh:%02dm:%02ds"), hrs, mins, secs);
597         }
598
599         disk_space_label.set_text (buf);
600 }                 
601
602 gint
603 ARDOUR_UI::update_wall_clock ()
604 {
605         time_t now;
606         struct tm *tm_now;
607         char buf[16];
608
609         time (&now);
610         tm_now = localtime (&now);
611
612         sprintf (buf, "%02d:%02d", tm_now->tm_hour, tm_now->tm_min);
613         wall_clock_label.set_text (buf);
614
615         return TRUE;
616 }
617 void
618 ARDOUR_UI::control_methods_adjusted ()
619
620 {
621         int which_method;
622
623         which_method = (int) online_control_button->adjustment.get_value();
624         switch (which_method) {
625         case 0:
626                 allow_mmc_and_local ();
627                 break;
628         case 1:
629                 allow_mmc_only ();
630                 break;
631         case 2:
632                 allow_local_only ();
633                 break;
634         default:
635                 fatal << _("programming error: impossible control method") << endmsg;
636         }
637 }
638         
639
640 void
641 ARDOUR_UI::mmc_device_id_adjusted ()
642
643 {
644 #if 0
645         if (mmc) {
646                 int dev_id = (int) mmc_id_button->adjustment.get_value();
647                 mmc->set_device_id (dev_id);
648         }
649 #endif
650 }
651
652 gint
653 ARDOUR_UI::session_menu (GdkEventButton *ev)
654 {
655         session_popup_menu->popup (0, 0);
656         return TRUE;
657 }
658
659 void
660 ARDOUR_UI::redisplay_recent_sessions ()
661 {
662         vector<string *> *sessions;
663         vector<string *>::iterator i;
664         RecentSessionsSorter cmp;
665         
666         recent_session_display.set_model (Glib::RefPtr<TreeModel>(0));
667         recent_session_model->clear ();
668
669         RecentSessions rs;
670         ARDOUR::read_recent_sessions (rs);
671
672         if (rs.empty()) {
673                 recent_session_display.set_model (recent_session_model);
674                 return;
675         }
676
677         /* sort them alphabetically */
678         sort (rs.begin(), rs.end(), cmp);
679         sessions = new vector<string*>;
680
681         for (RecentSessions::iterator i = rs.begin(); i != rs.end(); ++i) {
682                 sessions->push_back (new string ((*i).second));
683         }
684
685         for (i = sessions->begin(); i != sessions->end(); ++i) {
686
687                 vector<string*>* states;
688                 vector<const gchar*> item;
689                 string fullpath = *(*i);
690                 
691                 /* remove any trailing / */
692
693                 if (fullpath[fullpath.length()-1] == '/') {
694                         fullpath = fullpath.substr (0, fullpath.length()-1);
695                 }
696
697                 /* now get available states for this session */
698
699                 if ((states = Session::possible_states (fullpath)) == 0) {
700                         /* no state file? */
701                         continue;
702                 }
703
704                 TreeModel::Row row = *(recent_session_model->append());
705
706                 row[recent_session_columns.visible_name] = Glib::path_get_basename (fullpath);
707                 row[recent_session_columns.fullpath] = fullpath;
708
709                 if (states->size() > 1) {
710
711                         /* add the children */
712                         
713                         for (vector<string*>::iterator i2 = states->begin(); i2 != states->end(); ++i2) {
714                                 
715                                 TreeModel::Row child_row = *(recent_session_model->append (row.children()));
716
717                                 child_row[recent_session_columns.visible_name] = **i2;
718                                 child_row[recent_session_columns.fullpath] = fullpath;
719
720                                 delete *i2;
721                         }
722                 }
723
724                 delete states;
725         }
726
727         recent_session_display.set_model (recent_session_model);
728         delete sessions;
729 }
730
731 void
732 ARDOUR_UI::build_session_selector ()
733 {
734         session_selector_window = new ArdourDialog ("session selector");
735         
736         Gtk::ScrolledWindow *scroller = manage (new Gtk::ScrolledWindow);
737         
738         session_selector_window->add_button (Stock::CANCEL, RESPONSE_CANCEL);
739         session_selector_window->add_button (Stock::OPEN, RESPONSE_ACCEPT);
740         session_selector_window->set_default_response (RESPONSE_ACCEPT);
741         recent_session_model = TreeStore::create (recent_session_columns);
742         recent_session_display.set_model (recent_session_model);
743         recent_session_display.append_column (_("Recent Sessions"), recent_session_columns.visible_name);
744         recent_session_display.set_headers_visible (false);
745         recent_session_display.get_selection()->set_mode (SELECTION_SINGLE);
746
747         recent_session_display.signal_row_activated().connect (mem_fun (*this, &ARDOUR_UI::recent_session_row_activated));
748
749         scroller->add (recent_session_display);
750         scroller->set_policy (Gtk::POLICY_NEVER, Gtk::POLICY_AUTOMATIC);
751
752         session_selector_window->set_name ("SessionSelectorWindow");
753         session_selector_window->set_size_request (200, 400);
754         session_selector_window->get_vbox()->pack_start (*scroller);
755         session_selector_window->show_all_children();
756 }
757
758 void
759 ARDOUR_UI::recent_session_row_activated (const TreePath& path, TreeViewColumn* col)
760 {
761         session_selector_window->response (RESPONSE_ACCEPT);
762 }
763
764 void
765 ARDOUR_UI::open_recent_session ()
766 {
767         /* popup selector window */
768
769         if (session_selector_window == 0) {
770                 build_session_selector ();
771         }
772
773         redisplay_recent_sessions ();
774
775         ResponseType r = (ResponseType) session_selector_window->run ();
776
777         session_selector_window->hide();
778
779         switch (r) {
780         case RESPONSE_ACCEPT:
781                 break;
782         default:
783                 return;
784         }
785
786         Gtk::TreeModel::iterator i = recent_session_display.get_selection()->get_selected();
787
788         if (i == recent_session_model->children().end()) {
789                 return;
790         }
791         
792         Glib::ustring path = (*i)[recent_session_columns.fullpath];
793         Glib::ustring state = (*i)[recent_session_columns.visible_name];
794
795         _session_is_new = false;
796
797         load_session (path, state);
798 }
799
800 bool
801 ARDOUR_UI::filter_ardour_session_dirs (const FileFilter::Info& info) 
802 {
803         struct stat statbuf;
804
805         if (stat (info.filename.c_str(), &statbuf) != 0) {
806                 return false;
807         }
808
809         if (!S_ISDIR(statbuf.st_mode)) {
810                 return false;
811         }
812
813         // XXX Portability
814         
815         string session_file = info.filename;
816         session_file += '/';
817         session_file += Glib::path_get_basename (info.filename);
818         session_file += ".ardour";
819         
820         if (stat (session_file.c_str(), &statbuf) != 0) {
821                 return false;
822         }
823
824         return S_ISREG (statbuf.st_mode);
825 }
826
827 void
828 ARDOUR_UI::open_session ()
829 {
830         /* popup selector window */
831
832         if (open_session_selector == 0) {
833
834                 /* ardour sessions are folders */
835
836                 open_session_selector = new Gtk::FileChooserDialog (_("open session"), FILE_CHOOSER_ACTION_OPEN);
837                 open_session_selector->add_button (Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
838                 open_session_selector->add_button (Gtk::Stock::OPEN, Gtk::RESPONSE_ACCEPT);
839
840                 FileFilter session_filter;
841                 session_filter.add_pattern ("*.ardour");
842                 session_filter.set_name (_("Ardour sessions"));
843                 open_session_selector->add_filter (session_filter);
844                 open_session_selector->set_filter (session_filter);
845         }
846
847         int response = open_session_selector->run();
848         open_session_selector->hide ();
849
850         switch (response) {
851         case RESPONSE_ACCEPT:
852                 break;
853         default:
854                 open_session_selector->hide();
855                 return;
856         }
857
858         open_session_selector->hide();
859         string session_path = open_session_selector->get_filename();
860         string path, name;
861         bool isnew;
862
863         if (session_path.length() > 0) {
864                 if (Session::find_session (session_path, path, name, isnew) == 0) {
865                         _session_is_new = isnew;
866                         load_session (path, name);
867                 }
868         }
869 }
870
871
872 void
873 ARDOUR_UI::session_add_midi_route (bool disk)
874 {
875         boost::shared_ptr<Route> route;
876
877         if (session == 0) {
878                 warning << _("You cannot add a track without a session already loaded.") << endmsg;
879                 return;
880         }
881
882         try { 
883                 if (disk) {
884                         if ((route = session->new_midi_track (/*mode*/)) == 0) {
885                                 error << _("could not create new midi track") << endmsg;
886                         }
887                 } else {
888                         if ((route = session->new_midi_route ()) == 0) {
889                                 error << _("could not create new midi bus") << endmsg;
890                         }
891                 }
892         }
893
894         catch (...) {
895                 MessageDialog msg (*editor, 
896                                    _("There are insufficient JACK ports available\n\
897 to create a new track or bus.\n\
898 You should save Ardour, exit and\n\
899 restart JACK with more ports."));
900                 msg.run ();
901         }
902 }
903
904
905 void
906 ARDOUR_UI::session_add_audio_route (bool disk, int32_t input_channels, int32_t output_channels, ARDOUR::TrackMode mode)
907 {
908         boost::shared_ptr<Route> route;
909
910         if (session == 0) {
911                 warning << _("You cannot add a track without a session already loaded.") << endmsg;
912                 return;
913         }
914
915         try { 
916                 if (disk) {
917                         if ((route = session->new_audio_track (input_channels, output_channels, mode)) == 0) {
918                                 error << _("could not create new audio track") << endmsg;
919                         }
920                 } else {
921                         if ((route = session->new_audio_route (input_channels, output_channels)) == 0) {
922                                 error << _("could not create new audio bus") << endmsg;
923                         }
924                 }
925                 
926 #if CONTROLOUTS
927                 if (need_control_room_outs) {
928                         pan_t pans[2];
929                         
930                         pans[0] = 0.5;
931                         pans[1] = 0.5;
932                         
933                         route->set_stereo_control_outs (control_lr_channels);
934                         route->control_outs()->set_stereo_pan (pans, this);
935                 }
936 #endif /* CONTROLOUTS */
937         }
938
939         catch (...) {
940                 MessageDialog msg (*editor, 
941                                    _("There are insufficient JACK ports available\n\
942 to create a new track or bus.\n\
943 You should save Ardour, exit and\n\
944 restart JACK with more ports."));
945                 msg.run ();
946         }
947 }
948
949 void
950 ARDOUR_UI::diskstream_added (Diskstream* ds)
951 {
952 }
953
954 void
955 ARDOUR_UI::do_transport_locate (jack_nframes_t new_position)
956 {
957         jack_nframes_t _preroll;
958
959         if (session) {
960                 _preroll = session->convert_to_frames_at (new_position, session->preroll);
961
962                 if (new_position > _preroll) {
963                         new_position -= _preroll;
964                 } else {
965                         new_position = 0;
966                 }
967
968                 session->request_locate (new_position);
969         }
970 }
971
972 void
973 ARDOUR_UI::transport_goto_start ()
974 {
975         if (session) {
976                 session->goto_start();
977
978                 
979                 /* force displayed area in editor to start no matter
980                    what "follow playhead" setting is.
981                 */
982                 
983                 if (editor) {
984                         editor->reposition_x_origin (session->current_start_frame());
985                 }
986         }
987 }
988
989 void
990 ARDOUR_UI::transport_goto_zero ()
991 {
992         if (session) {
993                 session->request_locate (0);
994
995                 
996                 /* force displayed area in editor to start no matter
997                    what "follow playhead" setting is.
998                 */
999                 
1000                 if (editor) {
1001                         editor->reposition_x_origin (0);
1002                 }
1003         }
1004 }
1005
1006 void
1007 ARDOUR_UI::transport_goto_end ()
1008 {
1009         if (session) {
1010                 jack_nframes_t frame = session->current_end_frame();
1011                 session->request_locate (frame);
1012
1013                 /* force displayed area in editor to start no matter
1014                    what "follow playhead" setting is.
1015                 */
1016                 
1017                 if (editor) {
1018                         editor->reposition_x_origin (frame);
1019                 }
1020         }
1021 }
1022
1023 void
1024 ARDOUR_UI::transport_stop ()
1025 {
1026         if (!session) {
1027                 return;
1028         }
1029
1030         if (session->is_auditioning()) {
1031                 session->cancel_audition ();
1032                 return;
1033         }
1034         
1035         if (session->get_auto_loop()) {
1036                 session->request_auto_loop (false);
1037         }
1038         
1039         session->request_stop ();
1040 }
1041
1042 void
1043 ARDOUR_UI::transport_stop_and_forget_capture ()
1044 {
1045         if (session) {
1046                 session->request_stop (true);
1047         }
1048 }
1049
1050 void
1051 ARDOUR_UI::remove_last_capture()
1052 {
1053         if (editor) {
1054                 editor->remove_last_capture();
1055         }
1056 }
1057
1058 void
1059 ARDOUR_UI::transport_record ()
1060 {
1061         if (session) {
1062                 switch (session->record_status()) {
1063                 case Session::Disabled:
1064                         if (session->ntracks() == 0) {
1065                                 string txt = _("Please create 1 or more track\nbefore trying to record.\nCheck the Session menu.");
1066                                 MessageDialog msg (*editor, txt);
1067                                 msg.run ();
1068                                 return;
1069                         }
1070                         session->maybe_enable_record ();
1071                         break;
1072                 case Session::Recording:
1073                 case Session::Enabled:
1074                         session->disable_record (true);
1075                 }
1076         }
1077 }
1078
1079 void
1080 ARDOUR_UI::transport_roll ()
1081 {
1082         bool rolling;
1083
1084         if (!session) {
1085                 return;
1086         }
1087
1088         rolling = session->transport_rolling ();
1089
1090         if (session->get_auto_loop()) {
1091                 session->request_auto_loop (false);
1092                 auto_loop_button.set_active (false);
1093                 roll_button.set_active (true);
1094         } else if (session->get_play_range ()) {
1095                 session->request_play_range (false);
1096                 play_selection_button.set_active (false);
1097         } else if (rolling) {
1098                 session->request_locate (session->last_transport_start(), true);
1099         }
1100
1101         session->request_transport_speed (1.0f);
1102 }
1103
1104 void
1105 ARDOUR_UI::transport_loop()
1106 {
1107         if (session) {
1108                 if (session->get_auto_loop()) {
1109                         if (session->transport_rolling()) {
1110                                 Location * looploc = session->locations()->auto_loop_location();
1111                                 if (looploc) {
1112                                         session->request_locate (looploc->start(), true);
1113                                 }
1114                         }
1115                 }
1116                 else {
1117                         session->request_auto_loop (true);
1118                 }
1119         }
1120 }
1121
1122 void
1123 ARDOUR_UI::transport_play_selection ()
1124 {
1125         if (!session) {
1126                 return;
1127         }
1128
1129         if (!session->get_play_range()) {
1130                 session->request_stop ();
1131         }
1132
1133         editor->play_selection ();
1134 }
1135
1136 void
1137 ARDOUR_UI::transport_rewind (int option)
1138 {
1139         float current_transport_speed;
1140  
1141         if (session) {
1142                 current_transport_speed = session->transport_speed();
1143                 
1144                 if (current_transport_speed >= 0.0f) {
1145                         switch (option) {
1146                         case 0:
1147                                 session->request_transport_speed (-1.0f);
1148                                 break;
1149                         case 1:
1150                                 session->request_transport_speed (-4.0f);
1151                                 break;
1152                         case -1:
1153                                 session->request_transport_speed (-0.5f);
1154                                 break;
1155                         }
1156                 } else {
1157                         /* speed up */
1158                         session->request_transport_speed (current_transport_speed * 1.5f);
1159                 }
1160         }
1161 }
1162
1163 void
1164 ARDOUR_UI::transport_forward (int option)
1165 {
1166         float current_transport_speed;
1167         
1168         if (session) {
1169                 current_transport_speed = session->transport_speed();
1170                 
1171                 if (current_transport_speed <= 0.0f) {
1172                         switch (option) {
1173                         case 0:
1174                                 session->request_transport_speed (1.0f);
1175                                 break;
1176                         case 1:
1177                                 session->request_transport_speed (4.0f);
1178                                 break;
1179                         case -1:
1180                                 session->request_transport_speed (0.5f);
1181                                 break;
1182                         }
1183                 } else {
1184                         /* speed up */
1185                         session->request_transport_speed (current_transport_speed * 1.5f);
1186                 }
1187         }
1188 }
1189
1190 void
1191 ARDOUR_UI::toggle_record_enable (uint32_t dstream)
1192 {
1193         if (session == 0) {
1194                 return;
1195         }
1196
1197         boost::shared_ptr<Route> r;
1198         
1199         if ((r = session->route_by_remote_id (dstream)) != 0) {
1200
1201                 Track* t;
1202
1203                 if ((t = dynamic_cast<Track*>(r.get())) != 0) {
1204                         t->diskstream().set_record_enabled (!t->diskstream().record_enabled(), this);
1205                 }
1206         }
1207         if (session == 0) {
1208                 return;
1209         }
1210 }
1211
1212 void
1213 ARDOUR_UI::queue_transport_change ()
1214 {
1215         Gtkmm2ext::UI::instance()->call_slot (mem_fun(*this, &ARDOUR_UI::map_transport_state));
1216 }
1217
1218 void
1219 ARDOUR_UI::map_transport_state ()
1220 {
1221         float sp = session->transport_speed();
1222
1223         if (sp == 1.0f) {
1224                 transport_rolling ();
1225         } else if (sp < 0.0f) {
1226                 transport_rewinding ();
1227         } else if (sp > 0.0f) {
1228                 transport_forwarding ();
1229         } else {
1230                 transport_stopped ();
1231         }
1232 }
1233
1234 void
1235 ARDOUR_UI::allow_local_only ()
1236 {
1237
1238 }
1239
1240 void
1241 ARDOUR_UI::allow_mmc_only ()
1242 {
1243
1244 }
1245
1246 void
1247 ARDOUR_UI::allow_mmc_and_local ()
1248 {
1249
1250 }
1251
1252 void
1253 ARDOUR_UI::GlobalClickBox::printer (char buf[32], Adjustment &adj, void *arg)
1254 {
1255         snprintf (buf, sizeof(buf), "%s", ((GlobalClickBox *) arg)->strings[
1256                 (int) adj.get_value()].c_str());
1257 }
1258
1259 void
1260 ARDOUR_UI::engine_stopped ()
1261 {
1262         ENSURE_GUI_THREAD (mem_fun(*this, &ARDOUR_UI::engine_stopped));
1263         ActionManager::set_sensitive (ActionManager::jack_sensitive_actions, false);
1264         ActionManager::set_sensitive (ActionManager::jack_opposite_sensitive_actions, true);
1265 }
1266
1267
1268 void
1269 ARDOUR_UI::engine_running ()
1270 {
1271         ENSURE_GUI_THREAD (mem_fun(*this, &ARDOUR_UI::engine_running));
1272         ActionManager::set_sensitive (ActionManager::jack_sensitive_actions, true);
1273         ActionManager::set_sensitive (ActionManager::jack_opposite_sensitive_actions, false);
1274 }
1275
1276 void
1277 ARDOUR_UI::engine_halted ()
1278 {
1279         ENSURE_GUI_THREAD (mem_fun(*this, &ARDOUR_UI::engine_halted));
1280
1281         ActionManager::set_sensitive (ActionManager::jack_sensitive_actions, false);
1282         ActionManager::set_sensitive (ActionManager::jack_opposite_sensitive_actions, true);
1283
1284         update_sample_rate (0);
1285
1286         MessageDialog msg (*editor, 
1287                            _("\
1288 JACK has either been shutdown or it\n\
1289 disconnected Ardour because Ardour\n\
1290 was not fast enough. You can save the\n\
1291 session and/or try to reconnect to JACK ."));
1292         msg.run ();
1293 }
1294
1295 int32_t
1296 ARDOUR_UI::do_engine_start ()
1297 {
1298         try { 
1299                 engine->start();
1300         }
1301
1302         catch (AudioEngine::PortRegistrationFailure& err) {
1303                 engine->stop ();
1304                 error << _("Unable to create all required ports")
1305                       << endmsg;
1306                 unload_session ();
1307                 return -1;
1308         }
1309
1310         catch (...) {
1311                 engine->stop ();
1312                 error << _("Unable to start the session running")
1313                       << endmsg;
1314                 unload_session ();
1315                 return -2;
1316         }
1317         
1318         return 0;
1319 }
1320
1321 gint
1322 ARDOUR_UI::start_engine ()
1323 {
1324         if (do_engine_start () == 0) {
1325                 if (session && _session_is_new) {
1326                         /* we need to retain initial visual 
1327                            settings for a new session 
1328                         */
1329                         session->save_state ("");
1330                 }
1331
1332                 /* there is too much going on, in too many threads, for us to 
1333                    end up with a clean session. So wait 1 second after loading,
1334                    and fix it up. its ugly, but until i come across a better
1335                    solution, its what we have.
1336                 */
1337
1338                 Glib::signal_timeout().connect (mem_fun(*this, &ARDOUR_UI::make_session_clean), 1000);
1339         }
1340
1341         return FALSE;
1342 }
1343
1344 void
1345 ARDOUR_UI::update_clocks ()
1346 {
1347          Clock (session->audible_frame()); /* EMIT_SIGNAL */
1348 }
1349
1350 void
1351 ARDOUR_UI::start_clocking ()
1352 {
1353         clock_signal_connection = RapidScreenUpdate.connect (mem_fun(*this, &ARDOUR_UI::update_clocks));
1354 }
1355
1356 void
1357 ARDOUR_UI::stop_clocking ()
1358 {
1359         clock_signal_connection.disconnect ();
1360 }
1361         
1362 void
1363 ARDOUR_UI::toggle_clocking ()
1364 {
1365 #if 0
1366         if (clock_button.get_active()) {
1367                 start_clocking ();
1368         } else {
1369                 stop_clocking ();
1370         }
1371 #endif
1372 }
1373
1374 gint
1375 ARDOUR_UI::_blink (void *arg)
1376
1377 {
1378         ((ARDOUR_UI *) arg)->blink ();
1379         return TRUE;
1380 }
1381
1382 void
1383 ARDOUR_UI::blink ()
1384 {
1385          Blink (blink_on = !blink_on); /* EMIT_SIGNAL */
1386 }
1387
1388 void
1389 ARDOUR_UI::start_blinking ()
1390 {
1391         /* Start the blink signal. Everybody with a blinking widget
1392            uses Blink to drive the widget's state.
1393         */
1394
1395         if (blink_timeout_tag < 0) {
1396                 blink_on = false;       
1397                 blink_timeout_tag = gtk_timeout_add (240, _blink, this);
1398         }
1399 }
1400
1401 void
1402 ARDOUR_UI::stop_blinking ()
1403 {
1404         if (blink_timeout_tag >= 0) {
1405                 gtk_timeout_remove (blink_timeout_tag);
1406                 blink_timeout_tag = -1;
1407         }
1408 }
1409
1410 void
1411 ARDOUR_UI::name_io_setup (AudioEngine& engine, 
1412                           string& buf,
1413                           IO& io,
1414                           bool in)
1415 {
1416         if (in) {
1417                 if (io.n_inputs() == 0) {
1418                         buf = _("none");
1419                         return;
1420                 }
1421                 
1422                 /* XXX we're not handling multiple ports yet. */
1423
1424                 const char **connections = io.input(0)->get_connections();
1425                 
1426                 if (connections == 0 || connections[0] == '\0') {
1427                         buf = _("off");
1428                 } else {
1429                         buf = connections[0];
1430                 }
1431
1432                 free (connections);
1433
1434         } else {
1435
1436                 if (io.n_outputs() == 0) {
1437                         buf = _("none");
1438                         return;
1439                 }
1440                 
1441                 /* XXX we're not handling multiple ports yet. */
1442
1443                 const char **connections = io.output(0)->get_connections();
1444                 
1445                 if (connections == 0 || connections[0] == '\0') {
1446                         buf = _("off");
1447                 } else {
1448                         buf = connections[0];
1449                 }
1450
1451                 free (connections);
1452         }
1453 }
1454
1455 void
1456 ARDOUR_UI::snapshot_session ()
1457 {
1458         ArdourPrompter prompter (true);
1459         string snapname;
1460         string now;
1461         time_t n;
1462
1463         time (&n);
1464         now = ctime (&n);
1465         now = now.substr (20, 4) + now.substr (3, 16) + " (" + now.substr (0, 3) + ")";
1466
1467         prompter.set_name ("Prompter");
1468         prompter.add_button (Gtk::Stock::SAVE, Gtk::RESPONSE_ACCEPT);
1469         prompter.set_response_sensitive (Gtk::RESPONSE_ACCEPT, false);
1470         prompter.set_prompt (_("Name of New Snapshot"));
1471         prompter.set_initial_text (now);
1472         
1473         switch (prompter.run()) {
1474         case RESPONSE_ACCEPT:
1475                 prompter.get_result (snapname);
1476                 if (snapname.length()){
1477                         save_state (snapname);
1478                 }
1479                 break;
1480
1481         default:
1482                 break;
1483         }
1484 }
1485
1486 void
1487 ARDOUR_UI::save_state (const string & name)
1488 {
1489         (void) save_state_canfail (name);
1490 }
1491                 
1492 int
1493 ARDOUR_UI::save_state_canfail (string name)
1494 {
1495         if (session) {
1496                 int ret;
1497
1498                 if (name.length() == 0) {
1499                         name = session->snap_name();
1500                 }
1501
1502                 if ((ret = session->save_state (name)) != 0) {
1503                         return ret;
1504                 }
1505         }
1506         save_ardour_state (); /* XXX cannot fail? yeah, right ... */
1507         return 0;
1508 }
1509
1510 void
1511 ARDOUR_UI::restore_state (string name)
1512 {
1513         if (session) {
1514                 if (name.length() == 0) {
1515                         name = session->name();
1516                 }
1517                 session->restore_state (name);
1518         }
1519 }
1520
1521 void
1522 ARDOUR_UI::primary_clock_value_changed ()
1523 {
1524         if (session) {
1525                 session->request_locate (primary_clock.current_time ());
1526         }
1527 }
1528
1529 void
1530 ARDOUR_UI::secondary_clock_value_changed ()
1531 {
1532         if (session) {
1533                 session->request_locate (secondary_clock.current_time ());
1534         }
1535 }
1536
1537 void
1538 ARDOUR_UI::rec_enable_button_blink (bool onoff, AudioDiskstream *dstream, Widget *w)
1539 {
1540         if (session && dstream && dstream->record_enabled()) {
1541
1542                 Session::RecordState rs;
1543                 
1544                 rs = session->record_status ();
1545
1546                 switch (rs) {
1547                 case Session::Disabled:
1548                 case Session::Enabled:
1549                         if (w->get_state() != STATE_SELECTED) {
1550                                 w->set_state (STATE_SELECTED);
1551                         }
1552                         break;
1553
1554                 case Session::Recording:
1555                         if (w->get_state() != STATE_ACTIVE) {
1556                                 w->set_state (STATE_ACTIVE);
1557                         }
1558                         break;
1559                 }
1560
1561         } else {
1562                 if (w->get_state() != STATE_NORMAL) {
1563                         w->set_state (STATE_NORMAL);
1564                 }
1565         }
1566 }
1567
1568 void
1569 ARDOUR_UI::transport_rec_enable_blink (bool onoff) 
1570 {
1571         if (session == 0) {
1572                 return;
1573         }
1574         
1575         switch (session->record_status()) {
1576         case Session::Enabled:
1577                 if (onoff) {
1578                         rec_button.set_state (1);
1579                 } else {
1580                         rec_button.set_state (0);
1581                 }
1582                 break;
1583
1584         case Session::Recording:
1585                 rec_button.set_state (2);
1586                 break;
1587
1588         default:
1589                 rec_button.set_state (0);
1590                 break;
1591         }
1592 }
1593
1594 gint
1595 ARDOUR_UI::hide_and_quit (GdkEventAny *ev, ArdourDialog *window)
1596 {
1597         window->hide();
1598         Gtk::Main::quit ();
1599         return TRUE;
1600 }
1601
1602 void
1603 ARDOUR_UI::start_keyboard_prefix ()
1604 {
1605         keyboard->start_prefix();
1606 }
1607
1608 void
1609 ARDOUR_UI::save_template ()
1610
1611 {
1612         ArdourPrompter prompter (true);
1613         string name;
1614
1615         prompter.set_name (X_("Prompter"));
1616         prompter.set_prompt (_("Name for mix template:"));
1617         prompter.set_initial_text(session->name() + _("-template"));
1618         prompter.add_button (Gtk::Stock::SAVE, Gtk::RESPONSE_ACCEPT);
1619         prompter.set_response_sensitive (Gtk::RESPONSE_ACCEPT, false);
1620
1621         switch (prompter.run()) {
1622         case RESPONSE_ACCEPT:
1623                 prompter.get_result (name);
1624                 
1625                 if (name.length()) {
1626                         session->save_template (name);
1627                 }
1628                 break;
1629
1630         default:
1631                 break;
1632         }
1633 }
1634
1635 void
1636 ARDOUR_UI::new_session (bool startup, std::string predetermined_path)
1637 {
1638         m_new_session_dialog->show();
1639         m_new_session_dialog->set_modal(true);
1640         m_new_session_dialog->set_name(predetermined_path);
1641         m_new_session_dialog->reset_recent();
1642
1643         int response = Gtk::RESPONSE_CANCEL;
1644
1645         do {
1646                 response = m_new_session_dialog->run ();
1647                 if(response == Gtk::RESPONSE_CANCEL || response == Gtk::RESPONSE_DELETE_EVENT) {
1648                   quit();
1649                   return;
1650
1651                 } else if (response == Gtk::RESPONSE_NONE) {
1652                   /* Clear was pressed */
1653                   m_new_session_dialog->reset();
1654
1655                 } else if (response == Gtk::RESPONSE_YES) {
1656                   /* YES  == OPEN, but there's no enum for that */
1657                   std::string session_name = m_new_session_dialog->session_name();
1658                   std::string session_path = m_new_session_dialog->session_folder();
1659                   load_session (session_path, session_name);
1660
1661
1662                 } else if (response == Gtk::RESPONSE_OK) {
1663                   if (m_new_session_dialog->get_current_page() == 1) {
1664
1665                     /* XXX this is a bit of a hack.. 
1666                        i really want the new sesion dialog to return RESPONSE_YES
1667                        if we're on page 1 (the load page)
1668                        Unfortunately i can't see how atm.. 
1669                     */
1670                         std::string session_name = m_new_session_dialog->session_name();
1671                         std::string session_path = m_new_session_dialog->session_folder();
1672                         load_session (session_path, session_name);
1673
1674                   } else {
1675
1676                         _session_is_new = true;
1677                         
1678                         std::string session_name = m_new_session_dialog->session_name();
1679                         std::string session_path = m_new_session_dialog->session_folder();
1680                         
1681
1682                           //XXX This is needed because session constructor wants a 
1683                           //non-existant path. hopefully this will be fixed at some point.
1684                         
1685                         session_path = Glib::build_filename(session_path, session_name);
1686                         
1687                         std::string template_name = m_new_session_dialog->session_template_name();
1688                         
1689                         if (m_new_session_dialog->use_session_template()) {
1690                                 
1691                                 load_session (session_path, session_name, &template_name);
1692                                 
1693                         } else {
1694                                 
1695                                 uint32_t cchns;
1696                                 uint32_t mchns;
1697                                 Session::AutoConnectOption iconnect;
1698                                 Session::AutoConnectOption oconnect;
1699                                 
1700                                 if (m_new_session_dialog->create_control_bus()) {
1701                                         cchns = (uint32_t) m_new_session_dialog->control_channel_count();
1702                                 } else {
1703                                         cchns = 0;
1704                                 }
1705                                 
1706                                 if (m_new_session_dialog->create_master_bus()) {
1707                                         mchns = (uint32_t) m_new_session_dialog->master_channel_count();
1708                                 } else {
1709                                         mchns = 0;
1710                                 }
1711                                 
1712                                 if (m_new_session_dialog->connect_inputs()) {
1713                                         iconnect = Session::AutoConnectPhysical;
1714                                 } else {
1715                                         iconnect = Session::AutoConnectOption (0);
1716                                 }
1717                                 
1718                                 /// @todo some minor tweaks.
1719
1720                                 if (m_new_session_dialog->connect_outs_to_master()) {
1721                                         oconnect = Session::AutoConnectMaster;
1722                                 } else if (m_new_session_dialog->connect_outs_to_physical()) {
1723                                         oconnect = Session::AutoConnectPhysical;
1724                                 } else {
1725                                         oconnect = Session::AutoConnectOption (0);
1726                                 } 
1727                                 
1728                                 uint32_t nphysin = (uint32_t) m_new_session_dialog->input_limit_count();
1729                                 uint32_t nphysout = (uint32_t) m_new_session_dialog->output_limit_count();
1730                                 
1731                                 build_session (session_path,
1732                                                session_name,
1733                                                cchns,
1734                                                mchns,
1735                                                iconnect,
1736                                                oconnect,
1737                                                nphysin,
1738                                                nphysout, 
1739                                                engine->frame_rate() * 60 * 5);
1740                         }
1741                   }     
1742                 }
1743                 
1744         } while (response == Gtk::RESPONSE_NONE);
1745         m_new_session_dialog->hide();
1746         show();
1747
1748 }
1749
1750 void
1751 ARDOUR_UI::close_session()
1752 {
1753   unload_session();
1754   new_session ();
1755 }
1756
1757 int
1758 ARDOUR_UI::load_session (const string & path, const string & snap_name, string* mix_template)
1759 {
1760         Session *new_session;
1761         int x;
1762         session_loaded = false;
1763         x = unload_session ();
1764
1765         if (x < 0) {
1766                 return -1;
1767         } else if (x > 0) {
1768                 return 0;
1769         }
1770
1771         /* if it already exists, we must have write access */
1772
1773         if (::access (path.c_str(), F_OK) == 0 && ::access (path.c_str(), W_OK)) {
1774                 MessageDialog msg (*editor, _("\
1775 You do not have write access to this session.\n\
1776 This prevents the session from being loaded."));
1777                 msg.run ();
1778                 return -1;
1779         }
1780
1781         try {
1782                 new_session = new Session (*engine, path, snap_name, mix_template);
1783         }
1784
1785         catch (...) {
1786
1787                 error << string_compose(_("Session \"%1 (snapshot %2)\" did not load successfully"), path, snap_name) << endmsg;
1788                 return -1;
1789         }
1790
1791         connect_to_session (new_session);
1792
1793         //if (engine->running()) {
1794         //mixer->show_window();
1795         //}
1796         session_loaded = true;
1797         return 0;
1798 }
1799
1800 int
1801 ARDOUR_UI::make_session_clean ()
1802 {
1803         if (session) {
1804                 session->set_clean ();
1805         }
1806
1807         show ();
1808
1809         return FALSE;
1810 }
1811
1812 int
1813 ARDOUR_UI::build_session (const string & path, const string & snap_name, 
1814                           uint32_t control_channels,
1815                           uint32_t master_channels, 
1816                           Session::AutoConnectOption input_connect,
1817                           Session::AutoConnectOption output_connect,
1818                           uint32_t nphysin,
1819                           uint32_t nphysout,
1820                           jack_nframes_t initial_length)
1821 {
1822         Session *new_session;
1823         int x;
1824
1825         session_loaded = false;
1826         x = unload_session ();
1827         if (x < 0) {
1828                 return -1;
1829         } else if (x > 0) {
1830                 return 0;
1831         }
1832         
1833         _session_is_new = true;
1834
1835         try {
1836                 new_session = new Session (*engine, path, snap_name, input_connect, output_connect,
1837                                            control_channels, master_channels, nphysin, nphysout, initial_length);
1838         }
1839
1840         catch (...) {
1841
1842                 error << string_compose(_("Session \"%1 (snapshot %2)\" did not load successfully"), path, snap_name) << endmsg;
1843                 return -1;
1844         }
1845
1846         connect_to_session (new_session);
1847
1848         //if (engine->running()) {
1849         //mixer->show_window();
1850         //}
1851         session_loaded = true;
1852         return 0;
1853 }
1854
1855 void
1856 ARDOUR_UI::show ()
1857 {
1858         if (editor) {
1859                 editor->show_window ();
1860                 shown_flag = true;
1861         }
1862
1863         if (session && mixer) {
1864                 // mixer->show_window ();
1865         }
1866         
1867         if (about) {
1868                 about->present ();
1869         }
1870 }
1871
1872 void
1873 ARDOUR_UI::show_splash ()
1874 {
1875         if (about == 0) {
1876                 about = new About();
1877         }
1878         about->present();
1879 }
1880
1881 void
1882 ARDOUR_UI::hide_splash ()
1883 {
1884         if (about) {
1885                 // about->hide();
1886         }
1887 }
1888
1889 void
1890 ARDOUR_UI::display_cleanup_results (Session::cleanup_report& rep, const gchar* list_title, const string & msg)
1891 {
1892         size_t removed;
1893
1894         removed = rep.paths.size();
1895
1896         if (removed == 0) {
1897                 MessageDialog msgd (*editor,
1898                                     _("No audio files were ready for cleanup"), 
1899                                     true,
1900                                     Gtk::MESSAGE_INFO,
1901                                     (Gtk::ButtonsType)(Gtk::BUTTONS_CLOSE)  );
1902                 msgd.set_secondary_text (_("If this seems suprising, \n\
1903 check for any existing snapshots.\n\
1904 These may still include regions that\n\
1905 require some unused files to continue to exist."));
1906         
1907                 msgd.run ();
1908                 return;
1909         } 
1910
1911         ArdourDialog results (_("ardour: cleanup"), true, false);
1912         
1913         struct CleanupResultsModelColumns : public Gtk::TreeModel::ColumnRecord {
1914             CleanupResultsModelColumns() { 
1915                     add (visible_name);
1916                     add (fullpath);
1917             }
1918             Gtk::TreeModelColumn<Glib::ustring> visible_name;
1919             Gtk::TreeModelColumn<Glib::ustring> fullpath;
1920         };
1921
1922         
1923         CleanupResultsModelColumns results_columns;
1924         Glib::RefPtr<Gtk::ListStore> results_model;
1925         Gtk::TreeView results_display;
1926         
1927         results_model = ListStore::create (results_columns);
1928         results_display.set_model (results_model);
1929         results_display.append_column (list_title, results_columns.visible_name);
1930
1931         results_display.set_name ("CleanupResultsList");
1932         results_display.set_headers_visible (true);
1933         results_display.set_headers_clickable (false);
1934         results_display.set_reorderable (false);
1935
1936         Gtk::ScrolledWindow list_scroller;
1937         Gtk::Label txt;
1938         Gtk::VBox dvbox;
1939         Gtk::HBox dhbox;  // the hbox for the image and text
1940         Gtk::HBox ddhbox; // the hbox we eventually pack into the dialog's vbox
1941         Gtk::Image* dimage = manage (new Gtk::Image(Stock::DIALOG_INFO,  Gtk::ICON_SIZE_DIALOG));
1942
1943         dimage->set_alignment(ALIGN_LEFT, ALIGN_TOP);
1944
1945         if (rep.space < 1048576.0f) {
1946                 if (removed > 1) {
1947                   txt.set_text (string_compose (msg, removed, _("files were"), session->path() + "dead_sounds", (float) rep.space / 1024.0f, "kilo"));
1948                 } else {
1949                         txt.set_text (string_compose (msg, removed, _("file was"), session->path() + "dead_sounds", (float) rep.space / 1024.0f, "kilo"));
1950                 }
1951         } else {
1952                 if (removed > 1) {
1953                         txt.set_text (string_compose (msg, removed, _("files were"), session->path() + "dead_sounds", (float) rep.space / 1048576.0f, "mega"));
1954                 } else {
1955                         txt.set_text (string_compose (msg, removed, _("file was"), session->path() + "dead_sounds", (float) rep.space / 1048576.0f, "mega"));
1956                 }
1957         }
1958
1959         dhbox.pack_start (*dimage, true, false, 5);
1960         dhbox.pack_start (txt, true, false, 5);
1961
1962         for (vector<string>::iterator i = rep.paths.begin(); i != rep.paths.end(); ++i) {
1963                 TreeModel::Row row = *(results_model->append());
1964                 row[results_columns.visible_name] = *i;
1965                 row[results_columns.fullpath] = *i;
1966         }
1967         
1968         list_scroller.add (results_display);
1969         list_scroller.set_size_request (-1, 150);
1970         list_scroller.set_policy (Gtk::POLICY_NEVER, Gtk::POLICY_AUTOMATIC);
1971
1972         dvbox.pack_start (dhbox, true, false, 5);
1973         dvbox.pack_start (list_scroller, true, false, 5);
1974         ddhbox.pack_start (dvbox, true, false, 5);
1975
1976         results.get_vbox()->pack_start (ddhbox, true, false, 5);
1977         results.add_button (Stock::CLOSE, RESPONSE_CLOSE);
1978         results.set_default_response (RESPONSE_CLOSE);
1979         results.set_position (Gtk::WIN_POS_MOUSE);
1980         results.show_all_children ();
1981         results.set_resizable (false);
1982
1983         results.run ();
1984
1985 }
1986
1987 void
1988 ARDOUR_UI::cleanup ()
1989 {
1990         if (session == 0) {
1991                 /* shouldn't happen: menu item is insensitive */
1992                 return;
1993         }
1994
1995
1996         MessageDialog  checker (_("Are you sure you want to cleanup?"),
1997                                 true,
1998                                 Gtk::MESSAGE_QUESTION,
1999                                 (Gtk::ButtonsType)(Gtk::BUTTONS_NONE));
2000
2001         checker.set_secondary_text(_("Cleanup is a destructive operation.\n\
2002 ALL undo/redo information will be lost if you cleanup.\n\
2003 After cleanup, unused audio files will be moved to a \
2004 \"dead sounds\" location."));
2005         
2006         checker.add_button (Stock::CANCEL, RESPONSE_CANCEL);
2007         checker.add_button (_("Clean Up"), RESPONSE_ACCEPT);
2008         checker.set_default_response (RESPONSE_CANCEL);
2009
2010         checker.set_name (_("CleanupDialog"));
2011         checker.set_wmclass (_("ardour_cleanup"), "Ardour");
2012         checker.set_position (Gtk::WIN_POS_MOUSE);
2013
2014         switch (checker.run()) {
2015         case RESPONSE_ACCEPT:
2016                 break;
2017         default:
2018                 return;
2019         }
2020
2021         Session::cleanup_report rep;
2022
2023         editor->prepare_for_cleanup ();
2024
2025         if (session->cleanup_sources (rep)) {
2026                 return;
2027         }
2028         checker.hide();
2029         display_cleanup_results (rep, 
2030                                  _("cleaned files"),
2031                                  _("\
2032 The following %1 %2 not in use and \n\
2033 have been moved to:\n\
2034 %3. \n\n\
2035 Flushing the wastebasket will \n\
2036 release an additional\n\
2037 %4 %5bytes of disk space.\n"
2038                                          ));
2039 }
2040
2041 void
2042 ARDOUR_UI::flush_trash ()
2043 {
2044         if (session == 0) {
2045                 /* shouldn't happen: menu item is insensitive */
2046                 return;
2047         }
2048
2049         Session::cleanup_report rep;
2050
2051         if (session->cleanup_trash_sources (rep)) {
2052                 return;
2053         }
2054
2055         display_cleanup_results (rep, 
2056                                  _("deleted file"),
2057                                  _("The following %1 %2 deleted from\n\
2058 %3,\n\
2059 releasing %4 %5bytes of disk space"));
2060 }
2061
2062 void
2063 ARDOUR_UI::add_route ()
2064 {
2065         int count;
2066
2067         if (!session) {
2068                 return;
2069         }
2070
2071         if (add_route_dialog == 0) {
2072                 add_route_dialog = new AddRouteDialog;
2073                 editor->ensure_float (*add_route_dialog);
2074         }
2075
2076         if (add_route_dialog->is_visible()) {
2077                 /* we're already doing this */
2078                 return;
2079         }
2080
2081         ResponseType r = (ResponseType) add_route_dialog->run ();
2082         
2083         add_route_dialog->hide();
2084
2085         switch (r) {
2086         case RESPONSE_ACCEPT:
2087                 break;
2088         default:
2089                 return;
2090                 break;
2091         }
2092
2093         if ((count = add_route_dialog->count()) <= 0) {
2094                 return;
2095         }
2096
2097         uint32_t input_chan = add_route_dialog->channels ();
2098         uint32_t output_chan;
2099         string name_template = add_route_dialog->name_template ();
2100         bool track = add_route_dialog->track ();
2101
2102         Session::AutoConnectOption oac = session->get_output_auto_connect();
2103
2104         if (oac & Session::AutoConnectMaster) {
2105                 output_chan = (session->master_out() ? session->master_out()->n_inputs() : input_chan);
2106         } else {
2107                 output_chan = input_chan;
2108         }
2109
2110         /* XXX do something with name template */
2111
2112         while (count) {
2113                 if (track && add_route_dialog->midi()) {
2114                         session_add_midi_track();
2115                 } else if (add_route_dialog->midi()) {
2116                         session_add_midi_bus();
2117                 } else if (track) {
2118                         session_add_audio_track (input_chan, output_chan, add_route_dialog->mode());
2119                 } else {
2120                         session_add_audio_bus (input_chan, output_chan);
2121                 }
2122                 --count;
2123                 
2124                 while (Main::events_pending()) {
2125                         Main::iteration ();
2126                 }
2127         }
2128 }
2129
2130 XMLNode*
2131 ARDOUR_UI::mixer_settings () const
2132 {
2133         XMLNode* node = 0;
2134
2135         if (session) {
2136                 node = session->instant_xml(X_("Mixer"), session->path());
2137         } else {
2138                 node = Config->instant_xml(X_("Mixer"), get_user_ardour_path());
2139         }
2140
2141         if (!node) {
2142                 node = new XMLNode (X_("Mixer"));
2143         }
2144
2145         return node;
2146 }
2147
2148 XMLNode*
2149 ARDOUR_UI::editor_settings () const
2150 {
2151         XMLNode* node = 0;
2152
2153         if (session) {
2154                 node = session->instant_xml(X_("Editor"), session->path());
2155         } else {
2156                 node = Config->instant_xml(X_("Editor"), get_user_ardour_path());
2157         }
2158
2159         if (!node) {
2160                 node = new XMLNode (X_("Editor"));
2161         }
2162         return node;
2163 }
2164
2165 XMLNode*
2166 ARDOUR_UI::keyboard_settings () const
2167 {
2168         XMLNode* node = 0;
2169
2170         node = Config->extra_xml(X_("Keyboard"));
2171         
2172         if (!node) {
2173                 node = new XMLNode (X_("Keyboard"));
2174         }
2175         return node;
2176 }
2177
2178 void
2179 ARDOUR_UI::halt_on_xrun_message ()
2180 {
2181         ENSURE_GUI_THREAD (mem_fun(*this, &ARDOUR_UI::halt_on_xrun_message));
2182
2183         MessageDialog msg (*editor,
2184                            _("Recording was stopped because your system could not keep up."));
2185         msg.run ();
2186 }
2187
2188 void 
2189 ARDOUR_UI::delete_sources_in_the_right_thread (list<ARDOUR::AudioFileSource*>* deletion_list)
2190 {
2191         ENSURE_GUI_THREAD (bind (mem_fun(*this, &ARDOUR_UI::delete_sources_in_the_right_thread), deletion_list));
2192
2193         for (list<AudioFileSource*>::iterator i = deletion_list->begin(); i != deletion_list->end(); ++i) {
2194                 delete *i;
2195         }
2196
2197         delete deletion_list;
2198 }
2199
2200 void
2201 ARDOUR_UI::disk_overrun_handler ()
2202 {
2203         ENSURE_GUI_THREAD (mem_fun(*this, &ARDOUR_UI::disk_underrun_handler));
2204
2205         if (!have_disk_overrun_displayed) {
2206                 have_disk_overrun_displayed = true;
2207                 MessageDialog msg (*editor, X_("diskrate dialog"), _("\
2208 The disk system on your computer\n\
2209 was not able to keep up with Ardour.\n\
2210 \n\
2211 Specifically, it failed to write data to disk\n\
2212 quickly enough to keep up with recording.\n"));
2213                 msg.run ();
2214                 have_disk_overrun_displayed = false;
2215         }
2216 }
2217
2218 void
2219 ARDOUR_UI::disk_underrun_handler ()
2220 {
2221         ENSURE_GUI_THREAD (mem_fun(*this, &ARDOUR_UI::disk_underrun_handler));
2222
2223         if (!have_disk_underrun_displayed) {
2224                 have_disk_underrun_displayed = true;
2225                 MessageDialog msg (*editor,
2226                         (_("The disk system on your computer\n\
2227 was not able to keep up with Ardour.\n\
2228 \n\
2229 Specifically, it failed to read data from disk\n\
2230 quickly enough to keep up with playback.\n")));
2231                 msg.run ();
2232                 have_disk_underrun_displayed = false;
2233         } 
2234 }
2235
2236 void
2237 ARDOUR_UI::disk_underrun_message_gone ()
2238 {
2239         have_disk_underrun_displayed = false;
2240 }
2241
2242 void
2243 ARDOUR_UI::disk_overrun_message_gone ()
2244 {
2245         have_disk_underrun_displayed = false;
2246 }
2247
2248 int
2249 ARDOUR_UI::pending_state_dialog ()
2250 {
2251         ArdourDialog dialog ("pending state dialog");
2252         Label  message (_("\
2253 This session appears to have been in\n\
2254 middle of recording when ardour or\n\
2255 the computer was shutdown.\n\
2256 \n\
2257 Ardour can recover any captured audio for\n\
2258 you, or it can ignore it. Please decide\n\
2259 what you would like to do.\n"));
2260
2261         dialog.get_vbox()->pack_start (message);
2262         dialog.add_button (_("Recover from crash"), RESPONSE_ACCEPT);
2263         dialog.add_button (_("Ignore crash data"), RESPONSE_REJECT);
2264
2265         dialog.set_position (WIN_POS_CENTER);
2266         dialog.show_all ();
2267         
2268         switch (dialog.run ()) {
2269         case RESPONSE_ACCEPT:
2270                 return 1;
2271         default:
2272                 return 0;
2273         }
2274 }
2275         
2276 void
2277 ARDOUR_UI::disconnect_from_jack ()
2278 {
2279         if (engine) {
2280                 if( engine->disconnect_from_jack ()) {
2281                         MessageDialog msg (*editor, _("Could not disconnect from JACK"));
2282                         msg.run ();
2283                 }
2284
2285                 update_sample_rate (0);
2286         }
2287 }
2288
2289 void
2290 ARDOUR_UI::reconnect_to_jack ()
2291 {
2292         if (engine) {
2293                 if (engine->reconnect_to_jack ()) {
2294                         MessageDialog msg (*editor,  _("Could not reconnect to JACK"));
2295                         msg.run ();
2296                 }
2297
2298                 update_sample_rate (0);
2299         }
2300 }
2301
2302 void
2303 ARDOUR_UI::set_jack_buffer_size (jack_nframes_t nframes)
2304 {
2305         engine->request_buffer_size (nframes);
2306         update_sample_rate (0);
2307 }
2308
2309 int
2310 ARDOUR_UI::cmdline_new_session (string path)
2311 {
2312         if (path[0] != '/') {
2313                 char buf[PATH_MAX+1];
2314                 string str;
2315
2316                 getcwd (buf, sizeof (buf));
2317                 str = buf;
2318                 str += '/';
2319                 str += path;
2320                 path = str;
2321         }
2322
2323         new_session (false, path);
2324
2325         _will_create_new_session_automatically = false; /* done it */
2326         return FALSE; /* don't call it again */
2327 }
2328
2329 void
2330 ARDOUR_UI::set_native_file_header_format (HeaderFormat hf)
2331 {
2332         Glib::RefPtr<Action> act;
2333         
2334         switch (hf) {
2335         case BWF:
2336                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatBWF"));
2337                 break;
2338         case WAVE:
2339                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatWAVE"));
2340                 break;
2341         case WAVE64:
2342                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatWAVE64"));
2343                 break;
2344         case iXML:
2345                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatiXML"));
2346                 break;
2347         case RF64:
2348                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatRF64"));
2349                 break;
2350         case CAF:
2351                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatCAF"));
2352                 break;
2353         case AIFF:
2354                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatAIFF"));
2355                 break;
2356         }
2357
2358         if (act) {
2359                 Glib::RefPtr<RadioAction> ract = Glib::RefPtr<RadioAction>::cast_dynamic(act);
2360                 if (ract && ract->get_active() && Config->get_native_file_header_format() != hf) {
2361                         Config->set_native_file_header_format (hf);
2362                         if (session) {
2363                                 session->reset_native_file_format ();
2364                         }
2365                 }
2366         }
2367 }
2368
2369 void
2370 ARDOUR_UI::set_native_file_data_format (SampleFormat sf)
2371 {
2372         Glib::RefPtr<Action> act;
2373         
2374         switch (sf) {
2375         case FormatFloat:
2376                 act = ActionManager::get_action (X_("options"), X_("FileDataFormatFloat"));
2377                 break;
2378         case FormatInt24:
2379                 act = ActionManager::get_action (X_("options"), X_("FileDataFormat24bit"));
2380                 break;
2381         }
2382
2383         if (act) {
2384                 Glib::RefPtr<RadioAction> ract = Glib::RefPtr<RadioAction>::cast_dynamic(act);
2385
2386                 if (ract && ract->get_active() && Config->get_native_file_data_format() != sf) {
2387                         Config->set_native_file_data_format (sf);
2388                         if (session) {
2389                                 session->reset_native_file_format ();
2390                         }
2391                 }
2392         }
2393 }
2394
2395 void
2396 ARDOUR_UI::use_config ()
2397 {
2398         Glib::RefPtr<Action> act;
2399
2400         switch (Config->get_native_file_data_format ()) {
2401         case FormatFloat:
2402                 act = ActionManager::get_action (X_("options"), X_("FileDataFormatFloat"));
2403                 break;
2404         case FormatInt24:
2405                 act = ActionManager::get_action (X_("options"), X_("FileDataFormat24bit"));
2406                 break;
2407         }
2408
2409         if (act) {
2410                 Glib::RefPtr<RadioAction> ract = Glib::RefPtr<RadioAction>::cast_dynamic(act);
2411                 ract->set_active ();
2412         }       
2413
2414         switch (Config->get_native_file_header_format ()) {
2415         case BWF:
2416                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatBWF"));
2417                 break;
2418         case WAVE:
2419                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatWAVE"));
2420                 break;
2421         case WAVE64:
2422                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatWAVE64"));
2423                 break;
2424         case iXML:
2425                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatiXML"));
2426                 break;
2427         case RF64:
2428                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatRF64"));
2429                 break;
2430         case CAF:
2431                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatCAF"));
2432                 break;
2433         case AIFF:
2434                 act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatAIFF"));
2435                 break;
2436         }
2437
2438         if (act) {
2439                 Glib::RefPtr<RadioAction> ract = Glib::RefPtr<RadioAction>::cast_dynamic(act);
2440                 ract->set_active ();
2441         }       
2442 }