fix incorrect accumulation of export video options each time the dialog is used
[ardour.git] / gtk2_ardour / transport_masters_dialog.cc
index ae84ec4639c404fb47be97348f11991e591b6b82..33d0ce5ca4fa0b4ba7c0e823f494bc7fa1cd29ba 100644 (file)
@@ -83,6 +83,8 @@ TransportMastersWidget::TransportMastersWidget ()
        table.set_spacings (6);
 
        TransportMasterManager::instance().CurrentChanged.connect (current_connection, invalidator (*this), boost::bind (&TransportMastersWidget::current_changed, this, _1, _2), gui_context());
+       TransportMasterManager::instance().Added.connect (add_connection, invalidator (*this), boost::bind (&TransportMastersWidget::rebuild, this), gui_context());
+       TransportMasterManager::instance().Removed.connect (remove_connection, invalidator (*this), boost::bind (&TransportMastersWidget::rebuild, this), gui_context());
 
        rebuild ();
 }
@@ -114,8 +116,29 @@ TransportMastersWidget::current_changed (boost::shared_ptr<TransportMaster> old_
 void
 TransportMastersWidget::add_master ()
 {
-       if (!TransportMasterManager::instance().add (LTC, "new ltc")) {
-               rebuild ();
+       AddTransportMasterDialog d;
+
+       d.present ();
+       string name;
+
+       while (name.empty()) {
+
+               int r = d.run ();
+
+               switch (r) {
+               case RESPONSE_ACCEPT:
+                       name = d.get_name();
+                       break;
+               default:
+                       return;
+               }
+       }
+
+       d.hide ();
+
+       if (TransportMasterManager::instance().add (d.get_type(), name)) {
+               MessageDialog msg (_("New transport master not added - check error log for details"));
+               msg.run ();
        }
 }
 
@@ -139,8 +162,6 @@ TransportMastersWidget::rebuild ()
 
        uint32_t n = 1;
 
-       cerr << "There are " << masters.size() << endl;
-
        Gtk::RadioButtonGroup use_button_group;
 
        for (TransportMasterManager::TransportMasters::const_iterator m = masters.begin(); m != masters.end(); ++m, ++n) {
@@ -148,8 +169,6 @@ TransportMastersWidget::rebuild ()
                Row* r = new Row (*this);
                rows.push_back (r);
 
-               cerr << "Rows now holds " << rows.size() << endl;
-
                r->tm = *m;
                r->label.set_text ((*m)->name());
                r->type.set_text (enum_2_string  ((*m)->type()));
@@ -194,7 +213,6 @@ TransportMastersWidget::rebuild ()
 
                table.show_all ();
 
-               // r->label_box.set_events (Gdk::BUTTON_PRESS_MASK|Gdk::BUTTON_RELEASE_MASK);
                r->label_box.signal_button_press_event().connect (sigc::mem_fun (*r, &TransportMastersWidget::Row::name_press));
                r->port_combo.signal_changed().connect (sigc::mem_fun (*r, &TransportMastersWidget::Row::port_choice_changed));
                r->use_button.signal_toggled().connect (sigc::mem_fun (*r, &TransportMastersWidget::Row::use_button_toggled));
@@ -248,9 +266,20 @@ TransportMastersWidget::Row::name_press (GdkEventButton* ev)
        return false;
 }
 
+bool
+TransportMastersWidget::idle_remove (TransportMastersWidget::Row* row)
+{
+       TransportMasterManager::instance().remove (row->tm->name());
+       return false;
+}
+
 void
 TransportMastersWidget::Row::remove_clicked ()
 {
+       /* have to do this via an idle callback, because it will destroy the
+          widget from which this callback was initiated.
+       */
+       Glib::signal_idle().connect (sigc::bind (sigc::mem_fun (parent, &TransportMastersWidget::idle_remove), this));
 }
 
 void
@@ -473,11 +502,17 @@ TransportMastersWidget::Row::update (Session* s, samplepos_t now)
                                last.set_text ("");
                        }
                        current.set_text (Timecode::timecode_format_time (t));
-                       timestamp.set_markup (tm->position_string());
                        delta.set_markup (tm->delta_string ());
 
                        char gap[32];
-                       snprintf (gap, sizeof (gap), "%.3fs", (when - now) / (float) AudioEngine::instance()->sample_rate());
+                       const float seconds = (when - now) / (float) AudioEngine::instance()->sample_rate();
+                       if (abs (seconds) < 1.0) {
+                               snprintf (gap, sizeof (gap), "%.3fs", seconds);
+                       } else if (abs (seconds) < 4.0) {
+                               snprintf (gap, sizeof (gap), "%ds", (int) floor (seconds));
+                       } else {
+                               snprintf (gap, sizeof (gap), "%s", _(">4s ago"));
+                       }
                        timestamp.set_text (gap);
                        save_when = when;
 
@@ -486,16 +521,25 @@ TransportMastersWidget::Row::update (Session* s, samplepos_t now)
                        if (save_when) {
                                char gap[32];
 
-                               snprintf (gap, sizeof (gap), "%.3fs", (save_when - now) / (float) AudioEngine::instance()->sample_rate());
+                               const float seconds = (when - now) / (float) AudioEngine::instance()->sample_rate();
+                               if (abs (seconds) < 1.0) {
+                                       snprintf (gap, sizeof (gap), "%.3fs", seconds);
+                               } else if (abs (seconds) < 4.0) {
+                                       snprintf (gap, sizeof (gap), "%ds", (int) floor (seconds));
+                               } else {
+                                       snprintf (gap, sizeof (gap), "%s", _(">4s ago"));
+                               }
                                timestamp.set_text (gap);
                                save_when = when;
                        }
+                       delta.set_text ("");
+                       current.set_text ("");
                }
        }
 }
 
 void
-       TransportMastersWidget::update (samplepos_t /* audible */)
+TransportMastersWidget::update (samplepos_t /* audible */)
 {
        samplepos_t now = AudioEngine::instance()->sample_time ();
 
@@ -541,3 +585,61 @@ TransportMastersWindow::set_session (ARDOUR::Session* s)
        ArdourWindow::set_session (s);
        w.set_session (s);
 }
+
+TransportMastersWidget::AddTransportMasterDialog::AddTransportMasterDialog ()
+       : ArdourDialog (_("Add Transport Master"), true, false)
+       , name_label (_("Name"))
+       , type_label (_("Type"))
+{
+       name_hbox.set_spacing (6);
+       name_hbox.pack_start (name_label, false, false);
+       name_hbox.pack_start (name_entry, true, true);
+
+       type_hbox.set_spacing (6);
+       type_hbox.pack_start (type_label, false, false);
+       type_hbox.pack_start (type_combo, true, true);
+
+       vector<string> s;
+
+       s.push_back (X_("MTC"));
+       s.push_back (X_("LTC"));
+       s.push_back (X_("MIDI Clock"));
+
+       set_popdown_strings (type_combo, s);
+       type_combo.set_active_text (X_("LTC"));
+
+       get_vbox()->pack_start (name_hbox, false, false);
+       get_vbox()->pack_start (type_hbox, false, false);
+
+       add_button (_("Cancel"), RESPONSE_CANCEL);
+       add_button (_("Add"), RESPONSE_ACCEPT);
+
+       name_entry.show ();
+       type_combo.show ();
+       name_label.show ();
+       type_label.show ();
+       name_hbox.show ();
+       type_hbox.show ();
+
+       name_entry.signal_activate().connect (sigc::bind (sigc::mem_fun (*this, &Gtk::Dialog::response), Gtk::RESPONSE_ACCEPT));
+}
+
+string
+TransportMastersWidget::AddTransportMasterDialog::get_name () const
+{
+       return name_entry.get_text ();
+}
+
+SyncSource
+TransportMastersWidget::AddTransportMasterDialog::get_type() const
+{
+       string t = type_combo.get_active_text ();
+
+       if (t == X_("MTC")) {
+               return MTC;
+       } else if (t == X_("MIDI Clock")) {
+               return MIDIClock;
+       }
+
+       return LTC;
+}