major changes to Region, AudioRegion, Playlist, AudioPlaylist and Crossfade state...
[ardour.git] / gtk2_ardour / ardour_ui.cc
index c65346881a9711ab31159abc9912b46872506de9..7548f94c5b7ee6c9e3ba66099500d858490eae61 100644 (file)
@@ -86,7 +86,7 @@ ARDOUR_UI *ARDOUR_UI::theArdourUI = 0;
 sigc::signal<void,bool> ARDOUR_UI::Blink;
 sigc::signal<void>      ARDOUR_UI::RapidScreenUpdate;
 sigc::signal<void>      ARDOUR_UI::SuperRapidScreenUpdate;
-sigc::signal<void,jack_nframes_t> ARDOUR_UI::Clock;
+sigc::signal<void,nframes_t> ARDOUR_UI::Clock;
 
 ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[], string rcfile)
 
@@ -172,16 +172,12 @@ ARDOUR_UI::ARDOUR_UI (int *argcp, char **argvp[], string rcfile)
        shuttle_fract = 0.0;
        shuttle_max_speed = 8.0f;
 
-       set_shuttle_units (Percentage);
-       set_shuttle_behaviour (Sprung);
-
        shuttle_style_menu = 0;
        shuttle_unit_menu = 0;
 
        gettimeofday (&last_peak_grab, 0);
        gettimeofday (&last_shuttle_request, 0);
 
-       ARDOUR::AudioDiskstream::DeleteSources.connect (mem_fun(*this, &ARDOUR_UI::delete_sources_in_the_right_thread));
        ARDOUR::Diskstream::DiskOverrun.connect (mem_fun(*this, &ARDOUR_UI::disk_overrun_handler));
        ARDOUR::Diskstream::DiskUnderrun.connect (mem_fun(*this, &ARDOUR_UI::disk_underrun_handler));
 
@@ -491,7 +487,7 @@ ARDOUR_UI::every_point_zero_one_seconds ()
 }
 
 void
-ARDOUR_UI::update_sample_rate (jack_nframes_t ignored)
+ARDOUR_UI::update_sample_rate (nframes_t ignored)
 {
        char buf[32];
 
@@ -503,7 +499,7 @@ ARDOUR_UI::update_sample_rate (jack_nframes_t ignored)
 
        } else {
 
-               jack_nframes_t rate = engine->frame_rate();
+               nframes_t rate = engine->frame_rate();
                
                if (fmod (rate, 1000.0) != 0.0) {
                        snprintf (buf, sizeof (buf), _("%.1f kHz / %4.1f msecs"), 
@@ -557,7 +553,7 @@ ARDOUR_UI::update_disk_space()
                return;
        }
 
-       jack_nframes_t frames = session->available_capture_duration();
+       nframes_t frames = session->available_capture_duration();
        char buf[64];
 
        if (frames == max_frames) {
@@ -566,23 +562,13 @@ ARDOUR_UI::update_disk_space()
                int hrs;
                int mins;
                int secs;
-               jack_nframes_t fr = session->frame_rate();
+               nframes_t fr = session->frame_rate();
                
-               if (session->actively_recording()){
-                       
-                       rec_enabled_diskstreams = 0;
-                       session->foreach_route (this, &ARDOUR_UI::count_recenabled_diskstreams);
-                       
-                       if (rec_enabled_diskstreams) {
-                               frames /= rec_enabled_diskstreams;
-                       }
-                       
-               } else {
-                       
-                       /* hmmm. shall we divide by the route count? or the diskstream count?
-                          or what? for now, do nothing ...
-                       */
-                       
+               rec_enabled_diskstreams = 0;
+               session->foreach_route (this, &ARDOUR_UI::count_recenabled_diskstreams);
+               
+               if (rec_enabled_diskstreams) {
+                       frames /= rec_enabled_diskstreams;
                }
                
                hrs  = frames / (fr * 3600);
@@ -933,12 +919,13 @@ restart JACK with more ports."));
 }
 
 void
-ARDOUR_UI::do_transport_locate (jack_nframes_t new_position)
+ARDOUR_UI::do_transport_locate (nframes_t new_position)
 {
-       jack_nframes_t _preroll;
+       nframes_t _preroll = 0;
 
        if (session) {
-               _preroll = session->convert_to_frames_at (new_position, session->preroll);
+               // XXX CONFIG_CHANGE FIX - requires AnyTime handling
+               // _preroll = session->convert_to_frames_at (new_position, Config->get_preroll());
 
                if (new_position > _preroll) {
                        new_position -= _preroll;
@@ -988,7 +975,7 @@ void
 ARDOUR_UI::transport_goto_end ()
 {
        if (session) {
-               jack_nframes_t frame = session->current_end_frame();
+               nframes_t frame = session->current_end_frame();
                session->request_locate (frame);
 
                /* force displayed area in editor to start no matter
@@ -1013,8 +1000,8 @@ ARDOUR_UI::transport_stop ()
                return;
        }
        
-       if (session->get_auto_loop()) {
-               session->request_auto_loop (false);
+       if (Config->get_auto_loop()) {
+               session->request_play_loop (false);
        }
        
        session->request_stop ();
@@ -1043,8 +1030,7 @@ ARDOUR_UI::transport_record ()
                switch (session->record_status()) {
                case Session::Disabled:
                        if (session->ntracks() == 0) {
-                               string txt = _("Please create 1 or more track\nbefore trying to record.\nCheck the Session menu.");
-                               MessageDialog msg (*editor, txt);
+                               MessageDialog msg (*editor, _("Please create 1 or more track\nbefore trying to record.\nCheck the Session menu."));
                                msg.run ();
                                return;
                        }
@@ -1068,8 +1054,8 @@ ARDOUR_UI::transport_roll ()
 
        rolling = session->transport_rolling ();
 
-       if (session->get_auto_loop()) {
-               session->request_auto_loop (false);
+       if (Config->get_auto_loop()) {
+               session->request_play_loop (false);
                auto_loop_button.set_active (false);
                roll_button.set_active (true);
        } else if (session->get_play_range ()) {
@@ -1086,7 +1072,7 @@ void
 ARDOUR_UI::transport_loop()
 {
        if (session) {
-               if (session->get_auto_loop()) {
+               if (Config->get_auto_loop()) {
                        if (session->transport_rolling()) {
                                Location * looploc = session->locations()->auto_loop_location();
                                if (looploc) {
@@ -1095,7 +1081,7 @@ ARDOUR_UI::transport_loop()
                        }
                }
                else {
-                       session->request_auto_loop (true);
+                       session->request_play_loop (true);
                }
        }
 }
@@ -1616,6 +1602,9 @@ ARDOUR_UI::save_template ()
 void
 ARDOUR_UI::new_session (bool startup, std::string predetermined_path)
 {
+       string session_name;
+       string session_path;
+
        int response = Gtk::RESPONSE_NONE;
 
        new_session_dialog->set_modal(true);
@@ -1623,11 +1612,9 @@ ARDOUR_UI::new_session (bool startup, std::string predetermined_path)
        new_session_dialog->reset_recent();
        new_session_dialog->show();
 
-       //Glib::RefPtr<Gdk::Window> nsd_window = new_session_dialog->get_window();
-
        do {
                response = new_session_dialog->run ();
-               //nsd_window ->set_cursor(Gdk::Cursor(Gdk::WATCH));
+
                if(response == Gtk::RESPONSE_CANCEL || response == Gtk::RESPONSE_DELETE_EVENT) {
                        quit();
                        return;
@@ -1637,14 +1624,29 @@ ARDOUR_UI::new_session (bool startup, std::string predetermined_path)
                        new_session_dialog->reset();
 
                } else if (response == Gtk::RESPONSE_YES) {
-                       /* YES  == OPEN, but there's no enum for that */
 
-                       std::string session_name = new_session_dialog->session_name();
-                       std::string session_path = new_session_dialog->session_folder();
-                       load_session (session_path, session_name);
+                       /* YES  == OPEN, but there's no enum for that */
 
+                       session_name = new_session_dialog->session_name();
+                       
+                       if (session_name.empty()) {
+                               response = Gtk::RESPONSE_NONE;
+                               continue;
+                       } 
+
+                       if (session_name[0] == '/' || 
+                           (session_name.length() > 2 && session_name[0] == '.' && session_name[1] == '/') ||
+                           (session_name.length() > 3 && session_name[0] == '.' && session_name[1] == '.' && session_name[2] == '/')) {
+                               load_session (Glib::path_get_dirname (session_name), session_name);
+                       } else {
+                               session_path = new_session_dialog->session_folder();
+                               load_session (session_path, session_name);
+                       }
                        
                } else if (response == Gtk::RESPONSE_OK) {
+
+                       session_name = new_session_dialog->session_name();
+                       
                        if (new_session_dialog->get_current_page() == 1) {
                  
                                /* XXX this is a bit of a hack.. 
@@ -1652,93 +1654,117 @@ ARDOUR_UI::new_session (bool startup, std::string predetermined_path)
                                   if we're on page 1 (the load page)
                                   Unfortunately i can't see how atm.. 
                                */
-                        
-                               std::string session_name = new_session_dialog->session_name();
-                               std::string session_path = new_session_dialog->session_folder();
-                               load_session (session_path, session_name);
-                              
+                               
+                               if (session_name.empty()) {
+                                       response = Gtk::RESPONSE_NONE;
+                                       continue;
+                               } 
+                               
+                               if (session_name[0] == '/' || 
+                                   (session_name.length() > 2 && session_name[0] == '.' && session_name[1] == '/') ||
+                                   (session_name.length() > 3 && session_name[0] == '.' && session_name[1] == '.' && session_name[2] == '/')) {
+                                       load_session (Glib::path_get_dirname (session_name), session_name);
+                               } else {
+                                       session_path = new_session_dialog->session_folder();
+                                       load_session (session_path, session_name);
+                               }
+                       
                        } else {
 
                                _session_is_new = true;
                              
-                               std::string session_name = new_session_dialog->session_name();
-                               std::string session_path = new_session_dialog->session_folder();
-                       
+                               if (session_name.empty()) {
+                                       response = Gtk::RESPONSE_NONE;
+                                       continue;
+                               } 
+
+                               if (session_name[0] == '/' || 
+                                   (session_name.length() > 2 && session_name[0] == '.' && session_name[1] == '/') ||
+                                   (session_name.length() > 3 && session_name[0] == '.' && session_name[1] == '.' && session_name[2] == '/')) {
+
+                                       session_path = Glib::path_get_dirname (session_name);
+                                       session_name = Glib::path_get_basename (session_name);
+
+                               } else {
+
+                                       session_path = new_session_dialog->session_folder();
+                                       
+                               }
                        
                                //XXX This is needed because session constructor wants a 
                                //non-existant path. hopefully this will be fixed at some point.
-                       
-                               session_path = Glib::build_filename(session_path, session_name);
-                       
+                               
+                               session_path = Glib::build_filename (session_path, session_name);
+                                               
                                std::string template_name = new_session_dialog->session_template_name();
-                       
+                                               
                                if (new_session_dialog->use_session_template()) {
-                         
-                                       load_session (session_path, session_name, &template_name);
+                                                       
+                                       load_session (session_path, session_name, &template_name);
                          
                                } else {
-                               
-                                       uint32_t cchns;
+                                                       
+                                       uint32_t cchns;
                                        uint32_t mchns;
-                                       Session::AutoConnectOption iconnect;
-                                       Session::AutoConnectOption oconnect;
-                               
+                                       AutoConnectOption iconnect;
+                                       AutoConnectOption oconnect;
+                                                       
                                        if (new_session_dialog->create_control_bus()) {
-                                               cchns = (uint32_t) new_session_dialog->control_channel_count();
+                                               cchns = (uint32_t) new_session_dialog->control_channel_count();
                                        } else {
-                                               cchns = 0;
+                                               cchns = 0;
                                        }
-                               
+                                                       
                                        if (new_session_dialog->create_master_bus()) {
-                                               mchns = (uint32_t) new_session_dialog->master_channel_count();
+                                               mchns = (uint32_t) new_session_dialog->master_channel_count();
                                        } else {
-                                               mchns = 0;
+                                               mchns = 0;
                                        }
-                                     
+                                                       
                                        if (new_session_dialog->connect_inputs()) {
-                                               iconnect = Session::AutoConnectPhysical;
+                                               iconnect = AutoConnectPhysical;
                                        } else {
-                                               iconnect = Session::AutoConnectOption (0);
+                                               iconnect = AutoConnectOption (0);
                                        }
-                                     
+                                                       
                                        /// @todo some minor tweaks.
-                               
+                                                       
                                        if (new_session_dialog->connect_outs_to_master()) {
-                                               oconnect = Session::AutoConnectMaster;
+                                               oconnect = AutoConnectMaster;
                                        } else if (new_session_dialog->connect_outs_to_physical()) {
-                                               oconnect = Session::AutoConnectPhysical;
+                                               oconnect = AutoConnectPhysical;
                                        } else {
-                                               oconnect = Session::AutoConnectOption (0);
+                                               oconnect = AutoConnectOption (0);
                                        } 
-                               
+                                                       
                                        uint32_t nphysin = (uint32_t) new_session_dialog->input_limit_count();
                                        uint32_t nphysout = (uint32_t) new_session_dialog->output_limit_count();
-                               
+                                                       
                                        build_session (session_path,
-                                              session_name,
-                                              cchns,
-                                              mchns,
-                                              iconnect,
-                                              oconnect,
-                                              nphysin,
-                                              nphysout, 
-                                              engine->frame_rate() * 60 * 5);
+                                                      session_name,
+                                                      cchns,
+                                                      mchns,
+                                                      iconnect,
+                                                      oconnect,
+                                                      nphysin,
+                                                      nphysout, 
+                                                      engine->frame_rate() * 60 * 5);
                                }
-                       }       
+                       }
                }
                
        } while (response == Gtk::RESPONSE_NONE);
+
        show();
        new_session_dialog->get_window()->set_cursor();
-       
        new_session_dialog->hide();
 }
 
 void
 ARDOUR_UI::close_session()
 {
-  unload_session();
-  new_session ();
+       unload_session();
+       new_session ();
 }
 
 int
@@ -1777,6 +1803,8 @@ This prevents the session from being loaded."));
 
        connect_to_session (new_session);
 
+       Config->set_current_owner (ConfigVariableBase::Interface);
+
        session_loaded = true;
        return 0;
 }
@@ -1797,11 +1825,11 @@ int
 ARDOUR_UI::build_session (const string & path, const string & snap_name, 
                          uint32_t control_channels,
                          uint32_t master_channels, 
-                         Session::AutoConnectOption input_connect,
-                         Session::AutoConnectOption output_connect,
+                         AutoConnectOption input_connect,
+                         AutoConnectOption output_connect,
                          uint32_t nphysin,
                          uint32_t nphysout,
-                         jack_nframes_t initial_length)
+                         nframes_t initial_length)
 {
        Session *new_session;
        int x;
@@ -1838,6 +1866,11 @@ ARDOUR_UI::show ()
 {
        if (editor) {
                editor->show_window ();
+               
+               if (!shown_flag) {
+                       editor->present ();
+               }
+
                shown_flag = true;
        }
        
@@ -2077,9 +2110,9 @@ ARDOUR_UI::add_route ()
        string name_template = add_route_dialog->name_template ();
        bool track = add_route_dialog->track ();
 
-       Session::AutoConnectOption oac = session->get_output_auto_connect();
+       AutoConnectOption oac = Config->get_output_auto_connect();
 
-       if (oac & Session::AutoConnectMaster) {
+       if (oac & AutoConnectMaster) {
                output_chan = (session->master_out() ? session->master_out()->n_inputs() : input_chan);
        } else {
                output_chan = input_chan;
@@ -2152,18 +2185,6 @@ ARDOUR_UI::halt_on_xrun_message ()
        msg.run ();
 }
 
-void 
-ARDOUR_UI::delete_sources_in_the_right_thread (list<boost::shared_ptr<ARDOUR::Source> >* deletion_list)
-{
-       ENSURE_GUI_THREAD (bind (mem_fun(*this, &ARDOUR_UI::delete_sources_in_the_right_thread), deletion_list));
-
-       for (list<boost::shared_ptr<Source> >::iterator i = deletion_list->begin(); i != deletion_list->end(); ++i) {
-               (*i)->drop_references ();
-       }
-
-       delete deletion_list;
-}
-
 void
 ARDOUR_UI::disk_overrun_handler ()
 {
@@ -2267,7 +2288,7 @@ ARDOUR_UI::reconnect_to_jack ()
 }
 
 void
-ARDOUR_UI::set_jack_buffer_size (jack_nframes_t nframes)
+ARDOUR_UI::set_jack_buffer_size (nframes_t nframes)
 {
        engine->request_buffer_size (nframes);
        update_sample_rate (0);
@@ -2293,72 +2314,6 @@ ARDOUR_UI::cmdline_new_session (string path)
        return FALSE; /* don't call it again */
 }
 
-void
-ARDOUR_UI::set_native_file_header_format (HeaderFormat hf)
-{
-       Glib::RefPtr<Action> act;
-       
-       switch (hf) {
-       case BWF:
-               act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatBWF"));
-               break;
-       case WAVE:
-               act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatWAVE"));
-               break;
-       case WAVE64:
-               act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatWAVE64"));
-               break;
-       case iXML:
-               act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatiXML"));
-               break;
-       case RF64:
-               act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatRF64"));
-               break;
-       case CAF:
-               act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatCAF"));
-               break;
-       case AIFF:
-               act = ActionManager::get_action (X_("options"), X_("FileHeaderFormatAIFF"));
-               break;
-       }
-
-       if (act) {
-               Glib::RefPtr<RadioAction> ract = Glib::RefPtr<RadioAction>::cast_dynamic(act);
-               if (ract && ract->get_active() && Config->get_native_file_header_format() != hf) {
-                       Config->set_native_file_header_format (hf);
-                       if (session) {
-                               session->reset_native_file_format ();
-                       }
-               }
-       }
-}
-
-void
-ARDOUR_UI::set_native_file_data_format (SampleFormat sf)
-{
-       Glib::RefPtr<Action> act;
-       
-       switch (sf) {
-       case FormatFloat:
-               act = ActionManager::get_action (X_("options"), X_("FileDataFormatFloat"));
-               break;
-       case FormatInt24:
-               act = ActionManager::get_action (X_("options"), X_("FileDataFormat24bit"));
-               break;
-       }
-
-       if (act) {
-               Glib::RefPtr<RadioAction> ract = Glib::RefPtr<RadioAction>::cast_dynamic(act);
-
-               if (ract && ract->get_active() && Config->get_native_file_data_format() != sf) {
-                       Config->set_native_file_data_format (sf);
-                       if (session) {
-                               session->reset_native_file_format ();
-                       }
-               }
-       }
-}
-
 void
 ARDOUR_UI::use_config ()
 {