diff --git a/gtk2_ardour/analysis_window.cc b/gtk2_ardour/analysis_window.cc index b6802352aa..2ccaf3876d 100644 --- a/gtk2_ardour/analysis_window.cc +++ b/gtk2_ardour/analysis_window.cc @@ -259,7 +259,7 @@ AnalysisWindow::analyze_data (Gtk::Button * /*button*/) // std::cerr << "Analyzing ranges on track " << rui->route()->name() << std::endl; FFTResult *res = fft_graph.prepareResult(rui->route_color(), rui->route()->name()); - for (std::list::iterator j = ts.begin(); j != ts.end(); ++j) { + for (std::list::iterator j = ts.begin(); j != ts.end(); ++j) { int n; for (int channel = 0; channel < n_inputs; channel++) { diff --git a/gtk2_ardour/ardour_ui.cc b/gtk2_ardour/ardour_ui.cc index 5eccc95d1e..770e7bc01d 100644 --- a/gtk2_ardour/ardour_ui.cc +++ b/gtk2_ardour/ardour_ui.cc @@ -1904,13 +1904,13 @@ ARDOUR_UI::toggle_roll (bool with_abort, bool roll_out_of_bounded_mode) } if (_session->get_play_loop() && Config->get_loop_is_mode()) { - _session->request_locate (_session->locations()->auto_loop_location()->start(), MustRoll); + _session->request_locate (_session->locations()->auto_loop_location()->start().samples(), MustRoll); } else { if (UIConfiguration::instance().get_follow_edits()) { - list& range = editor->get_selection().time; - if (range.front().start == _session->transport_sample()) { // if playhead is exactly at the start of a range, we assume it was placed there by follow_edits + list& range = editor->get_selection().time; + if (range.front().start().samples() == _session->transport_sample()) { // if playhead is exactly at the start of a range, we assume it was placed there by follow_edits _session->request_play_range (&range, true); - _session->set_requested_return_sample (range.front().start); //force an auto-return here + _session->set_requested_return_sample (range.front().start().samples()); //force an auto-return here } } _session->request_roll (); diff --git a/gtk2_ardour/ardour_ui3.cc b/gtk2_ardour/ardour_ui3.cc index 86ad0042d8..9112a7410b 100644 --- a/gtk2_ardour/ardour_ui3.cc +++ b/gtk2_ardour/ardour_ui3.cc @@ -188,7 +188,7 @@ ARDOUR_UI::update_transport_clocks (samplepos_t pos) case DeltaOriginMarker: { Location* loc = _session->locations()->clock_origin_location (); - primary_clock->set (pos, false, loc ? loc->start() : 0); + primary_clock->set (pos, false, loc ? loc->start_sample() : 0); } break; } @@ -203,7 +203,7 @@ ARDOUR_UI::update_transport_clocks (samplepos_t pos) case DeltaOriginMarker: { Location* loc = _session->locations()->clock_origin_location (); - secondary_clock->set (pos, false, loc ? loc->start() : 0); + secondary_clock->set (pos, false, loc ? loc->start_sample() : 0); } break; } diff --git a/gtk2_ardour/ardour_ui_engine.cc b/gtk2_ardour/ardour_ui_engine.cc index 9b2e46373c..326f827a27 100644 --- a/gtk2_ardour/ardour_ui_engine.cc +++ b/gtk2_ardour/ardour_ui_engine.cc @@ -114,7 +114,7 @@ void ARDOUR_UI::create_xrun_marker (samplepos_t where) { if (_session) { - Location *location = new Location (*_session, where, where, _("xrun"), Location::IsMark, 0); + Location *location = new Location (*_session, timepos_t (where), timepos_t (where), _("xrun"), Location::IsMark); _session->locations()->add (location); } } diff --git a/gtk2_ardour/audio_clock.cc b/gtk2_ardour/audio_clock.cc index 41e7a54f4c..fb77ddb9d3 100644 --- a/gtk2_ardour/audio_clock.cc +++ b/gtk2_ardour/audio_clock.cc @@ -891,6 +891,85 @@ AudioClock::set (samplepos_t when, bool force, samplecnt_t offset) } } + finish_set (timepos_t (when), btn_en); +} + +void +AudioClock::set_duration (Temporal::timecnt_t const & d, bool force, Temporal::timecnt_t const & offset) +{ + set_time (timepos_t (d), force, offset); +} + +void +AudioClock::set_time (Temporal::timepos_t const & w, bool force, Temporal::timecnt_t const & offset) +{ + Temporal::timepos_t when (w); + + if ((!force && !is_visible()) || _session == 0) { + return; + } + + if (is_duration) { + when = when.earlier (offset); + } + + if (when > _limit_pos) { + when = _limit_pos; + } else if (when < -_limit_pos) { + when = -_limit_pos; + } + + if (when == last_when && !force) { +#if 0 // XXX return if no change and no change forced. verify Aug/2014 + if (_mode != Timecode && _mode != MinSec) { + /* may need to force display of TC source + * time, so don't return early. + */ + /* ^^ Why was that?, delta times? + * Timecode FPS, pull-up/down, etc changes + * trigger a 'session_property_changed' which + * eventually calls set(last_when, true) + * + * re-rendering the clock every 40ms or so just + * because we can is not ideal. + */ + return; + } +#else + return; +#endif + } + + bool btn_en = false; + + if (!editing) { + + switch (_mode) { + case Timecode: + set_timecode (when.sample(), force); + break; + + case BBT: + _set_bbt (when.bbt(), when.bbt() < Temporal::timepos_t (Temporal::BBT_Time())); + btn_en = true; + break; + + case MinSec: + set_minsec (when.sample(), force); + break; + + case Samples: + set_samples (when.sample(), force); + break; + } + } + + finish_set (when, btn_en); +} + +void +AudioClock::finish_set (Temporal::timepos_t const & when, bool btn_en) +{ if (_with_info) { _left_btn.set_sensitive (btn_en); _right_btn.set_sensitive (btn_en); @@ -2295,14 +2374,25 @@ AudioClock::set_editable (bool yn) } void -AudioClock::set_is_duration (bool yn) +AudioClock::set_is_duration (bool yn, timepos_t const & p) { if (yn == is_duration) { + if (yn) { + /* just reset position */ + duration_position = p; + } + return; } is_duration = yn; - AudioClock::set (last_when, true); + if (yn) { + duration_position = p; + } else { + duration_position = timepos_t (); + } + + set_time (last_when, true); } void diff --git a/gtk2_ardour/audio_clock.h b/gtk2_ardour/audio_clock.h index 43486ce95e..8abda14e86 100644 --- a/gtk2_ardour/audio_clock.h +++ b/gtk2_ardour/audio_clock.h @@ -74,11 +74,15 @@ class AudioClock : public CairoWidget, public ARDOUR::SessionHandlePtr void focus (); virtual void set (samplepos_t, bool force = false, ARDOUR::samplecnt_t offset = 0); + void set_time (Temporal::timepos_t const &, bool force = false, Temporal::timecnt_t const & offset = Temporal::timecnt_t()); + void set_duration (Temporal::timecnt_t const &, bool force = false, Temporal::timecnt_t const & offset = Temporal::timecnt_t()); + void set_from_playhead (); void locate (); void set_mode (Mode, bool noemit = false); void set_bbt_reference (samplepos_t); void set_is_duration (bool); + void set_is_duration (bool, Temporal::timepos_t const &); void copy_text_to_clipboard () const; @@ -139,6 +143,7 @@ class AudioClock : public CairoWidget, public ARDOUR::SessionHandlePtr bool edit_is_negative; samplepos_t _limit_pos; + Temporal::timepos_t duration_position; ARDOUR::samplecnt_t _offset; @@ -223,6 +228,7 @@ class AudioClock : public CairoWidget, public ARDOUR::SessionHandlePtr void set_seconds (samplepos_t, bool); void set_samples (samplepos_t, bool); void set_out_of_bounds (bool negative); + void finish_set (Temporal::timepos_t const &, bool); void set_clock_dimensions (Gtk::Requisition&); diff --git a/gtk2_ardour/audio_streamview.cc b/gtk2_ardour/audio_streamview.cc index 18d030dc71..bf6ecc296d 100644 --- a/gtk2_ardour/audio_streamview.cc +++ b/gtk2_ardour/audio_streamview.cc @@ -126,7 +126,7 @@ AudioStreamView::create_region_view (boost::shared_ptr r, bool wait_for_ insensitive to events */ - if (region->length() == 1) { + if (region->length_samples() == 1) { region_view->set_sensitive (false); } @@ -226,7 +226,7 @@ AudioStreamView::setup_rec_box () samplepos_t start = 0; if (rec_regions.size() > 0) { - start = rec_regions.back().first->start() + start = rec_regions.back().first->start_sample() + _trackview.track()->get_captured_samples(rec_regions.size()-1); } @@ -241,7 +241,7 @@ AudioStreamView::setup_rec_box () boost::dynamic_pointer_cast(RegionFactory::create (sources, plist, false))); assert(region); - region->set_position (_trackview.session()->transport_sample()); + region->set_position (timepos_t (_trackview.session()->transport_sample())); rec_regions.push_back (make_pair(region, (RegionView*) 0)); } @@ -355,20 +355,20 @@ AudioStreamView::update_rec_regions (samplepos_t start, samplecnt_t cnt) continue; } - samplecnt_t origlen = region->length(); + samplecnt_t origlen = region->length_samples(); if (region == rec_regions.back().first && rec_active) { - if (last_rec_data_sample > region->start()) { + if (last_rec_data_sample > region->start_sample()) { - samplecnt_t nlen = last_rec_data_sample - region->start(); + samplecnt_t nlen = last_rec_data_sample - region->start_sample(); - if (nlen != region->length()) { + if (nlen != region->length_samples()) { region->suspend_property_changes (); /* set non-musical position / length */ - region->set_position (_trackview.track()->get_capture_start_sample(n)); - region->set_length (nlen, 0); + region->set_position (timepos_t (_trackview.track()->get_capture_start_sample(n))); + region->set_length (timecnt_t (nlen)); region->resume_property_changes (); if (origlen == 1) { @@ -377,11 +377,11 @@ AudioStreamView::update_rec_regions (samplepos_t start, samplecnt_t cnt) setup_new_rec_layer_time (region); } - check_record_layers (region, (region->position() - region->start() + start + cnt)); + check_record_layers (region, (region->position_sample() - region->start_sample() + start + cnt)); /* also update rect */ ArdourCanvas::Rectangle * rect = rec_rects[n].rectangle; - gdouble xend = _trackview.editor().sample_to_pixel (region->position() + region->length()); + gdouble xend = _trackview.editor().sample_to_pixel (region->position_sample() + region->length_samples()); rect->set_x1 (xend); } @@ -389,13 +389,13 @@ AudioStreamView::update_rec_regions (samplepos_t start, samplecnt_t cnt) samplecnt_t nlen = _trackview.track()->get_captured_samples(n); - if (nlen != region->length()) { + if (nlen != region->length_samples()) { - if (region->source_length(0) >= region->start() + nlen) { + if (region->source_length(0) >= region->start_sample() + nlen) { region->suspend_property_changes (); - region->set_position (_trackview.track()->get_capture_start_sample(n)); - region->set_length (nlen, 0); + region->set_position (timepos_t (_trackview.track()->get_capture_start_sample(n))); + region->set_length (timecnt_t (nlen)); region->resume_property_changes (); if (origlen == 1) { @@ -451,8 +451,8 @@ AudioStreamView::hide_xfades_with (boost::shared_ptr ar) for (list::iterator i = region_views.begin(); i != region_views.end(); ++i) { AudioRegionView* const arv = dynamic_cast(*i); if (arv) { - switch (arv->region()->coverage (ar->position(), ar->last_sample())) { - case Evoral::OverlapNone: + switch (arv->region()->coverage (ar->nt_position(), ar->nt_last())) { + case Temporal::OverlapNone: break; default: if (arv->start_xfade_visible ()) { diff --git a/gtk2_ardour/automation_line.cc b/gtk2_ardour/automation_line.cc index fa321c0705..452b53f777 100644 --- a/gtk2_ardour/automation_line.cc +++ b/gtk2_ardour/automation_line.cc @@ -83,15 +83,14 @@ AutomationLine::AutomationLine (const string& name, TimeAxisView& tv, ArdourCanvas::Item& parent, boost::shared_ptr al, - const ParameterDescriptor& desc, - Evoral::TimeConverter* converter) + const ParameterDescriptor& desc) : trackview (tv) , _name (name) , alist (al) , _time_converter (converter ? converter : new Evoral::IdentityConverter) , _parent_group (parent) , _offset (0) - , _maximum_time (max_samplepos) + , _maximum_time (timepos_t::max (al->time_domain())) , _fill (false) , _desc (desc) { @@ -1178,11 +1177,29 @@ AutomationLine::set_state (const XMLNode &node, int version) return alist->set_state (node, version); } -void -AutomationLine::view_to_model_coord (double& x, double& y) const +Temporal::timepos_t +AutomationLine::view_to_model_coord (double x, double& y) const { - x = _time_converter->from (x); + assert (alist->time_style() != Temporal::BarTime); + view_to_model_coord_y (y); + + Temporal::timepos_t w; + + switch (alist->time_style()) { + case Temporal::AudioTime: + return timepos_t (samplepos_t (x)); + break; + case Temporal::BeatTime: + return timepos_t (Beats::from_double (x)); + break; + default: + /*NOTREACHED*/ + break; + } + + /*NOTREACHED*/ + return timepos_t(); } void @@ -1251,11 +1268,12 @@ AutomationLine::model_to_view_coord_y (double& y) const y = _desc.to_interface (y); } -void -AutomationLine::model_to_view_coord (double& x, double& y) const +double +AutomationLine::model_to_view_coord (Evoral::ControlEvent const & ev, double& y) const { + Temporal::timepos_t w (ev.when()); model_to_view_coord_y (y); - x = _time_converter->to (x) - _offset; + return (w).earlier (_offset).samples(); } /** Called when our list has announced that its interpolation style has changed */ @@ -1336,7 +1354,7 @@ AutomationLine::memento_command_binder () * to the start of the track or region that it is on. */ void -AutomationLine::set_maximum_time (samplecnt_t t) +AutomationLine::set_maximum_time (Temporal::timepos_t const & t) { if (_maximum_time == t) { return; diff --git a/gtk2_ardour/automation_line.h b/gtk2_ardour/automation_line.h index 0d89025964..16c5429001 100644 --- a/gtk2_ardour/automation_line.h +++ b/gtk2_ardour/automation_line.h @@ -33,8 +33,6 @@ #include -#include "evoral/TimeConverter.h" - #include "pbd/undo.h" #include "pbd/statefuldestructible.h" #include "pbd/memento_command.h" @@ -71,8 +69,7 @@ public: TimeAxisView& tv, ArdourCanvas::Item& parent, boost::shared_ptr al, - const ARDOUR::ParameterDescriptor& desc, - Evoral::TimeConverter* converter = 0); + const ARDOUR::ParameterDescriptor& desc); virtual ~AutomationLine (); @@ -126,9 +123,9 @@ public: std::string fraction_to_string (double) const; std::string delta_to_string (double) const; double string_to_fraction (std::string const &) const; - void view_to_model_coord (double& x, double& y) const; + Temporal::timepos_t view_to_model_coord (double& x, double& y) const; void view_to_model_coord_y (double &) const; - void model_to_view_coord (double& x, double& y) const; + Temporal::timepos_t model_to_view_coord (Evoral::ControlEvent const &, double& y) const; void model_to_view_coord_y (double &) const; double compute_delta (double from, double to) const; @@ -151,20 +148,16 @@ public: virtual MementoCommandBinder* memento_command_binder (); - const Evoral::TimeConverter& time_converter () const { - return *_time_converter; - } - std::pair get_point_x_range () const; - void set_maximum_time (ARDOUR::samplecnt_t); - ARDOUR::samplecnt_t maximum_time () const { + void set_maximum_time (Temporal::timepos_t const &); + Temporal::timepos_t maximum_time () const { return _maximum_time; } - void set_offset (ARDOUR::samplecnt_t); - ARDOUR::samplecnt_t offset () { return _offset; } - void set_width (ARDOUR::samplecnt_t); + void set_offset (Temporal::timecnt_t const &); + Temporal::timecnt_t offset () { return _offset; } + void set_width (Temporal::timecnt_t const &); samplepos_t session_position (ARDOUR::AutomationList::const_iterator) const; @@ -175,9 +168,6 @@ protected: uint32_t _line_color; boost::shared_ptr alist; - Evoral::TimeConverter* _time_converter; - /** true if _time_converter belongs to us (ie we should delete it on destruction) */ - bool _our_time_converter; VisibleAspects _visible; @@ -231,7 +221,7 @@ private: /** offset from the start of the automation list to the start of the line, so that * a +ve offset means that the 0 on the line is at _offset in the list */ - ARDOUR::samplecnt_t _offset; + Temporal::timecnt_t _offset; bool is_stepped() const; void update_visibility (); @@ -244,7 +234,7 @@ private: PBD::ScopedConnectionList _list_connections; /** maximum time that a point on this line can be at, relative to the position of its region or start of its track */ - ARDOUR::samplecnt_t _maximum_time; + Temporal::timepos_t _maximum_time; bool _fill; diff --git a/gtk2_ardour/automation_region_view.cc b/gtk2_ardour/automation_region_view.cc index 53773f2c76..f2654e519a 100644 --- a/gtk2_ardour/automation_region_view.cc +++ b/gtk2_ardour/automation_region_view.cc @@ -44,6 +44,8 @@ #include "pbd/i18n.h" +using namespace Temporal; + AutomationRegionView::AutomationRegionView (ArdourCanvas::Container* parent, AutomationTimeAxisView& time_axis, boost::shared_ptr region, @@ -52,11 +54,9 @@ AutomationRegionView::AutomationRegionView (ArdourCanvas::Container* double spu, uint32_t basic_color) : RegionView(parent, time_axis, region, spu, basic_color, true) - , _region_relative_time_converter(region->session().tempo_map(), region->position()) - , _source_relative_time_converter(region->session().tempo_map(), region->position() - region->start()) , _parameter(param) { - TimeAxisViewItem::set_position (_region->position(), this); + TimeAxisViewItem::set_position (_region->nt_position(), this); if (list) { assert(list->parameter() == param); @@ -83,7 +83,7 @@ AutomationRegionView::init (bool /*wfd*/) RegionView::init (false); - reset_width_dependent_items ((double) _region->length() / samples_per_pixel); + reset_width_dependent_items ((double) _region->length_samples() / samples_per_pixel); set_height (trackview.current_height()); @@ -100,13 +100,12 @@ AutomationRegionView::create_line (boost::shared_ptr lis ARDOUR::EventTypeMap::instance().to_symbol(list->parameter()), trackview, *get_canvas_group(), list, boost::dynamic_pointer_cast (_region), - _parameter, - &_source_relative_time_converter)); + _parameter)); _line->set_colors(); _line->set_height ((uint32_t)rint(trackview.current_height() - 2.5 - NAME_HIGHLIGHT_SIZE)); _line->set_visibility (AutomationLine::VisibleAspects (AutomationLine::Line|AutomationLine::ControlPoints)); - _line->set_maximum_time (_region->length()); - _line->set_offset (_region->start ()); + _line->set_maximum_time (timepos_t (_region->nt_length())); + _line->set_offset (_region->nt_start ()); } uint32_t @@ -157,7 +156,8 @@ AutomationRegionView::canvas_group_event (GdkEvent* ev) /* guard points only if primary modifier is used */ bool with_guard_points = Gtkmm2ext::Keyboard::modifier_state_equals (ev->button.state, Gtkmm2ext::Keyboard::PrimaryModifier); - add_automation_event (ev, e.pixel_to_sample (x) - _region->position() + _region->start(), y, with_guard_points); +#warning NUTEMPO what if this automation list is not using audio time? + add_automation_event (ev, timepos_t (e.pixel_to_sample (x) - _region->position_sample() + _region->start_sample()), y, with_guard_points); return true; } @@ -168,10 +168,11 @@ AutomationRegionView::canvas_group_event (GdkEvent* ev) * @param y y position, relative to our TimeAxisView. */ void -AutomationRegionView::add_automation_event (GdkEvent *, samplepos_t when, double y, bool with_guard_points) +AutomationRegionView::add_automation_event (GdkEvent *, timepos_t const & w, double y, bool with_guard_points) { boost::shared_ptr c = _region->control(_parameter, true); boost::shared_ptr ac = boost::dynamic_pointer_cast(c); + timepos_t when (w); /* the non-const copy */ if (!_line) { assert(ac); @@ -184,11 +185,13 @@ AutomationRegionView::add_automation_event (GdkEvent *, samplepos_t when, double /* compute vertical fractional position */ y = 1.0 - (y / _line->height()); - /* snap sample, prepare conversion to double beats */ - double when_d = snap_sample_to_sample (when - _region->start ()).sample + _region->start (); + /* snap time */ - /* convert 'when' to music-time relative to the region and scale y from interface to internal */ - _line->view_to_model_coord (when_d, y); + when = snap_region_time_to_region_time (when.earlier (_region->nt_start()), false) + _region->nt_start (); + + /* map using line */ + + _line->view_to_model_coord_y (y); if (UIConfiguration::instance().get_new_automation_points_on_lane()) { if (c->list()->size () == 0) { @@ -205,6 +208,7 @@ AutomationRegionView::add_automation_event (GdkEvent *, samplepos_t when, double XMLNode& before = _line->the_list()->get_state(); +<<<<<<< HEAD if (_line->the_list()->editor_add (when_d, y, with_guard_points)) { if (ac->automation_state () == ARDOUR::Off) { @@ -214,6 +218,9 @@ AutomationRegionView::add_automation_event (GdkEvent *, samplepos_t when, double RouteTimeAxisView::signal_ctrl_touched (false); } +======= + if (_line->the_list()->editor_add (when, y, with_guard_points)) { +>>>>>>> intermediate, unfinished snapshot of ongoing timeline types work on GTK GUI view->editor().begin_reversible_command (_("add automation event")); XMLNode& after = _line->the_list()->get_state(); @@ -226,7 +233,7 @@ AutomationRegionView::add_automation_event (GdkEvent *, samplepos_t when, double } bool -AutomationRegionView::paste (samplepos_t pos, +AutomationRegionView::paste (timepos_t const & pos, unsigned paste_count, float times, boost::shared_ptr slist) @@ -241,24 +248,18 @@ AutomationRegionView::paste (samplepos_t pos return false; } - AutomationType src_type = (AutomationType)slist->parameter().type (); - double len = slist->length(); + timecnt_t len = slist->length(); + timepos_t p (pos); /* add multi-paste offset if applicable */ - if (parameter_is_midi (src_type)) { - // convert length to samples (incl tempo-ramps) - len = BeatsSamplesConverter (view->session()->tempo_map(), pos).to (Temporal::Beats::from_double (len * paste_count)); - pos += view->editor ().get_paste_offset (pos, paste_count > 0 ? 1 : 0, len); - } else { - pos += view->editor ().get_paste_offset (pos, paste_count, len); - } + p += view->editor ().get_paste_offset (pos, paste_count > 0 ? 1 : 0, len); /* convert sample-position to model's unit and position */ - const double model_pos = _source_relative_time_converter.from ( - pos - _source_relative_time_converter.origin_b()); + timepos_t model_pos = timepos_t (source_relative_distance (timecnt_t (p, timepos_t()), slist->time_domain())); XMLNode& before = my_list->get_state(); - my_list->paste(*slist, model_pos, BeatsSamplesConverter (view->session()->tempo_map(), pos)); +#warning NUTEMPO fixme needs new tempo map + //my_list->paste (*slist, model_pos, _region->session().tempo_map()); view->session()->add_command( new MementoCommand(_line->memento_command_binder(), &before, &my_list->get_state())); @@ -276,10 +277,10 @@ AutomationRegionView::set_height (double h) } bool -AutomationRegionView::set_position (samplepos_t pos, void* src, double* ignored) +AutomationRegionView::set_position (timepos_t const & pos, void* src, double* ignored) { if (_line) { - _line->set_maximum_time (_region->length ()); + _line->set_maximum_time (timepos_t (_region->nt_length ())); } return RegionView::set_position(pos, src, ignored); @@ -302,25 +303,16 @@ AutomationRegionView::region_resized (const PBD::PropertyChange& what_changed) { RegionView::region_resized (what_changed); - if (what_changed.contains (ARDOUR::Properties::position)) { - _region_relative_time_converter.set_origin_b(_region->position()); - } - - if (what_changed.contains (ARDOUR::Properties::start) || - what_changed.contains (ARDOUR::Properties::position)) { - _source_relative_time_converter.set_origin_b (_region->position() - _region->start()); - } - if (!_line) { return; } if (what_changed.contains (ARDOUR::Properties::start)) { - _line->set_offset (_region->start ()); + _line->set_offset (_region->nt_start ()); } if (what_changed.contains (ARDOUR::Properties::length)) { - _line->set_maximum_time (_region->length()); + _line->set_maximum_time (timepos_t (_region->nt_length())); } } diff --git a/gtk2_ardour/automation_region_view.h b/gtk2_ardour/automation_region_view.h index c313ee24fa..abd3666b68 100644 --- a/gtk2_ardour/automation_region_view.h +++ b/gtk2_ardour/automation_region_view.h @@ -50,19 +50,11 @@ public: void init (bool wfd); - bool paste (samplepos_t pos, + bool paste (Temporal::timepos_t const & pos, unsigned paste_count, float times, boost::shared_ptr slist); - ARDOUR::DoubleBeatsSamplesConverter const & region_relative_time_converter () const { - return _region_relative_time_converter; - } - - ARDOUR::DoubleBeatsSamplesConverter const & source_relative_time_converter () const { - return _source_relative_time_converter; - } - inline AutomationTimeAxisView* automation_view() const { return dynamic_cast(&trackview); } @@ -78,17 +70,15 @@ public: protected: void create_line(boost::shared_ptr list); - bool set_position(samplepos_t pos, void* src, double* ignored); + bool set_position(Temporal::timepos_t const & pos, void* src, double* ignored); void region_resized (const PBD::PropertyChange&); bool canvas_group_event(GdkEvent* ev); - void add_automation_event (GdkEvent* event, samplepos_t when, double y, bool with_guard_points); + void add_automation_event (GdkEvent* event, Temporal::timepos_t const & when, double y, bool with_guard_points); void mouse_mode_changed (); void entered(); void exited(); private: - ARDOUR::DoubleBeatsSamplesConverter _region_relative_time_converter; - ARDOUR::DoubleBeatsSamplesConverter _source_relative_time_converter; Evoral::Parameter _parameter; boost::shared_ptr _line; PBD::ScopedConnection _mouse_mode_connection; diff --git a/gtk2_ardour/automation_streamview.cc b/gtk2_ardour/automation_streamview.cc index 1628612bad..de38d94f73 100644 --- a/gtk2_ardour/automation_streamview.cc +++ b/gtk2_ardour/automation_streamview.cc @@ -323,7 +323,7 @@ AutomationStreamView::get_lines () const } bool -AutomationStreamView::paste (samplepos_t pos, +AutomationStreamView::paste (timepos_t const & pos, unsigned paste_count, float times, boost::shared_ptr alist) @@ -339,7 +339,7 @@ AutomationStreamView::paste (samplepos_t pos, list::const_iterator prev = region_views.begin (); for (list::const_iterator i = region_views.begin(); i != region_views.end(); ++i) { - if ((*i)->region()->position() > pos) { + if ((*i)->region()->nt_position() > pos) { break; } prev = i; @@ -348,7 +348,7 @@ AutomationStreamView::paste (samplepos_t pos, boost::shared_ptr r = (*prev)->region (); /* If *prev doesn't cover pos, it's no good */ - if (r->position() > pos || ((r->position() + r->length()) < pos)) { + if (r->nt_position() > pos || ((r->nt_position() + r->nt_length()) < pos)) { return false; } diff --git a/gtk2_ardour/automation_streamview.h b/gtk2_ardour/automation_streamview.h index b6b4801720..77e5c58263 100644 --- a/gtk2_ardour/automation_streamview.h +++ b/gtk2_ardour/automation_streamview.h @@ -68,7 +68,7 @@ public: std::list > get_lines () const; - bool paste (samplepos_t pos, + bool paste (Temporal::timepos_t const & pos, unsigned paste_count, float times, boost::shared_ptr list); diff --git a/gtk2_ardour/automation_time_axis.h b/gtk2_ardour/automation_time_axis.h index 1bd51bbf90..3c826819ea 100644 --- a/gtk2_ardour/automation_time_axis.h +++ b/gtk2_ardour/automation_time_axis.h @@ -107,7 +107,7 @@ public: /* editing operations */ void cut_copy_clear (Selection&, Editing::CutCopyOp); - bool paste (ARDOUR::samplepos_t, const Selection&, PasteContext&, const int32_t sub_num); + bool paste (Temporal::timepos_t const &, const Selection&, PasteContext&); int set_state (const XMLNode&, int version); diff --git a/gtk2_ardour/editor.cc b/gtk2_ardour/editor.cc index f9889c1544..dad5ceca59 100644 --- a/gtk2_ardour/editor.cc +++ b/gtk2_ardour/editor.cc @@ -1749,7 +1749,7 @@ Editor::loudness_analyze_range_selection () if (!pl || !rui) { continue; } - for (std::list::iterator j = ts.begin (); j != ts.end (); ++j) { + for (std::list::iterator j = ts.begin (); j != ts.end (); ++j) { total_work += j->length (); } } @@ -2610,7 +2610,7 @@ Editor::set_snapped_cursor_position (samplepos_t pos) * @param event Event to get current key modifier information from, or 0. */ void -Editor::snap_to_with_modifier (MusicSample& start, GdkEvent const * event, RoundMode direction, SnapPref pref) +Editor::snap_to_with_modifier (Temporal::timepos_t & start, GdkEvent const * event, Temporal::RoundMode direction, bool for_mark) { if (!_session || !event) { return; @@ -2618,33 +2618,32 @@ Editor::snap_to_with_modifier (MusicSample& start, GdkEvent const * event, Round if (ArdourKeyboard::indicates_snap (event->button.state)) { if (_snap_mode == SnapOff) { - snap_to_internal (start, direction, pref); + snap_to_internal (start, direction, for_mark); } else { - start.set (start.sample, 0); + start = start.sample(); } } else { if (_snap_mode != SnapOff) { - snap_to_internal (start, direction, pref); + snap_to_internal (start, direction, for_mark); } else if (ArdourKeyboard::indicates_snap_delta (event->button.state)) { /* SnapOff, but we pressed the snap_delta modifier */ - snap_to_internal (start, direction, pref); + snap_to_internal (start, direction, for_mark); } else { - start.set (start.sample, 0); + start = start.sample (); } } } void -Editor::snap_to (MusicSample& start, RoundMode direction, SnapPref pref, bool ensure_snap) +Editor::snap_to (Temporal::timepos_t & start, Temporal::RoundMode direction, bool for_mark, bool ensure_snap) { if (!_session || (_snap_mode == SnapOff && !ensure_snap)) { - start.set (start.sample, 0); + start = start.sample (); return; } - snap_to_internal (start, direction, pref, ensure_snap); + snap_to_internal (start, direction, for_mark, ensure_snap); } - static void check_best_snap (samplepos_t presnap, samplepos_t &test, samplepos_t &dist, samplepos_t &best) { @@ -2936,7 +2935,7 @@ Editor::snap_to_marker (samplepos_t presnap, RoundMode direction) } void -Editor::snap_to_internal (MusicSample& start, RoundMode direction, SnapPref pref, bool ensure_snap) +Editor::snap_to_internal (timepos_t const & start, RoundMode direction, SnapPref pref, bool ensure_snap) { UIConfiguration const& uic (UIConfiguration::instance ()); const samplepos_t presnap = start.sample; @@ -4054,23 +4053,28 @@ Editor::set_show_touched_automation (bool yn) instant_save (); } -samplecnt_t -Editor::get_paste_offset (samplepos_t pos, unsigned paste_count, samplecnt_t duration) +PlaylistSelector& +Editor::playlist_selector () const +{ + return *_playlist_selector; +} + +Temporal::timecnt_t +Editor::get_paste_offset (Temporal::timepos_t const & pos, unsigned paste_count, Temporal::timecnt_t const & duration) { if (paste_count == 0) { /* don't bother calculating an offset that will be zero anyway */ - return 0; + return timecnt_t (0, timepos_t()); } /* calculate basic unsnapped multi-paste offset */ - samplecnt_t offset = paste_count * duration; + Temporal::timecnt_t offset = duration * paste_count; /* snap offset so pos + offset is aligned to the grid */ - MusicSample offset_pos (pos + offset, 0); - snap_to(offset_pos, RoundUpMaybe); - offset = offset_pos.sample - pos; + Temporal::timepos_t snap_pos (pos + offset); + snap_to (snap_pos, Temporal::RoundUpMaybe); - return offset; + return pos.distance (snap_pos); } unsigned diff --git a/gtk2_ardour/editor.h b/gtk2_ardour/editor.h index 6bfe1c6a6d..5f341d7ff4 100644 --- a/gtk2_ardour/editor.h +++ b/gtk2_ardour/editor.h @@ -351,10 +351,10 @@ public: /* nudge is initiated by transport controls owned by ARDOUR_UI */ - samplecnt_t get_nudge_distance (samplepos_t pos, samplecnt_t& next); - samplecnt_t get_paste_offset (samplepos_t pos, unsigned paste_count, samplecnt_t duration); - unsigned get_grid_beat_divisions(samplepos_t position); - Temporal::Beats get_grid_type_as_beats (bool& success, samplepos_t position); + Temporal::timecnt_t get_nudge_distance (Temporal::timepos_t const & pos, Temporal::timecnt_t& next); + Temporal::timecnt_t get_paste_offset (Temporal::timepos_t const & pos, unsigned paste_count, Temporal::timecnt_t const & duration); + unsigned get_grid_beat_divisions(Temporal::timepos_t const & position); + Temporal::Beats get_grid_type_as_beats (bool& success, Temporal::timepos_t const & position); int32_t get_grid_music_divisions (uint32_t event_state); @@ -384,7 +384,7 @@ public: void set_group_tabs (); /* returns the left-most and right-most time that the gui should allow the user to scroll to */ - std::pair session_gui_extents (bool use_extra = true) const; + std::pair session_gui_extents (bool use_extra = true) const; /* RTAV Automation display option */ bool show_touched_automation () const; @@ -457,15 +457,13 @@ public: ARDOUR::SrcQuality quality, ARDOUR::MidiTrackNameSource mts, ARDOUR::MidiTempoMapDisposition mtd, - samplepos_t& pos, - boost::shared_ptr instrument = boost::shared_ptr(), - bool with_markers = false - ); + Temporal::timepos_t& pos, + boost::shared_ptr instrument = boost::shared_ptr()); void do_embed (std::vector paths, Editing::ImportDisposition disposition, Editing::ImportMode mode, - samplepos_t& pos, + Temporal::timepos_t& pos, boost::shared_ptr instrument = boost::shared_ptr()); void get_regionview_corresponding_to (boost::shared_ptr region, std::vector& regions); @@ -477,15 +475,15 @@ public: TrackViewList axis_views_from_routes (boost::shared_ptr) const; - void snap_to (ARDOUR::MusicSample& first, + void snap_to (Temporal::timepos_t & first, ARDOUR::RoundMode direction = ARDOUR::RoundNearest, ARDOUR::SnapPref pref = ARDOUR::SnapToAny_Visual, bool ensure_snap = false); - void snap_to_with_modifier (ARDOUR::MusicSample& first, + void snap_to_with_modifier (Temporal::timepos_t & first, GdkEvent const* ev, ARDOUR::RoundMode direction = ARDOUR::RoundNearest, - ARDOUR::SnapPref pref = ARDOUR::SnapToAny_Visual); + ARDOUR::SnapPref gpref = ARDOUR::SnapToAny_Visual); void set_snapped_cursor_position (samplepos_t pos); @@ -729,7 +727,7 @@ private: void setup_lines (); void set_name (const std::string&); - void set_position (samplepos_t start, samplepos_t end = 0); + void set_position (Temporal::timepos_t const & start, Temporal::timepos_t const & end = Temporal::timepos_t()); void set_color_rgba (uint32_t); }; @@ -1393,8 +1391,8 @@ private: void bring_in_external_audio (Editing::ImportMode mode, samplepos_t& pos); - bool idle_drop_paths (std::vector paths, samplepos_t sample, double ypos, bool copy); - void drop_paths_part_two (const std::vector& paths, samplepos_t sample, double ypos, bool copy); + bool idle_drop_paths (std::vector paths, Temporal::timepos_t sample, double ypos, bool copy); + void drop_paths_part_two (const std::vector& paths, Temporal::timepos_t const & sample, double ypos, bool copy); int import_sndfiles (std::vector paths, Editing::ImportDisposition disposition, @@ -1977,7 +1975,7 @@ private: /* object rubberband select process */ - void select_all_within (samplepos_t, samplepos_t, double, double, TrackViewList const &, Selection::Operation, bool); + void select_all_within (Temporal::timepos_t const &, Temporal::timepos_t const &, double, double, TrackViewList const &, Selection::Operation, bool); ArdourCanvas::Rectangle* rubberband_rect; @@ -2081,7 +2079,7 @@ private: void external_edit_region (); int write_audio_selection (TimeSelection&); - bool write_audio_range (ARDOUR::AudioPlaylist&, const ARDOUR::ChanCount& channels, std::list&); + bool write_audio_range (ARDOUR::AudioPlaylist&, const ARDOUR::ChanCount& channels, std::list&); void write_selection (); @@ -2269,10 +2267,14 @@ private: ARDOUR::RoundMode direction, ARDOUR::SnapPref gpref); - void snap_to_internal (ARDOUR::MusicSample& first, - ARDOUR::RoundMode direction = ARDOUR::RoundNearest, - ARDOUR::SnapPref gpref = ARDOUR::SnapToAny_Visual, - bool ensure_snap = false); + void snap_to_internal (Temporal::timepos_t & first, + Temporal::RoundMode direction = Temporal::RoundNearest, + bool for_mark = false, + bool ensure_snap = false); + + void timecode_snap_to_internal (Temporal::timepos_t & first, + Temporal::RoundMode direction = Temporal::RoundNearest, + bool for_mark = false); samplepos_t snap_to_marker (samplepos_t presnap, ARDOUR::RoundMode direction = ARDOUR::RoundNearest); diff --git a/gtk2_ardour/editor_audio_import.cc b/gtk2_ardour/editor_audio_import.cc index c9a73d1917..7a766ca7a3 100644 --- a/gtk2_ardour/editor_audio_import.cc +++ b/gtk2_ardour/editor_audio_import.cc @@ -347,9 +347,9 @@ Editor::do_import (vector paths, SrcQuality quality, MidiTrackNameSource midi_track_name_source, MidiTempoMapDisposition smf_tempo_disposition, - samplepos_t& pos, + timepos_t& pos, ARDOUR::PluginInfoPtr instrument, - bool with_markers) + bool with_markers) { boost::shared_ptr track; vector to_import; @@ -502,11 +502,7 @@ Editor::do_import (vector paths, } void -Editor::do_embed (vector paths, - ImportDisposition import_as, - ImportMode mode, - samplepos_t& pos, - ARDOUR::PluginInfoPtr instrument) +Editor::do_embed (vector paths, ImportDisposition import_as, ImportMode mode, timepos_t& pos, ARDOUR::PluginInfoPtr instrument) { boost::shared_ptr track; bool check_sample_rate = true; diff --git a/gtk2_ardour/editor_canvas.cc b/gtk2_ardour/editor_canvas.cc index f9b87614f6..6dcad7f9a5 100644 --- a/gtk2_ardour/editor_canvas.cc +++ b/gtk2_ardour/editor_canvas.cc @@ -390,16 +390,17 @@ Editor::track_canvas_drag_data_received (const RefPtr& context } bool -Editor::idle_drop_paths (vector paths, samplepos_t sample, double ypos, bool copy) +Editor::idle_drop_paths (vector paths, timepos_t sample, double ypos, bool copy) { drop_paths_part_two (paths, sample, ypos, copy); return false; } void -Editor::drop_paths_part_two (const vector& paths, samplepos_t sample, double ypos, bool copy) +Editor::drop_paths_part_two (const vector& paths, timepos_t const & p, double ypos, bool copy) { RouteTimeAxisView* tv; + timepos_t pos (p); /* MIDI files must always be imported, because we consider them * writable. So split paths into two vectors, and follow the import @@ -423,13 +424,13 @@ Editor::drop_paths_part_two (const vector& paths, samplepos_t sample, do /* drop onto canvas background: create new tracks */ InstrumentSelector is; // instantiation builds instrument-list and sets default. - do_import (midi_paths, Editing::ImportDistinctFiles, ImportAsTrack, SrcBest, SMFTrackName, SMFTempoIgnore, sample, is.selected_instrument(), false); + do_import (midi_paths, Editing::ImportDistinctFiles, ImportAsTrack, SrcBest, SMFTrackName, SMFTempoIgnore, pos, is.selected_instrument(), false); if (UIConfiguration::instance().get_only_copy_imported_files() || copy) { do_import (audio_paths, Editing::ImportDistinctFiles, Editing::ImportAsTrack, - SrcBest, SMFTrackName, SMFTempoIgnore, sample); + SrcBest, SMFTrackName, SMFTempoIgnore, pos); } else { - do_embed (audio_paths, Editing::ImportDistinctFiles, ImportAsTrack, sample); + do_embed (audio_paths, Editing::ImportDistinctFiles, ImportAsTrack, pos); } } else if ((tv = dynamic_cast (tvp.first)) != 0) { @@ -441,13 +442,13 @@ Editor::drop_paths_part_two (const vector& paths, samplepos_t sample, do selection->set (tv); do_import (midi_paths, Editing::ImportSerializeFiles, ImportToTrack, - SrcBest, SMFTrackName, SMFTempoIgnore, sample); + SrcBest, SMFTrackName, SMFTempoIgnore, pos); if (UIConfiguration::instance().get_only_copy_imported_files() || copy) { do_import (audio_paths, Editing::ImportSerializeFiles, Editing::ImportToTrack, - SrcBest, SMFTrackName, SMFTempoIgnore, sample, boost::shared_ptr(), false); + SrcBest, SMFTrackName, SMFTempoIgnore, pos, boost::shared_ptr(), false); } else { - do_embed (audio_paths, Editing::ImportSerializeFiles, ImportToTrack, sample); + do_embed (audio_paths, Editing::ImportSerializeFiles, ImportToTrack, pos); } } } @@ -472,7 +473,7 @@ Editor::drop_paths (const RefPtr& context, ev.button.x = x; ev.button.y = y; - MusicSample when (window_event_sample (&ev, 0, &cy), 0); + timepos_t when (window_event_sample (&ev, 0, &cy)); snap_to (when); bool copy = ((context->get_actions() & (Gdk::ACTION_COPY | Gdk::ACTION_LINK | Gdk::ACTION_MOVE)) == Gdk::ACTION_COPY); @@ -483,7 +484,7 @@ Editor::drop_paths (const RefPtr& context, */ Glib::signal_idle().connect (sigc::bind (sigc::mem_fun (*this, &Editor::idle_drop_paths), paths, when.sample, cy, copy)); #else - drop_paths_part_two (paths, when.sample, cy, copy); + drop_paths_part_two (paths, when, cy, copy); #endif } @@ -602,15 +603,15 @@ Editor::autoscroll_active () const return autoscroll_connection.connected (); } -std::pair +std::pair Editor::session_gui_extents (bool use_extra) const { if (!_session) { - return std::pair (max_samplepos,0); + return std::make_pair (timepos_t::max (Temporal::AudioTime), timepos_t (0)); } - samplecnt_t session_extent_start = _session->current_start_sample(); - samplecnt_t session_extent_end = _session->current_end_sample(); + timepos_t session_extent_start (_session->current_start_sample()); + timepos_t session_extent_end (_session->current_end_sample()); /* calculate the extents of all regions in every playlist * NOTE: we should listen to playlists, and cache these values so we don't calculate them every time. @@ -619,13 +620,14 @@ Editor::session_gui_extents (bool use_extra) const boost::shared_ptr rl = _session->get_routes(); for (RouteList::iterator r = rl->begin(); r != rl->end(); ++r) { boost::shared_ptr tr = boost::dynamic_pointer_cast (*r); + if (!tr) { continue; } if (tr->presentation_info ().hidden ()) { continue; } - pair e = tr->playlist()->get_extent (); + pair e = tr->playlist()->get_extent (); if (e.first == e.second) { /* no regions present */ continue; @@ -641,19 +643,18 @@ Editor::session_gui_extents (bool use_extra) const if (use_extra) { samplecnt_t const extra = UIConfiguration::instance().get_extra_ui_extents_time() * 60 * _session->nominal_sample_rate(); session_extent_end += extra; - session_extent_start -= extra; + session_extent_start.shift_earlier (extra); } /* range-check */ - if (session_extent_end > max_samplepos) { - session_extent_end = max_samplepos; + if (session_extent_end >= timepos_t::max (Temporal::AudioTime)) { + session_extent_end = timepos_t::max (Temporal::AudioTime); } - if (session_extent_start < 0) { - session_extent_start = 0; + if (session_extent_start.negative()) { + session_extent_start = timepos_t (0); } - std::pair ret (session_extent_start, session_extent_end); - return ret; + return std::make_pair (session_extent_start, session_extent_end); } bool diff --git a/gtk2_ardour/editor_drag.cc b/gtk2_ardour/editor_drag.cc index 973f2a750e..b7e3673f4c 100644 --- a/gtk2_ardour/editor_drag.cc +++ b/gtk2_ardour/editor_drag.cc @@ -2026,7 +2026,7 @@ RegionMoveDrag::finished_no_copy ( rv->region()->set_position (where.sample, 0); } else { /* move by music offset */ - rv->region()->set_position_music (rv->region()->quarter_note() - qn_delta); + rv->region()->set_position (rv->region()->quarter_note() - qn_delta); } } _editor->session()->add_command (new StatefulDiffCommand (rv->region())); @@ -6091,7 +6091,7 @@ NoteDrag::aborted (bool) } /** Make an AutomationRangeDrag for lines in an AutomationTimeAxisView */ -AutomationRangeDrag::AutomationRangeDrag (Editor* editor, AutomationTimeAxisView* atv, list const & r) +AutomationRangeDrag::AutomationRangeDrag (Editor* editor, AutomationTimeAxisView* atv, list const & r) : Drag (editor, atv->base_item ()) , _ranges (r) , _y_origin (atv->y_position()) @@ -6103,7 +6103,7 @@ AutomationRangeDrag::AutomationRangeDrag (Editor* editor, AutomationTimeAxisView } /** Make an AutomationRangeDrag for region gain lines or MIDI controller regions */ -AutomationRangeDrag::AutomationRangeDrag (Editor* editor, list const & v, list const & r, double y_origin, double y_height) +AutomationRangeDrag::AutomationRangeDrag (Editor* editor, list const & v, list const & r, double y_origin, double y_height) : Drag (editor, v.front()->get_canvas_group ()) , _ranges (r) , _y_origin (y_origin) @@ -6151,8 +6151,8 @@ AutomationRangeDrag::setup (list > const & lin r.second = max_samplepos; } - /* check this range against all the AudioRanges that we are using */ - list::const_iterator k = _ranges.begin (); + /* check this range against all the TimelineRanges that we are using */ + list::const_iterator k = _ranges.begin (); while (k != _ranges.end()) { if (k->coverage (r.first, r.second) != Evoral::OverlapNone) { break; @@ -6228,7 +6228,7 @@ AutomationRangeDrag::motion (GdkEvent*, bool first_move) if (!_ranges.empty()) { /* add guard points */ - for (list::const_iterator i = _ranges.begin(); i != _ranges.end(); ++i) { + for (list::const_iterator i = _ranges.begin(); i != _ranges.end(); ++i) { samplecnt_t const half = (i->start + i->end) / 2; @@ -6308,7 +6308,7 @@ AutomationRangeDrag::motion (GdkEvent*, bool first_move) double const w = i->line->time_converter().to ((*p->model())->when) + i->line->time_converter().origin_b (); /* see if it's inside a range */ - list::const_iterator k = _ranges.begin (); + list::const_iterator k = _ranges.begin (); while (k != _ranges.end() && (k->start >= w || k->end <= w)) { ++k; } diff --git a/gtk2_ardour/editor_drag.h b/gtk2_ardour/editor_drag.h index 7ea94ff1be..372e8ad198 100644 --- a/gtk2_ardour/editor_drag.h +++ b/gtk2_ardour/editor_drag.h @@ -1310,8 +1310,8 @@ private: class AutomationRangeDrag : public Drag { public: - AutomationRangeDrag (Editor *, AutomationTimeAxisView *, std::list const &); - AutomationRangeDrag (Editor *, std::list const &, std::list const &, double y_origin, double y_height); + AutomationRangeDrag (Editor *, AutomationTimeAxisView *, std::list const &); + AutomationRangeDrag (Editor *, std::list const &, std::list const &, double y_origin, double y_height); void start_grab (GdkEvent *, Gdk::Cursor* c = 0); void motion (GdkEvent *, bool); @@ -1327,7 +1327,7 @@ private: double y_fraction (double global_y_position) const; double value (boost::shared_ptr list, double x) const; - std::list _ranges; + std::list _ranges; /** A line that is part of the drag */ struct Line { diff --git a/gtk2_ardour/editor_export_audio.cc b/gtk2_ardour/editor_export_audio.cc index 91ab3babd1..08110c2ee1 100644 --- a/gtk2_ardour/editor_export_audio.cc +++ b/gtk2_ardour/editor_export_audio.cc @@ -118,7 +118,7 @@ Editor::loudness_assistant (bool range_selection) samplepos_t start, end; TimeSelection const& ts (get_selection().time); if (range_selection && !ts.empty ()) { - start = ts.start(); + start = ts.start_sample(); end = ts.end_sample(); } else { start = _session->current_start_sample(); @@ -158,7 +158,7 @@ Editor::measure_master_loudness (samplepos_t start, samplepos_t end, bool is_ran return; } - ARDOUR::AudioRange ar (start, end, 0); + ARDOUR::TimelineRange ar (timepos_t (start), timepos_t (end), 0); LoudnessDialog ld (_session, ar, is_range_selection); @@ -320,9 +320,9 @@ Editor::bounce_region_selection (bool with_processing) boost::shared_ptr r; if (with_processing) { - r = track->bounce_range (region->position(), region->position() + region->length(), itt, track->main_outs(), false, bounce_name); + r = track->bounce_range (region->position_sample(), region->position_sample() + region->length_samples(), itt, track->main_outs(), false, bounce_name); } else { - r = track->bounce_range (region->position(), region->position() + region->length(), itt, boost::shared_ptr(), false, bounce_name); + r = track->bounce_range (region->position_sample(), region->position_sample() + region->length_samples(), itt, boost::shared_ptr(), false, bounce_name); } } } @@ -347,7 +347,7 @@ Editor::write_region (string path, boost::shared_ptr region) /* don't do duplicate of the entire source if that's what is going on here */ - if (region->start() == 0 && region->length() == region->source_length(0)) { + if (region->nt_start().zero() && region->nt_length() == region->source_length(0)) { /* XXX should link(2) to create a new inode with "path" */ return true; } @@ -396,8 +396,8 @@ Editor::write_region (string path, boost::shared_ptr region) } - to_read = region->length(); - pos = region->position(); + to_read = region->length_samples(); + pos = region->position_sample(); while (to_read) { samplepos_t this_time; @@ -475,14 +475,14 @@ Editor::write_audio_selection (TimeSelection& ts) } bool -Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list& range) +Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list& range) { boost::shared_ptr fs; const samplepos_t chunk_size = 4096; - samplepos_t nframes; + timecnt_t nframes; Sample buf[chunk_size]; gain_t gain_buffer[chunk_size]; - samplepos_t pos; + timepos_t pos; char s[PATH_MAX+1]; uint32_t cnt; string path; @@ -529,15 +529,14 @@ Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list } - for (list::iterator i = range.begin(); i != range.end();) { + for (list::iterator i = range.begin(); i != range.end();) { nframes = (*i).length(); - pos = (*i).start; + pos = (*i).start(); - while (nframes) { - samplepos_t this_time; + while (nframes.positive()) { - this_time = min (nframes, chunk_size); + timecnt_t this_time = min (nframes, timecnt_t (chunk_size)); for (uint32_t n=0; n < channels; ++n) { @@ -547,7 +546,7 @@ Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list break; } - if (fs->write (buf, this_time) != this_time) { + if (fs->write (buf, this_time.samples()) != this_time.samples()) { goto error_out; } } @@ -556,24 +555,24 @@ Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list pos += this_time; } - list::iterator tmp = i; + list::iterator tmp = i; ++tmp; if (tmp != range.end()) { /* fill gaps with silence */ - nframes = (*tmp).start - (*i).end; + nframes = (*i).end().distance ((*tmp).start()); - while (nframes) { + while (nframes.positive()) { - samplepos_t this_time = min (nframes, chunk_size); - memset (buf, 0, sizeof (Sample) * this_time); + timecnt_t this_time = min (nframes, timecnt_t (chunk_size)); + memset (buf, 0, sizeof (Sample) * this_time.samples()); for (uint32_t n=0; n < channels; ++n) { fs = sources[n]; - if (fs->write (buf, this_time) != this_time) { + if (fs->write (buf, this_time.samples()) != this_time.samples()) { goto error_out; } } diff --git a/gtk2_ardour/editor_keys.cc b/gtk2_ardour/editor_keys.cc index 9e86c615cc..1275b1e5af 100644 --- a/gtk2_ardour/editor_keys.cc +++ b/gtk2_ardour/editor_keys.cc @@ -46,27 +46,32 @@ using namespace Editing; void Editor::keyboard_selection_finish (bool /*add*/, Editing::EditIgnoreOption ign) { - if (_session) { - - MusicSample start (selection->time.start(), 0); - samplepos_t end; - if ((_edit_point == EditAtPlayhead) && _session->transport_rolling()) { - end = _session->audible_sample(); - } else { - end = get_preferred_edit_position(ign); - } - - //if no tracks are selected and we're working from the keyboard, enable all tracks (_something_ has to be selected for any range selection) - if ( (_edit_point == EditAtPlayhead) && selection->tracks.empty() ) - select_all_visible_lanes(); - - selection->set (start.sample, end); - - //if session is playing a range, cancel that - if (_session->get_play_range()) - _session->request_cancel_play_range(); - + if (!_session) { + return; } + + timepos_t start = selection->time.start_time(); + timepos_t end; + if ((_edit_point == EditAtPlayhead) && _session->transport_rolling()) { + end = _session->audible_sample(); + } else { + end = get_preferred_edit_position(ign); + } + + //snap the selection start/end + snap_to (start); + + //if no tracks are selected and we're working from the keyboard, enable all tracks (_something_ has to be selected for any range selection) + if ( (_edit_point == EditAtPlayhead) && selection->tracks.empty() ) + select_all_tracks(); + + selection->set (start, end); + + //if session is playing a range, cancel that + if (_session->get_play_range()) { + _session->request_cancel_play_range(); + } + } void @@ -74,22 +79,22 @@ Editor::keyboard_selection_begin (Editing::EditIgnoreOption ign) { if (_session) { - MusicSample start (0, 0); - MusicSample end (selection->time.end_sample(), 0); + timepos_t start; + timepos_t end (selection->time.end_time()); if ((_edit_point == EditAtPlayhead) && _session->transport_rolling()) { - start.sample = _session->audible_sample(); + start = _session->audible_sample(); } else { - start.sample = get_preferred_edit_position(ign); + start = get_preferred_edit_position(ign); } //if there's not already a sensible selection endpoint, go "forever" - if (start.sample > end.sample) { + if (start > end ) { #ifdef MIXBUS // 4hours at most. // This works around a visual glitch in red-bordered selection rect. - end.sample = start.sample + _session->nominal_sample_rate() * 60 * 60 * 4; + end = start + timepos_t (_session->nominal_sample_rate() * 60 * 60 * 4); #else - end.sample = max_samplepos; + end = timepos_t::max (end.time_domain()); #endif } @@ -97,7 +102,7 @@ Editor::keyboard_selection_begin (Editing::EditIgnoreOption ign) if ( selection->tracks.empty() ) select_all_visible_lanes(); - selection->set (start.sample, end.sample); + selection->set (start, end); //if session is playing a range, cancel that if (_session->get_play_range()) diff --git a/gtk2_ardour/editor_markers.cc b/gtk2_ardour/editor_markers.cc index 733639a75c..a334d32563 100644 --- a/gtk2_ardour/editor_markers.cc +++ b/gtk2_ardour/editor_markers.cc @@ -174,7 +174,7 @@ Editor::add_new_location_internal (Location* location) } location->name_changed.connect (*this, invalidator (*this), boost::bind (&Editor::location_changed, this, _1), gui_context()); - location->position_lock_style_changed.connect (*this, invalidator (*this), boost::bind (&Editor::location_changed, this, _1), gui_context()); + location->position_time_domain_changed.connect (*this, invalidator (*this), boost::bind (&Editor::location_changed, this, _1), gui_context()); location->FlagsChanged.connect (*this, invalidator (*this), boost::bind (&Editor::location_flags_changed, this, location), gui_context()); pair newpair; @@ -214,7 +214,7 @@ Editor::location_changed (Location *location) return; } - if (location->position_lock_style() == MusicTime) { + if (location->position_time_domain() == Temporal::BeatTime) { lam->set_name ("\u266B" + location->name ()); // BEAMED EIGHTH NOTES } else { lam->set_name (location->name ()); @@ -278,7 +278,7 @@ Editor::check_marker_label (ArdourMarker* m) /* Update just the available space between the previous marker and this one */ - double const p = sample_to_pixel (m->position() - (*prev)->position()); + double const p = sample_to_pixel ((*prev)->position().distance (m->position()).samples()); if (m->label_on_left()) { (*prev)->set_right_label_limit (p / 2); @@ -297,7 +297,7 @@ Editor::check_marker_label (ArdourMarker* m) /* Update just the available space between this marker and the next */ - double const p = sample_to_pixel ((*next)->position() - m->position()); + double const p = sample_to_pixel (m->position().distance ((*next)->position()).samples()); if ((*next)->label_on_left()) { m->set_right_label_limit (p / 2); @@ -354,7 +354,7 @@ Editor::update_marker_labels (ArdourCanvas::Container* group) while (i != sorted.end()) { if (prev != sorted.end()) { - double const p = sample_to_pixel ((*i)->position() - (*prev)->position()); + double const p = sample_to_pixel ((*prev)->position().distance ((*i)->position()).samples()); if ((*prev)->label_on_left()) { (*i)->set_left_label_limit (p); @@ -365,7 +365,7 @@ Editor::update_marker_labels (ArdourCanvas::Container* group) } if (next != sorted.end()) { - double const p = sample_to_pixel ((*next)->position() - (*i)->position()); + double const p = sample_to_pixel ((*i)->position().distance ((*next)->position()).samples()); if ((*next)->label_on_left()) { (*i)->set_right_label_limit (p / 2); @@ -613,12 +613,12 @@ Editor::LocationMarkers::set_name (const string& str) } void -Editor::LocationMarkers::set_position (samplepos_t startf, - samplepos_t endf) +Editor::LocationMarkers::set_position (timepos_t const & startt, + timepos_t const & endt) { - start->set_position (startf); - if (end) { - end->set_position (endf); + start->set_position (startt); + if (!endt.zero()) { + end->set_position (endt); } } @@ -678,7 +678,8 @@ Editor::mouse_add_new_marker (samplepos_t where, bool is_cd) if (!choose_new_marker_name(markername)) { return; } - Location *location = new Location (*_session, where, where, markername, (Location::Flags) flags, get_grid_music_divisions (0)); +#warning NUTEMPO how do we make the position be in musical time from a mouse event? + Location *location = new Location (*_session, timepos_t (where), timepos_t (where), markername, (Location::Flags) flags); begin_reversible_command (_("add marker")); XMLNode &before = _session->locations()->get_state(); @@ -745,7 +746,8 @@ Editor::mouse_add_new_range (samplepos_t where) string name; _session->locations()->next_available_name (name, _("range")); - Location* loc = new Location (*_session, where, end, name, Location::IsRangeMarker); +#warning NUTEMPO how do we get music time here from a mouse event? + Location* loc = new Location (*_session, timepos_t (where), timepos_t (end), name, Location::IsRangeMarker); begin_reversible_command (_("new range marker")); XMLNode& before = _session->locations()->get_state (); @@ -989,7 +991,7 @@ Editor::build_marker_menu (Location* loc) items.push_back (CheckMenuElem (_("Glue to Bars and Beats"))); Gtk::CheckMenuItem* glue_item = static_cast (&items.back()); - glue_item->set_active (loc->position_lock_style() == MusicTime); + glue_item->set_active (loc->position_time_domain() == Temporal::BeatTime); glue_item->signal_activate().connect (sigc::mem_fun (*this, &Editor::toggle_marker_menu_glue)); @@ -1025,7 +1027,7 @@ Editor::build_range_marker_menu (Location* loc, bool loop_or_punch, bool session items.push_back (CheckMenuElem (_("Glue to Bars and Beats"))); Gtk::CheckMenuItem* glue_item = static_cast (&items.back()); - glue_item->set_active (loc->position_lock_style() == MusicTime); + glue_item->set_active (loc->position_time_domain() == Temporal::BeatTime); glue_item->signal_activate().connect (sigc::mem_fun (*this, &Editor::toggle_marker_menu_glue)); items.push_back (SeparatorElem()); @@ -1202,7 +1204,7 @@ Editor::marker_menu_select_all_selectables_using_range () bool is_start; if (((l = find_location_from_marker (marker, is_start)) != 0) && (l->end() > l->start())) { - select_all_within (l->start(), l->end() - 1, 0, DBL_MAX, track_views, Selection::Set, false); + select_all_within (l->start(), l->end().decrement(), 0, DBL_MAX, track_views, Selection::Set, false); } } @@ -1242,15 +1244,15 @@ Editor::marker_menu_play_from () if ((l = find_location_from_marker (marker, is_start)) != 0) { if (l->is_mark()) { - _session->request_locate (l->start(), MustRoll); + _session->request_locate (l->start_sample(), MustRoll); } else { - //_session->request_bounded_roll (l->start(), l->end()); + //_session->request_bounded_roll (l->start_sample(), l->end()); if (is_start) { - _session->request_locate (l->start(), MustRoll); + _session->request_locate (l->start_sample(), MustRoll); } else { - _session->request_locate (l->end(), MustRoll); + _session->request_locate (l->end_sample(), MustRoll); } } } @@ -1272,13 +1274,13 @@ Editor::marker_menu_set_playhead () if ((l = find_location_from_marker (marker, is_start)) != 0) { if (l->is_mark()) { - _session->request_locate (l->start(), MustStop); + _session->request_locate (l->start_sample(), MustStop); } else { if (is_start) { - _session->request_locate (l->start(), MustStop); + _session->request_locate (l->start_sample(), MustStop); } else { - _session->request_locate (l->end(), MustStop); + _session->request_locate (l->end_sample(), MustStop); } } } @@ -1304,8 +1306,8 @@ Editor::marker_menu_range_to_next () return; } - samplepos_t start; - samplepos_t end; + timepos_t start; + timepos_t end; _session->locations()->marks_either_side (marker->position(), start, end); if (end != max_samplepos) { @@ -1329,18 +1331,19 @@ Editor::marker_menu_set_from_playhead () Location* l; bool is_start; - const int32_t divisions = get_grid_music_divisions (0); if ((l = find_location_from_marker (marker, is_start)) != 0) { +#warning NUTEMPO what if the user wants musical time here? + if (l->is_mark()) { - l->set_start (_session->audible_sample (), false, true, divisions); + l->set_start (timepos_t (_session->audible_sample ()), false); } else { if (is_start) { - l->set_start (_session->audible_sample (), false, true, divisions); + l->set_start (timepos_t (_session->audible_sample ()), false); } else { - l->set_end (_session->audible_sample (), false, true, divisions); + l->set_end (timepos_t (_session->audible_sample ()), false); } } } @@ -1368,9 +1371,9 @@ Editor::marker_menu_set_from_selection (bool /*force_regions*/) } else { if (!selection->time.empty()) { - l->set (selection->time.start(), selection->time.end_sample()); + l->set (selection->time.start_time(), selection->time.end_time()); } else if (!selection->regions.empty()) { - l->set (selection->regions.start(), selection->regions.end_sample()); + l->set (selection->regions.start_time(), selection->regions.end_time()); } } } @@ -1393,10 +1396,10 @@ Editor::marker_menu_play_range () if ((l = find_location_from_marker (marker, is_start)) != 0) { if (l->is_mark()) { - _session->request_locate (l->start(), MustRoll); + _session->request_locate (l->start().samples(), MustRoll); } else { - _session->request_bounded_roll (l->start(), l->end()); + _session->request_bounded_roll (l->start().samples(), l->end().samples()); } } @@ -1418,7 +1421,7 @@ Editor::marker_menu_loop_range () if ((l = find_location_from_marker (marker, is_start)) != 0) { if (l != transport_loop_location()) { cerr << "Set loop\n"; - set_loop_range (l->start(), l->end(), _("loop range from marker")); + set_loop_range (l->start().samples(), l->end().samples(), _("loop range from marker")); } else { cerr << " at TL\n"; } @@ -1439,18 +1442,18 @@ Editor::marker_menu_zoom_to_range () return; } - samplecnt_t const extra = l->length() * 0.05; - samplepos_t a = l->start (); - if (a >= extra) { - a -= extra; + timecnt_t const extra = l->length() * Temporal::ratio_t (5, 100); + timepos_t a = l->start (); + if (a >= timepos_t (extra)) { + a.shift_earlier (extra); } - samplepos_t b = l->end (); - if (b < (max_samplepos - extra)) { + timepos_t b = l->end (); + if (b < (extra.distance (timepos_t::max (extra.time_domain())))) { b += extra; } - temporal_zoom_by_sample (a, b); + temporal_zoom_by_sample (a.samples(), b.samples()); } void diff --git a/gtk2_ardour/editor_mouse.cc b/gtk2_ardour/editor_mouse.cc index 374cd09e76..14ce6f4665 100644 --- a/gtk2_ardour/editor_mouse.cc +++ b/gtk2_ardour/editor_mouse.cc @@ -1236,7 +1236,7 @@ Editor::button_press_handler_1 (ArdourCanvas::Item* item, GdkEvent* event, ItemT if (boost::dynamic_pointer_cast (playlist) == 0) { continue; } - for (list::const_iterator j = selection->time.begin(); j != selection->time.end(); ++j) { + for (list::const_iterator j = selection->time.begin(); j != selection->time.end(); ++j) { boost::shared_ptr rl = playlist->regions_touched (j->start, j->end); for (RegionList::iterator ir = rl->begin(); ir != rl->end(); ++ir) { RegionView* rv; diff --git a/gtk2_ardour/editor_ops.cc b/gtk2_ardour/editor_ops.cc index c9350eb546..c5cb840fb0 100644 --- a/gtk2_ardour/editor_ops.cc +++ b/gtk2_ardour/editor_ops.cc @@ -2723,8 +2723,8 @@ Editor::play_selection () if (!get_selection_extents (start, end)) return; - AudioRange ar (start, end, 0); - list lar; + TimelineRange ar (start, end, 0); + list lar; lar.push_back (ar); _session->request_play_range (&lar, true); @@ -2767,8 +2767,8 @@ Editor::play_with_preroll () end = end + preroll; //"post-roll" - AudioRange ar (start, end, 0); - list lar; + TimelineRange ar (start, end, 0); + list lar; lar.push_back (ar); _session->request_play_range (&lar, true); @@ -3152,10 +3152,10 @@ Editor::new_region_from_selection () } static void -add_if_covered (RegionView* rv, const AudioRange* ar, RegionSelection* rs) +add_if_covered (RegionView* rv, const TimelineRange* ar, RegionSelection* rs) { switch (rv->region()->coverage (ar->start, ar->end - 1)) { - // n.b. -1 because AudioRange::end is one past the end, but coverage expects inclusive ranges + // n.b. -1 because TimelineRange::end is one past the end, but coverage expects inclusive ranges case Evoral::OverlapNone: break; default: @@ -3229,7 +3229,7 @@ Editor::separate_regions_between (const TimeSelection& ts) /* XXX need to consider musical time selections here at some point */ - for (list::const_iterator t = ts.begin(); t != ts.end(); ++t) { + for (list::const_iterator t = ts.begin(); t != ts.end(); ++t) { if (!in_command) { begin_reversible_command (_("separate")); @@ -3313,7 +3313,7 @@ Editor::separate_region_from_selection () if (get_edit_op_range (start, end)) { - AudioRange ar (start, end, 1); + TimelineRange ar (start, end, 1); TimeSelection ts; ts.push_back (ar); @@ -3347,7 +3347,7 @@ Editor::separate_regions_using_location (Location& loc) return; } - AudioRange ar (loc.start(), loc.end(), 1); + TimelineRange ar (loc.start(), loc.end(), 1); TimeSelection ts; ts.push_back (ar); @@ -3437,7 +3437,7 @@ Editor::crop_region_to_selection () if (!selection->time.empty()) { begin_reversible_command (_("Crop Regions to Time Selection")); - for (std::list::iterator i = selection->time.begin(); i != selection->time.end(); ++i) { + for (std::list::iterator i = selection->time.begin(); i != selection->time.end(); ++i) { crop_region_to ((*i).start, (*i).end); } commit_reversible_command(); @@ -4207,8 +4207,8 @@ Editor::bounce_range_selection (bool replace, bool enable_processing) if (replace) { /*remove the edxisting regions under the edit range*/ - list ranges; - ranges.push_back (AudioRange (start, start+cnt, 0)); + list ranges; + ranges.push_back (TimelineRange (start, start+cnt, 0)); playlist->cut (ranges); // discard result /*SPECIAL CASE: we are bouncing to a new Source *AND* replacing the existing range on the timeline (consolidate)*/ @@ -8163,8 +8163,8 @@ Editor::remove_time (samplepos_t pos, samplecnt_t samples, InsertTimeOption opt, in_command = true; } - std::list rl; - AudioRange ar(pos, pos+samples, 0); + std::list rl; + TimelineRange ar(pos, pos+samples, 0); rl.push_back(ar); pl->cut (rl); pl->shift (pos, -samples, true, ignore_music_glue); diff --git a/gtk2_ardour/editor_regions.cc b/gtk2_ardour/editor_regions.cc index 3c924ba745..b6cb867106 100644 --- a/gtk2_ardour/editor_regions.cc +++ b/gtk2_ardour/editor_regions.cc @@ -601,10 +601,11 @@ EditorRegions::clock_format_changed () } void -EditorRegions::format_position (samplepos_t pos, char* buf, size_t bufsize, bool onoff) +EditorRegions::format_position (timepos_t const & p, char* buf, size_t bufsize, bool onoff) { Temporal::BBT_Time bbt; Timecode::Time timecode; + samplepos_t pos (p.samples()); if (pos < 0) { error << string_compose (_ ("EditorRegions::format_position: negative timecode position: %1"), pos) << endmsg; @@ -713,7 +714,7 @@ EditorRegions::populate_row (boost::shared_ptr region, TreeModel::Row co if (all || what_changed.contains (Properties::locked)) { populate_row_locked (region, row); } - if (all || what_changed.contains (Properties::position_lock_style)) { + if (all || what_changed.contains (Properties::time_domain)) { populate_row_glued (region, row); } if (all || what_changed.contains (Properties::muted)) { @@ -775,7 +776,7 @@ EditorRegions::populate_row_length (boost::shared_ptr region, TreeModel: Temporal::BBT_Time bbt = map.bbt_at_beat (map.beat_at_sample (region->last_sample ()) - map.beat_at_sample (region->first_sample ())); snprintf (buf, sizeof (buf), "%03d|%02d|%04d", bbt.bars, bbt.beats, bbt.ticks); } else { - format_position (region->length (), buf, sizeof (buf)); + format_position (timepos_t (region->nt_length ()), buf, sizeof (buf)); } row[_columns.length] = buf; @@ -790,7 +791,7 @@ EditorRegions::populate_row_end (boost::shared_ptr region, TreeModel::Ro if (region->last_sample () >= region->first_sample ()) { char buf[16]; - format_position (region->last_sample (), buf, sizeof (buf)); + format_position (region->nt_last (), buf, sizeof (buf)); row[_columns.end] = buf; } else { row[_columns.end] = "empty"; @@ -800,10 +801,10 @@ EditorRegions::populate_row_end (boost::shared_ptr region, TreeModel::Ro void EditorRegions::populate_row_position (boost::shared_ptr region, TreeModel::Row const& row) { - row[_columns.position] = region->position (); + row[_columns.position] = region->nt_position (); char buf[16]; - format_position (region->position (), buf, sizeof (buf)); + format_position (region->nt_position (), buf, sizeof (buf)); row[_columns.start] = buf; } @@ -813,7 +814,7 @@ EditorRegions::populate_row_sync (boost::shared_ptr region, TreeModel::R #ifndef SHOW_REGION_EXTRAS return; #endif - if (region->sync_position () == region->position ()) { + if (region->sync_position () == region->nt_position ()) { row[_columns.sync] = _ ("Start"); } else if (region->sync_position () == (region->last_sample ())) { row[_columns.sync] = _ ("End"); @@ -863,7 +864,7 @@ EditorRegions::populate_row_locked (boost::shared_ptr region, TreeModel: void EditorRegions::populate_row_glued (boost::shared_ptr region, TreeModel::Row const& row) { - if (region->position_lock_style () == MusicTime) { + if (region->position_time_domain () == Temporal::BeatTime) { row[_columns.glued] = true; } else { row[_columns.glued] = false; @@ -890,7 +891,7 @@ EditorRegions::populate_row_name (boost::shared_ptr region, TreeModel::R if (region->data_type() == DataType::MIDI) { row[_columns.channels] = 0; /*TODO: some better recognition of midi regions*/ } else { - row[_columns.channels] = region->n_channels(); + row[_columns.channels] = region->sources().size(); } row[_columns.tags] = region->tags (); @@ -1027,8 +1028,8 @@ EditorRegions::drag_data_received (const RefPtr& context, } if (_editor->convert_drop_to_paths (paths, context, x, y, data, info, dtime) == 0) { - samplepos_t pos = 0; - bool copy = ((context->get_actions () & (Gdk::ACTION_COPY | Gdk::ACTION_LINK | Gdk::ACTION_MOVE)) == Gdk::ACTION_COPY); + timepos_t pos; + bool copy = ((context->get_actions () & (Gdk::ACTION_COPY | Gdk::ACTION_LINK | Gdk::ACTION_MOVE)) == Gdk::ACTION_COPY); if (UIConfiguration::instance ().get_only_copy_imported_files () || copy) { _editor->do_import (paths, Editing::ImportDistinctFiles, Editing::ImportAsRegion, @@ -1232,7 +1233,7 @@ EditorRegions::glued_changed (std::string const& path) boost::shared_ptr region = (*i)[_columns.region]; if (region) { /* `glued' means MusicTime, and we're toggling here */ - region->set_position_lock_style ((*i)[_columns.glued] ? AudioTime : MusicTime); + region->set_position_time_domain ((*i)[_columns.glued] ? Temporal::AudioTime : Temporal::BeatTime); } } } diff --git a/gtk2_ardour/editor_regions.h b/gtk2_ardour/editor_regions.h index b1ef05ec15..a2475f70fd 100644 --- a/gtk2_ardour/editor_regions.h +++ b/gtk2_ardour/editor_regions.h @@ -99,7 +99,7 @@ private: Gtk::TreeModelColumn name; Gtk::TreeModelColumn channels; Gtk::TreeModelColumn tags; - Gtk::TreeModelColumn position; + Gtk::TreeModelColumn position; Gtk::TreeModelColumn start; Gtk::TreeModelColumn end; Gtk::TreeModelColumn length; @@ -158,7 +158,7 @@ private: void show_context_menu (int button, int time); - void format_position (ARDOUR::samplepos_t pos, char* buf, size_t bufsize, bool onoff = true); + void format_position (Temporal::timepos_t const & pos, char* buf, size_t bufsize, bool onoff = true); void add_region (boost::shared_ptr); void destroy_region (boost::shared_ptr); diff --git a/gtk2_ardour/editor_summary.cc b/gtk2_ardour/editor_summary.cc index d29c3a2a02..4409c46fbc 100644 --- a/gtk2_ardour/editor_summary.cc +++ b/gtk2_ardour/editor_summary.cc @@ -149,9 +149,9 @@ EditorSummary::render_background_image () /* compute start and end points for the summary */ - std::pair ext = _editor->session_gui_extents(); - double theoretical_start = ext.first; - double theoretical_end = ext.second; + std::pair ext = _editor->session_gui_extents(); + double theoretical_start = ext.first.samples(); + double theoretical_end = ext.second.samples(); /* the summary should encompass the full extent of everywhere we've visited since the session was opened */ if (_leftmost < theoretical_start) @@ -337,14 +337,14 @@ EditorSummary::render_region (RegionView* r, cairo_t* cr, double y) const uint32_t const c = r->get_fill_color (); cairo_set_source_rgb (cr, UINT_RGBA_R (c) / 255.0, UINT_RGBA_G (c) / 255.0, UINT_RGBA_B (c) / 255.0); - if (r->region()->position() > _start) { - cairo_move_to (cr, (r->region()->position() - _start) * _x_scale, y); + if (r->region()->position_sample() > _start) { + cairo_move_to (cr, (r->region()->position_sample() - _start) * _x_scale, y); } else { cairo_move_to (cr, 0, y); } - if ((r->region()->position() + r->region()->length()) > _start) { - cairo_line_to (cr, ((r->region()->position() - _start + r->region()->length())) * _x_scale, y); + if ((r->region()->nt_position() + r->region()->nt_length()) > _start) { + cairo_line_to (cr, ((r->region()->position_sample() - _start + r->region()->length_samples())) * _x_scale, y); } else { cairo_line_to (cr, 0, y); } diff --git a/gtk2_ardour/editor_videotimeline.cc b/gtk2_ardour/editor_videotimeline.cc index 48b46cbe89..421b8b3d5b 100644 --- a/gtk2_ardour/editor_videotimeline.cc +++ b/gtk2_ardour/editor_videotimeline.cc @@ -103,7 +103,7 @@ Editor::embed_audio_from_video (std::string path, samplepos_t n, bool lock_posit if (ok && track) { if (lock_position_to_video) { boost::shared_ptr pl = track->playlist(); - pl->find_next_region(n, ARDOUR::End, 0)->set_video_locked(true); + pl->find_next_region (Temporal::timepos_t (n), ARDOUR::End, 0)->set_video_locked (true); } _session->save_state ("", true); } diff --git a/gtk2_ardour/loudness_dialog.cc b/gtk2_ardour/loudness_dialog.cc index 9baad02161..1d09350f30 100644 --- a/gtk2_ardour/loudness_dialog.cc +++ b/gtk2_ardour/loudness_dialog.cc @@ -58,7 +58,7 @@ using namespace ArdourWidgets; bool LoudnessDialog::_first_time = true; CLoudnessPreset LoudnessDialog::_last_preset; -LoudnessDialog::LoudnessDialog (Session* s, AudioRange const& ar, bool as) +LoudnessDialog::LoudnessDialog (Session* s, TimelineRange const& ar, bool as) : ArdourDialog (as ? _("Loudness Assistant") : _("Loudness Analyzer and Normalizer")) , _lp (false) , _session (s) diff --git a/gtk2_ardour/loudness_dialog.h b/gtk2_ardour/loudness_dialog.h index 0780f7bb9d..eb6c0e20d7 100644 --- a/gtk2_ardour/loudness_dialog.h +++ b/gtk2_ardour/loudness_dialog.h @@ -36,7 +36,7 @@ #include "loudness_settings.h" namespace ARDOUR { - class AudioRange; + class TimelineRange; class ExportAnalysis; class ExportStatus; class PluginInsert; @@ -47,7 +47,7 @@ namespace ARDOUR { class LoudnessDialog : public ArdourDialog { public: - LoudnessDialog (ARDOUR::Session*, ARDOUR::AudioRange const&, bool); + LoudnessDialog (ARDOUR::Session*, ARDOUR::TimelineRange const&, bool); int run (); float gain_db () const; @@ -86,7 +86,7 @@ private: static CLoudnessPreset _last_preset; ARDOUR::Session* _session; - ARDOUR::AudioRange const& _range; + ARDOUR::TimelineRange const& _range; boost::shared_ptr _status; bool _autostart; diff --git a/gtk2_ardour/luainstance.cc b/gtk2_ardour/luainstance.cc index 89ecd92d61..039ea86016 100644 --- a/gtk2_ardour/luainstance.cc +++ b/gtk2_ardour/luainstance.cc @@ -852,7 +852,7 @@ LuaInstance::register_classes (lua_State* L) .addFunction ("regionlist", &RegionSelection::regionlist) // XXX check windows binding (libardour) .endClass () - .deriveClass > ("TimeSelection") + .deriveClass > ("TimeSelection") .addFunction ("start", &TimeSelection::start) .addFunction ("end_sample", &TimeSelection::end_sample) .addFunction ("length", &TimeSelection::length) diff --git a/gtk2_ardour/marker.cc b/gtk2_ardour/marker.cc index 21893ff7b9..1c55a1aaec 100644 --- a/gtk2_ardour/marker.cc +++ b/gtk2_ardour/marker.cc @@ -71,7 +71,7 @@ void ArdourMarker::setup_sizes(const double timebar_height) } ArdourMarker::ArdourMarker (PublicEditor& ed, ArdourCanvas::Container& parent, guint32 rgba, const string& annotation, - Type type, samplepos_t sample, bool handle_events, RegionView* rv) + Type type, timepos_t const & pos, bool handle_events, RegionView* rc) : editor (ed) , _parent (&parent) @@ -267,8 +267,8 @@ ArdourMarker::ArdourMarker (PublicEditor& ed, ArdourCanvas::Container& parent, g } - sample_position = sample; - unit_position = editor.sample_to_pixel (sample); + _position = pos; + unit_position = editor.sample_to_pixel (pos.samples()); unit_position -= _shift; group = new ArdourCanvas::Container (&parent, ArdourCanvas::Duple (unit_position, 1)); @@ -530,18 +530,18 @@ ArdourMarker::setup_name_display () } void -ArdourMarker::set_position (samplepos_t sample) +ArdourMarker::set_position (timepos_t const & pos) { - unit_position = editor.sample_to_pixel (sample) - _shift; + unit_position = editor.sample_to_pixel (pos.samples()) - _shift; group->set_x_position (unit_position); setup_line (); - sample_position = sample; + _position = pos; } void ArdourMarker::reposition () { - set_position (sample_position); + set_position (_position); } void @@ -633,7 +633,9 @@ ArdourMarker::set_right_label_limit (double p) TempoMarker::TempoMarker (PublicEditor& editor, ArdourCanvas::Container& parent, guint32 rgba, const string& text, ARDOUR::TempoSection& temp) - : ArdourMarker (editor, parent, rgba, text, Tempo, temp.sample(), false), +#warning NUTEMPO needs new tempo map +// : ArdourMarker (editor, parent, rgba, text, Tempo, temp.sample(), false), + : ArdourMarker (editor, parent, rgba, text, Tempo, timepos_t (), false), _tempo (temp) { group->Event.connect (sigc::bind (sigc::mem_fun (editor, &PublicEditor::canvas_tempo_marker_event), group, this)); @@ -667,7 +669,10 @@ TempoMarker::update_height_mark (const double ratio) MeterMarker::MeterMarker (PublicEditor& editor, ArdourCanvas::Container& parent, guint32 rgba, const string& text, ARDOUR::MeterSection& m) - : ArdourMarker (editor, parent, rgba, text, Meter, m.sample(), false), + +#warning NUTEMPO needs new tempo map +// : ArdourMarker (editor, parent, rgba, text, Meter, m.sample(), false), + : ArdourMarker (editor, parent, rgba, text, Meter, timepos_t(), false), _meter (m) { group->Event.connect (sigc::bind (sigc::mem_fun (editor, &PublicEditor::canvas_meter_marker_event), group, this)); diff --git a/gtk2_ardour/marker.h b/gtk2_ardour/marker.h index d2dc0c8ebc..6b51ecae85 100644 --- a/gtk2_ardour/marker.h +++ b/gtk2_ardour/marker.h @@ -67,8 +67,8 @@ public: ArdourMarker (PublicEditor& editor, ArdourCanvas::Container &, guint32 rgba, const std::string& text, Type, - samplepos_t sample = 0, bool handle_events = true, RegionView* rv = 0); - + ARDOUR::timepos_t const & position, bool handle_events = true, RegionView* rv = 0); + virtual ~ArdourMarker (); static PBD::Signal1 CatchDeletion; @@ -82,13 +82,13 @@ public: void set_show_line (bool); void set_line_height (double); - void set_position (samplepos_t); + void set_position (Temporal::timepos_t const &); void set_name (const std::string&); void set_points_color (uint32_t rgba); void set_color_rgba (uint32_t rgba); void setup_line (); - samplepos_t position() const { return sample_position; } + ARDOUR::timepos_t position() const { return _position; } ArdourCanvas::Container * get_parent() { return _parent; } void reparent (ArdourCanvas::Container & parent); @@ -126,7 +126,7 @@ protected: std::string _name; double unit_position; - samplepos_t sample_position; + ARDOUR::timepos_t _position; double _shift; Type _type; int name_height; diff --git a/gtk2_ardour/midi_automation_line.h b/gtk2_ardour/midi_automation_line.h index b233aed04e..72f9108baa 100644 --- a/gtk2_ardour/midi_automation_line.h +++ b/gtk2_ardour/midi_automation_line.h @@ -33,8 +33,7 @@ public: MidiAutomationLine (const std::string&, TimeAxisView&, ArdourCanvas::Item&, boost::shared_ptr, boost::shared_ptr, - Evoral::Parameter, - Evoral::TimeConverter* converter = 0); + Evoral::Parameter); MementoCommandBinder* memento_command_binder (); diff --git a/gtk2_ardour/midi_region_view.cc b/gtk2_ardour/midi_region_view.cc index 46b9235e83..cef7ab33ee 100644 --- a/gtk2_ardour/midi_region_view.cc +++ b/gtk2_ardour/midi_region_view.cc @@ -2834,46 +2834,6 @@ MidiRegionView::get_end_position_pixels() return trackview.editor().sample_to_pixel(sample); } -samplepos_t -MidiRegionView::source_beats_to_absolute_samples(Temporal::Beats beats) const -{ - /* the time converter will return the sample corresponding to `beats' - relative to the start of the source. The start of the source - is an implied position given by region->position - region->start - */ - const samplepos_t source_start = _region->position() - _region->start(); - return source_start + _source_relative_time_converter.to (beats); -} - -Temporal::Beats -MidiRegionView::absolute_samples_to_source_beats(samplepos_t samples) const -{ - /* the `samples' argument needs to be converted into a sample count - relative to the start of the source before being passed in to the - converter. - */ - const samplepos_t source_start = _region->position() - _region->start(); - return _source_relative_time_converter.from (samples - source_start); -} - -samplepos_t -MidiRegionView::region_beats_to_region_samples(Temporal::Beats beats) const -{ - return _region_relative_time_converter.to(beats); -} - -Temporal::Beats -MidiRegionView::region_samples_to_region_beats(samplepos_t samples) const -{ - return _region_relative_time_converter.from(samples); -} - -double -MidiRegionView::region_samples_to_region_beats_double (samplepos_t samples) const -{ - return _region_relative_time_converter_double.from(samples); -} - void MidiRegionView::begin_resizing (bool /*at_front*/) { diff --git a/gtk2_ardour/midi_region_view.h b/gtk2_ardour/midi_region_view.h index dfa11d568f..e41bbe1b66 100644 --- a/gtk2_ardour/midi_region_view.h +++ b/gtk2_ardour/midi_region_view.h @@ -271,46 +271,13 @@ public: */ double snap_to_pixel(double x, bool ensure_snap = false); - /** Snap a region relative pixel coordinate to sample units. + /** Snap a region relative pixel coordinate to time units. * @param x a pixel coordinate relative to region start * @param ensure_snap ignore SnapOff and magnetic snap. * Required for inverting snap logic with modifier keys and snap delta calculation. - * @return the snapped samplepos_t coordinate relative to region start + * @return the snapped timepos_t coordinate relative to region start */ - samplepos_t snap_pixel_to_sample(double x, bool ensure_snap = false); - - /** Convert a timestamp in beats into samples (both relative to region position) */ - samplepos_t region_beats_to_region_samples(Temporal::Beats beats) const; - /** Convert a timestamp in beats into absolute samples */ - samplepos_t region_beats_to_absolute_samples(Temporal::Beats beats) const { - return _region->position() + region_beats_to_region_samples (beats); - } - /** Convert a timestamp in samples to beats (both relative to region position) */ - Temporal::Beats region_samples_to_region_beats(samplepos_t) const; - double region_samples_to_region_beats_double(samplepos_t) const; - - /** Convert a timestamp in beats measured from source start into absolute samples */ - samplepos_t source_beats_to_absolute_samples(Temporal::Beats beats) const; - /** Convert a timestamp in beats measured from source start into region-relative samples */ - samplepos_t source_beats_to_region_samples(Temporal::Beats beats) const { - return source_beats_to_absolute_samples (beats) - _region->position(); - } - /** Convert a timestamp in absolute samples to beats measured from source start*/ - Temporal::Beats absolute_samples_to_source_beats(samplepos_t) const; - - ARDOUR::BeatsSamplesConverter const & region_relative_time_converter () const { - return _region_relative_time_converter; - } - - ARDOUR::BeatsSamplesConverter const & source_relative_time_converter () const { - return _source_relative_time_converter; - } - - ARDOUR::BeatsSamplesConverter const & region_relative_time_converter_double () const { - return _region_relative_time_converter; - } - - double session_relative_qn (double qn) const; + Temporal::timepos_t snap_pixel_to_time (double x, bool ensure_snap = false); void goto_previous_note (bool add_to_selection); void goto_next_note (bool add_to_selection); diff --git a/gtk2_ardour/midi_time_axis.h b/gtk2_ardour/midi_time_axis.h index 5458d74bf5..10c3de96c4 100644 --- a/gtk2_ardour/midi_time_axis.h +++ b/gtk2_ardour/midi_time_axis.h @@ -95,7 +95,7 @@ public: void get_regions_with_selected_data (RegionSelection&); - bool paste (ARDOUR::samplepos_t, const Selection&, PasteContext& ctx, const int32_t sub_num); + bool paste (Temporal::timepos_t const &, const Selection&, PasteContext& ctx); ARDOUR::NoteMode note_mode() const { return _note_mode; } ARDOUR::ColorMode color_mode() const { return _color_mode; } diff --git a/gtk2_ardour/mixer_ui.cc b/gtk2_ardour/mixer_ui.cc index be1af288f8..ccab7a0859 100644 --- a/gtk2_ardour/mixer_ui.cc +++ b/gtk2_ardour/mixer_ui.cc @@ -984,7 +984,7 @@ Mixer_UI::fan_out (boost::weak_ptr wr, bool to_busses, bool group) boost::shared_ptr msac = route->master_send_enable_controllable (); if (msac) { - msac->start_touch (msac->session().transport_sample()); + msac->start_touch (timepos_t (msac->session().transport_sample())); msac->set_value (0, PBD::Controllable::NoGroup); } @@ -3635,7 +3635,7 @@ Mixer_UI::control_action (boost::shared_ptr (Stripable::*get_control)() const if (s) { ac = (s.get()->*get_control)(); if (ac) { - ac->start_touch (_session->audible_sample ()); + ac->start_touch (timepos_t (_session->audible_sample ())); cl->push_back (ac); if (!have_val) { val = !ac->get_value(); diff --git a/gtk2_ardour/public_editor.h b/gtk2_ardour/public_editor.h index a6027b953b..ed3c22b3bd 100644 --- a/gtk2_ardour/public_editor.h +++ b/gtk2_ardour/public_editor.h @@ -152,7 +152,7 @@ public: * Snap a value according to the current snap setting. * ensure_snap overrides SnapOff and magnetic snap */ - virtual void snap_to (ARDOUR::MusicSample& first, + virtual void snap_to (Temporal::timepos_t & first, ARDOUR::RoundMode direction = ARDOUR::RoundNearest, ARDOUR::SnapPref gpref = ARDOUR::SnapToAny_Visual, bool ensure_snap = false) = 0; @@ -261,10 +261,10 @@ public: /** Import existing media */ virtual void do_import (std::vector paths, Editing::ImportDisposition, Editing::ImportMode mode, ARDOUR::SrcQuality, - ARDOUR::MidiTrackNameSource, ARDOUR::MidiTempoMapDisposition, samplepos_t&, + ARDOUR::MidiTrackNameSource, ARDOUR::MidiTempoMapDisposition, Temporal::timepos_t&, boost::shared_ptr instrument = boost::shared_ptr(), bool with_markers = false) = 0; - virtual void do_embed (std::vector paths, Editing::ImportDisposition, Editing::ImportMode mode, samplepos_t&, + virtual void do_embed (std::vector paths, Editing::ImportDisposition, Editing::ImportMode mode, Temporal::timepos_t&, boost::shared_ptr instrument = boost::shared_ptr()) = 0; /** Open main export dialog */ @@ -357,10 +357,10 @@ public: virtual void mouse_add_new_marker (samplepos_t where, bool is_cd=false) = 0; virtual void foreach_time_axis_view (sigc::slot) = 0; virtual void add_to_idle_resize (TimeAxisView*, int32_t) = 0; - virtual samplecnt_t get_nudge_distance (samplepos_t pos, samplecnt_t& next) = 0; - virtual samplecnt_t get_paste_offset (samplepos_t pos, unsigned paste_count, samplecnt_t duration) = 0; - virtual unsigned get_grid_beat_divisions(samplepos_t position) = 0; - virtual Temporal::Beats get_grid_type_as_beats (bool& success, samplepos_t position) = 0; + virtual Temporal::timecnt_t get_nudge_distance (Temporal::timepos_t const & pos, Temporal::timecnt_t& next) = 0; + virtual Temporal::timecnt_t get_paste_offset (Temporal::timepos_t const & pos, unsigned paste_count, Temporal::timecnt_t const & duration) = 0; + virtual unsigned get_grid_beat_divisions(Temporal::timepos_t const & position) = 0; + virtual Temporal::Beats get_grid_type_as_beats (bool& success, Temporal::timepos_t const & position) = 0; virtual int32_t get_grid_music_divisions (uint32_t event_state) = 0; virtual void edit_notes (MidiRegionView*) = 0; @@ -496,7 +496,7 @@ public: virtual ARDOUR::Location* find_location_from_marker (ArdourMarker*, bool&) const = 0; virtual ArdourMarker* find_marker_from_location_id (PBD::ID const&, bool) const = 0; - virtual void snap_to_with_modifier (ARDOUR::MusicSample& first, + virtual void snap_to_with_modifier (Temporal::timepos_t & first, GdkEvent const* ev, ARDOUR::RoundMode direction = ARDOUR::RoundNearest, ARDOUR::SnapPref gpref = ARDOUR::SnapToAny_Visual) = 0; diff --git a/gtk2_ardour/quantize_dialog.cc b/gtk2_ardour/quantize_dialog.cc index 9593c58c48..49636dab7e 100644 --- a/gtk2_ardour/quantize_dialog.cc +++ b/gtk2_ardour/quantize_dialog.cc @@ -153,7 +153,7 @@ QuantizeDialog::grid_size_to_musical_time (const string& txt) const if ( txt == _grid_strings[0] ) { //"Main Grid" bool success; - Temporal::Beats b = editor.get_grid_type_as_beats (success, 0); + Temporal::Beats b = editor.get_grid_type_as_beats (success, timepos_t (0)); if (!success) { return 1.0; } diff --git a/gtk2_ardour/region_selection.cc b/gtk2_ardour/region_selection.cc index 93a46938ce..409ac2ca4b 100644 --- a/gtk2_ardour/region_selection.cc +++ b/gtk2_ardour/region_selection.cc @@ -286,27 +286,37 @@ RegionSelection::involves (const TimeAxisView& tv) const return false; } -samplepos_t -RegionSelection::start () const +timepos_t +RegionSelection::start_time () const { - samplepos_t s = max_samplepos; - for (RegionSelection::const_iterator i = begin(); i != end(); ++i) { - s = min (s, (*i)->region()->position ()); + if (empty()) { + return timepos_t (); } - if (s == max_samplepos) { - return 0; + timepos_t s = timepos_t::max (front()->nt_position().time_domain()); + + for (RegionSelection::const_iterator i = begin(); i != end(); ++i) { + s = min (s, (*i)->region()->nt_position ()); + } + + if (s == timepos_t::max (front()->nt_position().time_domain())) { + return timepos_t (); } return s; } -samplepos_t -RegionSelection::end_sample () const +timepos_t +RegionSelection::end_time () const { - samplepos_t e = 0; + if (empty()) { + return timepos_t (); + } + + timepos_t e (timepos_t::zero (front()->nt_position().time_domain())); + for (RegionSelection::const_iterator i = begin(); i != end(); ++i) { - e = max (e, (*i)->region()->last_sample ()); + e = max (e, (*i)->region()->nt_end ()); } return e; diff --git a/gtk2_ardour/region_selection.h b/gtk2_ardour/region_selection.h index 4a3b633b87..670b522a64 100644 --- a/gtk2_ardour/region_selection.h +++ b/gtk2_ardour/region_selection.h @@ -57,11 +57,8 @@ public: void clear_all(); - samplepos_t start () const; - - /* "end" collides with list<>::end */ - - samplepos_t end_sample () const; + Temporal::timepos_t start_time () const; + Temporal::timepos_t end_time () const; const std::list& by_layer() const { return _bylayer; } void by_position (std::list&) const; diff --git a/gtk2_ardour/region_view.cc b/gtk2_ardour/region_view.cc index 70ef21e995..2d22a43081 100644 --- a/gtk2_ardour/region_view.cc +++ b/gtk2_ardour/region_view.cc @@ -1160,31 +1160,48 @@ RegionView::move_contents (sampleoffset_t distance) region_changed (PropertyChange (ARDOUR::Properties::start)); } -/** Snap a sample offset within our region using the current snap settings. - * @param x Frame offset from this region's position. + +/** Snap a time offset within our region using the current snap settings. + * @param x Time offset from this region's position. * @param ensure_snap whether to ignore snap_mode (in the case of SnapOff) and magnetic snap. * Used when inverting snap mode logic with key modifiers, or snap distance calculation. - * @return Snapped sample offset from this region's position. + * @return Snapped time offset from this region's position. */ -MusicSample -RegionView::snap_sample_to_sample (sampleoffset_t x, bool ensure_snap) const +timepos_t +RegionView::snap_region_time_to_region_time (timepos_t const & x, bool ensure_snap) const { PublicEditor& editor = trackview.editor(); - /* x is region relative, convert it to global absolute samples */ - samplepos_t const session_sample = x + _region->position(); + /* x is region relative, convert it to global absolute time */ + timepos_t const session_sample = _region->position() + x; /* try a snap in either direction */ - MusicSample sample (session_sample, 0); - editor.snap_to (sample, RoundNearest, SnapToAny_Visual, ensure_snap); + timepos_t snapped = session_sample; + editor.snap_to (snapped, RoundNearest, false, ensure_snap); /* if we went off the beginning of the region, snap forwards */ - if (sample.sample < _region->position ()) { - sample.sample = session_sample; - editor.snap_to (sample, RoundUpAlways, SnapToAny_Visual, ensure_snap); + if (snapped < _region->position ()) { + snapped = session_sample; + editor.snap_to (snapped, RoundUpAlways, false, ensure_snap); } - /* back to region relative, keeping the relevant divisor */ - return MusicSample (sample.sample - _region->position(), sample.division); + /* back to region relative */ + return _region->region_relative_position (snapped); +} + +timecnt_t +RegionView::region_relative_distance (timecnt_t const & duration, Temporal::TimeDomain domain) +{ +#warning NUTEMPO fixme needs new tempo map + //return _region->session().tempo_map().full_duration_at (_region->position(), duration, domain); + return timecnt_t(); +} + +timecnt_t +RegionView::source_relative_distance (timecnt_t const & duration, Temporal::TimeDomain domain) +{ +#warning NUTEMPO fixme needs new tempo map + //return _region->session().tempo_map().full_duration_at (_region->source_position(), duration, domain); + return timecnt_t(); } void diff --git a/gtk2_ardour/region_view.h b/gtk2_ardour/region_view.h index 777c32f370..7e00c90e99 100644 --- a/gtk2_ardour/region_view.h +++ b/gtk2_ardour/region_view.h @@ -79,14 +79,14 @@ public: virtual void set_height (double); virtual void set_samples_per_pixel (double); - virtual bool set_duration (samplecnt_t, void*); + virtual bool set_duration (Temporal::timecnt_t const &, void*); void move (double xdelta, double ydelta); void raise_to_top (); void lower_to_bottom (); - bool set_position(samplepos_t pos, void* src, double* delta = 0); + bool set_position(Temporal::timepos_t const & pos, void* src, double* delta = 0); virtual void show_region_editor (); void hide_region_editor (); @@ -125,11 +125,11 @@ public: struct PositionOrder { bool operator()(const RegionView* a, const RegionView* b) { - return a->region()->position() < b->region()->position(); + return a->region()->nt_position() < b->region()->nt_position(); } }; - ARDOUR::MusicSample snap_sample_to_sample (ARDOUR::sampleoffset_t, bool ensure_snap = false) const; + Temporal::timepos_t snap_region_time_to_region_time (Temporal::timepos_t const &, bool ensure_snap = false) const; void update_visibility (); @@ -172,6 +172,9 @@ protected: void maybe_raise_cue_markers (); + Temporal::timecnt_t region_relative_distance (Temporal::timecnt_t const &, Temporal::TimeDomain desired_time_domain); + Temporal::timecnt_t source_relative_distance (Temporal::timecnt_t const &, Temporal::TimeDomain desired_time_domain); + boost::shared_ptr _region; ArdourCanvas::Polygon* sync_mark; ///< polgyon for sync position diff --git a/gtk2_ardour/rhythm_ferret.cc b/gtk2_ardour/rhythm_ferret.cc index 370b8b9e27..76a4c45c40 100644 --- a/gtk2_ardour/rhythm_ferret.cc +++ b/gtk2_ardour/rhythm_ferret.cc @@ -241,14 +241,14 @@ RhythmFerret::run_analysis () for (RegionSelection::iterator i = regions_with_transients.begin(); i != regions_with_transients.end(); ++i) { - boost::shared_ptr rd = boost::static_pointer_cast ((*i)->region()); + boost::shared_ptr rd = boost::static_pointer_cast ((*i)->region()); switch (get_analysis_mode()) { case PercussionOnset: - run_percussion_onset_analysis (rd, (*i)->region()->position(), current_results); + run_percussion_onset_analysis (rd, (*i)->region()->position_sample(), current_results); break; case NoteOnset: - run_note_onset_analysis (rd, (*i)->region()->position(), current_results); + run_note_onset_analysis (rd, (*i)->region()->position_sample(), current_results); break; default: break; @@ -260,7 +260,7 @@ RhythmFerret::run_analysis () } int -RhythmFerret::run_percussion_onset_analysis (boost::shared_ptr readable, sampleoffset_t /*offset*/, AnalysisFeatureList& results) +RhythmFerret::run_percussion_onset_analysis (boost::shared_ptr readable, sampleoffset_t /*offset*/, AnalysisFeatureList& results) { try { TransientDetector t (_session->sample_rate()); @@ -315,7 +315,7 @@ RhythmFerret::get_note_onset_function () } int -RhythmFerret::run_note_onset_analysis (boost::shared_ptr readable, sampleoffset_t /*offset*/, AnalysisFeatureList& results) +RhythmFerret::run_note_onset_analysis (boost::shared_ptr readable, sampleoffset_t /*offset*/, AnalysisFeatureList& results) { try { OnsetDetector t (_session->sample_rate()); diff --git a/gtk2_ardour/rhythm_ferret.h b/gtk2_ardour/rhythm_ferret.h index 481d319048..ac0b459842 100644 --- a/gtk2_ardour/rhythm_ferret.h +++ b/gtk2_ardour/rhythm_ferret.h @@ -36,7 +36,7 @@ #include "region_selection.h" namespace ARDOUR { - class Readable; + class AudioReadable; } class Editor; @@ -117,8 +117,8 @@ private: int get_note_onset_function (); void run_analysis (); - int run_percussion_onset_analysis (boost::shared_ptr region, ARDOUR::sampleoffset_t offset, ARDOUR::AnalysisFeatureList& results); - int run_note_onset_analysis (boost::shared_ptr region, ARDOUR::sampleoffset_t offset, ARDOUR::AnalysisFeatureList& results); + int run_percussion_onset_analysis (boost::shared_ptr region, ARDOUR::sampleoffset_t offset, ARDOUR::AnalysisFeatureList& results); + int run_note_onset_analysis (boost::shared_ptr region, ARDOUR::sampleoffset_t offset, ARDOUR::AnalysisFeatureList& results); void do_action (); void do_split_action (); diff --git a/gtk2_ardour/route_time_axis.cc b/gtk2_ardour/route_time_axis.cc index df9a1c91de..5d886f1797 100644 --- a/gtk2_ardour/route_time_axis.cc +++ b/gtk2_ardour/route_time_axis.cc @@ -1225,7 +1225,7 @@ RouteTimeAxisView::name_entry_changed (string const& str) } boost::shared_ptr -RouteTimeAxisView::find_next_region (samplepos_t pos, RegionPoint point, int32_t dir) +RouteTimeAxisView::find_next_region (timepos_t const & pos, RegionPoint point, int32_t dir) { boost::shared_ptr pl = playlist (); @@ -1236,8 +1236,8 @@ RouteTimeAxisView::find_next_region (samplepos_t pos, RegionPoint point, int32_t return boost::shared_ptr (); } -samplepos_t -RouteTimeAxisView::find_next_region_boundary (samplepos_t pos, int32_t dir) +timepos_t +RouteTimeAxisView::find_next_region_boundary (timepos_t const & pos, int32_t dir) { boost::shared_ptr pl = playlist (); @@ -1245,7 +1245,7 @@ RouteTimeAxisView::find_next_region_boundary (samplepos_t pos, int32_t dir) return pl->find_next_region_boundary (pos, dir); } - return -1; + return timepos_t::max (pos.time_domain()); } void @@ -1299,7 +1299,7 @@ RouteTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op) case Delete: if (playlist->cut (time) != 0) { if (_editor.should_ripple()) { - playlist->ripple (time.start(), -time.length(), 0); + playlist->ripple (time.start_time(), -time.length(), NULL); } playlist->rdiff_and_add_command (_session); } @@ -1309,7 +1309,7 @@ RouteTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op) if ((what_we_got = playlist->cut (time)) != 0) { _editor.get_cut_buffer().add (what_we_got); if (_editor.should_ripple()) { - playlist->ripple (time.start(), -time.length(), 0); + playlist->ripple (time.start_time(), -time.length(), NULL); } playlist->rdiff_and_add_command (_session); } @@ -1323,7 +1323,7 @@ RouteTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op) case Clear: if ((what_we_got = playlist->cut (time)) != 0) { if (_editor.should_ripple()) { - playlist->ripple (time.start(), -time.length(), 0); + playlist->ripple (time.start_time(), -time.length(), NULL); } playlist->rdiff_and_add_command (_session); what_we_got->release (); @@ -1333,7 +1333,7 @@ RouteTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op) } bool -RouteTimeAxisView::paste (samplepos_t pos, const Selection& selection, PasteContext& ctx, const int32_t sub_num) +RouteTimeAxisView::paste (timepos_t const & pos, const Selection& selection, PasteContext& ctx) { if (!is_track()) { return false; @@ -1351,18 +1351,20 @@ RouteTimeAxisView::paste (samplepos_t pos, const Selection& selection, PasteCont DEBUG_TRACE (DEBUG::CutNPaste, string_compose ("paste to %1\n", pos)); /* add multi-paste offset if applicable */ - std::pair extent = (*p)->get_extent(); - const samplecnt_t duration = extent.second - extent.first; - pos += _editor.get_paste_offset(pos, ctx.count, duration); + std::pair extent = (*p)->get_extent(); + const timecnt_t duration = extent.first.distance (extent.second); + + timepos_t ppos = pos; + ppos += _editor.get_paste_offset (ppos, ctx.count, duration); pl->clear_changes (); pl->clear_owned_changes (); if (_editor.should_ripple()) { - std::pair extent = (*p)->get_extent_with_endspace(); - samplecnt_t amount = extent.second - extent.first; - pl->ripple(pos, amount * ctx.times, boost::shared_ptr()); + std::pair extent = (*p)->get_extent_with_endspace(); + timecnt_t amount = extent.first.distance (extent.second); + pl->ripple (ppos, amount * ctx.times, boost::shared_ptr()); } - pl->paste (*p, pos, ctx.times, sub_num); + pl->paste (*p, ppos, ctx.times); vector cmds; pl->rdiff (cmds); diff --git a/gtk2_ardour/route_time_axis.h b/gtk2_ardour/route_time_axis.h index e7c80bb2d5..95f3eb7d01 100644 --- a/gtk2_ardour/route_time_axis.h +++ b/gtk2_ardour/route_time_axis.h @@ -107,12 +107,12 @@ public: void toggle_layer_display (); LayerDisplay layer_display () const; - boost::shared_ptr find_next_region (samplepos_t pos, ARDOUR::RegionPoint, int32_t dir); - samplepos_t find_next_region_boundary (samplepos_t pos, int32_t dir); + boost::shared_ptr find_next_region (ARDOUR::timepos_t const & pos, ARDOUR::RegionPoint, int32_t dir); + ARDOUR::timepos_t find_next_region_boundary (ARDOUR::timepos_t const & pos, int32_t dir); /* Editing operations */ void cut_copy_clear (Selection&, Editing::CutCopyOp); - bool paste (ARDOUR::samplepos_t, const Selection&, PasteContext& ctx, const int32_t sub_num); + bool paste (Temporal::timepos_t const &, const Selection&, PasteContext& ctx); RegionView* combine_regions (); void uncombine_regions (); void uncombine_region (RegionView*); diff --git a/gtk2_ardour/route_ui.cc b/gtk2_ardour/route_ui.cc index ffc7c80e12..f6e869d9bb 100644 --- a/gtk2_ardour/route_ui.cc +++ b/gtk2_ardour/route_ui.cc @@ -533,7 +533,7 @@ RouteUI::mute_press (GdkEventButton* ev) } boost::shared_ptr mc = _route->mute_control(); - mc->start_touch (_session->audible_sample ()); + mc->start_touch (timepos_t (_session->audible_sample ())); _session->set_controls (route_list_to_control_list (rl, &Stripable::mute_control), _route->muted_by_self() ? 0.0 : 1.0, Controllable::InverseGroup); } @@ -549,7 +549,7 @@ RouteUI::mute_press (GdkEventButton* ev) } boost::shared_ptr mc = _route->mute_control(); - mc->start_touch (_session->audible_sample ()); + mc->start_touch (timepos_t (_session->audible_sample ())); mc->set_value (!_route->muted_by_self(), Controllable::UseGroup); } } @@ -567,7 +567,7 @@ RouteUI::mute_release (GdkEventButton* /*ev*/) _mute_release = 0; } - _route->mute_control()->stop_touch (_session->audible_sample ()); + _route->mute_control()->stop_touch (timepos_t (_session->audible_sample ())); return false; } diff --git a/gtk2_ardour/selection.cc b/gtk2_ardour/selection.cc index ee048c62db..eecb7e5163 100644 --- a/gtk2_ardour/selection.cc +++ b/gtk2_ardour/selection.cc @@ -56,8 +56,8 @@ using namespace std; using namespace ARDOUR; using namespace PBD; -struct AudioRangeComparator { - bool operator()(AudioRange a, AudioRange b) { +struct TimelineRangeComparator { + bool operator()(TimelineRange a, TimelineRange b) { return a.start < b.start; } }; @@ -306,11 +306,11 @@ Selection::toggle (samplepos_t start, samplepos_t end) { clear_objects(); // enforce object/range exclusivity - AudioRangeComparator cmp; + TimelineRangeComparator cmp; /* XXX this implementation is incorrect */ - time.push_back (AudioRange (start, end, ++next_time_id)); + time.push_back (TimelineRange (start, end, ++next_time_id)); time.consolidate (); time.sort (cmp); @@ -437,11 +437,11 @@ Selection::add (samplepos_t start, samplepos_t end) { clear_objects(); // enforce object/range exclusivity - AudioRangeComparator cmp; + TimelineRangeComparator cmp; /* XXX this implementation is incorrect */ - time.push_back (AudioRange (start, end, ++next_time_id)); + time.push_back (TimelineRange (start, end, ++next_time_id)); time.consolidate (); time.sort (cmp); @@ -457,7 +457,7 @@ Selection::move_time (samplecnt_t distance) return; } - for (list::iterator i = time.begin(); i != time.end(); ++i) { + for (list::iterator i = time.begin(); i != time.end(); ++i) { (*i).start += distance; (*i).end += distance; } @@ -470,15 +470,15 @@ Selection::replace (uint32_t sid, samplepos_t start, samplepos_t end) { clear_objects(); // enforce object/range exclusivity - for (list::iterator i = time.begin(); i != time.end(); ++i) { + for (list::iterator i = time.begin(); i != time.end(); ++i) { if ((*i).id == sid) { time.erase (i); - time.push_back (AudioRange(start,end, sid)); + time.push_back (TimelineRange(start,end, sid)); /* don't consolidate here */ - AudioRangeComparator cmp; + TimelineRangeComparator cmp; time.sort (cmp); TimeChanged (); @@ -606,7 +606,7 @@ Selection::remove (uint32_t selection_id) return; } - for (list::iterator i = time.begin(); i != time.end(); ++i) { + for (list::iterator i = time.begin(); i != time.end(); ++i) { if ((*i).id == selection_id) { time.erase (i); @@ -703,17 +703,17 @@ Selection::set (vector& v) * the list of tracks it applies to. */ long -Selection::set (samplepos_t start, samplepos_t end) +Selection::set (timepos_t const & start, timepos_t const & end) { clear_objects(); // enforce region/object exclusivity clear_time(); - if ((start == 0 && end == 0) || end < start) { + if ((start.zero() && end.zero()) || end < start) { return 0; } if (time.empty()) { - time.push_back (AudioRange (start, end, ++next_time_id)); + time.push_back (TimelineRange (start, end, ++next_time_id)); } else { /* reuse the first entry, and remove all the rest */ @@ -749,9 +749,9 @@ Selection::set_preserving_all_ranges (samplepos_t start, samplepos_t end) } if (time.empty ()) { - time.push_back (AudioRange (start, end, ++next_time_id)); + time.push_back (TimelineRange (start, end, ++next_time_id)); } else { - time.sort (AudioRangeComparator ()); + time.sort (TimelineRangeComparator ()); time.front().start = start; time.back().end = end; } @@ -1130,7 +1130,7 @@ Selection::get_state () const } for (TimeSelection::const_iterator i = time.begin(); i != time.end(); ++i) { - XMLNode* t = node->add_child (X_("AudioRange")); + XMLNode* t = node->add_child (X_("TimelineRange")); t->set_property (X_("start"), (*i).start); t->set_property (X_("end"), (*i).end); } @@ -1297,7 +1297,7 @@ Selection::set_state (XMLNode const & node, int) } } - } else if ((*i)->name() == X_("AudioRange")) { + } else if ((*i)->name() == X_("TimelineRange")) { samplepos_t start; samplepos_t end; diff --git a/gtk2_ardour/selection.h b/gtk2_ardour/selection.h index 318bb717af..8fc1bfd77e 100644 --- a/gtk2_ardour/selection.h +++ b/gtk2_ardour/selection.h @@ -136,7 +136,7 @@ public: void set (const MidiNoteSelection&); void set (RegionView*, bool also_clear_tracks = true); void set (std::vector&); - long set (samplepos_t, samplepos_t); + long set (Temporal::timepos_t const &, Temporal::timepos_t const &); void set_preserving_all_ranges (samplepos_t, samplepos_t); void set (boost::shared_ptr); void set (boost::shared_ptr); diff --git a/gtk2_ardour/time_axis_view.cc b/gtk2_ardour/time_axis_view.cc index 5076f663d7..2c6a898f82 100644 --- a/gtk2_ardour/time_axis_view.cc +++ b/gtk2_ardour/time_axis_view.cc @@ -880,7 +880,7 @@ TimeAxisView::show_selection (TimeSelection& ts) gap = ceil (gap * ui_scale); } - for (list::iterator i = ts.begin(); i != ts.end(); ++i) { + for (list::iterator i = ts.begin(); i != ts.end(); ++i) { samplepos_t start, end; samplecnt_t cnt; diff --git a/gtk2_ardour/time_axis_view.h b/gtk2_ardour/time_axis_view.h index f783db5743..04f8f25f43 100644 --- a/gtk2_ardour/time_axis_view.h +++ b/gtk2_ardour/time_axis_view.h @@ -190,10 +190,9 @@ public: * @param ctx Paste context. * @param sub_num music-time sub-division: \c -1: snap to bar, \c 1: exact beat, \c >1: \c (1 \c / \p sub_num \c ) beat-divisions */ - virtual bool paste (ARDOUR::samplepos_t pos, + virtual bool paste (Temporal::timepos_t const & pos, const Selection& selection, - PasteContext& ctx, - const int32_t sub_num) + PasteContext& ctx) { return false; } @@ -204,7 +203,7 @@ public: virtual void fade_range (TimeSelection&) {} - virtual boost::shared_ptr find_next_region (samplepos_t /*pos*/, ARDOUR::RegionPoint, int32_t /*dir*/) { + virtual boost::shared_ptr find_next_region (ARDOUR::timepos_t const & /*pos*/, ARDOUR::RegionPoint, int32_t /*dir*/) { return boost::shared_ptr (); } diff --git a/gtk2_ardour/time_axis_view_item.cc b/gtk2_ardour/time_axis_view_item.cc index c684a47db9..dd1692b499 100644 --- a/gtk2_ardour/time_axis_view_item.cc +++ b/gtk2_ardour/time_axis_view_item.cc @@ -283,15 +283,15 @@ TimeAxisViewItem::canvas_group_event (GdkEvent* /*ev*/) */ bool -TimeAxisViewItem::set_position(samplepos_t pos, void* src, double* delta) +TimeAxisViewItem::set_position(timepos_t const & pos, void* src, double* delta) { if (position_locked) { return false; } - sample_position = pos; + sample_position = pos.samples(); - double new_unit_pos = trackview.editor().sample_to_pixel (pos); + double new_unit_pos = trackview.editor().sample_to_pixel (sample_position); if (delta) { (*delta) = new_unit_pos - group->position().x; diff --git a/gtk2_ardour/time_axis_view_item.h b/gtk2_ardour/time_axis_view_item.h index 07761d9695..b75fc0c0e9 100644 --- a/gtk2_ardour/time_axis_view_item.h +++ b/gtk2_ardour/time_axis_view_item.h @@ -54,14 +54,14 @@ class TimeAxisViewItem : public Selectable, public PBD::ScopedConnectionList public: virtual ~TimeAxisViewItem(); - virtual bool set_position(samplepos_t, void*, double* delta = 0); - samplepos_t get_position() const; - virtual bool set_duration(samplecnt_t, void*); - samplecnt_t get_duration() const; - virtual void set_max_duration(samplecnt_t, void*); - samplecnt_t get_max_duration() const; - virtual void set_min_duration(samplecnt_t, void*); - samplecnt_t get_min_duration() const; + virtual bool set_position(Temporal::timepos_t const &, void*, double* delta = 0); + Temporal::timepos_t get_position() const; + virtual bool set_duration(Temporal::timecnt_t const &, void*); + Temporal::timecnt_t get_duration() const; + virtual void set_max_duration(Temporal::timecnt_t const &, void*); + Temporal::timecnt_t get_max_duration() const; + virtual void set_min_duration(Temporal::timecnt_t const &, void*); + Temporal::timecnt_t get_min_duration() const; virtual void set_position_locked(bool, void*); bool get_position_locked() const; void set_max_duration_active(bool, void*); diff --git a/gtk2_ardour/time_info_box.cc b/gtk2_ardour/time_info_box.cc index fc48fb2860..87976be2a4 100644 --- a/gtk2_ardour/time_info_box.cc +++ b/gtk2_ardour/time_info_box.cc @@ -234,16 +234,16 @@ TimeInfoBox::set_session (Session* s) void TimeInfoBox::region_selection_changed () { - samplepos_t s, e; + timepos_t s, e; Selection& selection (Editor::instance().get_selection()); - s = selection.regions.start(); - e = selection.regions.end_sample(); + s = selection.regions.start_time(); + e = selection.regions.end_sample_time(); selection_start->set_off (false); selection_end->set_off (false); selection_length->set_off (false); - selection_start->set (s); - selection_end->set (e); - selection_length->set (e, false, s); + selection_start->set_time (s); + selection_end->set_time (e); + selection_length->set_duration (e, false, s); } void @@ -272,9 +272,10 @@ TimeInfoBox::selection_changed () selection_start->set_off (false); selection_end->set_off (false); selection_length->set_off (false); - selection_start->set (selection.time.start()); - selection_end->set (selection.time.end_sample()); - selection_length->set (selection.time.end_sample(), false, selection.time.start()); + selection_start->set_time (selection.time.start_time()); + selection_end->set_time (selection.time.end_time()); + selection_length->set_is_duration (true, selection.time.start_time()); + selection_length->set_duration (selection.time.start_time().distance (selection.time.end_time())); } else { selection_start->set_off (true); selection_end->set_off (true); @@ -335,9 +336,10 @@ TimeInfoBox::selection_changed () selection_start->set_off (false); selection_end->set_off (false); selection_length->set_off (false); - selection_start->set (selection.time.start()); - selection_end->set (selection.time.end_sample()); - selection_length->set (selection.time.end_sample(), false, selection.time.start()); + selection_start->set_time (selection.time.start_time()); + selection_end->set_time (selection.time.end_time()); + selection_length->set_is_duration (true, selection.time.start_time()); + selection_length->set_duration (selection.time.start_time().distance (selection.time.end_time())); } break; @@ -382,6 +384,6 @@ TimeInfoBox::punch_changed (Location* loc) punch_start->set_off (false); punch_end->set_off (false); - punch_start->set (loc->start()); - punch_end->set (loc->end()); + punch_start->set_time (loc->start()); + punch_end->set_time (loc->end()); } diff --git a/gtk2_ardour/time_selection.cc b/gtk2_ardour/time_selection.cc index 4d59f9dcfb..3b1b74b7b7 100644 --- a/gtk2_ardour/time_selection.cc +++ b/gtk2_ardour/time_selection.cc @@ -1,22 +1,21 @@ /* - * Copyright (C) 2005-2017 Paul Davis - * Copyright (C) 2009-2012 Carl Hetherington - * Copyright (C) 2009-2012 David Robillard - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License along - * with this program; if not, write to the Free Software Foundation, Inc., - * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - */ + Copyright (C) 2003-2004 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + +*/ #include @@ -30,17 +29,17 @@ using namespace ARDOUR; using namespace PBD; -AudioRange& +TimelineRange& TimeSelection::operator[] (uint32_t which) { - for (std::list::iterator i = begin(); i != end(); ++i) { + for (std::list::iterator i = begin(); i != end(); ++i) { if ((*i).id == which) { return *i; } } fatal << string_compose (_("programming error: request for non-existent audio range (%1)!"), which) << endmsg; abort(); /*NOTREACHED*/ - return *(new AudioRange(0,0,0)); /* keep the compiler happy; never called */ + return *(new ARDOUR::TimelineRange(0,0,0)); /* keep the compiler happy; never called */ } bool @@ -49,16 +48,16 @@ TimeSelection::consolidate () bool changed = false; restart: - for (std::list::iterator a = begin(); a != end(); ++a) { - for (std::list::iterator b = begin(); b != end(); ++b) { + for (std::list::iterator a = begin(); a != end(); ++a) { + for (std::list::iterator b = begin(); b != end(); ++b) { if (&(*a) == &(*b)) { continue; } - if (a->coverage (b->start, b->end) != Evoral::OverlapNone) { - a->start = std::min (a->start, b->start); - a->end = std::max (a->end, b->end); + if (a->coverage (b->start(), b->end()) != Temporal::OverlapNone) { + a->set_start (std::min (a->start(), b->start())); + a->set_end (std::max (a->end(), b->end())); erase (b); changed = true; goto restart; @@ -70,43 +69,59 @@ TimeSelection::consolidate () } samplepos_t -TimeSelection::start () const +TimeSelection::start_sample () const { - if (empty()) { - return 0; - } - - samplepos_t first = max_samplepos; - - for (std::list::const_iterator i = begin(); i != end(); ++i) { - if ((*i).start < first) { - first = (*i).start; - } - } - return first; + return start_time().sample (); } samplepos_t TimeSelection::end_sample () const { - samplepos_t last = 0; - - /* XXX make this work like RegionSelection: no linear search needed */ - - for (std::list::const_iterator i = begin(); i != end(); ++i) { - if ((*i).end > last) { - last = (*i).end; - } - } - return last; + return end_time().sample (); } samplecnt_t -TimeSelection::length() const +TimeSelection::length_samples() const +{ + return length().samples(); +} + +timepos_t +TimeSelection::start_time () const { if (empty()) { return 0; } - return end_sample() - start() + 1; + timepos_t first = std::numeric_limits::max(); + + for (std::list::const_iterator i = begin(); i != end(); ++i) { + if ((*i).start() < first) { + first = (*i).start(); + } + } + return first; +} + +timepos_t +TimeSelection::end_time() const +{ + timepos_t last = std::numeric_limits::min(); + + for (std::list::const_iterator i = begin(); i != end(); ++i) { + if ((*i).end() > last) { + last = (*i).end(); + } + } + return last; +} + +timecnt_t +TimeSelection::length() const +{ + if (empty()) { + return timecnt_t(); + } + + return start_time().distance (end_time()); } diff --git a/gtk2_ardour/time_selection.h b/gtk2_ardour/time_selection.h index 53a0f28662..eb6ef1ca4a 100644 --- a/gtk2_ardour/time_selection.h +++ b/gtk2_ardour/time_selection.h @@ -1,22 +1,21 @@ /* - * Copyright (C) 2006-2017 Paul Davis - * Copyright (C) 2009-2011 David Robillard - * Copyright (C) 2009 Carl Hetherington - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License along - * with this program; if not, write to the Free Software Foundation, Inc., - * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - */ + Copyright (C) 2000-2020 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + +*/ #ifndef __ardour_gtk_time_selection_h__ #define __ardour_gtk_time_selection_h__ @@ -28,14 +27,18 @@ namespace ARDOUR { class RouteGroup; } -class TimeSelection : public std::list +class TimeSelection : public std::list { public: - ARDOUR::AudioRange& operator[](uint32_t); + ARDOUR::TimelineRange & operator[](uint32_t); - ARDOUR::samplepos_t start() const; + ARDOUR::samplepos_t start_sample() const; ARDOUR::samplepos_t end_sample() const; - ARDOUR::samplepos_t length() const; + ARDOUR::samplepos_t length_samples() const; + + Temporal::timepos_t start_time() const; + Temporal::timepos_t end_time() const; + Temporal::timecnt_t length() const; bool consolidate (); };