reset the visibility of the template selector stuff every time the startup/NSD gets...
[ardour.git] / gtk2_ardour / startup.cc
1 /*
2     Copyright (C) 2010 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 */
19
20 #ifdef WAF_BUILD
21 #include "gtk2ardour-config.h"
22 #endif
23
24 #include <fstream>
25 #include <algorithm>
26
27 #include <gtkmm/main.h>
28 #include <gtkmm/filechooser.h>
29
30 #include "pbd/failed_constructor.h"
31 #include "pbd/file_utils.h"
32 #include "pbd/replace_all.h"
33 #include "pbd/whitespace.h"
34 #include "pbd/stacktrace.h"
35 #include "pbd/openuri.h"
36
37 #include "ardour/audioengine.h"
38 #include "ardour/filesystem_paths.h"
39 #include "ardour/recent_sessions.h"
40 #include "ardour/session.h"
41 #include "ardour/session_state_utils.h"
42 #include "ardour/template_utils.h"
43 #include "ardour/filename_extensions.h"
44
45 #include "ardour_ui.h"
46 #include "startup.h"
47 #include "opts.h"
48 #include "engine_dialog.h"
49 #include "i18n.h"
50 #include "utils.h"
51
52 using namespace std;
53 using namespace Gtk;
54 using namespace Gdk;
55 using namespace Glib;
56 using namespace PBD;
57 using namespace ARDOUR;
58
59 ArdourStartup* ArdourStartup::the_startup = 0;
60
61 static string poor_mans_glob (string path)
62 {
63         string copy = path;
64         replace_all (copy, "~", Glib::get_home_dir());
65         return copy;
66 }
67
68 ArdourStartup::ArdourStartup (bool require_new, const std::string& session_name, const std::string& session_path, const std::string& template_name)
69         : _response (RESPONSE_OK)
70         , config_modified (false)
71         , new_only (require_new)
72         , default_dir_chooser (0)
73         , monitor_via_hardware_button (string_compose (_("Use an external mixer or the hardware mixer of your audio interface.\n"
74                                                          "%1 will play NO role in monitoring"), PROGRAM_NAME))
75         , monitor_via_ardour_button (string_compose (_("Ask %1 to play back material as it is being recorded"), PROGRAM_NAME))
76         , new_folder_chooser (FILE_CHOOSER_ACTION_SELECT_FOLDER)
77         , more_new_session_options_button (_("Advanced options ..."))
78         , _output_limit_count_adj (1, 0, 100, 1, 10, 0)
79         , _input_limit_count_adj (1, 0, 100, 1, 10, 0)
80         , _master_bus_channel_count_adj (2, 0, 100, 1, 10, 0)
81         , audio_page_index (-1)
82         , new_user_page_index (-1)
83         , default_folder_page_index (-1)
84         , monitoring_page_index (-1)
85         , new_session_page_index (-1)
86         , initial_choice_index (-1)
87         , final_page_index (-1)
88         , session_options_page_index (-1)
89         , _existing_session_chooser_used (false)
90 {
91         new_user = !Glib::file_test (been_here_before_path(), Glib::FILE_TEST_EXISTS);
92         need_session_info = (session_name.empty() || require_new);
93
94         _provided_session_name = session_name;
95         _provided_session_path = session_path;
96         
97         if (need_session_info || new_user) {
98
99                 use_template_button.set_group (session_template_group);
100                 use_session_as_template_button.set_group (session_template_group);
101                 
102                 set_keep_above (true);
103                 set_position (WIN_POS_CENTER);
104                 set_border_width (12);
105                 
106                 if ((icon_pixbuf = ::get_icon ("ardour_icon_48px")) == 0) {
107                         throw failed_constructor();
108                 }
109                 
110                 list<Glib::RefPtr<Gdk::Pixbuf> > window_icons;
111                 Glib::RefPtr<Gdk::Pixbuf> icon;
112                 
113                 if ((icon = ::get_icon ("ardour_icon_16px")) != 0) {
114                         window_icons.push_back (icon);
115                 }
116                 if ((icon = ::get_icon ("ardour_icon_22px")) != 0) {
117                         window_icons.push_back (icon);
118                 }
119                 if ((icon = ::get_icon ("ardour_icon_32px")) != 0) {
120                         window_icons.push_back (icon);
121                 }
122                 if ((icon = ::get_icon ("ardour_icon_48px")) != 0) {
123                         window_icons.push_back (icon);
124                 }
125                 if (!window_icons.empty ()) {
126                         set_default_icon_list (window_icons);
127                 }
128
129 #ifdef __APPLE__
130                 setup_prerelease_page ();
131 #endif
132                 if (new_user) {
133                         
134                         setup_new_user_page ();
135                         setup_first_time_config_page ();
136                         setup_monitoring_choice_page ();
137                         setup_monitor_section_choice_page ();
138                         setup_final_page ();
139                         setup_new_session_page ();
140
141                 } else {
142
143                         if (!new_only) {
144                                 setup_initial_choice_page ();
145                         }
146                         setup_new_session_page ();
147                 }
148
149                 if (!template_name.empty()) {
150                         use_template_button.set_active (false);
151                         load_template_override = template_name;
152                 }
153         }
154
155         the_startup = this;
156 }
157
158 ArdourStartup::~ArdourStartup ()
159 {
160 }
161
162 bool
163 ArdourStartup::ready_without_display () const
164 {
165         return !new_user && !need_session_info;
166 }
167
168 void
169 ArdourStartup::setup_prerelease_page ()
170 {
171         VBox* vbox = manage (new VBox);
172         Label* label = manage (new Label);
173         label->set_markup (string_compose (_("<b>Welcome to this BETA release of Ardour %1</b>\n\n\
174 Ardour %1 has been released for Linux but because of the lack of testers,\n\
175 it is still at the beta stage on OS X. So, a few guidelines:\n\
176 \n\
177 1) Please do <b>NOT</b> use this software with the expectation that it is stable or reliable\n\
178    though it may be so, depending on your workflow.\n\
179 2) <b>Please do NOT use the forums at ardour.org to report issues</b>.\n\
180 3) Please <b>DO</b> use the bugtracker at http://tracker.ardour.org/ to report issues\n\
181    making sure to note the product version number as %1-beta.\n\
182 4) Please <b>DO</b> use the ardour-users mailing list to discuss ideas and pass on comments.\n\
183 5) Please <b>DO</b> join us on IRC for real time discussions about ardour3. You\n\
184    can get there directly from Ardour via the Help->Chat menu option.\n\
185 \n\
186 Full information on all the above can be found on the support page at\n\
187 \n\
188                 http://ardour.org/support\n\
189 "), VERSIONSTRING));
190
191         vbox->set_border_width (12);
192         vbox->pack_start (*label, false, false, 12);
193         vbox->show_all ();
194         
195         append_page (*vbox);
196         set_page_type (*vbox, ASSISTANT_PAGE_CONTENT);
197         set_page_title (*vbox, _("This is a BETA RELEASE"));
198         set_page_complete (*vbox, true);
199 }
200
201 bool
202 ArdourStartup::use_session_template ()
203 {
204         if (!load_template_override.empty()) {
205                 return true;
206         }
207
208         if (use_template_button.get_active()) {
209                 return template_chooser.get_active_row_number() > 0;
210         } else {
211                 return !session_template_chooser.get_filename().empty();
212         }
213 }
214
215 std::string
216 ArdourStartup::session_template_name ()
217 {
218         if (!load_template_override.empty()) {
219                 string the_path (ARDOUR::user_template_directory());
220                 return Glib::build_filename (the_path, load_template_override + ARDOUR::template_suffix);
221         }
222
223         if (use_template_button.get_active()) {
224                 TreeModel::iterator iter = template_chooser.get_active ();
225                 TreeModel::Row row = (*iter);
226                 string s = row[session_template_columns.path];
227                 return s;
228         } else {
229                 return session_template_chooser.get_filename();
230
231         }
232 }
233
234 std::string
235 ArdourStartup::session_name (bool& should_be_new)
236 {
237         if (ready_without_display()) {
238                 return _provided_session_name;
239         }
240
241         /* Try recent session selection */
242
243         TreeIter iter = recent_session_display.get_selection()->get_selected();
244         
245         if (iter) {
246                 should_be_new = false;
247                 return (*iter)[recent_session_columns.visible_name];
248         }
249
250         if (_existing_session_chooser_used) {
251                 /* existing session chosen from file chooser */
252                 should_be_new = false;
253                 return existing_session_chooser.get_filename ();
254         } else {
255                 should_be_new = true;
256                 string val = new_name_entry.get_text ();
257                 strip_whitespace_edges (val);
258                 return val;
259         }
260 }
261
262 std::string
263 ArdourStartup::session_folder ()
264 {
265         if (ready_without_display()) {
266                 return _provided_session_path;
267         }
268
269         /* Try recent session selection */
270         
271         TreeIter iter = recent_session_display.get_selection()->get_selected();
272         
273         if (iter) {
274                 return (*iter)[recent_session_columns.fullpath];
275         }
276
277         if (_existing_session_chooser_used) {
278                 /* existing session chosen from file chooser */
279                 return existing_session_chooser.get_current_folder ();
280         } else {
281                 std::string legal_session_folder_name = legalize_for_path (new_name_entry.get_text());
282                 return Glib::build_filename (new_folder_chooser.get_current_folder(), legal_session_folder_name);
283         }
284 }
285
286 void
287 ArdourStartup::setup_new_user_page ()
288 {
289         Label* foomatic = manage (new Label);
290
291         foomatic->set_markup (string_compose (_("\
292 <span size=\"larger\">%1 is a digital audio workstation. You can use it to \
293 record, edit and mix multi-track audio. You can produce your \
294 own CDs, mix video soundtracks, or experiment with new \
295 ideas about music and sound. \
296 \n\n\
297 There are a few things that need to be configured before you start \
298 using the program.</span> \
299 "), PROGRAM_NAME));
300         foomatic->set_justify (JUSTIFY_FILL);
301         foomatic->set_line_wrap ();
302
303         HBox* hbox = manage (new HBox);
304         HBox* vbox = manage (new HBox);
305
306         vbox->set_border_width (24);
307
308         hbox->pack_start (*foomatic, true, true);
309         vbox->pack_start (*hbox, true, true);
310
311         foomatic->show ();
312         hbox->show ();
313         vbox->show ();
314
315         new_user_page_index = append_page (*vbox);
316         set_page_type (*vbox, ASSISTANT_PAGE_INTRO);
317         set_page_title (*vbox, string_compose (_("Welcome to %1"), PROGRAM_NAME));
318         set_page_header_image (*vbox, icon_pixbuf);
319         set_page_complete (*vbox, true);
320 }
321
322 void
323 ArdourStartup::default_dir_changed ()
324 {
325         Config->set_default_session_parent_dir (default_dir_chooser->get_filename());
326         // make new session folder chooser point to the new default
327         new_folder_chooser.set_current_folder (Config->get_default_session_parent_dir());       
328         config_changed ();
329 }
330
331 void
332 ArdourStartup::config_changed ()
333 {
334         config_modified = true;
335 }
336
337 void
338 ArdourStartup::setup_first_time_config_page ()
339 {
340         default_dir_chooser = manage (new FileChooserButton (string_compose (_("Default folder for %1 sessions"), PROGRAM_NAME),
341                                                              FILE_CHOOSER_ACTION_SELECT_FOLDER));
342         Gtk::Label* txt = manage (new Label);
343         HBox* hbox = manage (new HBox);
344         VBox* vbox = manage (new VBox);
345
346         txt->set_markup (string_compose (_("\
347 Each project that you work on with %1 has its own folder.\n\
348 These can require a lot of disk space if you are recording audio.\n\
349 \n\
350 Where would you like new %1 sessions to be stored by default?\n\n\
351 <i>(You can put new sessions anywhere, this is just a default)</i>"), PROGRAM_NAME));
352         txt->set_alignment (0.0, 0.0);
353
354         vbox->set_spacing (18);
355         vbox->set_border_width (24);
356
357         hbox->pack_start (*default_dir_chooser, false, true, 8);
358         vbox->pack_start (*txt, false, false);
359         vbox->pack_start (*hbox, false, true);
360
361         default_dir_chooser->set_current_folder (poor_mans_glob (Config->get_default_session_parent_dir()));
362         default_dir_chooser->signal_current_folder_changed().connect (sigc::mem_fun (*this, &ArdourStartup::default_dir_changed));
363         default_dir_chooser->show ();
364
365         vbox->show_all ();
366
367         default_folder_page_index = append_page (*vbox);
368         set_page_title (*vbox, _("Default folder for new sessions"));
369         set_page_header_image (*vbox, icon_pixbuf);
370         set_page_type (*vbox, ASSISTANT_PAGE_CONTENT);
371
372         /* user can just skip all these settings if they want to */
373
374         set_page_complete (*vbox, true);
375 }
376
377 void
378 ArdourStartup::setup_monitoring_choice_page ()
379 {
380         mon_vbox.set_spacing (18);
381         mon_vbox.set_border_width (24);
382
383         HBox* hbox = manage (new HBox);
384         VBox* vbox = manage (new VBox);
385         /* first button will be on by default */
386         RadioButton::Group g (monitor_via_ardour_button.get_group());
387         monitor_via_hardware_button.set_group (g);
388
389         monitor_label.set_markup(_("\
390 While recording instruments or vocals, you probably want to listen to the\n\
391 signal as well as record it. This is called \"monitoring\". There are\n\
392 different ways to do this depending on the equipment you have and the\n\
393 configuration of that equipment. The two most common are presented here.\n\
394 Please choose whichever one is right for your setup.\n\n\
395 <i>(You can change this preference at any time, via the Preferences dialog)</i>\n\n\
396 <i>If you do not understand what this is about, just accept the default.</i>"));
397         monitor_label.set_alignment (0.0, 0.0);
398
399         vbox->set_spacing (6);
400
401         vbox->pack_start (monitor_via_hardware_button, false, true);
402         vbox->pack_start (monitor_via_ardour_button, false, true);
403         hbox->pack_start (*vbox, true, true, 8);
404         mon_vbox.pack_start (monitor_label, false, false);
405         mon_vbox.pack_start (*hbox, false, false);
406
407         mon_vbox.show_all ();
408
409         monitoring_page_index = append_page (mon_vbox);
410         set_page_title (mon_vbox, _("Monitoring Choices"));
411         set_page_header_image (mon_vbox, icon_pixbuf);
412
413         /* user could just click on "Forward" if default
414          * choice is correct.
415          */
416
417         set_page_complete (mon_vbox, true);
418 }
419
420 void
421 ArdourStartup::setup_monitor_section_choice_page ()
422 {
423         mon_sec_vbox.set_spacing (18);
424         mon_sec_vbox.set_border_width (24);
425
426         HBox* hbox = manage (new HBox);
427         VBox* main_vbox = manage (new VBox);
428         VBox* vbox;
429         Label* l = manage (new Label);
430
431         main_vbox->set_spacing (32);
432
433         no_monitor_section_button.set_label (_("Use a Master bus directly"));
434         l->set_alignment (0.0, 1.0);
435         l->set_markup(_("Connect the Master bus directly to your hardware outputs. This is preferable for simple usage."));
436
437         vbox = manage (new VBox);
438         vbox->set_spacing (6);
439         vbox->pack_start (no_monitor_section_button, false, true);
440         vbox->pack_start (*l, false, true);
441
442         main_vbox->pack_start (*vbox, false, false);
443
444         use_monitor_section_button.set_label (_("Use an additional Monitor bus"));
445         l = manage (new Label);
446         l->set_alignment (0.0, 1.0);
447         l->set_text (_("Use a Monitor bus between Master bus and hardware outputs for \n\
448 greater control in monitoring without affecting the mix."));
449
450         vbox = manage (new VBox);
451         vbox->set_spacing (6);
452         vbox->pack_start (use_monitor_section_button, false, true);
453         vbox->pack_start (*l, false, true);
454
455         main_vbox->pack_start (*vbox, false, false);
456
457         RadioButton::Group g (use_monitor_section_button.get_group());
458         no_monitor_section_button.set_group (g);
459
460         if (Config->get_use_monitor_bus()) {
461                 use_monitor_section_button.set_active (true);
462         } else {
463                 no_monitor_section_button.set_active (true);
464         }
465
466         use_monitor_section_button.signal_toggled().connect (sigc::mem_fun (*this, &ArdourStartup::config_changed));
467         no_monitor_section_button.signal_toggled().connect (sigc::mem_fun (*this, &ArdourStartup::config_changed));
468
469         monitor_section_label.set_markup(_("<i>You can change this preference at any time via the Preferences dialog.\nYou can also add or remove the monitor section to/from any session.</i>\n\n\
470 <i>If you do not understand what this is about, just accept the default.</i>"));
471         monitor_section_label.set_alignment (0.0, 0.0);
472
473         hbox->pack_start (*main_vbox, true, true, 8);
474         mon_sec_vbox.pack_start (*hbox, false, false);
475         mon_sec_vbox.pack_start (monitor_section_label, false, false);
476
477         mon_sec_vbox.show_all ();
478
479         monitor_section_page_index = append_page (mon_sec_vbox);
480         set_page_title (mon_sec_vbox, _("Monitor Section"));
481         set_page_header_image (mon_sec_vbox, icon_pixbuf);
482
483         /* user could just click on "Forward" if default
484          * choice is correct.
485          */
486
487         set_page_complete (mon_sec_vbox, true);
488 }
489
490 void
491 ArdourStartup::setup_initial_choice_page ()
492 {
493         ic_vbox.set_spacing (6);
494         ic_vbox.set_border_width (24);
495
496         /* append the page early because the recent session display will cause
497            calls to set_page_complete() on this page.
498         */
499
500         initial_choice_index = append_page (ic_vbox);
501         set_page_title (ic_vbox, string_compose("%1 %2", PROGRAM_NAME, VERSIONSTRING));
502         set_page_header_image (ic_vbox, icon_pixbuf);
503
504
505         HBox* centering_hbox = manage (new HBox);
506         VBox* centering_vbox = manage (new VBox);
507
508         centering_vbox->set_spacing (6);
509
510         Label* new_label = manage (new Label);
511         new_label->set_markup (string_compose ("<span weight=\"bold\" size=\"large\">%1</span>", _("Create a new session")));
512         new_label->set_alignment (0, 0.5);
513
514         ic_new_session_button.set_label (_("Configure the new session ..."));
515         ic_new_session_button.signal_clicked().connect (sigc::mem_fun (*this, &ArdourStartup::new_session_button_clicked));
516
517         centering_vbox->pack_start (*new_label, false, false, 12);
518         centering_vbox->pack_start (ic_new_session_button, false, true);
519
520         /* Possible update message */
521
522         if (ARDOUR_UI::instance()->announce_string() != "" ) {
523
524                 Gtk::Frame *info_frame = manage(new Gtk::Frame);
525                 info_frame->set_shadow_type(SHADOW_ETCHED_OUT);
526                 centering_vbox->pack_start (*info_frame, false, false, 20);
527
528                 Box *info_box = manage (new VBox);
529                 info_box->set_border_width (12);
530                 info_box->set_spacing (6);
531                 info_box->set_name("mixbus_info_box");
532
533                 info_box->pack_start (info_scroller_label, false, false);
534
535                 info_frame->add (*info_box);
536                 info_frame->show_all();
537
538                 info_scroller_count = 0;
539                 info_scroller_connection = Glib::signal_timeout().connect (mem_fun(*this, &ArdourStartup::info_scroller_update), 50);
540
541                 Gtk::Button *updates_button = manage (new Gtk::Button (_("Check the website for more...")));
542
543                 updates_button->signal_clicked().connect (mem_fun(*this, &ArdourStartup::updates_button_clicked) );
544                 ARDOUR_UI::instance()->tooltips().set_tip (*updates_button, _("Click to open the program website in your web browser"));
545
546                 info_box->pack_start (*updates_button, false, false);
547         }
548
549         ARDOUR::RecentSessions rs;
550         ARDOUR::read_recent_sessions (rs);
551         
552         if (!rs.empty()) {
553
554                 /* recent session scroller */
555
556                 Label* load_label = manage (new Label);
557                 load_label->set_markup (string_compose ("<span weight=\"bold\" size=\"large\">%1</span>", _("Load a recent session")));
558                 load_label->set_alignment (0, 0.5);
559
560                 centering_vbox->pack_start (*load_label, false, false, 12);
561
562                 recent_session_model = TreeStore::create (recent_session_columns);
563                 redisplay_recent_sessions ();
564
565                 recent_session_display.set_model (recent_session_model);
566                 recent_session_display.append_column (_("Recent Sessions"), recent_session_columns.visible_name);
567                 recent_session_display.set_headers_visible (false);
568                 recent_session_display.get_selection()->set_mode (SELECTION_SINGLE);
569         
570                 recent_session_display.get_selection()->signal_changed().connect (sigc::mem_fun (*this, &ArdourStartup::recent_session_row_selected));
571         
572                 recent_scroller.add (recent_session_display);
573                 recent_scroller.set_policy (Gtk::POLICY_NEVER, Gtk::POLICY_AUTOMATIC);
574                 recent_scroller.set_shadow_type (Gtk::SHADOW_IN);
575         
576                 recent_session_display.show();
577         
578                 recent_scroller.show();
579                 recent_session_display.signal_row_activated().connect (sigc::mem_fun (*this, &ArdourStartup::recent_row_activated));
580         
581                 int cnt = redisplay_recent_sessions ();
582                 if (cnt > 4) {
583                         recent_scroller.set_size_request (-1, 300);
584                 }
585         
586                 centering_vbox->pack_start (recent_scroller, false, true);
587         }
588
589         /* Browse button */
590         
591         existing_session_chooser.set_title (_("Select session file"));
592         existing_session_chooser.signal_file_set().connect (sigc::mem_fun (*this, &ArdourStartup::existing_session_selected));
593         existing_session_chooser.set_current_folder(poor_mans_glob (Config->get_default_session_parent_dir()));
594         
595         FileFilter session_filter;
596         session_filter.add_pattern ("*.ardour");
597         session_filter.set_name (string_compose (_("%1 sessions"), PROGRAM_NAME));
598         existing_session_chooser.add_filter (session_filter);
599         existing_session_chooser.set_filter (session_filter);
600         
601 #ifdef GTKOSX
602         existing_session_chooser.add_shortcut_folder ("/Volumes");
603 #endif
604         
605         Label* browse_label = manage (new Label);
606         browse_label->set_markup (string_compose ("<span weight=\"bold\" size=\"large\">%1</span>", _("Browse for other sessions")));
607         browse_label->set_alignment (0, 0.5);
608         
609         centering_vbox->pack_start (*browse_label, false, false, 12);
610         centering_vbox->pack_start (existing_session_chooser, false, false);
611
612         /* pack it all up */
613
614         centering_hbox->pack_start (*centering_vbox, true, true);
615         ic_vbox.pack_start (*centering_hbox, true, true);
616         ic_vbox.show_all ();
617
618         /* user could just click on "Forward" if default
619          * choice is correct.
620          */
621
622         set_page_complete (ic_vbox, true);
623 }
624
625 void
626 ArdourStartup::session_selected ()
627 {
628         /* HACK HACK HACK ... change the "Apply" button label
629            to say "Open"
630         */
631
632         Gtk::Widget* tl = ic_vbox.get_toplevel();
633         Gtk::Window* win;
634         if ((win = dynamic_cast<Gtk::Window*>(tl)) != 0) {
635                 /* ::get_default_widget() is not wrapped in gtkmm */
636                 Gtk::Widget* def = wrap (gtk_window_get_default_widget (win->gobj()));
637                 Gtk::Button* button;
638                 if ((button = dynamic_cast<Gtk::Button*>(def)) != 0) {
639                         button->set_label (_("Open"));
640                 }
641         }
642 }
643
644 void
645 ArdourStartup::new_session_button_clicked ()
646 {
647         _existing_session_chooser_used = false;
648         recent_session_display.get_selection()->unselect_all ();
649         set_current_page (new_session_page_index);
650 }
651
652 void
653 ArdourStartup::setup_final_page ()
654 {
655         final_page.set_text (string_compose (_("%1 is ready for use"), PROGRAM_NAME));
656         final_page.show ();
657         final_page_index = append_page (final_page);
658         set_page_complete (final_page, true);
659         set_page_header_image (final_page, icon_pixbuf);
660         set_page_type (final_page, ASSISTANT_PAGE_CONFIRM);
661 }
662
663 void
664 ArdourStartup::on_cancel ()
665 {
666         _response = RESPONSE_CANCEL;
667         gtk_main_quit ();
668 }
669
670 void
671 ArdourStartup::on_prepare (Gtk::Widget* page)
672 {
673         if (page == &session_new_vbox) {
674
675                 /* if the user already defined a name by using the recent
676                  * session list or browsing to an existing session
677                  * then we are done.
678                  */
679                 
680                 bool expect_new_ignored;
681
682                 if (!session_name (expect_new_ignored).empty()) {
683                         on_apply ();
684                 }
685         }
686 }
687
688 bool
689 ArdourStartup::on_delete_event (GdkEventAny*)
690 {
691         _response = RESPONSE_CLOSE;
692         gtk_main_quit ();
693         return true;
694 }
695
696 void
697 ArdourStartup::on_apply ()
698 {
699         if (config_modified) {
700
701                 if (default_dir_chooser) {
702                         Config->set_default_session_parent_dir (default_dir_chooser->get_filename());
703                 }
704
705                 if (monitor_via_hardware_button.get_active()) {
706                         Config->set_monitoring_model (ExternalMonitoring);
707                 } else if (monitor_via_ardour_button.get_active()) {
708                         Config->set_monitoring_model (SoftwareMonitoring);
709                 }
710
711                 Config->set_use_monitor_bus (use_monitor_section_button.get_active());
712
713                 Config->save_state ();
714
715         }
716
717         {
718                 /* "touch" the been-here-before path now we've successfully
719                    made it through the first time setup (at least)
720                 */
721                 ofstream fout (been_here_before_path().c_str());
722
723         }
724                 
725         _response = RESPONSE_OK;
726         gtk_main_quit ();
727 }
728
729 void
730 ArdourStartup::populate_session_templates ()
731 {
732         vector<TemplateInfo> templates;
733
734         find_session_templates (templates);
735
736         template_model->clear ();
737
738         for (vector<TemplateInfo>::iterator x = templates.begin(); x != templates.end(); ++x) {
739                 TreeModel::Row row;
740
741                 row = *(template_model->append ());
742
743                 row[session_template_columns.name] = (*x).name;
744                 row[session_template_columns.path] = (*x).path;
745         }
746 }
747
748 void
749 ArdourStartup::setup_new_session_page ()
750 {
751         session_new_vbox.set_border_width (12);
752         session_new_vbox.set_spacing (18);
753
754         VBox *vbox1 = manage (new VBox);
755         HBox* hbox1 = manage (new HBox);
756         Label* label1 = manage (new Label);
757
758         vbox1->set_spacing (6);
759
760         hbox1->set_spacing (6);
761         hbox1->pack_start (*label1, false, false);
762         hbox1->pack_start (new_name_entry, true, true);
763
764         label1->set_text (_("Session name:"));
765
766
767         if (!ARDOUR_COMMAND_LINE::session_name.empty()) {
768                 new_name_entry.set_text  (Glib::path_get_basename (ARDOUR_COMMAND_LINE::session_name));
769                 /* name provided - they can move right along */
770                 set_page_complete (session_new_vbox, true);
771         }
772
773         new_name_entry.signal_changed().connect (sigc::mem_fun (*this, &ArdourStartup::new_name_changed));
774         new_name_entry.signal_activate().connect (sigc::mem_fun (*this, &ArdourStartup::move_along_now));
775
776         vbox1->pack_start (*hbox1, true, true);
777
778         /* --- */
779
780         HBox* hbox2 = manage (new HBox);
781         Label* label2 = manage (new Label);
782
783         hbox2->set_spacing (6);
784         hbox2->pack_start (*label2, false, false);
785         hbox2->pack_start (new_folder_chooser, true, true);
786
787         label2->set_text (_("Create session folder in:"));
788
789         if (!ARDOUR_COMMAND_LINE::session_name.empty()) {
790                 new_folder_chooser.set_current_folder (poor_mans_glob (Glib::path_get_dirname (ARDOUR_COMMAND_LINE::session_name)));
791         } else if (ARDOUR_UI::instance()->session_loaded) {
792                 // point the new session file chooser at the parent directory of the current session
793                 string session_parent_dir = Glib::path_get_dirname(ARDOUR_UI::instance()->the_session()->path());
794                 string::size_type last_dir_sep = session_parent_dir.rfind(G_DIR_SEPARATOR);
795                 session_parent_dir = session_parent_dir.substr(0, last_dir_sep);
796                 new_folder_chooser.set_current_folder (session_parent_dir);
797                 string default_session_folder = poor_mans_glob (Config->get_default_session_parent_dir());
798
799                 try {
800                         /* add_shortcut_folder throws an exception if the folder being added already has a shortcut */
801                         new_folder_chooser.add_shortcut_folder (default_session_folder);
802                 }
803                 catch (Glib::Error & e) {
804                         std::cerr << "new_folder_chooser.add_shortcut_folder (" << default_session_folder << ") threw Glib::Error " << e.what() << std::endl;
805                 }
806         } else {
807                 new_folder_chooser.set_current_folder (poor_mans_glob (Config->get_default_session_parent_dir()));
808         }
809         new_folder_chooser.show ();
810         new_folder_chooser.set_title (_("Select folder for session"));
811
812 #ifdef __APPLE__
813         new_folder_chooser.add_shortcut_folder ("/Volumes");
814 #endif
815
816         vbox1->pack_start (*hbox2, false, false);
817                 
818         session_new_vbox.pack_start (*vbox1, false, false);
819
820         /* --- */
821
822         VBox *vbox2 = manage (new VBox);
823         HBox* hbox3 = manage (new HBox);
824         template_model = ListStore::create (session_template_columns);
825
826         vbox2->set_spacing (6);
827
828         VBox *vbox3 = manage (new VBox);
829
830         vbox3->set_spacing (6);
831
832         /* we may want to hide this and show it at various
833            times depending on the existence of templates.
834         */
835         template_chooser.set_no_show_all (true);
836         use_template_button.set_no_show_all (true);
837
838         HBox* hbox4a = manage (new HBox);
839         use_template_button.set_label (_("Use this template"));
840                 
841         TreeModel::Row row = *template_model->prepend ();
842         row[session_template_columns.name] = (_("no template"));
843         row[session_template_columns.path] = string();
844                 
845         hbox4a->set_spacing (6);
846         hbox4a->pack_start (use_template_button, false, false);
847         hbox4a->pack_start (template_chooser, true, true);
848                 
849         template_chooser.set_model (template_model);
850                 
851         Gtk::CellRendererText* text_renderer = Gtk::manage (new Gtk::CellRendererText);
852         text_renderer->property_editable() = false;
853                 
854         template_chooser.pack_start (*text_renderer);
855         template_chooser.add_attribute (text_renderer->property_text(), session_template_columns.name);
856         template_chooser.set_active (0);
857
858         vbox3->pack_start (*hbox4a, false, false);
859
860         /* --- */
861
862         if (!new_user) {
863                 session_template_chooser.set_current_folder (poor_mans_glob (Config->get_default_session_parent_dir()));
864                 
865                 HBox* hbox4b = manage (new HBox);
866                 use_session_as_template_button.set_label (_("Use an existing session as a template:"));
867                 
868                 hbox4b->set_spacing (6);
869                 hbox4b->pack_start (use_session_as_template_button, false, false);
870                 hbox4b->pack_start (session_template_chooser, true, true);
871                 
872                 use_session_as_template_button.show ();
873                 session_template_chooser.show ();
874                 
875                 Gtk::FileFilter* session_filter = manage (new (Gtk::FileFilter));
876                 session_filter->add_pattern (X_("*.ardour"));
877                 session_template_chooser.set_filter (*session_filter);
878                 session_template_chooser.set_title (_("Select template"));
879                 
880                 vbox3->pack_start (*hbox4b, false, false);
881         }
882         
883         /* --- */
884         
885         HBox* hbox5 = manage (new HBox);
886         
887         hbox5->set_spacing (6);
888         hbox5->pack_start (more_new_session_options_button, false, false);
889         
890         setup_more_options_box ();
891         more_new_session_options_button.add (more_options_vbox);
892         
893         vbox3->pack_start (*hbox5, false, false);
894         hbox3->pack_start (*vbox3, true, true, 8);
895         vbox2->pack_start (*hbox3, false, false);
896         
897         /* --- */
898         
899         session_new_vbox.pack_start (*vbox2, false, false);
900         session_new_vbox.show_all ();
901
902         new_session_page_index = append_page (session_new_vbox);
903         set_page_type (session_new_vbox, ASSISTANT_PAGE_CONTENT);
904         set_page_title (session_new_vbox, _("New Session"));
905
906         set_page_type (session_new_vbox, ASSISTANT_PAGE_CONFIRM);
907 }
908
909 void
910 ArdourStartup::new_name_changed ()
911 {
912         if (!new_name_entry.get_text().empty()) {
913                 session_selected ();
914                 set_page_complete (session_new_vbox, true);
915         } else {
916                 set_page_complete (session_new_vbox, false);
917         }
918 }
919
920 int
921 ArdourStartup::redisplay_recent_sessions ()
922 {
923         std::vector<std::string> session_directories;
924         RecentSessionsSorter cmp;
925
926         recent_session_display.set_model (Glib::RefPtr<TreeModel>(0));
927         recent_session_model->clear ();
928
929         ARDOUR::RecentSessions rs;
930         ARDOUR::read_recent_sessions (rs);
931
932         if (rs.empty()) {
933                 recent_session_display.set_model (recent_session_model);
934                 return 0;
935         }
936         //
937         // sort them alphabetically
938         sort (rs.begin(), rs.end(), cmp);
939
940         for (ARDOUR::RecentSessions::iterator i = rs.begin(); i != rs.end(); ++i) {
941                 session_directories.push_back ((*i).second);
942         }
943         
944         int session_snapshot_count = 0;
945
946         for (vector<std::string>::const_iterator i = session_directories.begin(); i != session_directories.end(); ++i)
947         {
948                 std::vector<std::string> state_file_paths;
949
950                 // now get available states for this session
951
952                 get_state_files_in_directory (*i, state_file_paths);
953
954                 vector<string*>* states;
955                 vector<const gchar*> item;
956                 string fullpath = *i;
957
958                 /* remove any trailing / */
959
960                 if (fullpath[fullpath.length()-1] == '/') {
961                         fullpath = fullpath.substr (0, fullpath.length()-1);
962                 }
963
964                 /* check whether session still exists */
965                 if (!Glib::file_test(fullpath.c_str(), Glib::FILE_TEST_EXISTS)) {
966                         /* session doesn't exist */
967                         continue;
968                 }
969
970                 /* now get available states for this session */
971
972                 if ((states = Session::possible_states (fullpath)) == 0) {
973                         /* no state file? */
974                         continue;
975                 }
976
977                 std::vector<string> state_file_names(get_file_names_no_extension (state_file_paths));
978
979                 Gtk::TreeModel::Row row = *(recent_session_model->append());
980
981                 row[recent_session_columns.visible_name] = Glib::path_get_basename (fullpath);
982                 row[recent_session_columns.fullpath] = fullpath;
983                 row[recent_session_columns.tip] = Glib::Markup::escape_text (fullpath);
984                 
985                 ++session_snapshot_count;
986
987                 if (state_file_names.size() > 1) {
988
989                         // add the children
990
991                         for (std::vector<std::string>::iterator i2 = state_file_names.begin();
992                                         i2 != state_file_names.end(); ++i2) {
993
994                                 Gtk::TreeModel::Row child_row = *(recent_session_model->append (row.children()));
995
996                                 child_row[recent_session_columns.visible_name] = *i2;
997                                 child_row[recent_session_columns.fullpath] = fullpath;
998                                 child_row[recent_session_columns.tip] = Glib::Markup::escape_text (fullpath);
999                                 ++session_snapshot_count;
1000                         }
1001                 }
1002         }
1003
1004         recent_session_display.set_tooltip_column(1); // recent_session_columns.tip 
1005         recent_session_display.set_model (recent_session_model);
1006         return session_snapshot_count;
1007         // return rs.size();
1008 }
1009
1010 void
1011 ArdourStartup::recent_session_row_selected ()
1012 {
1013         if (recent_session_display.get_selection()->count_selected_rows() > 0) {
1014                 set_page_complete (ic_vbox, true);
1015                 session_selected ();
1016         } else {
1017                 set_page_complete (ic_vbox, false);
1018         }
1019 }
1020
1021 void
1022 ArdourStartup::setup_more_options_box ()
1023 {
1024         more_options_vbox.set_border_width (24);
1025
1026         _output_limit_count.set_adjustment (_output_limit_count_adj);
1027         _input_limit_count.set_adjustment (_input_limit_count_adj);
1028         _master_bus_channel_count.set_adjustment (_master_bus_channel_count_adj);
1029
1030         chan_count_label_1.set_text (_("channels"));
1031         chan_count_label_3.set_text (_("channels"));
1032         chan_count_label_4.set_text (_("channels"));
1033
1034         chan_count_label_1.set_alignment(0,0.5);
1035         chan_count_label_1.set_padding(0,0);
1036         chan_count_label_1.set_line_wrap(false);
1037
1038         chan_count_label_3.set_alignment(0,0.5);
1039         chan_count_label_3.set_padding(0,0);
1040         chan_count_label_3.set_line_wrap(false);
1041
1042         chan_count_label_4.set_alignment(0,0.5);
1043         chan_count_label_4.set_padding(0,0);
1044         chan_count_label_4.set_line_wrap(false);
1045
1046         bus_label.set_markup (_("<b>Busses</b>"));
1047         input_label.set_markup (_("<b>Inputs</b>"));
1048         output_label.set_markup (_("<b>Outputs</b>"));
1049
1050         _master_bus_channel_count.set_flags(Gtk::CAN_FOCUS);
1051         _master_bus_channel_count.set_update_policy(Gtk::UPDATE_ALWAYS);
1052         _master_bus_channel_count.set_numeric(true);
1053         _master_bus_channel_count.set_digits(0);
1054         _master_bus_channel_count.set_wrap(false);
1055
1056         _create_master_bus.set_label (_("Create master bus"));
1057         _create_master_bus.set_flags(Gtk::CAN_FOCUS);
1058         _create_master_bus.set_relief(Gtk::RELIEF_NORMAL);
1059         _create_master_bus.set_mode(true);
1060         _create_master_bus.set_active(true);
1061         _create_master_bus.set_border_width(0);
1062
1063         advanced_table.set_row_spacings(0);
1064         advanced_table.set_col_spacings(0);
1065
1066         _connect_inputs.set_label (_("Automatically connect to physical inputs"));
1067         _connect_inputs.set_flags(Gtk::CAN_FOCUS);
1068         _connect_inputs.set_relief(Gtk::RELIEF_NORMAL);
1069         _connect_inputs.set_mode(true);
1070         _connect_inputs.set_active(Config->get_input_auto_connect() != ManualConnect);
1071         _connect_inputs.set_border_width(0);
1072
1073         _limit_input_ports.set_label (_("Use only"));
1074         _limit_input_ports.set_flags(Gtk::CAN_FOCUS);
1075         _limit_input_ports.set_relief(Gtk::RELIEF_NORMAL);
1076         _limit_input_ports.set_mode(true);
1077         _limit_input_ports.set_sensitive(true);
1078         _limit_input_ports.set_border_width(0);
1079
1080         _input_limit_count.set_flags(Gtk::CAN_FOCUS);
1081         _input_limit_count.set_update_policy(Gtk::UPDATE_ALWAYS);
1082         _input_limit_count.set_numeric(true);
1083         _input_limit_count.set_digits(0);
1084         _input_limit_count.set_wrap(false);
1085         _input_limit_count.set_sensitive(false);
1086
1087         bus_hbox.pack_start (bus_table, Gtk::PACK_SHRINK, 18);
1088
1089         bus_label.set_alignment(0, 0.5);
1090         bus_label.set_padding(0,0);
1091         bus_label.set_line_wrap(false);
1092         bus_label.set_selectable(false);
1093         bus_label.set_use_markup(true);
1094         bus_frame.set_shadow_type(Gtk::SHADOW_NONE);
1095         bus_frame.set_label_align(0,0.5);
1096         bus_frame.add(bus_hbox);
1097         bus_frame.set_label_widget(bus_label);
1098
1099         bus_table.set_row_spacings (0);
1100         bus_table.set_col_spacings (0);
1101         bus_table.attach (_create_master_bus, 0, 1, 0, 1, Gtk::EXPAND|Gtk::FILL, Gtk::EXPAND|Gtk::FILL, 0, 0);
1102         bus_table.attach (_master_bus_channel_count, 1, 2, 0, 1, Gtk::EXPAND|Gtk::FILL, Gtk::EXPAND|Gtk::FILL, 0, 0);
1103         bus_table.attach (chan_count_label_1, 2, 3, 0, 1, Gtk::EXPAND|Gtk::FILL, Gtk::EXPAND|Gtk::FILL, 6, 0);
1104
1105         input_port_limit_hbox.pack_start(_limit_input_ports, Gtk::PACK_SHRINK, 6);
1106         input_port_limit_hbox.pack_start(_input_limit_count, Gtk::PACK_SHRINK, 0);
1107         input_port_limit_hbox.pack_start(chan_count_label_3, Gtk::PACK_SHRINK, 6);
1108         input_port_vbox.pack_start(_connect_inputs, Gtk::PACK_SHRINK, 0);
1109         input_port_vbox.pack_start(input_port_limit_hbox, Gtk::PACK_EXPAND_PADDING, 0);
1110         input_table.set_row_spacings(0);
1111         input_table.set_col_spacings(0);
1112         input_table.attach(input_port_vbox, 0, 1, 0, 1, Gtk::EXPAND|Gtk::FILL, Gtk::EXPAND|Gtk::FILL, 6, 6);
1113
1114         input_hbox.pack_start (input_table, Gtk::PACK_SHRINK, 18);
1115
1116         input_label.set_alignment(0, 0.5);
1117         input_label.set_padding(0,0);
1118         input_label.set_line_wrap(false);
1119         input_label.set_selectable(false);
1120         input_label.set_use_markup(true);
1121         input_frame.set_shadow_type(Gtk::SHADOW_NONE);
1122         input_frame.set_label_align(0,0.5);
1123         input_frame.add(input_hbox);
1124         input_frame.set_label_widget(input_label);
1125
1126         _connect_outputs.set_label (_("Automatically connect outputs"));
1127         _connect_outputs.set_flags(Gtk::CAN_FOCUS);
1128         _connect_outputs.set_relief(Gtk::RELIEF_NORMAL);
1129         _connect_outputs.set_mode(true);
1130         _connect_outputs.set_active(Config->get_output_auto_connect() != ManualConnect);
1131         _connect_outputs.set_border_width(0);
1132         _limit_output_ports.set_label (_("Use only"));
1133         _limit_output_ports.set_flags(Gtk::CAN_FOCUS);
1134         _limit_output_ports.set_relief(Gtk::RELIEF_NORMAL);
1135         _limit_output_ports.set_mode(true);
1136         _limit_output_ports.set_sensitive(true);
1137         _limit_output_ports.set_border_width(0);
1138         _output_limit_count.set_flags(Gtk::CAN_FOCUS);
1139         _output_limit_count.set_update_policy(Gtk::UPDATE_ALWAYS);
1140         _output_limit_count.set_numeric(false);
1141         _output_limit_count.set_digits(0);
1142         _output_limit_count.set_wrap(false);
1143         _output_limit_count.set_sensitive(false);
1144         output_port_limit_hbox.pack_start(_limit_output_ports, Gtk::PACK_SHRINK, 6);
1145         output_port_limit_hbox.pack_start(_output_limit_count, Gtk::PACK_SHRINK, 0);
1146         output_port_limit_hbox.pack_start(chan_count_label_4, Gtk::PACK_SHRINK, 6);
1147
1148         _connect_outputs_to_master.set_label (_("... to master bus"));
1149         _connect_outputs_to_master.set_flags(Gtk::CAN_FOCUS);
1150         _connect_outputs_to_master.set_relief(Gtk::RELIEF_NORMAL);
1151         _connect_outputs_to_master.set_mode(true);
1152         _connect_outputs_to_master.set_active(Config->get_output_auto_connect() == AutoConnectMaster);
1153         _connect_outputs_to_master.set_border_width(0);
1154
1155         _connect_outputs_to_master.set_group (connect_outputs_group);
1156         _connect_outputs_to_physical.set_group (connect_outputs_group);
1157
1158         _connect_outputs_to_physical.set_label (_("... to physical outputs"));
1159         _connect_outputs_to_physical.set_flags(Gtk::CAN_FOCUS);
1160         _connect_outputs_to_physical.set_relief(Gtk::RELIEF_NORMAL);
1161         _connect_outputs_to_physical.set_mode(true);
1162         _connect_outputs_to_physical.set_active(Config->get_output_auto_connect() == AutoConnectPhysical);
1163         _connect_outputs_to_physical.set_border_width(0);
1164
1165         output_conn_vbox.pack_start(_connect_outputs, Gtk::PACK_SHRINK, 0);
1166         output_conn_vbox.pack_start(_connect_outputs_to_master, Gtk::PACK_SHRINK, 0);
1167         output_conn_vbox.pack_start(_connect_outputs_to_physical, Gtk::PACK_SHRINK, 0);
1168         output_vbox.set_border_width(6);
1169
1170         output_port_vbox.pack_start(output_port_limit_hbox, Gtk::PACK_SHRINK, 0);
1171
1172         output_vbox.pack_start(output_conn_vbox);
1173         output_vbox.pack_start(output_port_vbox);
1174
1175         output_label.set_alignment(0, 0.5);
1176         output_label.set_padding(0,0);
1177         output_label.set_line_wrap(false);
1178         output_label.set_selectable(false);
1179         output_label.set_use_markup(true);
1180         output_frame.set_shadow_type(Gtk::SHADOW_NONE);
1181         output_frame.set_label_align(0,0.5);
1182
1183         output_hbox.pack_start (output_vbox, Gtk::PACK_SHRINK, 18);
1184
1185         output_frame.add(output_hbox);
1186         output_frame.set_label_widget(output_label);
1187
1188         more_options_vbox.pack_start(advanced_table, Gtk::PACK_SHRINK, 0);
1189         more_options_vbox.pack_start(bus_frame, Gtk::PACK_SHRINK, 6);
1190         more_options_vbox.pack_start(input_frame, Gtk::PACK_SHRINK, 6);
1191         more_options_vbox.pack_start(output_frame, Gtk::PACK_SHRINK, 0);
1192
1193         /* signals */
1194
1195         _connect_inputs.signal_clicked().connect (sigc::mem_fun (*this, &ArdourStartup::connect_inputs_clicked));
1196         _connect_outputs.signal_clicked().connect (sigc::mem_fun (*this, &ArdourStartup::connect_outputs_clicked));
1197         _limit_input_ports.signal_clicked().connect (sigc::mem_fun (*this, &ArdourStartup::limit_inputs_clicked));
1198         _limit_output_ports.signal_clicked().connect (sigc::mem_fun (*this, &ArdourStartup::limit_outputs_clicked));
1199         _create_master_bus.signal_clicked().connect (sigc::mem_fun (*this, &ArdourStartup::master_bus_button_clicked));
1200
1201         /* note that more_options_vbox is "visible" by default even
1202          * though it may not be displayed to the user, this is so the dialog
1203          * doesn't resize.
1204          */
1205         more_options_vbox.show_all ();
1206 }
1207
1208 bool
1209 ArdourStartup::create_master_bus() const
1210 {
1211         return _create_master_bus.get_active();
1212 }
1213
1214 int
1215 ArdourStartup::master_channel_count() const
1216 {
1217         return _master_bus_channel_count.get_value_as_int();
1218 }
1219
1220 bool
1221 ArdourStartup::connect_inputs() const
1222 {
1223         return _connect_inputs.get_active();
1224 }
1225
1226 bool
1227 ArdourStartup::limit_inputs_used_for_connection() const
1228 {
1229         return _limit_input_ports.get_active();
1230 }
1231
1232 int
1233 ArdourStartup::input_limit_count() const
1234 {
1235         return _input_limit_count.get_value_as_int();
1236 }
1237
1238 bool
1239 ArdourStartup::connect_outputs() const
1240 {
1241         return _connect_outputs.get_active();
1242 }
1243
1244 bool
1245 ArdourStartup::limit_outputs_used_for_connection() const
1246 {
1247         return _limit_output_ports.get_active();
1248 }
1249
1250 int
1251 ArdourStartup::output_limit_count() const
1252 {
1253         return _output_limit_count.get_value_as_int();
1254 }
1255
1256 bool
1257 ArdourStartup::connect_outs_to_master() const
1258 {
1259         return _connect_outputs_to_master.get_active();
1260 }
1261
1262 bool
1263 ArdourStartup::connect_outs_to_physical() const
1264 {
1265         return _connect_outputs_to_physical.get_active();
1266 }
1267
1268 void
1269 ArdourStartup::connect_inputs_clicked ()
1270 {
1271         _limit_input_ports.set_sensitive(_connect_inputs.get_active());
1272
1273         if (_connect_inputs.get_active() && _limit_input_ports.get_active()) {
1274                 _input_limit_count.set_sensitive(true);
1275         } else {
1276                 _input_limit_count.set_sensitive(false);
1277         }
1278 }
1279
1280 void
1281 ArdourStartup::connect_outputs_clicked ()
1282 {
1283         bool const co = _connect_outputs.get_active ();
1284         _limit_output_ports.set_sensitive(co);
1285         _connect_outputs_to_master.set_sensitive(co);
1286         _connect_outputs_to_physical.set_sensitive(co);
1287
1288         if (co && _limit_output_ports.get_active()) {
1289                 _output_limit_count.set_sensitive(true);
1290         } else {
1291                 _output_limit_count.set_sensitive(false);
1292         }
1293 }
1294
1295 void
1296 ArdourStartup::limit_inputs_clicked ()
1297 {
1298         _input_limit_count.set_sensitive(_limit_input_ports.get_active());
1299 }
1300
1301 void
1302 ArdourStartup::limit_outputs_clicked ()
1303 {
1304         _output_limit_count.set_sensitive(_limit_output_ports.get_active());
1305 }
1306
1307 void
1308 ArdourStartup::master_bus_button_clicked ()
1309 {
1310         bool const yn = _create_master_bus.get_active();
1311
1312         _master_bus_channel_count.set_sensitive(yn);
1313         _connect_outputs_to_master.set_sensitive(yn);
1314 }
1315
1316 void
1317 ArdourStartup::move_along_now ()
1318 {
1319         on_apply ();
1320 }
1321
1322 void
1323 ArdourStartup::recent_row_activated (const Gtk::TreePath&, Gtk::TreeViewColumn*)
1324 {
1325         set_page_complete (ic_vbox, true);
1326         move_along_now ();
1327 }
1328
1329 void
1330 ArdourStartup::existing_session_selected ()
1331 {
1332         _existing_session_chooser_used = true;
1333
1334         session_selected ();
1335         set_page_complete (ic_vbox, true);
1336         move_along_now ();
1337 }
1338
1339 std::string
1340 ArdourStartup::been_here_before_path () const
1341 {
1342         // XXXX use more specific version so we can catch upgrades
1343         return Glib::build_filename (user_config_directory (), ".a3");
1344 }
1345
1346 void
1347 ArdourStartup::updates_button_clicked ()
1348 {
1349         //now open a browser window so user can see more
1350         PBD::open_uri (Config->get_updates_url());
1351 }
1352
1353 bool
1354 ArdourStartup::info_scroller_update()
1355 {
1356         info_scroller_count++;
1357
1358         char buf[512];
1359         snprintf (buf, std::min(info_scroller_count,sizeof(buf)-1), "%s", ARDOUR_UI::instance()->announce_string().c_str() );
1360         buf[info_scroller_count] = 0;
1361         info_scroller_label.set_text (buf);
1362         info_scroller_label.show();
1363
1364         if (info_scroller_count > ARDOUR_UI::instance()->announce_string().length()) {
1365                 info_scroller_connection.disconnect();
1366         }
1367
1368         return true;
1369 }
1370
1371 void
1372 ArdourStartup::on_map ()
1373 {
1374         Gtk::Assistant::on_map ();
1375
1376         redisplay_recent_sessions ();
1377         populate_session_templates ();
1378
1379         if (!template_model->children().empty()) {
1380                 use_template_button.show();
1381                 template_chooser.show ();
1382         } else {
1383                 use_template_button.hide();
1384                 template_chooser.hide ();
1385         }
1386 }
1387