intermediate, unfinished snapshot of ongoing timeline types work on GTK GUI

This commit is contained in:
Paul Davis 2020-09-26 09:14:59 -06:00
parent 69ab030f55
commit 7433bc27e0
59 changed files with 694 additions and 618 deletions

View file

@ -259,7 +259,7 @@ AnalysisWindow::analyze_data (Gtk::Button * /*button*/)
// std::cerr << "Analyzing ranges on track " << rui->route()->name() << std::endl; // std::cerr << "Analyzing ranges on track " << rui->route()->name() << std::endl;
FFTResult *res = fft_graph.prepareResult(rui->route_color(), rui->route()->name()); FFTResult *res = fft_graph.prepareResult(rui->route_color(), rui->route()->name());
for (std::list<AudioRange>::iterator j = ts.begin(); j != ts.end(); ++j) { for (std::list<TimelineRange>::iterator j = ts.begin(); j != ts.end(); ++j) {
int n; int n;
for (int channel = 0; channel < n_inputs; channel++) { for (int channel = 0; channel < n_inputs; channel++) {

View file

@ -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()) { 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 { } else {
if (UIConfiguration::instance().get_follow_edits()) { if (UIConfiguration::instance().get_follow_edits()) {
list<AudioRange>& range = editor->get_selection().time; list<TimelineRange>& 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 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->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 (); _session->request_roll ();

View file

@ -188,7 +188,7 @@ ARDOUR_UI::update_transport_clocks (samplepos_t pos)
case DeltaOriginMarker: case DeltaOriginMarker:
{ {
Location* loc = _session->locations()->clock_origin_location (); 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; break;
} }
@ -203,7 +203,7 @@ ARDOUR_UI::update_transport_clocks (samplepos_t pos)
case DeltaOriginMarker: case DeltaOriginMarker:
{ {
Location* loc = _session->locations()->clock_origin_location (); 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; break;
} }

View file

@ -114,7 +114,7 @@ void
ARDOUR_UI::create_xrun_marker (samplepos_t where) ARDOUR_UI::create_xrun_marker (samplepos_t where)
{ {
if (_session) { 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); _session->locations()->add (location);
} }
} }

View file

@ -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) { if (_with_info) {
_left_btn.set_sensitive (btn_en); _left_btn.set_sensitive (btn_en);
_right_btn.set_sensitive (btn_en); _right_btn.set_sensitive (btn_en);
@ -2295,14 +2374,25 @@ AudioClock::set_editable (bool yn)
} }
void void
AudioClock::set_is_duration (bool yn) AudioClock::set_is_duration (bool yn, timepos_t const & p)
{ {
if (yn == is_duration) { if (yn == is_duration) {
if (yn) {
/* just reset position */
duration_position = p;
}
return; return;
} }
is_duration = yn; is_duration = yn;
AudioClock::set (last_when, true); if (yn) {
duration_position = p;
} else {
duration_position = timepos_t ();
}
set_time (last_when, true);
} }
void void

View file

@ -74,11 +74,15 @@ class AudioClock : public CairoWidget, public ARDOUR::SessionHandlePtr
void focus (); void focus ();
virtual void set (samplepos_t, bool force = false, ARDOUR::samplecnt_t offset = 0); 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 set_from_playhead ();
void locate (); void locate ();
void set_mode (Mode, bool noemit = false); void set_mode (Mode, bool noemit = false);
void set_bbt_reference (samplepos_t); void set_bbt_reference (samplepos_t);
void set_is_duration (bool); void set_is_duration (bool);
void set_is_duration (bool, Temporal::timepos_t const &);
void copy_text_to_clipboard () const; void copy_text_to_clipboard () const;
@ -139,6 +143,7 @@ class AudioClock : public CairoWidget, public ARDOUR::SessionHandlePtr
bool edit_is_negative; bool edit_is_negative;
samplepos_t _limit_pos; samplepos_t _limit_pos;
Temporal::timepos_t duration_position;
ARDOUR::samplecnt_t _offset; ARDOUR::samplecnt_t _offset;
@ -223,6 +228,7 @@ class AudioClock : public CairoWidget, public ARDOUR::SessionHandlePtr
void set_seconds (samplepos_t, bool); void set_seconds (samplepos_t, bool);
void set_samples (samplepos_t, bool); void set_samples (samplepos_t, bool);
void set_out_of_bounds (bool negative); void set_out_of_bounds (bool negative);
void finish_set (Temporal::timepos_t const &, bool);
void set_clock_dimensions (Gtk::Requisition&); void set_clock_dimensions (Gtk::Requisition&);

View file

@ -126,7 +126,7 @@ AudioStreamView::create_region_view (boost::shared_ptr<Region> r, bool wait_for_
insensitive to events insensitive to events
*/ */
if (region->length() == 1) { if (region->length_samples() == 1) {
region_view->set_sensitive (false); region_view->set_sensitive (false);
} }
@ -226,7 +226,7 @@ AudioStreamView::setup_rec_box ()
samplepos_t start = 0; samplepos_t start = 0;
if (rec_regions.size() > 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); + _trackview.track()->get_captured_samples(rec_regions.size()-1);
} }
@ -241,7 +241,7 @@ AudioStreamView::setup_rec_box ()
boost::dynamic_pointer_cast<AudioRegion>(RegionFactory::create (sources, plist, false))); boost::dynamic_pointer_cast<AudioRegion>(RegionFactory::create (sources, plist, false)));
assert(region); 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)); rec_regions.push_back (make_pair(region, (RegionView*) 0));
} }
@ -355,20 +355,20 @@ AudioStreamView::update_rec_regions (samplepos_t start, samplecnt_t cnt)
continue; continue;
} }
samplecnt_t origlen = region->length(); samplecnt_t origlen = region->length_samples();
if (region == rec_regions.back().first && rec_active) { 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 (); region->suspend_property_changes ();
/* set non-musical position / length */ /* set non-musical position / length */
region->set_position (_trackview.track()->get_capture_start_sample(n)); region->set_position (timepos_t (_trackview.track()->get_capture_start_sample(n)));
region->set_length (nlen, 0); region->set_length (timecnt_t (nlen));
region->resume_property_changes (); region->resume_property_changes ();
if (origlen == 1) { if (origlen == 1) {
@ -377,11 +377,11 @@ AudioStreamView::update_rec_regions (samplepos_t start, samplecnt_t cnt)
setup_new_rec_layer_time (region); 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 */ /* also update rect */
ArdourCanvas::Rectangle * rect = rec_rects[n].rectangle; 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); 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); 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->suspend_property_changes ();
region->set_position (_trackview.track()->get_capture_start_sample(n)); region->set_position (timepos_t (_trackview.track()->get_capture_start_sample(n)));
region->set_length (nlen, 0); region->set_length (timecnt_t (nlen));
region->resume_property_changes (); region->resume_property_changes ();
if (origlen == 1) { if (origlen == 1) {
@ -451,8 +451,8 @@ AudioStreamView::hide_xfades_with (boost::shared_ptr<AudioRegion> ar)
for (list<RegionView*>::iterator i = region_views.begin(); i != region_views.end(); ++i) { for (list<RegionView*>::iterator i = region_views.begin(); i != region_views.end(); ++i) {
AudioRegionView* const arv = dynamic_cast<AudioRegionView*>(*i); AudioRegionView* const arv = dynamic_cast<AudioRegionView*>(*i);
if (arv) { if (arv) {
switch (arv->region()->coverage (ar->position(), ar->last_sample())) { switch (arv->region()->coverage (ar->nt_position(), ar->nt_last())) {
case Evoral::OverlapNone: case Temporal::OverlapNone:
break; break;
default: default:
if (arv->start_xfade_visible ()) { if (arv->start_xfade_visible ()) {

View file

@ -83,15 +83,14 @@ AutomationLine::AutomationLine (const string& name,
TimeAxisView& tv, TimeAxisView& tv,
ArdourCanvas::Item& parent, ArdourCanvas::Item& parent,
boost::shared_ptr<AutomationList> al, boost::shared_ptr<AutomationList> al,
const ParameterDescriptor& desc, const ParameterDescriptor& desc)
Evoral::TimeConverter<double, samplepos_t>* converter)
: trackview (tv) : trackview (tv)
, _name (name) , _name (name)
, alist (al) , alist (al)
, _time_converter (converter ? converter : new Evoral::IdentityConverter<double, samplepos_t>) , _time_converter (converter ? converter : new Evoral::IdentityConverter<double, samplepos_t>)
, _parent_group (parent) , _parent_group (parent)
, _offset (0) , _offset (0)
, _maximum_time (max_samplepos) , _maximum_time (timepos_t::max (al->time_domain()))
, _fill (false) , _fill (false)
, _desc (desc) , _desc (desc)
{ {
@ -1178,11 +1177,29 @@ AutomationLine::set_state (const XMLNode &node, int version)
return alist->set_state (node, version); return alist->set_state (node, version);
} }
void Temporal::timepos_t
AutomationLine::view_to_model_coord (double& x, double& y) const 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); 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 void
@ -1251,11 +1268,12 @@ AutomationLine::model_to_view_coord_y (double& y) const
y = _desc.to_interface (y); y = _desc.to_interface (y);
} }
void double
AutomationLine::model_to_view_coord (double& x, double& y) const AutomationLine::model_to_view_coord (Evoral::ControlEvent const & ev, double& y) const
{ {
Temporal::timepos_t w (ev.when());
model_to_view_coord_y (y); 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 */ /** 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. * to the start of the track or region that it is on.
*/ */
void void
AutomationLine::set_maximum_time (samplecnt_t t) AutomationLine::set_maximum_time (Temporal::timepos_t const & t)
{ {
if (_maximum_time == t) { if (_maximum_time == t) {
return; return;

View file

@ -33,8 +33,6 @@
#include <sigc++/signal.h> #include <sigc++/signal.h>
#include "evoral/TimeConverter.h"
#include "pbd/undo.h" #include "pbd/undo.h"
#include "pbd/statefuldestructible.h" #include "pbd/statefuldestructible.h"
#include "pbd/memento_command.h" #include "pbd/memento_command.h"
@ -71,8 +69,7 @@ public:
TimeAxisView& tv, TimeAxisView& tv,
ArdourCanvas::Item& parent, ArdourCanvas::Item& parent,
boost::shared_ptr<ARDOUR::AutomationList> al, boost::shared_ptr<ARDOUR::AutomationList> al,
const ARDOUR::ParameterDescriptor& desc, const ARDOUR::ParameterDescriptor& desc);
Evoral::TimeConverter<double, ARDOUR::samplepos_t>* converter = 0);
virtual ~AutomationLine (); virtual ~AutomationLine ();
@ -126,9 +123,9 @@ public:
std::string fraction_to_string (double) const; std::string fraction_to_string (double) const;
std::string delta_to_string (double) const; std::string delta_to_string (double) const;
double string_to_fraction (std::string const &) 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 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; void model_to_view_coord_y (double &) const;
double compute_delta (double from, double to) const; double compute_delta (double from, double to) const;
@ -151,20 +148,16 @@ public:
virtual MementoCommandBinder<ARDOUR::AutomationList>* memento_command_binder (); virtual MementoCommandBinder<ARDOUR::AutomationList>* memento_command_binder ();
const Evoral::TimeConverter<double, ARDOUR::samplepos_t>& time_converter () const {
return *_time_converter;
}
std::pair<ARDOUR::samplepos_t, ARDOUR::samplepos_t> get_point_x_range () const; std::pair<ARDOUR::samplepos_t, ARDOUR::samplepos_t> get_point_x_range () const;
void set_maximum_time (ARDOUR::samplecnt_t); void set_maximum_time (Temporal::timepos_t const &);
ARDOUR::samplecnt_t maximum_time () const { Temporal::timepos_t maximum_time () const {
return _maximum_time; return _maximum_time;
} }
void set_offset (ARDOUR::samplecnt_t); void set_offset (Temporal::timecnt_t const &);
ARDOUR::samplecnt_t offset () { return _offset; } Temporal::timecnt_t offset () { return _offset; }
void set_width (ARDOUR::samplecnt_t); void set_width (Temporal::timecnt_t const &);
samplepos_t session_position (ARDOUR::AutomationList::const_iterator) const; samplepos_t session_position (ARDOUR::AutomationList::const_iterator) const;
@ -175,9 +168,6 @@ protected:
uint32_t _line_color; uint32_t _line_color;
boost::shared_ptr<ARDOUR::AutomationList> alist; boost::shared_ptr<ARDOUR::AutomationList> alist;
Evoral::TimeConverter<double, ARDOUR::samplepos_t>* _time_converter;
/** true if _time_converter belongs to us (ie we should delete it on destruction) */
bool _our_time_converter;
VisibleAspects _visible; VisibleAspects _visible;
@ -231,7 +221,7 @@ private:
/** offset from the start of the automation list to the start of the line, so that /** 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 * 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; bool is_stepped() const;
void update_visibility (); void update_visibility ();
@ -244,7 +234,7 @@ private:
PBD::ScopedConnectionList _list_connections; 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 */ /** 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; bool _fill;

View file

@ -44,6 +44,8 @@
#include "pbd/i18n.h" #include "pbd/i18n.h"
using namespace Temporal;
AutomationRegionView::AutomationRegionView (ArdourCanvas::Container* parent, AutomationRegionView::AutomationRegionView (ArdourCanvas::Container* parent,
AutomationTimeAxisView& time_axis, AutomationTimeAxisView& time_axis,
boost::shared_ptr<ARDOUR::Region> region, boost::shared_ptr<ARDOUR::Region> region,
@ -52,11 +54,9 @@ AutomationRegionView::AutomationRegionView (ArdourCanvas::Container*
double spu, double spu,
uint32_t basic_color) uint32_t basic_color)
: RegionView(parent, time_axis, region, spu, basic_color, true) : 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) , _parameter(param)
{ {
TimeAxisViewItem::set_position (_region->position(), this); TimeAxisViewItem::set_position (_region->nt_position(), this);
if (list) { if (list) {
assert(list->parameter() == param); assert(list->parameter() == param);
@ -83,7 +83,7 @@ AutomationRegionView::init (bool /*wfd*/)
RegionView::init (false); 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()); set_height (trackview.current_height());
@ -100,13 +100,12 @@ AutomationRegionView::create_line (boost::shared_ptr<ARDOUR::AutomationList> lis
ARDOUR::EventTypeMap::instance().to_symbol(list->parameter()), ARDOUR::EventTypeMap::instance().to_symbol(list->parameter()),
trackview, *get_canvas_group(), list, trackview, *get_canvas_group(), list,
boost::dynamic_pointer_cast<ARDOUR::MidiRegion> (_region), boost::dynamic_pointer_cast<ARDOUR::MidiRegion> (_region),
_parameter, _parameter));
&_source_relative_time_converter));
_line->set_colors(); _line->set_colors();
_line->set_height ((uint32_t)rint(trackview.current_height() - 2.5 - NAME_HIGHLIGHT_SIZE)); _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_visibility (AutomationLine::VisibleAspects (AutomationLine::Line|AutomationLine::ControlPoints));
_line->set_maximum_time (_region->length()); _line->set_maximum_time (timepos_t (_region->nt_length()));
_line->set_offset (_region->start ()); _line->set_offset (_region->nt_start ());
} }
uint32_t uint32_t
@ -157,7 +156,8 @@ AutomationRegionView::canvas_group_event (GdkEvent* ev)
/* guard points only if primary modifier is used */ /* guard points only if primary modifier is used */
bool with_guard_points = Gtkmm2ext::Keyboard::modifier_state_equals (ev->button.state, Gtkmm2ext::Keyboard::PrimaryModifier); 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; return true;
} }
@ -168,10 +168,11 @@ AutomationRegionView::canvas_group_event (GdkEvent* ev)
* @param y y position, relative to our TimeAxisView. * @param y y position, relative to our TimeAxisView.
*/ */
void 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<Evoral::Control> c = _region->control(_parameter, true); boost::shared_ptr<Evoral::Control> c = _region->control(_parameter, true);
boost::shared_ptr<ARDOUR::AutomationControl> ac = boost::dynamic_pointer_cast<ARDOUR::AutomationControl>(c); boost::shared_ptr<ARDOUR::AutomationControl> ac = boost::dynamic_pointer_cast<ARDOUR::AutomationControl>(c);
timepos_t when (w); /* the non-const copy */
if (!_line) { if (!_line) {
assert(ac); assert(ac);
@ -184,11 +185,13 @@ AutomationRegionView::add_automation_event (GdkEvent *, samplepos_t when, double
/* compute vertical fractional position */ /* compute vertical fractional position */
y = 1.0 - (y / _line->height()); y = 1.0 - (y / _line->height());
/* snap sample, prepare conversion to double beats */ /* snap time */
double when_d = snap_sample_to_sample (when - _region->start ()).sample + _region->start ();
/* convert 'when' to music-time relative to the region and scale y from interface to internal */ when = snap_region_time_to_region_time (when.earlier (_region->nt_start()), false) + _region->nt_start ();
_line->view_to_model_coord (when_d, y);
/* map using line */
_line->view_to_model_coord_y (y);
if (UIConfiguration::instance().get_new_automation_points_on_lane()) { if (UIConfiguration::instance().get_new_automation_points_on_lane()) {
if (c->list()->size () == 0) { 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(); XMLNode& before = _line->the_list()->get_state();
<<<<<<< HEAD
if (_line->the_list()->editor_add (when_d, y, with_guard_points)) { if (_line->the_list()->editor_add (when_d, y, with_guard_points)) {
if (ac->automation_state () == ARDOUR::Off) { if (ac->automation_state () == ARDOUR::Off) {
@ -214,6 +218,9 @@ AutomationRegionView::add_automation_event (GdkEvent *, samplepos_t when, double
RouteTimeAxisView::signal_ctrl_touched (false); 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")); view->editor().begin_reversible_command (_("add automation event"));
XMLNode& after = _line->the_list()->get_state(); XMLNode& after = _line->the_list()->get_state();
@ -226,7 +233,7 @@ AutomationRegionView::add_automation_event (GdkEvent *, samplepos_t when, double
} }
bool bool
AutomationRegionView::paste (samplepos_t pos, AutomationRegionView::paste (timepos_t const & pos,
unsigned paste_count, unsigned paste_count,
float times, float times,
boost::shared_ptr<const ARDOUR::AutomationList> slist) boost::shared_ptr<const ARDOUR::AutomationList> slist)
@ -241,24 +248,18 @@ AutomationRegionView::paste (samplepos_t pos
return false; return false;
} }
AutomationType src_type = (AutomationType)slist->parameter().type (); timecnt_t len = slist->length();
double len = slist->length(); timepos_t p (pos);
/* add multi-paste offset if applicable */ /* add multi-paste offset if applicable */
if (parameter_is_midi (src_type)) { p += view->editor ().get_paste_offset (pos, paste_count > 0 ? 1 : 0, len);
// 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);
}
/* convert sample-position to model's unit and position */ /* convert sample-position to model's unit and position */
const double model_pos = _source_relative_time_converter.from ( timepos_t model_pos = timepos_t (source_relative_distance (timecnt_t (p, timepos_t()), slist->time_domain()));
pos - _source_relative_time_converter.origin_b());
XMLNode& before = my_list->get_state(); 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( view->session()->add_command(
new MementoCommand<ARDOUR::AutomationList>(_line->memento_command_binder(), &before, &my_list->get_state())); new MementoCommand<ARDOUR::AutomationList>(_line->memento_command_binder(), &before, &my_list->get_state()));
@ -276,10 +277,10 @@ AutomationRegionView::set_height (double h)
} }
bool bool
AutomationRegionView::set_position (samplepos_t pos, void* src, double* ignored) AutomationRegionView::set_position (timepos_t const & pos, void* src, double* ignored)
{ {
if (_line) { if (_line) {
_line->set_maximum_time (_region->length ()); _line->set_maximum_time (timepos_t (_region->nt_length ()));
} }
return RegionView::set_position(pos, src, ignored); return RegionView::set_position(pos, src, ignored);
@ -302,25 +303,16 @@ AutomationRegionView::region_resized (const PBD::PropertyChange& what_changed)
{ {
RegionView::region_resized (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) { if (!_line) {
return; return;
} }
if (what_changed.contains (ARDOUR::Properties::start)) { 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)) { if (what_changed.contains (ARDOUR::Properties::length)) {
_line->set_maximum_time (_region->length()); _line->set_maximum_time (timepos_t (_region->nt_length()));
} }
} }

View file

@ -50,19 +50,11 @@ public:
void init (bool wfd); void init (bool wfd);
bool paste (samplepos_t pos, bool paste (Temporal::timepos_t const & pos,
unsigned paste_count, unsigned paste_count,
float times, float times,
boost::shared_ptr<const ARDOUR::AutomationList> slist); boost::shared_ptr<const ARDOUR::AutomationList> 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 inline AutomationTimeAxisView* automation_view() const
{ return dynamic_cast<AutomationTimeAxisView*>(&trackview); } { return dynamic_cast<AutomationTimeAxisView*>(&trackview); }
@ -78,17 +70,15 @@ public:
protected: protected:
void create_line(boost::shared_ptr<ARDOUR::AutomationList> list); void create_line(boost::shared_ptr<ARDOUR::AutomationList> 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&); void region_resized (const PBD::PropertyChange&);
bool canvas_group_event(GdkEvent* ev); 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 mouse_mode_changed ();
void entered(); void entered();
void exited(); void exited();
private: private:
ARDOUR::DoubleBeatsSamplesConverter _region_relative_time_converter;
ARDOUR::DoubleBeatsSamplesConverter _source_relative_time_converter;
Evoral::Parameter _parameter; Evoral::Parameter _parameter;
boost::shared_ptr<AutomationLine> _line; boost::shared_ptr<AutomationLine> _line;
PBD::ScopedConnection _mouse_mode_connection; PBD::ScopedConnection _mouse_mode_connection;

View file

@ -323,7 +323,7 @@ AutomationStreamView::get_lines () const
} }
bool bool
AutomationStreamView::paste (samplepos_t pos, AutomationStreamView::paste (timepos_t const & pos,
unsigned paste_count, unsigned paste_count,
float times, float times,
boost::shared_ptr<ARDOUR::AutomationList> alist) boost::shared_ptr<ARDOUR::AutomationList> alist)
@ -339,7 +339,7 @@ AutomationStreamView::paste (samplepos_t pos,
list<RegionView*>::const_iterator prev = region_views.begin (); list<RegionView*>::const_iterator prev = region_views.begin ();
for (list<RegionView*>::const_iterator i = region_views.begin(); i != region_views.end(); ++i) { for (list<RegionView*>::const_iterator i = region_views.begin(); i != region_views.end(); ++i) {
if ((*i)->region()->position() > pos) { if ((*i)->region()->nt_position() > pos) {
break; break;
} }
prev = i; prev = i;
@ -348,7 +348,7 @@ AutomationStreamView::paste (samplepos_t pos,
boost::shared_ptr<Region> r = (*prev)->region (); boost::shared_ptr<Region> r = (*prev)->region ();
/* If *prev doesn't cover pos, it's no good */ /* 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; return false;
} }

View file

@ -68,7 +68,7 @@ public:
std::list<boost::shared_ptr<AutomationLine> > get_lines () const; std::list<boost::shared_ptr<AutomationLine> > get_lines () const;
bool paste (samplepos_t pos, bool paste (Temporal::timepos_t const & pos,
unsigned paste_count, unsigned paste_count,
float times, float times,
boost::shared_ptr<ARDOUR::AutomationList> list); boost::shared_ptr<ARDOUR::AutomationList> list);

View file

@ -107,7 +107,7 @@ public:
/* editing operations */ /* editing operations */
void cut_copy_clear (Selection&, Editing::CutCopyOp); 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); int set_state (const XMLNode&, int version);

View file

@ -1749,7 +1749,7 @@ Editor::loudness_analyze_range_selection ()
if (!pl || !rui) { if (!pl || !rui) {
continue; continue;
} }
for (std::list<AudioRange>::iterator j = ts.begin (); j != ts.end (); ++j) { for (std::list<TimelineRange>::iterator j = ts.begin (); j != ts.end (); ++j) {
total_work += j->length (); 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. * @param event Event to get current key modifier information from, or 0.
*/ */
void 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) { if (!_session || !event) {
return; return;
@ -2618,33 +2618,32 @@ Editor::snap_to_with_modifier (MusicSample& start, GdkEvent const * event, Round
if (ArdourKeyboard::indicates_snap (event->button.state)) { if (ArdourKeyboard::indicates_snap (event->button.state)) {
if (_snap_mode == SnapOff) { if (_snap_mode == SnapOff) {
snap_to_internal (start, direction, pref); snap_to_internal (start, direction, for_mark);
} else { } else {
start.set (start.sample, 0); start = start.sample();
} }
} else { } else {
if (_snap_mode != SnapOff) { 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)) { } else if (ArdourKeyboard::indicates_snap_delta (event->button.state)) {
/* SnapOff, but we pressed the snap_delta modifier */ /* SnapOff, but we pressed the snap_delta modifier */
snap_to_internal (start, direction, pref); snap_to_internal (start, direction, for_mark);
} else { } else {
start.set (start.sample, 0); start = start.sample ();
} }
} }
} }
void 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)) { if (!_session || (_snap_mode == SnapOff && !ensure_snap)) {
start.set (start.sample, 0); start = start.sample ();
return; return;
} }
snap_to_internal (start, direction, pref, ensure_snap); snap_to_internal (start, direction, for_mark, ensure_snap);
} }
static void static void
check_best_snap (samplepos_t presnap, samplepos_t &test, samplepos_t &dist, samplepos_t &best) 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 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 ()); UIConfiguration const& uic (UIConfiguration::instance ());
const samplepos_t presnap = start.sample; const samplepos_t presnap = start.sample;
@ -4054,23 +4053,28 @@ Editor::set_show_touched_automation (bool yn)
instant_save (); instant_save ();
} }
samplecnt_t PlaylistSelector&
Editor::get_paste_offset (samplepos_t pos, unsigned paste_count, samplecnt_t duration) 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) { if (paste_count == 0) {
/* don't bother calculating an offset that will be zero anyway */ /* 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 */ /* 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 */ /* snap offset so pos + offset is aligned to the grid */
MusicSample offset_pos (pos + offset, 0); Temporal::timepos_t snap_pos (pos + offset);
snap_to(offset_pos, RoundUpMaybe); snap_to (snap_pos, Temporal::RoundUpMaybe);
offset = offset_pos.sample - pos;
return offset; return pos.distance (snap_pos);
} }
unsigned unsigned

View file

@ -351,10 +351,10 @@ public:
/* nudge is initiated by transport controls owned by ARDOUR_UI */ /* nudge is initiated by transport controls owned by ARDOUR_UI */
samplecnt_t get_nudge_distance (samplepos_t pos, samplecnt_t& next); Temporal::timecnt_t get_nudge_distance (Temporal::timepos_t const & pos, Temporal::timecnt_t& next);
samplecnt_t get_paste_offset (samplepos_t pos, unsigned paste_count, samplecnt_t duration); Temporal::timecnt_t get_paste_offset (Temporal::timepos_t const & pos, unsigned paste_count, Temporal::timecnt_t const & duration);
unsigned get_grid_beat_divisions(samplepos_t position); unsigned get_grid_beat_divisions(Temporal::timepos_t const & position);
Temporal::Beats get_grid_type_as_beats (bool& success, samplepos_t 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); int32_t get_grid_music_divisions (uint32_t event_state);
@ -384,7 +384,7 @@ public:
void set_group_tabs (); void set_group_tabs ();
/* returns the left-most and right-most time that the gui should allow the user to scroll to */ /* returns the left-most and right-most time that the gui should allow the user to scroll to */
std::pair <samplepos_t,samplepos_t> session_gui_extents (bool use_extra = true) const; std::pair <Temporal::timepos_t,Temporal::timepos_t> session_gui_extents (bool use_extra = true) const;
/* RTAV Automation display option */ /* RTAV Automation display option */
bool show_touched_automation () const; bool show_touched_automation () const;
@ -457,15 +457,13 @@ public:
ARDOUR::SrcQuality quality, ARDOUR::SrcQuality quality,
ARDOUR::MidiTrackNameSource mts, ARDOUR::MidiTrackNameSource mts,
ARDOUR::MidiTempoMapDisposition mtd, ARDOUR::MidiTempoMapDisposition mtd,
samplepos_t& pos, Temporal::timepos_t& pos,
boost::shared_ptr<ARDOUR::PluginInfo> instrument = boost::shared_ptr<ARDOUR::PluginInfo>(), boost::shared_ptr<ARDOUR::PluginInfo> instrument = boost::shared_ptr<ARDOUR::PluginInfo>());
bool with_markers = false
);
void do_embed (std::vector<std::string> paths, void do_embed (std::vector<std::string> paths,
Editing::ImportDisposition disposition, Editing::ImportDisposition disposition,
Editing::ImportMode mode, Editing::ImportMode mode,
samplepos_t& pos, Temporal::timepos_t& pos,
boost::shared_ptr<ARDOUR::PluginInfo> instrument = boost::shared_ptr<ARDOUR::PluginInfo>()); boost::shared_ptr<ARDOUR::PluginInfo> instrument = boost::shared_ptr<ARDOUR::PluginInfo>());
void get_regionview_corresponding_to (boost::shared_ptr<ARDOUR::Region> region, std::vector<RegionView*>& regions); void get_regionview_corresponding_to (boost::shared_ptr<ARDOUR::Region> region, std::vector<RegionView*>& regions);
@ -477,15 +475,15 @@ public:
TrackViewList axis_views_from_routes (boost::shared_ptr<ARDOUR::RouteList>) const; TrackViewList axis_views_from_routes (boost::shared_ptr<ARDOUR::RouteList>) const;
void snap_to (ARDOUR::MusicSample& first, void snap_to (Temporal::timepos_t & first,
ARDOUR::RoundMode direction = ARDOUR::RoundNearest, ARDOUR::RoundMode direction = ARDOUR::RoundNearest,
ARDOUR::SnapPref pref = ARDOUR::SnapToAny_Visual, ARDOUR::SnapPref pref = ARDOUR::SnapToAny_Visual,
bool ensure_snap = false); bool ensure_snap = false);
void snap_to_with_modifier (ARDOUR::MusicSample& first, void snap_to_with_modifier (Temporal::timepos_t & first,
GdkEvent const* ev, GdkEvent const* ev,
ARDOUR::RoundMode direction = ARDOUR::RoundNearest, 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); void set_snapped_cursor_position (samplepos_t pos);
@ -729,7 +727,7 @@ private:
void setup_lines (); void setup_lines ();
void set_name (const std::string&); 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); void set_color_rgba (uint32_t);
}; };
@ -1393,8 +1391,8 @@ private:
void bring_in_external_audio (Editing::ImportMode mode, samplepos_t& pos); void bring_in_external_audio (Editing::ImportMode mode, samplepos_t& pos);
bool idle_drop_paths (std::vector<std::string> paths, samplepos_t sample, double ypos, bool copy); bool idle_drop_paths (std::vector<std::string> paths, Temporal::timepos_t sample, double ypos, bool copy);
void drop_paths_part_two (const std::vector<std::string>& paths, samplepos_t sample, double ypos, bool copy); void drop_paths_part_two (const std::vector<std::string>& paths, Temporal::timepos_t const & sample, double ypos, bool copy);
int import_sndfiles (std::vector<std::string> paths, int import_sndfiles (std::vector<std::string> paths,
Editing::ImportDisposition disposition, Editing::ImportDisposition disposition,
@ -1977,7 +1975,7 @@ private:
/* object rubberband select process */ /* 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; ArdourCanvas::Rectangle* rubberband_rect;
@ -2081,7 +2079,7 @@ private:
void external_edit_region (); void external_edit_region ();
int write_audio_selection (TimeSelection&); int write_audio_selection (TimeSelection&);
bool write_audio_range (ARDOUR::AudioPlaylist&, const ARDOUR::ChanCount& channels, std::list<ARDOUR::AudioRange>&); bool write_audio_range (ARDOUR::AudioPlaylist&, const ARDOUR::ChanCount& channels, std::list<ARDOUR::TimelineRange>&);
void write_selection (); void write_selection ();
@ -2269,11 +2267,15 @@ private:
ARDOUR::RoundMode direction, ARDOUR::RoundMode direction,
ARDOUR::SnapPref gpref); ARDOUR::SnapPref gpref);
void snap_to_internal (ARDOUR::MusicSample& first, void snap_to_internal (Temporal::timepos_t & first,
ARDOUR::RoundMode direction = ARDOUR::RoundNearest, Temporal::RoundMode direction = Temporal::RoundNearest,
ARDOUR::SnapPref gpref = ARDOUR::SnapToAny_Visual, bool for_mark = false,
bool ensure_snap = 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, samplepos_t snap_to_marker (samplepos_t presnap,
ARDOUR::RoundMode direction = ARDOUR::RoundNearest); ARDOUR::RoundMode direction = ARDOUR::RoundNearest);

View file

@ -347,7 +347,7 @@ Editor::do_import (vector<string> paths,
SrcQuality quality, SrcQuality quality,
MidiTrackNameSource midi_track_name_source, MidiTrackNameSource midi_track_name_source,
MidiTempoMapDisposition smf_tempo_disposition, MidiTempoMapDisposition smf_tempo_disposition,
samplepos_t& pos, timepos_t& pos,
ARDOUR::PluginInfoPtr instrument, ARDOUR::PluginInfoPtr instrument,
bool with_markers) bool with_markers)
{ {
@ -502,11 +502,7 @@ Editor::do_import (vector<string> paths,
} }
void void
Editor::do_embed (vector<string> paths, Editor::do_embed (vector<string> paths, ImportDisposition import_as, ImportMode mode, timepos_t& pos, ARDOUR::PluginInfoPtr instrument)
ImportDisposition import_as,
ImportMode mode,
samplepos_t& pos,
ARDOUR::PluginInfoPtr instrument)
{ {
boost::shared_ptr<Track> track; boost::shared_ptr<Track> track;
bool check_sample_rate = true; bool check_sample_rate = true;

View file

@ -390,16 +390,17 @@ Editor::track_canvas_drag_data_received (const RefPtr<Gdk::DragContext>& context
} }
bool bool
Editor::idle_drop_paths (vector<string> paths, samplepos_t sample, double ypos, bool copy) Editor::idle_drop_paths (vector<string> paths, timepos_t sample, double ypos, bool copy)
{ {
drop_paths_part_two (paths, sample, ypos, copy); drop_paths_part_two (paths, sample, ypos, copy);
return false; return false;
} }
void void
Editor::drop_paths_part_two (const vector<string>& paths, samplepos_t sample, double ypos, bool copy) Editor::drop_paths_part_two (const vector<string>& paths, timepos_t const & p, double ypos, bool copy)
{ {
RouteTimeAxisView* tv; RouteTimeAxisView* tv;
timepos_t pos (p);
/* MIDI files must always be imported, because we consider them /* MIDI files must always be imported, because we consider them
* writable. So split paths into two vectors, and follow the import * writable. So split paths into two vectors, and follow the import
@ -423,13 +424,13 @@ Editor::drop_paths_part_two (const vector<string>& paths, samplepos_t sample, do
/* drop onto canvas background: create new tracks */ /* drop onto canvas background: create new tracks */
InstrumentSelector is; // instantiation builds instrument-list and sets default. 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) { if (UIConfiguration::instance().get_only_copy_imported_files() || copy) {
do_import (audio_paths, Editing::ImportDistinctFiles, Editing::ImportAsTrack, do_import (audio_paths, Editing::ImportDistinctFiles, Editing::ImportAsTrack,
SrcBest, SMFTrackName, SMFTempoIgnore, sample); SrcBest, SMFTrackName, SMFTempoIgnore, pos);
} else { } else {
do_embed (audio_paths, Editing::ImportDistinctFiles, ImportAsTrack, sample); do_embed (audio_paths, Editing::ImportDistinctFiles, ImportAsTrack, pos);
} }
} else if ((tv = dynamic_cast<RouteTimeAxisView*> (tvp.first)) != 0) { } else if ((tv = dynamic_cast<RouteTimeAxisView*> (tvp.first)) != 0) {
@ -441,13 +442,13 @@ Editor::drop_paths_part_two (const vector<string>& paths, samplepos_t sample, do
selection->set (tv); selection->set (tv);
do_import (midi_paths, Editing::ImportSerializeFiles, ImportToTrack, do_import (midi_paths, Editing::ImportSerializeFiles, ImportToTrack,
SrcBest, SMFTrackName, SMFTempoIgnore, sample); SrcBest, SMFTrackName, SMFTempoIgnore, pos);
if (UIConfiguration::instance().get_only_copy_imported_files() || copy) { if (UIConfiguration::instance().get_only_copy_imported_files() || copy) {
do_import (audio_paths, Editing::ImportSerializeFiles, Editing::ImportToTrack, do_import (audio_paths, Editing::ImportSerializeFiles, Editing::ImportToTrack,
SrcBest, SMFTrackName, SMFTempoIgnore, sample, boost::shared_ptr<PluginInfo>(), false); SrcBest, SMFTrackName, SMFTempoIgnore, pos, boost::shared_ptr<PluginInfo>(), false);
} else { } 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<Gdk::DragContext>& context,
ev.button.x = x; ev.button.x = x;
ev.button.y = y; 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); snap_to (when);
bool copy = ((context->get_actions() & (Gdk::ACTION_COPY | Gdk::ACTION_LINK | Gdk::ACTION_MOVE)) == Gdk::ACTION_COPY); 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<Gdk::DragContext>& context,
*/ */
Glib::signal_idle().connect (sigc::bind (sigc::mem_fun (*this, &Editor::idle_drop_paths), paths, when.sample, cy, copy)); Glib::signal_idle().connect (sigc::bind (sigc::mem_fun (*this, &Editor::idle_drop_paths), paths, when.sample, cy, copy));
#else #else
drop_paths_part_two (paths, when.sample, cy, copy); drop_paths_part_two (paths, when, cy, copy);
#endif #endif
} }
@ -602,15 +603,15 @@ Editor::autoscroll_active () const
return autoscroll_connection.connected (); return autoscroll_connection.connected ();
} }
std::pair <samplepos_t,samplepos_t> std::pair <timepos_t,timepos_t>
Editor::session_gui_extents (bool use_extra) const Editor::session_gui_extents (bool use_extra) const
{ {
if (!_session) { if (!_session) {
return std::pair <samplepos_t,samplepos_t>(max_samplepos,0); return std::make_pair (timepos_t::max (Temporal::AudioTime), timepos_t (0));
} }
samplecnt_t session_extent_start = _session->current_start_sample(); timepos_t session_extent_start (_session->current_start_sample());
samplecnt_t session_extent_end = _session->current_end_sample(); timepos_t session_extent_end (_session->current_end_sample());
/* calculate the extents of all regions in every playlist /* 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. * 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<RouteList> rl = _session->get_routes(); boost::shared_ptr<RouteList> rl = _session->get_routes();
for (RouteList::iterator r = rl->begin(); r != rl->end(); ++r) { for (RouteList::iterator r = rl->begin(); r != rl->end(); ++r) {
boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (*r); boost::shared_ptr<Track> tr = boost::dynamic_pointer_cast<Track> (*r);
if (!tr) { if (!tr) {
continue; continue;
} }
if (tr->presentation_info ().hidden ()) { if (tr->presentation_info ().hidden ()) {
continue; continue;
} }
pair<samplepos_t, samplepos_t> e = tr->playlist()->get_extent (); pair<timepos_t, timepos_t> e = tr->playlist()->get_extent ();
if (e.first == e.second) { if (e.first == e.second) {
/* no regions present */ /* no regions present */
continue; continue;
@ -641,19 +643,18 @@ Editor::session_gui_extents (bool use_extra) const
if (use_extra) { if (use_extra) {
samplecnt_t const extra = UIConfiguration::instance().get_extra_ui_extents_time() * 60 * _session->nominal_sample_rate(); samplecnt_t const extra = UIConfiguration::instance().get_extra_ui_extents_time() * 60 * _session->nominal_sample_rate();
session_extent_end += extra; session_extent_end += extra;
session_extent_start -= extra; session_extent_start.shift_earlier (extra);
} }
/* range-check */ /* range-check */
if (session_extent_end > max_samplepos) { if (session_extent_end >= timepos_t::max (Temporal::AudioTime)) {
session_extent_end = max_samplepos; session_extent_end = timepos_t::max (Temporal::AudioTime);
} }
if (session_extent_start < 0) { if (session_extent_start.negative()) {
session_extent_start = 0; session_extent_start = timepos_t (0);
} }
std::pair <samplepos_t,samplepos_t> ret (session_extent_start, session_extent_end); return std::make_pair (session_extent_start, session_extent_end);
return ret;
} }
bool bool

View file

@ -2026,7 +2026,7 @@ RegionMoveDrag::finished_no_copy (
rv->region()->set_position (where.sample, 0); rv->region()->set_position (where.sample, 0);
} else { } else {
/* move by music offset */ /* 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())); _editor->session()->add_command (new StatefulDiffCommand (rv->region()));
@ -6091,7 +6091,7 @@ NoteDrag::aborted (bool)
} }
/** Make an AutomationRangeDrag for lines in an AutomationTimeAxisView */ /** Make an AutomationRangeDrag for lines in an AutomationTimeAxisView */
AutomationRangeDrag::AutomationRangeDrag (Editor* editor, AutomationTimeAxisView* atv, list<AudioRange> const & r) AutomationRangeDrag::AutomationRangeDrag (Editor* editor, AutomationTimeAxisView* atv, list<TimelineRange> const & r)
: Drag (editor, atv->base_item ()) : Drag (editor, atv->base_item ())
, _ranges (r) , _ranges (r)
, _y_origin (atv->y_position()) , _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 */ /** Make an AutomationRangeDrag for region gain lines or MIDI controller regions */
AutomationRangeDrag::AutomationRangeDrag (Editor* editor, list<RegionView*> const & v, list<AudioRange> const & r, double y_origin, double y_height) AutomationRangeDrag::AutomationRangeDrag (Editor* editor, list<RegionView*> const & v, list<TimelineRange> const & r, double y_origin, double y_height)
: Drag (editor, v.front()->get_canvas_group ()) : Drag (editor, v.front()->get_canvas_group ())
, _ranges (r) , _ranges (r)
, _y_origin (y_origin) , _y_origin (y_origin)
@ -6151,8 +6151,8 @@ AutomationRangeDrag::setup (list<boost::shared_ptr<AutomationLine> > const & lin
r.second = max_samplepos; r.second = max_samplepos;
} }
/* check this range against all the AudioRanges that we are using */ /* check this range against all the TimelineRanges that we are using */
list<AudioRange>::const_iterator k = _ranges.begin (); list<TimelineRange>::const_iterator k = _ranges.begin ();
while (k != _ranges.end()) { while (k != _ranges.end()) {
if (k->coverage (r.first, r.second) != Evoral::OverlapNone) { if (k->coverage (r.first, r.second) != Evoral::OverlapNone) {
break; break;
@ -6228,7 +6228,7 @@ AutomationRangeDrag::motion (GdkEvent*, bool first_move)
if (!_ranges.empty()) { if (!_ranges.empty()) {
/* add guard points */ /* add guard points */
for (list<AudioRange>::const_iterator i = _ranges.begin(); i != _ranges.end(); ++i) { for (list<TimelineRange>::const_iterator i = _ranges.begin(); i != _ranges.end(); ++i) {
samplecnt_t const half = (i->start + i->end) / 2; 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 (); double const w = i->line->time_converter().to ((*p->model())->when) + i->line->time_converter().origin_b ();
/* see if it's inside a range */ /* see if it's inside a range */
list<AudioRange>::const_iterator k = _ranges.begin (); list<TimelineRange>::const_iterator k = _ranges.begin ();
while (k != _ranges.end() && (k->start >= w || k->end <= w)) { while (k != _ranges.end() && (k->start >= w || k->end <= w)) {
++k; ++k;
} }

View file

@ -1310,8 +1310,8 @@ private:
class AutomationRangeDrag : public Drag class AutomationRangeDrag : public Drag
{ {
public: public:
AutomationRangeDrag (Editor *, AutomationTimeAxisView *, std::list<ARDOUR::AudioRange> const &); AutomationRangeDrag (Editor *, AutomationTimeAxisView *, std::list<ARDOUR::TimelineRange> const &);
AutomationRangeDrag (Editor *, std::list<RegionView*> const &, std::list<ARDOUR::AudioRange> const &, double y_origin, double y_height); AutomationRangeDrag (Editor *, std::list<RegionView*> const &, std::list<ARDOUR::TimelineRange> const &, double y_origin, double y_height);
void start_grab (GdkEvent *, Gdk::Cursor* c = 0); void start_grab (GdkEvent *, Gdk::Cursor* c = 0);
void motion (GdkEvent *, bool); void motion (GdkEvent *, bool);
@ -1327,7 +1327,7 @@ private:
double y_fraction (double global_y_position) const; double y_fraction (double global_y_position) const;
double value (boost::shared_ptr<ARDOUR::AutomationList> list, double x) const; double value (boost::shared_ptr<ARDOUR::AutomationList> list, double x) const;
std::list<ARDOUR::AudioRange> _ranges; std::list<ARDOUR::TimelineRange> _ranges;
/** A line that is part of the drag */ /** A line that is part of the drag */
struct Line { struct Line {

View file

@ -118,7 +118,7 @@ Editor::loudness_assistant (bool range_selection)
samplepos_t start, end; samplepos_t start, end;
TimeSelection const& ts (get_selection().time); TimeSelection const& ts (get_selection().time);
if (range_selection && !ts.empty ()) { if (range_selection && !ts.empty ()) {
start = ts.start(); start = ts.start_sample();
end = ts.end_sample(); end = ts.end_sample();
} else { } else {
start = _session->current_start_sample(); start = _session->current_start_sample();
@ -158,7 +158,7 @@ Editor::measure_master_loudness (samplepos_t start, samplepos_t end, bool is_ran
return; return;
} }
ARDOUR::AudioRange ar (start, end, 0); ARDOUR::TimelineRange ar (timepos_t (start), timepos_t (end), 0);
LoudnessDialog ld (_session, ar, is_range_selection); LoudnessDialog ld (_session, ar, is_range_selection);
@ -320,9 +320,9 @@ Editor::bounce_region_selection (bool with_processing)
boost::shared_ptr<Region> r; boost::shared_ptr<Region> r;
if (with_processing) { 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 { } else {
r = track->bounce_range (region->position(), region->position() + region->length(), itt, boost::shared_ptr<Processor>(), false, bounce_name); r = track->bounce_range (region->position_sample(), region->position_sample() + region->length_samples(), itt, boost::shared_ptr<Processor>(), false, bounce_name);
} }
} }
} }
@ -347,7 +347,7 @@ Editor::write_region (string path, boost::shared_ptr<AudioRegion> region)
/* don't do duplicate of the entire source if that's what is going on here */ /* 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" */ /* XXX should link(2) to create a new inode with "path" */
return true; return true;
} }
@ -396,8 +396,8 @@ Editor::write_region (string path, boost::shared_ptr<AudioRegion> region)
} }
to_read = region->length(); to_read = region->length_samples();
pos = region->position(); pos = region->position_sample();
while (to_read) { while (to_read) {
samplepos_t this_time; samplepos_t this_time;
@ -475,14 +475,14 @@ Editor::write_audio_selection (TimeSelection& ts)
} }
bool bool
Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list<AudioRange>& range) Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list<TimelineRange>& range)
{ {
boost::shared_ptr<AudioFileSource> fs; boost::shared_ptr<AudioFileSource> fs;
const samplepos_t chunk_size = 4096; const samplepos_t chunk_size = 4096;
samplepos_t nframes; timecnt_t nframes;
Sample buf[chunk_size]; Sample buf[chunk_size];
gain_t gain_buffer[chunk_size]; gain_t gain_buffer[chunk_size];
samplepos_t pos; timepos_t pos;
char s[PATH_MAX+1]; char s[PATH_MAX+1];
uint32_t cnt; uint32_t cnt;
string path; string path;
@ -529,15 +529,14 @@ Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list
} }
for (list<AudioRange>::iterator i = range.begin(); i != range.end();) { for (list<TimelineRange>::iterator i = range.begin(); i != range.end();) {
nframes = (*i).length(); nframes = (*i).length();
pos = (*i).start; pos = (*i).start();
while (nframes) { while (nframes.positive()) {
samplepos_t this_time;
this_time = min (nframes, chunk_size); timecnt_t this_time = min (nframes, timecnt_t (chunk_size));
for (uint32_t n=0; n < channels; ++n) { for (uint32_t n=0; n < channels; ++n) {
@ -547,7 +546,7 @@ Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list
break; break;
} }
if (fs->write (buf, this_time) != this_time) { if (fs->write (buf, this_time.samples()) != this_time.samples()) {
goto error_out; goto error_out;
} }
} }
@ -556,24 +555,24 @@ Editor::write_audio_range (AudioPlaylist& playlist, const ChanCount& count, list
pos += this_time; pos += this_time;
} }
list<AudioRange>::iterator tmp = i; list<TimelineRange>::iterator tmp = i;
++tmp; ++tmp;
if (tmp != range.end()) { if (tmp != range.end()) {
/* fill gaps with silence */ /* 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); timecnt_t this_time = min (nframes, timecnt_t (chunk_size));
memset (buf, 0, sizeof (Sample) * this_time); memset (buf, 0, sizeof (Sample) * this_time.samples());
for (uint32_t n=0; n < channels; ++n) { for (uint32_t n=0; n < channels; ++n) {
fs = sources[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; goto error_out;
} }
} }

View file

@ -46,27 +46,32 @@ using namespace Editing;
void void
Editor::keyboard_selection_finish (bool /*add*/, Editing::EditIgnoreOption ign) Editor::keyboard_selection_finish (bool /*add*/, Editing::EditIgnoreOption ign)
{ {
if (_session) { if (!_session) {
return;
}
MusicSample start (selection->time.start(), 0); timepos_t start = selection->time.start_time();
samplepos_t end; timepos_t end;
if ((_edit_point == EditAtPlayhead) && _session->transport_rolling()) { if ((_edit_point == EditAtPlayhead) && _session->transport_rolling()) {
end = _session->audible_sample(); end = _session->audible_sample();
} else { } else {
end = get_preferred_edit_position(ign); 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 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() ) if ( (_edit_point == EditAtPlayhead) && selection->tracks.empty() )
select_all_visible_lanes(); select_all_tracks();
selection->set (start.sample, end); selection->set (start, end);
//if session is playing a range, cancel that //if session is playing a range, cancel that
if (_session->get_play_range()) if (_session->get_play_range()) {
_session->request_cancel_play_range(); _session->request_cancel_play_range();
} }
} }
void void
@ -74,22 +79,22 @@ Editor::keyboard_selection_begin (Editing::EditIgnoreOption ign)
{ {
if (_session) { if (_session) {
MusicSample start (0, 0); timepos_t start;
MusicSample end (selection->time.end_sample(), 0); timepos_t end (selection->time.end_time());
if ((_edit_point == EditAtPlayhead) && _session->transport_rolling()) { if ((_edit_point == EditAtPlayhead) && _session->transport_rolling()) {
start.sample = _session->audible_sample(); start = _session->audible_sample();
} else { } 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 there's not already a sensible selection endpoint, go "forever"
if (start.sample > end.sample) { if (start > end ) {
#ifdef MIXBUS #ifdef MIXBUS
// 4hours at most. // 4hours at most.
// This works around a visual glitch in red-bordered selection rect. // 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 #else
end.sample = max_samplepos; end = timepos_t::max (end.time_domain());
#endif #endif
} }
@ -97,7 +102,7 @@ Editor::keyboard_selection_begin (Editing::EditIgnoreOption ign)
if ( selection->tracks.empty() ) if ( selection->tracks.empty() )
select_all_visible_lanes(); select_all_visible_lanes();
selection->set (start.sample, end.sample); selection->set (start, end);
//if session is playing a range, cancel that //if session is playing a range, cancel that
if (_session->get_play_range()) if (_session->get_play_range())

View file

@ -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->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()); location->FlagsChanged.connect (*this, invalidator (*this), boost::bind (&Editor::location_flags_changed, this, location), gui_context());
pair<Location*,LocationMarkers*> newpair; pair<Location*,LocationMarkers*> newpair;
@ -214,7 +214,7 @@ Editor::location_changed (Location *location)
return; return;
} }
if (location->position_lock_style() == MusicTime) { if (location->position_time_domain() == Temporal::BeatTime) {
lam->set_name ("\u266B" + location->name ()); // BEAMED EIGHTH NOTES lam->set_name ("\u266B" + location->name ()); // BEAMED EIGHTH NOTES
} else { } else {
lam->set_name (location->name ()); 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 */ /* 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()) { if (m->label_on_left()) {
(*prev)->set_right_label_limit (p / 2); (*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 */ /* 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()) { if ((*next)->label_on_left()) {
m->set_right_label_limit (p / 2); m->set_right_label_limit (p / 2);
@ -354,7 +354,7 @@ Editor::update_marker_labels (ArdourCanvas::Container* group)
while (i != sorted.end()) { while (i != sorted.end()) {
if (prev != 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()) { if ((*prev)->label_on_left()) {
(*i)->set_left_label_limit (p); (*i)->set_left_label_limit (p);
@ -365,7 +365,7 @@ Editor::update_marker_labels (ArdourCanvas::Container* group)
} }
if (next != sorted.end()) { 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()) { if ((*next)->label_on_left()) {
(*i)->set_right_label_limit (p / 2); (*i)->set_right_label_limit (p / 2);
@ -613,12 +613,12 @@ Editor::LocationMarkers::set_name (const string& str)
} }
void void
Editor::LocationMarkers::set_position (samplepos_t startf, Editor::LocationMarkers::set_position (timepos_t const & startt,
samplepos_t endf) timepos_t const & endt)
{ {
start->set_position (startf); start->set_position (startt);
if (end) { if (!endt.zero()) {
end->set_position (endf); 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)) { if (!choose_new_marker_name(markername)) {
return; 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")); begin_reversible_command (_("add marker"));
XMLNode &before = _session->locations()->get_state(); XMLNode &before = _session->locations()->get_state();
@ -745,7 +746,8 @@ Editor::mouse_add_new_range (samplepos_t where)
string name; string name;
_session->locations()->next_available_name (name, _("range")); _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")); begin_reversible_command (_("new range marker"));
XMLNode& before = _session->locations()->get_state (); 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"))); items.push_back (CheckMenuElem (_("Glue to Bars and Beats")));
Gtk::CheckMenuItem* glue_item = static_cast<Gtk::CheckMenuItem*> (&items.back()); Gtk::CheckMenuItem* glue_item = static_cast<Gtk::CheckMenuItem*> (&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)); 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"))); items.push_back (CheckMenuElem (_("Glue to Bars and Beats")));
Gtk::CheckMenuItem* glue_item = static_cast<Gtk::CheckMenuItem*> (&items.back()); Gtk::CheckMenuItem* glue_item = static_cast<Gtk::CheckMenuItem*> (&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)); glue_item->signal_activate().connect (sigc::mem_fun (*this, &Editor::toggle_marker_menu_glue));
items.push_back (SeparatorElem()); items.push_back (SeparatorElem());
@ -1202,7 +1204,7 @@ Editor::marker_menu_select_all_selectables_using_range ()
bool is_start; bool is_start;
if (((l = find_location_from_marker (marker, is_start)) != 0) && (l->end() > l->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 = find_location_from_marker (marker, is_start)) != 0) {
if (l->is_mark()) { if (l->is_mark()) {
_session->request_locate (l->start(), MustRoll); _session->request_locate (l->start_sample(), MustRoll);
} }
else { else {
//_session->request_bounded_roll (l->start(), l->end()); //_session->request_bounded_roll (l->start_sample(), l->end());
if (is_start) { if (is_start) {
_session->request_locate (l->start(), MustRoll); _session->request_locate (l->start_sample(), MustRoll);
} else { } 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 = find_location_from_marker (marker, is_start)) != 0) {
if (l->is_mark()) { if (l->is_mark()) {
_session->request_locate (l->start(), MustStop); _session->request_locate (l->start_sample(), MustStop);
} }
else { else {
if (is_start) { if (is_start) {
_session->request_locate (l->start(), MustStop); _session->request_locate (l->start_sample(), MustStop);
} else { } 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; return;
} }
samplepos_t start; timepos_t start;
samplepos_t end; timepos_t end;
_session->locations()->marks_either_side (marker->position(), start, end); _session->locations()->marks_either_side (marker->position(), start, end);
if (end != max_samplepos) { if (end != max_samplepos) {
@ -1329,18 +1331,19 @@ Editor::marker_menu_set_from_playhead ()
Location* l; Location* l;
bool is_start; bool is_start;
const int32_t divisions = get_grid_music_divisions (0);
if ((l = find_location_from_marker (marker, is_start)) != 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()) { if (l->is_mark()) {
l->set_start (_session->audible_sample (), false, true, divisions); l->set_start (timepos_t (_session->audible_sample ()), false);
} }
else { else {
if (is_start) { if (is_start) {
l->set_start (_session->audible_sample (), false, true, divisions); l->set_start (timepos_t (_session->audible_sample ()), false);
} else { } 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 { } else {
if (!selection->time.empty()) { 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()) { } 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 = find_location_from_marker (marker, is_start)) != 0) {
if (l->is_mark()) { if (l->is_mark()) {
_session->request_locate (l->start(), MustRoll); _session->request_locate (l->start().samples(), MustRoll);
} }
else { 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 = find_location_from_marker (marker, is_start)) != 0) {
if (l != transport_loop_location()) { if (l != transport_loop_location()) {
cerr << "Set loop\n"; 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 { } else {
cerr << " at TL\n"; cerr << " at TL\n";
} }
@ -1439,18 +1442,18 @@ Editor::marker_menu_zoom_to_range ()
return; return;
} }
samplecnt_t const extra = l->length() * 0.05; timecnt_t const extra = l->length() * Temporal::ratio_t (5, 100);
samplepos_t a = l->start (); timepos_t a = l->start ();
if (a >= extra) { if (a >= timepos_t (extra)) {
a -= extra; a.shift_earlier (extra);
} }
samplepos_t b = l->end (); timepos_t b = l->end ();
if (b < (max_samplepos - extra)) { if (b < (extra.distance (timepos_t::max (extra.time_domain())))) {
b += extra; b += extra;
} }
temporal_zoom_by_sample (a, b); temporal_zoom_by_sample (a.samples(), b.samples());
} }
void void

View file

@ -1236,7 +1236,7 @@ Editor::button_press_handler_1 (ArdourCanvas::Item* item, GdkEvent* event, ItemT
if (boost::dynamic_pointer_cast<AudioPlaylist> (playlist) == 0) { if (boost::dynamic_pointer_cast<AudioPlaylist> (playlist) == 0) {
continue; continue;
} }
for (list<AudioRange>::const_iterator j = selection->time.begin(); j != selection->time.end(); ++j) { for (list<TimelineRange>::const_iterator j = selection->time.begin(); j != selection->time.end(); ++j) {
boost::shared_ptr<RegionList> rl = playlist->regions_touched (j->start, j->end); boost::shared_ptr<RegionList> rl = playlist->regions_touched (j->start, j->end);
for (RegionList::iterator ir = rl->begin(); ir != rl->end(); ++ir) { for (RegionList::iterator ir = rl->begin(); ir != rl->end(); ++ir) {
RegionView* rv; RegionView* rv;

View file

@ -2723,8 +2723,8 @@ Editor::play_selection ()
if (!get_selection_extents (start, end)) if (!get_selection_extents (start, end))
return; return;
AudioRange ar (start, end, 0); TimelineRange ar (start, end, 0);
list<AudioRange> lar; list<TimelineRange> lar;
lar.push_back (ar); lar.push_back (ar);
_session->request_play_range (&lar, true); _session->request_play_range (&lar, true);
@ -2767,8 +2767,8 @@ Editor::play_with_preroll ()
end = end + preroll; //"post-roll" end = end + preroll; //"post-roll"
AudioRange ar (start, end, 0); TimelineRange ar (start, end, 0);
list<AudioRange> lar; list<TimelineRange> lar;
lar.push_back (ar); lar.push_back (ar);
_session->request_play_range (&lar, true); _session->request_play_range (&lar, true);
@ -3152,10 +3152,10 @@ Editor::new_region_from_selection ()
} }
static void 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)) { 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: case Evoral::OverlapNone:
break; break;
default: default:
@ -3229,7 +3229,7 @@ Editor::separate_regions_between (const TimeSelection& ts)
/* XXX need to consider musical time selections here at some point */ /* XXX need to consider musical time selections here at some point */
for (list<AudioRange>::const_iterator t = ts.begin(); t != ts.end(); ++t) { for (list<TimelineRange>::const_iterator t = ts.begin(); t != ts.end(); ++t) {
if (!in_command) { if (!in_command) {
begin_reversible_command (_("separate")); begin_reversible_command (_("separate"));
@ -3313,7 +3313,7 @@ Editor::separate_region_from_selection ()
if (get_edit_op_range (start, end)) { if (get_edit_op_range (start, end)) {
AudioRange ar (start, end, 1); TimelineRange ar (start, end, 1);
TimeSelection ts; TimeSelection ts;
ts.push_back (ar); ts.push_back (ar);
@ -3347,7 +3347,7 @@ Editor::separate_regions_using_location (Location& loc)
return; return;
} }
AudioRange ar (loc.start(), loc.end(), 1); TimelineRange ar (loc.start(), loc.end(), 1);
TimeSelection ts; TimeSelection ts;
ts.push_back (ar); ts.push_back (ar);
@ -3437,7 +3437,7 @@ Editor::crop_region_to_selection ()
if (!selection->time.empty()) { if (!selection->time.empty()) {
begin_reversible_command (_("Crop Regions to Time Selection")); begin_reversible_command (_("Crop Regions to Time Selection"));
for (std::list<AudioRange>::iterator i = selection->time.begin(); i != selection->time.end(); ++i) { for (std::list<TimelineRange>::iterator i = selection->time.begin(); i != selection->time.end(); ++i) {
crop_region_to ((*i).start, (*i).end); crop_region_to ((*i).start, (*i).end);
} }
commit_reversible_command(); commit_reversible_command();
@ -4207,8 +4207,8 @@ Editor::bounce_range_selection (bool replace, bool enable_processing)
if (replace) { if (replace) {
/*remove the edxisting regions under the edit range*/ /*remove the edxisting regions under the edit range*/
list<AudioRange> ranges; list<TimelineRange> ranges;
ranges.push_back (AudioRange (start, start+cnt, 0)); ranges.push_back (TimelineRange (start, start+cnt, 0));
playlist->cut (ranges); // discard result playlist->cut (ranges); // discard result
/*SPECIAL CASE: we are bouncing to a new Source *AND* replacing the existing range on the timeline (consolidate)*/ /*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; in_command = true;
} }
std::list<AudioRange> rl; std::list<TimelineRange> rl;
AudioRange ar(pos, pos+samples, 0); TimelineRange ar(pos, pos+samples, 0);
rl.push_back(ar); rl.push_back(ar);
pl->cut (rl); pl->cut (rl);
pl->shift (pos, -samples, true, ignore_music_glue); pl->shift (pos, -samples, true, ignore_music_glue);

View file

@ -601,10 +601,11 @@ EditorRegions::clock_format_changed ()
} }
void 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; Temporal::BBT_Time bbt;
Timecode::Time timecode; Timecode::Time timecode;
samplepos_t pos (p.samples());
if (pos < 0) { if (pos < 0) {
error << string_compose (_ ("EditorRegions::format_position: negative timecode position: %1"), pos) << endmsg; error << string_compose (_ ("EditorRegions::format_position: negative timecode position: %1"), pos) << endmsg;
@ -713,7 +714,7 @@ EditorRegions::populate_row (boost::shared_ptr<Region> region, TreeModel::Row co
if (all || what_changed.contains (Properties::locked)) { if (all || what_changed.contains (Properties::locked)) {
populate_row_locked (region, row); 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); populate_row_glued (region, row);
} }
if (all || what_changed.contains (Properties::muted)) { if (all || what_changed.contains (Properties::muted)) {
@ -775,7 +776,7 @@ EditorRegions::populate_row_length (boost::shared_ptr<Region> region, TreeModel:
Temporal::BBT_Time bbt = map.bbt_at_beat (map.beat_at_sample (region->last_sample ()) - map.beat_at_sample (region->first_sample ())); 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); snprintf (buf, sizeof (buf), "%03d|%02d|%04d", bbt.bars, bbt.beats, bbt.ticks);
} else { } else {
format_position (region->length (), buf, sizeof (buf)); format_position (timepos_t (region->nt_length ()), buf, sizeof (buf));
} }
row[_columns.length] = buf; row[_columns.length] = buf;
@ -790,7 +791,7 @@ EditorRegions::populate_row_end (boost::shared_ptr<Region> region, TreeModel::Ro
if (region->last_sample () >= region->first_sample ()) { if (region->last_sample () >= region->first_sample ()) {
char buf[16]; char buf[16];
format_position (region->last_sample (), buf, sizeof (buf)); format_position (region->nt_last (), buf, sizeof (buf));
row[_columns.end] = buf; row[_columns.end] = buf;
} else { } else {
row[_columns.end] = "empty"; row[_columns.end] = "empty";
@ -800,10 +801,10 @@ EditorRegions::populate_row_end (boost::shared_ptr<Region> region, TreeModel::Ro
void void
EditorRegions::populate_row_position (boost::shared_ptr<Region> region, TreeModel::Row const& row) EditorRegions::populate_row_position (boost::shared_ptr<Region> region, TreeModel::Row const& row)
{ {
row[_columns.position] = region->position (); row[_columns.position] = region->nt_position ();
char buf[16]; char buf[16];
format_position (region->position (), buf, sizeof (buf)); format_position (region->nt_position (), buf, sizeof (buf));
row[_columns.start] = buf; row[_columns.start] = buf;
} }
@ -813,7 +814,7 @@ EditorRegions::populate_row_sync (boost::shared_ptr<Region> region, TreeModel::R
#ifndef SHOW_REGION_EXTRAS #ifndef SHOW_REGION_EXTRAS
return; return;
#endif #endif
if (region->sync_position () == region->position ()) { if (region->sync_position () == region->nt_position ()) {
row[_columns.sync] = _ ("Start"); row[_columns.sync] = _ ("Start");
} else if (region->sync_position () == (region->last_sample ())) { } else if (region->sync_position () == (region->last_sample ())) {
row[_columns.sync] = _ ("End"); row[_columns.sync] = _ ("End");
@ -863,7 +864,7 @@ EditorRegions::populate_row_locked (boost::shared_ptr<Region> region, TreeModel:
void void
EditorRegions::populate_row_glued (boost::shared_ptr<Region> region, TreeModel::Row const& row) EditorRegions::populate_row_glued (boost::shared_ptr<Region> region, TreeModel::Row const& row)
{ {
if (region->position_lock_style () == MusicTime) { if (region->position_time_domain () == Temporal::BeatTime) {
row[_columns.glued] = true; row[_columns.glued] = true;
} else { } else {
row[_columns.glued] = false; row[_columns.glued] = false;
@ -890,7 +891,7 @@ EditorRegions::populate_row_name (boost::shared_ptr<Region> region, TreeModel::R
if (region->data_type() == DataType::MIDI) { if (region->data_type() == DataType::MIDI) {
row[_columns.channels] = 0; /*TODO: some better recognition of midi regions*/ row[_columns.channels] = 0; /*TODO: some better recognition of midi regions*/
} else { } else {
row[_columns.channels] = region->n_channels(); row[_columns.channels] = region->sources().size();
} }
row[_columns.tags] = region->tags (); row[_columns.tags] = region->tags ();
@ -1027,7 +1028,7 @@ EditorRegions::drag_data_received (const RefPtr<Gdk::DragContext>& context,
} }
if (_editor->convert_drop_to_paths (paths, context, x, y, data, info, dtime) == 0) { if (_editor->convert_drop_to_paths (paths, context, x, y, data, info, dtime) == 0) {
samplepos_t pos = 0; timepos_t pos;
bool copy = ((context->get_actions () & (Gdk::ACTION_COPY | Gdk::ACTION_LINK | Gdk::ACTION_MOVE)) == Gdk::ACTION_COPY); 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) { if (UIConfiguration::instance ().get_only_copy_imported_files () || copy) {
@ -1232,7 +1233,7 @@ EditorRegions::glued_changed (std::string const& path)
boost::shared_ptr<ARDOUR::Region> region = (*i)[_columns.region]; boost::shared_ptr<ARDOUR::Region> region = (*i)[_columns.region];
if (region) { if (region) {
/* `glued' means MusicTime, and we're toggling here */ /* `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);
} }
} }
} }

View file

@ -99,7 +99,7 @@ private:
Gtk::TreeModelColumn<std::string> name; Gtk::TreeModelColumn<std::string> name;
Gtk::TreeModelColumn<int> channels; Gtk::TreeModelColumn<int> channels;
Gtk::TreeModelColumn<std::string> tags; Gtk::TreeModelColumn<std::string> tags;
Gtk::TreeModelColumn<samplepos_t> position; Gtk::TreeModelColumn<Temporal::timepos_t> position;
Gtk::TreeModelColumn<std::string> start; Gtk::TreeModelColumn<std::string> start;
Gtk::TreeModelColumn<std::string> end; Gtk::TreeModelColumn<std::string> end;
Gtk::TreeModelColumn<std::string> length; Gtk::TreeModelColumn<std::string> length;
@ -158,7 +158,7 @@ private:
void show_context_menu (int button, int time); 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<ARDOUR::Region>); void add_region (boost::shared_ptr<ARDOUR::Region>);
void destroy_region (boost::shared_ptr<ARDOUR::Region>); void destroy_region (boost::shared_ptr<ARDOUR::Region>);

View file

@ -149,9 +149,9 @@ EditorSummary::render_background_image ()
/* compute start and end points for the summary */ /* compute start and end points for the summary */
std::pair<samplepos_t, samplepos_t> ext = _editor->session_gui_extents(); std::pair<timepos_t, timepos_t> ext = _editor->session_gui_extents();
double theoretical_start = ext.first; double theoretical_start = ext.first.samples();
double theoretical_end = ext.second; double theoretical_end = ext.second.samples();
/* the summary should encompass the full extent of everywhere we've visited since the session was opened */ /* the summary should encompass the full extent of everywhere we've visited since the session was opened */
if (_leftmost < theoretical_start) 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 (); 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); 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) { if (r->region()->position_sample() > _start) {
cairo_move_to (cr, (r->region()->position() - _start) * _x_scale, y); cairo_move_to (cr, (r->region()->position_sample() - _start) * _x_scale, y);
} else { } else {
cairo_move_to (cr, 0, y); cairo_move_to (cr, 0, y);
} }
if ((r->region()->position() + r->region()->length()) > _start) { if ((r->region()->nt_position() + r->region()->nt_length()) > _start) {
cairo_line_to (cr, ((r->region()->position() - _start + r->region()->length())) * _x_scale, y); cairo_line_to (cr, ((r->region()->position_sample() - _start + r->region()->length_samples())) * _x_scale, y);
} else { } else {
cairo_line_to (cr, 0, y); cairo_line_to (cr, 0, y);
} }

View file

@ -103,7 +103,7 @@ Editor::embed_audio_from_video (std::string path, samplepos_t n, bool lock_posit
if (ok && track) { if (ok && track) {
if (lock_position_to_video) { if (lock_position_to_video) {
boost::shared_ptr<ARDOUR::Playlist> pl = track->playlist(); boost::shared_ptr<ARDOUR::Playlist> 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); _session->save_state ("", true);
} }

View file

@ -58,7 +58,7 @@ using namespace ArdourWidgets;
bool LoudnessDialog::_first_time = true; bool LoudnessDialog::_first_time = true;
CLoudnessPreset LoudnessDialog::_last_preset; 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")) : ArdourDialog (as ? _("Loudness Assistant") : _("Loudness Analyzer and Normalizer"))
, _lp (false) , _lp (false)
, _session (s) , _session (s)

View file

@ -36,7 +36,7 @@
#include "loudness_settings.h" #include "loudness_settings.h"
namespace ARDOUR { namespace ARDOUR {
class AudioRange; class TimelineRange;
class ExportAnalysis; class ExportAnalysis;
class ExportStatus; class ExportStatus;
class PluginInsert; class PluginInsert;
@ -47,7 +47,7 @@ namespace ARDOUR {
class LoudnessDialog : public ArdourDialog class LoudnessDialog : public ArdourDialog
{ {
public: public:
LoudnessDialog (ARDOUR::Session*, ARDOUR::AudioRange const&, bool); LoudnessDialog (ARDOUR::Session*, ARDOUR::TimelineRange const&, bool);
int run (); int run ();
float gain_db () const; float gain_db () const;
@ -86,7 +86,7 @@ private:
static CLoudnessPreset _last_preset; static CLoudnessPreset _last_preset;
ARDOUR::Session* _session; ARDOUR::Session* _session;
ARDOUR::AudioRange const& _range; ARDOUR::TimelineRange const& _range;
boost::shared_ptr<ARDOUR::ExportStatus> _status; boost::shared_ptr<ARDOUR::ExportStatus> _status;
bool _autostart; bool _autostart;

View file

@ -852,7 +852,7 @@ LuaInstance::register_classes (lua_State* L)
.addFunction ("regionlist", &RegionSelection::regionlist) // XXX check windows binding (libardour) .addFunction ("regionlist", &RegionSelection::regionlist) // XXX check windows binding (libardour)
.endClass () .endClass ()
.deriveClass <TimeSelection, std::list<ARDOUR::AudioRange> > ("TimeSelection") .deriveClass <TimeSelection, std::list<ARDOUR::TimelineRange> > ("TimeSelection")
.addFunction ("start", &TimeSelection::start) .addFunction ("start", &TimeSelection::start)
.addFunction ("end_sample", &TimeSelection::end_sample) .addFunction ("end_sample", &TimeSelection::end_sample)
.addFunction ("length", &TimeSelection::length) .addFunction ("length", &TimeSelection::length)

View file

@ -71,7 +71,7 @@ void ArdourMarker::setup_sizes(const double timebar_height)
} }
ArdourMarker::ArdourMarker (PublicEditor& ed, ArdourCanvas::Container& parent, guint32 rgba, const string& annotation, 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) : editor (ed)
, _parent (&parent) , _parent (&parent)
@ -267,8 +267,8 @@ ArdourMarker::ArdourMarker (PublicEditor& ed, ArdourCanvas::Container& parent, g
} }
sample_position = sample; _position = pos;
unit_position = editor.sample_to_pixel (sample); unit_position = editor.sample_to_pixel (pos.samples());
unit_position -= _shift; unit_position -= _shift;
group = new ArdourCanvas::Container (&parent, ArdourCanvas::Duple (unit_position, 1)); group = new ArdourCanvas::Container (&parent, ArdourCanvas::Duple (unit_position, 1));
@ -530,18 +530,18 @@ ArdourMarker::setup_name_display ()
} }
void 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); group->set_x_position (unit_position);
setup_line (); setup_line ();
sample_position = sample; _position = pos;
} }
void void
ArdourMarker::reposition () ArdourMarker::reposition ()
{ {
set_position (sample_position); set_position (_position);
} }
void void
@ -633,7 +633,9 @@ ArdourMarker::set_right_label_limit (double p)
TempoMarker::TempoMarker (PublicEditor& editor, ArdourCanvas::Container& parent, guint32 rgba, const string& text, TempoMarker::TempoMarker (PublicEditor& editor, ArdourCanvas::Container& parent, guint32 rgba, const string& text,
ARDOUR::TempoSection& temp) 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) _tempo (temp)
{ {
group->Event.connect (sigc::bind (sigc::mem_fun (editor, &PublicEditor::canvas_tempo_marker_event), group, this)); 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, MeterMarker::MeterMarker (PublicEditor& editor, ArdourCanvas::Container& parent, guint32 rgba, const string& text,
ARDOUR::MeterSection& m) 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) _meter (m)
{ {
group->Event.connect (sigc::bind (sigc::mem_fun (editor, &PublicEditor::canvas_meter_marker_event), group, this)); group->Event.connect (sigc::bind (sigc::mem_fun (editor, &PublicEditor::canvas_meter_marker_event), group, this));

View file

@ -67,7 +67,7 @@ public:
ArdourMarker (PublicEditor& editor, ArdourCanvas::Container &, guint32 rgba, const std::string& text, Type, 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 (); virtual ~ArdourMarker ();
@ -82,13 +82,13 @@ public:
void set_show_line (bool); void set_show_line (bool);
void set_line_height (double); 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_name (const std::string&);
void set_points_color (uint32_t rgba); void set_points_color (uint32_t rgba);
void set_color_rgba (uint32_t rgba); void set_color_rgba (uint32_t rgba);
void setup_line (); void setup_line ();
samplepos_t position() const { return sample_position; } ARDOUR::timepos_t position() const { return _position; }
ArdourCanvas::Container * get_parent() { return _parent; } ArdourCanvas::Container * get_parent() { return _parent; }
void reparent (ArdourCanvas::Container & parent); void reparent (ArdourCanvas::Container & parent);
@ -126,7 +126,7 @@ protected:
std::string _name; std::string _name;
double unit_position; double unit_position;
samplepos_t sample_position; ARDOUR::timepos_t _position;
double _shift; double _shift;
Type _type; Type _type;
int name_height; int name_height;

View file

@ -33,8 +33,7 @@ public:
MidiAutomationLine (const std::string&, TimeAxisView&, ArdourCanvas::Item&, MidiAutomationLine (const std::string&, TimeAxisView&, ArdourCanvas::Item&,
boost::shared_ptr<ARDOUR::AutomationList>, boost::shared_ptr<ARDOUR::AutomationList>,
boost::shared_ptr<ARDOUR::MidiRegion>, boost::shared_ptr<ARDOUR::MidiRegion>,
Evoral::Parameter, Evoral::Parameter);
Evoral::TimeConverter<double, ARDOUR::samplepos_t>* converter = 0);
MementoCommandBinder<ARDOUR::AutomationList>* memento_command_binder (); MementoCommandBinder<ARDOUR::AutomationList>* memento_command_binder ();

View file

@ -2834,46 +2834,6 @@ MidiRegionView::get_end_position_pixels()
return trackview.editor().sample_to_pixel(sample); 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 void
MidiRegionView::begin_resizing (bool /*at_front*/) MidiRegionView::begin_resizing (bool /*at_front*/)
{ {

View file

@ -271,46 +271,13 @@ public:
*/ */
double snap_to_pixel(double x, bool ensure_snap = false); 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 x a pixel coordinate relative to region start
* @param ensure_snap ignore SnapOff and magnetic snap. * @param ensure_snap ignore SnapOff and magnetic snap.
* Required for inverting snap logic with modifier keys and snap delta calculation. * 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); Temporal::timepos_t snap_pixel_to_time (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;
void goto_previous_note (bool add_to_selection); void goto_previous_note (bool add_to_selection);
void goto_next_note (bool add_to_selection); void goto_next_note (bool add_to_selection);

View file

@ -95,7 +95,7 @@ public:
void get_regions_with_selected_data (RegionSelection&); 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::NoteMode note_mode() const { return _note_mode; }
ARDOUR::ColorMode color_mode() const { return _color_mode; } ARDOUR::ColorMode color_mode() const { return _color_mode; }

View file

@ -984,7 +984,7 @@ Mixer_UI::fan_out (boost::weak_ptr<Route> wr, bool to_busses, bool group)
boost::shared_ptr<AutomationControl> msac = route->master_send_enable_controllable (); boost::shared_ptr<AutomationControl> msac = route->master_send_enable_controllable ();
if (msac) { 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); msac->set_value (0, PBD::Controllable::NoGroup);
} }
@ -3635,7 +3635,7 @@ Mixer_UI::control_action (boost::shared_ptr<T> (Stripable::*get_control)() const
if (s) { if (s) {
ac = (s.get()->*get_control)(); ac = (s.get()->*get_control)();
if (ac) { if (ac) {
ac->start_touch (_session->audible_sample ()); ac->start_touch (timepos_t (_session->audible_sample ()));
cl->push_back (ac); cl->push_back (ac);
if (!have_val) { if (!have_val) {
val = !ac->get_value(); val = !ac->get_value();

View file

@ -152,7 +152,7 @@ public:
* Snap a value according to the current snap setting. * Snap a value according to the current snap setting.
* ensure_snap overrides SnapOff and magnetic snap * 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::RoundMode direction = ARDOUR::RoundNearest,
ARDOUR::SnapPref gpref = ARDOUR::SnapToAny_Visual, ARDOUR::SnapPref gpref = ARDOUR::SnapToAny_Visual,
bool ensure_snap = false) = 0; bool ensure_snap = false) = 0;
@ -261,10 +261,10 @@ public:
/** Import existing media */ /** Import existing media */
virtual void do_import (std::vector<std::string> paths, Editing::ImportDisposition, Editing::ImportMode mode, ARDOUR::SrcQuality, virtual void do_import (std::vector<std::string> paths, Editing::ImportDisposition, Editing::ImportMode mode, ARDOUR::SrcQuality,
ARDOUR::MidiTrackNameSource, ARDOUR::MidiTempoMapDisposition, samplepos_t&, ARDOUR::MidiTrackNameSource, ARDOUR::MidiTempoMapDisposition, Temporal::timepos_t&,
boost::shared_ptr<ARDOUR::PluginInfo> instrument = boost::shared_ptr<ARDOUR::PluginInfo>(), boost::shared_ptr<ARDOUR::PluginInfo> instrument = boost::shared_ptr<ARDOUR::PluginInfo>(),
bool with_markers = false) = 0; bool with_markers = false) = 0;
virtual void do_embed (std::vector<std::string> paths, Editing::ImportDisposition, Editing::ImportMode mode, samplepos_t&, virtual void do_embed (std::vector<std::string> paths, Editing::ImportDisposition, Editing::ImportMode mode, Temporal::timepos_t&,
boost::shared_ptr<ARDOUR::PluginInfo> instrument = boost::shared_ptr<ARDOUR::PluginInfo>()) = 0; boost::shared_ptr<ARDOUR::PluginInfo> instrument = boost::shared_ptr<ARDOUR::PluginInfo>()) = 0;
/** Open main export dialog */ /** 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 mouse_add_new_marker (samplepos_t where, bool is_cd=false) = 0;
virtual void foreach_time_axis_view (sigc::slot<void,TimeAxisView&>) = 0; virtual void foreach_time_axis_view (sigc::slot<void,TimeAxisView&>) = 0;
virtual void add_to_idle_resize (TimeAxisView*, int32_t) = 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 Temporal::timecnt_t get_nudge_distance (Temporal::timepos_t const & pos, Temporal::timecnt_t& next) = 0;
virtual samplecnt_t get_paste_offset (samplepos_t pos, unsigned paste_count, samplecnt_t duration) = 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(samplepos_t position) = 0; virtual unsigned get_grid_beat_divisions(Temporal::timepos_t const & position) = 0;
virtual Temporal::Beats get_grid_type_as_beats (bool& success, samplepos_t 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 int32_t get_grid_music_divisions (uint32_t event_state) = 0;
virtual void edit_notes (MidiRegionView*) = 0; virtual void edit_notes (MidiRegionView*) = 0;
@ -496,7 +496,7 @@ public:
virtual ARDOUR::Location* find_location_from_marker (ArdourMarker*, bool&) const = 0; 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 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, GdkEvent const* ev,
ARDOUR::RoundMode direction = ARDOUR::RoundNearest, ARDOUR::RoundMode direction = ARDOUR::RoundNearest,
ARDOUR::SnapPref gpref = ARDOUR::SnapToAny_Visual) = 0; ARDOUR::SnapPref gpref = ARDOUR::SnapToAny_Visual) = 0;

View file

@ -153,7 +153,7 @@ QuantizeDialog::grid_size_to_musical_time (const string& txt) const
if ( txt == _grid_strings[0] ) { //"Main Grid" if ( txt == _grid_strings[0] ) { //"Main Grid"
bool success; 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) { if (!success) {
return 1.0; return 1.0;
} }

View file

@ -286,27 +286,37 @@ RegionSelection::involves (const TimeAxisView& tv) const
return false; return false;
} }
samplepos_t timepos_t
RegionSelection::start () const RegionSelection::start_time () const
{ {
samplepos_t s = max_samplepos; if (empty()) {
for (RegionSelection::const_iterator i = begin(); i != end(); ++i) { return timepos_t ();
s = min (s, (*i)->region()->position ());
} }
if (s == max_samplepos) { timepos_t s = timepos_t::max (front()->nt_position().time_domain());
return 0;
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; return s;
} }
samplepos_t timepos_t
RegionSelection::end_sample () const 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) { 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; return e;

View file

@ -57,11 +57,8 @@ public:
void clear_all(); void clear_all();
samplepos_t start () const; Temporal::timepos_t start_time () const;
Temporal::timepos_t end_time () const;
/* "end" collides with list<>::end */
samplepos_t end_sample () const;
const std::list<RegionView *>& by_layer() const { return _bylayer; } const std::list<RegionView *>& by_layer() const { return _bylayer; }
void by_position (std::list<RegionView*>&) const; void by_position (std::list<RegionView*>&) const;

View file

@ -1160,31 +1160,48 @@ RegionView::move_contents (sampleoffset_t distance)
region_changed (PropertyChange (ARDOUR::Properties::start)); 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. * @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. * 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 timepos_t
RegionView::snap_sample_to_sample (sampleoffset_t x, bool ensure_snap) const RegionView::snap_region_time_to_region_time (timepos_t const & x, bool ensure_snap) const
{ {
PublicEditor& editor = trackview.editor(); PublicEditor& editor = trackview.editor();
/* x is region relative, convert it to global absolute samples */ /* x is region relative, convert it to global absolute time */
samplepos_t const session_sample = x + _region->position(); timepos_t const session_sample = _region->position() + x;
/* try a snap in either direction */ /* try a snap in either direction */
MusicSample sample (session_sample, 0); timepos_t snapped = session_sample;
editor.snap_to (sample, RoundNearest, SnapToAny_Visual, ensure_snap); editor.snap_to (snapped, RoundNearest, false, ensure_snap);
/* if we went off the beginning of the region, snap forwards */ /* if we went off the beginning of the region, snap forwards */
if (sample.sample < _region->position ()) { if (snapped < _region->position ()) {
sample.sample = session_sample; snapped = session_sample;
editor.snap_to (sample, RoundUpAlways, SnapToAny_Visual, ensure_snap); editor.snap_to (snapped, RoundUpAlways, false, ensure_snap);
} }
/* back to region relative, keeping the relevant divisor */ /* back to region relative */
return MusicSample (sample.sample - _region->position(), sample.division); 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 void

View file

@ -79,14 +79,14 @@ public:
virtual void set_height (double); virtual void set_height (double);
virtual void set_samples_per_pixel (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 move (double xdelta, double ydelta);
void raise_to_top (); void raise_to_top ();
void lower_to_bottom (); 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 (); virtual void show_region_editor ();
void hide_region_editor (); void hide_region_editor ();
@ -125,11 +125,11 @@ public:
struct PositionOrder { struct PositionOrder {
bool operator()(const RegionView* a, const RegionView* b) { 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 (); void update_visibility ();
@ -172,6 +172,9 @@ protected:
void maybe_raise_cue_markers (); 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<ARDOUR::Region> _region; boost::shared_ptr<ARDOUR::Region> _region;
ArdourCanvas::Polygon* sync_mark; ///< polgyon for sync position ArdourCanvas::Polygon* sync_mark; ///< polgyon for sync position

View file

@ -241,14 +241,14 @@ RhythmFerret::run_analysis ()
for (RegionSelection::iterator i = regions_with_transients.begin(); i != regions_with_transients.end(); ++i) { for (RegionSelection::iterator i = regions_with_transients.begin(); i != regions_with_transients.end(); ++i) {
boost::shared_ptr<Readable> rd = boost::static_pointer_cast<AudioRegion> ((*i)->region()); boost::shared_ptr<AudioReadable> rd = boost::static_pointer_cast<AudioRegion> ((*i)->region());
switch (get_analysis_mode()) { switch (get_analysis_mode()) {
case PercussionOnset: case PercussionOnset:
run_percussion_onset_analysis (rd, (*i)->region()->position(), current_results); run_percussion_onset_analysis (rd, (*i)->region()->position_sample(), current_results);
break; break;
case NoteOnset: case NoteOnset:
run_note_onset_analysis (rd, (*i)->region()->position(), current_results); run_note_onset_analysis (rd, (*i)->region()->position_sample(), current_results);
break; break;
default: default:
break; break;
@ -260,7 +260,7 @@ RhythmFerret::run_analysis ()
} }
int int
RhythmFerret::run_percussion_onset_analysis (boost::shared_ptr<Readable> readable, sampleoffset_t /*offset*/, AnalysisFeatureList& results) RhythmFerret::run_percussion_onset_analysis (boost::shared_ptr<AudioReadable> readable, sampleoffset_t /*offset*/, AnalysisFeatureList& results)
{ {
try { try {
TransientDetector t (_session->sample_rate()); TransientDetector t (_session->sample_rate());
@ -315,7 +315,7 @@ RhythmFerret::get_note_onset_function ()
} }
int int
RhythmFerret::run_note_onset_analysis (boost::shared_ptr<Readable> readable, sampleoffset_t /*offset*/, AnalysisFeatureList& results) RhythmFerret::run_note_onset_analysis (boost::shared_ptr<AudioReadable> readable, sampleoffset_t /*offset*/, AnalysisFeatureList& results)
{ {
try { try {
OnsetDetector t (_session->sample_rate()); OnsetDetector t (_session->sample_rate());

View file

@ -36,7 +36,7 @@
#include "region_selection.h" #include "region_selection.h"
namespace ARDOUR { namespace ARDOUR {
class Readable; class AudioReadable;
} }
class Editor; class Editor;
@ -117,8 +117,8 @@ private:
int get_note_onset_function (); int get_note_onset_function ();
void run_analysis (); void run_analysis ();
int run_percussion_onset_analysis (boost::shared_ptr<ARDOUR::Readable> region, ARDOUR::sampleoffset_t offset, ARDOUR::AnalysisFeatureList& results); int run_percussion_onset_analysis (boost::shared_ptr<ARDOUR::AudioReadable> region, ARDOUR::sampleoffset_t offset, ARDOUR::AnalysisFeatureList& results);
int run_note_onset_analysis (boost::shared_ptr<ARDOUR::Readable> region, ARDOUR::sampleoffset_t offset, ARDOUR::AnalysisFeatureList& results); int run_note_onset_analysis (boost::shared_ptr<ARDOUR::AudioReadable> region, ARDOUR::sampleoffset_t offset, ARDOUR::AnalysisFeatureList& results);
void do_action (); void do_action ();
void do_split_action (); void do_split_action ();

View file

@ -1225,7 +1225,7 @@ RouteTimeAxisView::name_entry_changed (string const& str)
} }
boost::shared_ptr<Region> boost::shared_ptr<Region>
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<Playlist> pl = playlist (); boost::shared_ptr<Playlist> pl = playlist ();
@ -1236,8 +1236,8 @@ RouteTimeAxisView::find_next_region (samplepos_t pos, RegionPoint point, int32_t
return boost::shared_ptr<Region> (); return boost::shared_ptr<Region> ();
} }
samplepos_t timepos_t
RouteTimeAxisView::find_next_region_boundary (samplepos_t pos, int32_t dir) RouteTimeAxisView::find_next_region_boundary (timepos_t const & pos, int32_t dir)
{ {
boost::shared_ptr<Playlist> pl = playlist (); boost::shared_ptr<Playlist> 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 pl->find_next_region_boundary (pos, dir);
} }
return -1; return timepos_t::max (pos.time_domain());
} }
void void
@ -1299,7 +1299,7 @@ RouteTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op)
case Delete: case Delete:
if (playlist->cut (time) != 0) { if (playlist->cut (time) != 0) {
if (_editor.should_ripple()) { 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); 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) { if ((what_we_got = playlist->cut (time)) != 0) {
_editor.get_cut_buffer().add (what_we_got); _editor.get_cut_buffer().add (what_we_got);
if (_editor.should_ripple()) { 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); playlist->rdiff_and_add_command (_session);
} }
@ -1323,7 +1323,7 @@ RouteTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op)
case Clear: case Clear:
if ((what_we_got = playlist->cut (time)) != 0) { if ((what_we_got = playlist->cut (time)) != 0) {
if (_editor.should_ripple()) { 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); playlist->rdiff_and_add_command (_session);
what_we_got->release (); what_we_got->release ();
@ -1333,7 +1333,7 @@ RouteTimeAxisView::cut_copy_clear (Selection& selection, CutCopyOp op)
} }
bool 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()) { if (!is_track()) {
return false; 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)); DEBUG_TRACE (DEBUG::CutNPaste, string_compose ("paste to %1\n", pos));
/* add multi-paste offset if applicable */ /* add multi-paste offset if applicable */
std::pair<samplepos_t, samplepos_t> extent = (*p)->get_extent(); std::pair<timepos_t, timepos_t> extent = (*p)->get_extent();
const samplecnt_t duration = extent.second - extent.first; const timecnt_t duration = extent.first.distance (extent.second);
pos += _editor.get_paste_offset(pos, ctx.count, duration);
timepos_t ppos = pos;
ppos += _editor.get_paste_offset (ppos, ctx.count, duration);
pl->clear_changes (); pl->clear_changes ();
pl->clear_owned_changes (); pl->clear_owned_changes ();
if (_editor.should_ripple()) { if (_editor.should_ripple()) {
std::pair<samplepos_t, samplepos_t> extent = (*p)->get_extent_with_endspace(); std::pair<timepos_t, timepos_t> extent = (*p)->get_extent_with_endspace();
samplecnt_t amount = extent.second - extent.first; timecnt_t amount = extent.first.distance (extent.second);
pl->ripple(pos, amount * ctx.times, boost::shared_ptr<Region>()); pl->ripple (ppos, amount * ctx.times, boost::shared_ptr<Region>());
} }
pl->paste (*p, pos, ctx.times, sub_num); pl->paste (*p, ppos, ctx.times);
vector<Command*> cmds; vector<Command*> cmds;
pl->rdiff (cmds); pl->rdiff (cmds);

View file

@ -107,12 +107,12 @@ public:
void toggle_layer_display (); void toggle_layer_display ();
LayerDisplay layer_display () const; LayerDisplay layer_display () const;
boost::shared_ptr<ARDOUR::Region> find_next_region (samplepos_t pos, ARDOUR::RegionPoint, int32_t dir); boost::shared_ptr<ARDOUR::Region> find_next_region (ARDOUR::timepos_t const & pos, ARDOUR::RegionPoint, int32_t dir);
samplepos_t find_next_region_boundary (samplepos_t pos, int32_t dir); ARDOUR::timepos_t find_next_region_boundary (ARDOUR::timepos_t const & pos, int32_t dir);
/* Editing operations */ /* Editing operations */
void cut_copy_clear (Selection&, Editing::CutCopyOp); 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 (); RegionView* combine_regions ();
void uncombine_regions (); void uncombine_regions ();
void uncombine_region (RegionView*); void uncombine_region (RegionView*);

View file

@ -533,7 +533,7 @@ RouteUI::mute_press (GdkEventButton* ev)
} }
boost::shared_ptr<MuteControl> mc = _route->mute_control(); boost::shared_ptr<MuteControl> 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); _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<MuteControl> mc = _route->mute_control(); boost::shared_ptr<MuteControl> 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); mc->set_value (!_route->muted_by_self(), Controllable::UseGroup);
} }
} }
@ -567,7 +567,7 @@ RouteUI::mute_release (GdkEventButton* /*ev*/)
_mute_release = 0; _mute_release = 0;
} }
_route->mute_control()->stop_touch (_session->audible_sample ()); _route->mute_control()->stop_touch (timepos_t (_session->audible_sample ()));
return false; return false;
} }

View file

@ -56,8 +56,8 @@ using namespace std;
using namespace ARDOUR; using namespace ARDOUR;
using namespace PBD; using namespace PBD;
struct AudioRangeComparator { struct TimelineRangeComparator {
bool operator()(AudioRange a, AudioRange b) { bool operator()(TimelineRange a, TimelineRange b) {
return a.start < b.start; return a.start < b.start;
} }
}; };
@ -306,11 +306,11 @@ Selection::toggle (samplepos_t start, samplepos_t end)
{ {
clear_objects(); // enforce object/range exclusivity clear_objects(); // enforce object/range exclusivity
AudioRangeComparator cmp; TimelineRangeComparator cmp;
/* XXX this implementation is incorrect */ /* 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.consolidate ();
time.sort (cmp); time.sort (cmp);
@ -437,11 +437,11 @@ Selection::add (samplepos_t start, samplepos_t end)
{ {
clear_objects(); // enforce object/range exclusivity clear_objects(); // enforce object/range exclusivity
AudioRangeComparator cmp; TimelineRangeComparator cmp;
/* XXX this implementation is incorrect */ /* 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.consolidate ();
time.sort (cmp); time.sort (cmp);
@ -457,7 +457,7 @@ Selection::move_time (samplecnt_t distance)
return; return;
} }
for (list<AudioRange>::iterator i = time.begin(); i != time.end(); ++i) { for (list<TimelineRange>::iterator i = time.begin(); i != time.end(); ++i) {
(*i).start += distance; (*i).start += distance;
(*i).end += 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 clear_objects(); // enforce object/range exclusivity
for (list<AudioRange>::iterator i = time.begin(); i != time.end(); ++i) { for (list<TimelineRange>::iterator i = time.begin(); i != time.end(); ++i) {
if ((*i).id == sid) { if ((*i).id == sid) {
time.erase (i); time.erase (i);
time.push_back (AudioRange(start,end, sid)); time.push_back (TimelineRange(start,end, sid));
/* don't consolidate here */ /* don't consolidate here */
AudioRangeComparator cmp; TimelineRangeComparator cmp;
time.sort (cmp); time.sort (cmp);
TimeChanged (); TimeChanged ();
@ -606,7 +606,7 @@ Selection::remove (uint32_t selection_id)
return; return;
} }
for (list<AudioRange>::iterator i = time.begin(); i != time.end(); ++i) { for (list<TimelineRange>::iterator i = time.begin(); i != time.end(); ++i) {
if ((*i).id == selection_id) { if ((*i).id == selection_id) {
time.erase (i); time.erase (i);
@ -703,17 +703,17 @@ Selection::set (vector<RegionView*>& v)
* the list of tracks it applies to. * the list of tracks it applies to.
*/ */
long 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_objects(); // enforce region/object exclusivity
clear_time(); clear_time();
if ((start == 0 && end == 0) || end < start) { if ((start.zero() && end.zero()) || end < start) {
return 0; return 0;
} }
if (time.empty()) { if (time.empty()) {
time.push_back (AudioRange (start, end, ++next_time_id)); time.push_back (TimelineRange (start, end, ++next_time_id));
} else { } else {
/* reuse the first entry, and remove all the rest */ /* 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 ()) { if (time.empty ()) {
time.push_back (AudioRange (start, end, ++next_time_id)); time.push_back (TimelineRange (start, end, ++next_time_id));
} else { } else {
time.sort (AudioRangeComparator ()); time.sort (TimelineRangeComparator ());
time.front().start = start; time.front().start = start;
time.back().end = end; time.back().end = end;
} }
@ -1130,7 +1130,7 @@ Selection::get_state () const
} }
for (TimeSelection::const_iterator i = time.begin(); i != time.end(); ++i) { 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_("start"), (*i).start);
t->set_property (X_("end"), (*i).end); 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 start;
samplepos_t end; samplepos_t end;

View file

@ -136,7 +136,7 @@ public:
void set (const MidiNoteSelection&); void set (const MidiNoteSelection&);
void set (RegionView*, bool also_clear_tracks = true); void set (RegionView*, bool also_clear_tracks = true);
void set (std::vector<RegionView*>&); void set (std::vector<RegionView*>&);
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_preserving_all_ranges (samplepos_t, samplepos_t);
void set (boost::shared_ptr<Evoral::ControlList>); void set (boost::shared_ptr<Evoral::ControlList>);
void set (boost::shared_ptr<ARDOUR::Playlist>); void set (boost::shared_ptr<ARDOUR::Playlist>);

View file

@ -880,7 +880,7 @@ TimeAxisView::show_selection (TimeSelection& ts)
gap = ceil (gap * ui_scale); gap = ceil (gap * ui_scale);
} }
for (list<AudioRange>::iterator i = ts.begin(); i != ts.end(); ++i) { for (list<TimelineRange>::iterator i = ts.begin(); i != ts.end(); ++i) {
samplepos_t start, end; samplepos_t start, end;
samplecnt_t cnt; samplecnt_t cnt;

View file

@ -190,10 +190,9 @@ public:
* @param ctx Paste context. * @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 * @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, const Selection& selection,
PasteContext& ctx, PasteContext& ctx)
const int32_t sub_num)
{ {
return false; return false;
} }
@ -204,7 +203,7 @@ public:
virtual void fade_range (TimeSelection&) {} virtual void fade_range (TimeSelection&) {}
virtual boost::shared_ptr<ARDOUR::Region> find_next_region (samplepos_t /*pos*/, ARDOUR::RegionPoint, int32_t /*dir*/) { virtual boost::shared_ptr<ARDOUR::Region> find_next_region (ARDOUR::timepos_t const & /*pos*/, ARDOUR::RegionPoint, int32_t /*dir*/) {
return boost::shared_ptr<ARDOUR::Region> (); return boost::shared_ptr<ARDOUR::Region> ();
} }

View file

@ -283,15 +283,15 @@ TimeAxisViewItem::canvas_group_event (GdkEvent* /*ev*/)
*/ */
bool 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) { if (position_locked) {
return false; 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) { if (delta) {
(*delta) = new_unit_pos - group->position().x; (*delta) = new_unit_pos - group->position().x;

View file

@ -54,14 +54,14 @@ class TimeAxisViewItem : public Selectable, public PBD::ScopedConnectionList
public: public:
virtual ~TimeAxisViewItem(); virtual ~TimeAxisViewItem();
virtual bool set_position(samplepos_t, void*, double* delta = 0); virtual bool set_position(Temporal::timepos_t const &, void*, double* delta = 0);
samplepos_t get_position() const; Temporal::timepos_t get_position() const;
virtual bool set_duration(samplecnt_t, void*); virtual bool set_duration(Temporal::timecnt_t const &, void*);
samplecnt_t get_duration() const; Temporal::timecnt_t get_duration() const;
virtual void set_max_duration(samplecnt_t, void*); virtual void set_max_duration(Temporal::timecnt_t const &, void*);
samplecnt_t get_max_duration() const; Temporal::timecnt_t get_max_duration() const;
virtual void set_min_duration(samplecnt_t, void*); virtual void set_min_duration(Temporal::timecnt_t const &, void*);
samplecnt_t get_min_duration() const; Temporal::timecnt_t get_min_duration() const;
virtual void set_position_locked(bool, void*); virtual void set_position_locked(bool, void*);
bool get_position_locked() const; bool get_position_locked() const;
void set_max_duration_active(bool, void*); void set_max_duration_active(bool, void*);

View file

@ -234,16 +234,16 @@ TimeInfoBox::set_session (Session* s)
void void
TimeInfoBox::region_selection_changed () TimeInfoBox::region_selection_changed ()
{ {
samplepos_t s, e; timepos_t s, e;
Selection& selection (Editor::instance().get_selection()); Selection& selection (Editor::instance().get_selection());
s = selection.regions.start(); s = selection.regions.start_time();
e = selection.regions.end_sample(); e = selection.regions.end_sample_time();
selection_start->set_off (false); selection_start->set_off (false);
selection_end->set_off (false); selection_end->set_off (false);
selection_length->set_off (false); selection_length->set_off (false);
selection_start->set (s); selection_start->set_time (s);
selection_end->set (e); selection_end->set_time (e);
selection_length->set (e, false, s); selection_length->set_duration (e, false, s);
} }
void void
@ -272,9 +272,10 @@ TimeInfoBox::selection_changed ()
selection_start->set_off (false); selection_start->set_off (false);
selection_end->set_off (false); selection_end->set_off (false);
selection_length->set_off (false); selection_length->set_off (false);
selection_start->set (selection.time.start()); selection_start->set_time (selection.time.start_time());
selection_end->set (selection.time.end_sample()); selection_end->set_time (selection.time.end_time());
selection_length->set (selection.time.end_sample(), false, selection.time.start()); selection_length->set_is_duration (true, selection.time.start_time());
selection_length->set_duration (selection.time.start_time().distance (selection.time.end_time()));
} else { } else {
selection_start->set_off (true); selection_start->set_off (true);
selection_end->set_off (true); selection_end->set_off (true);
@ -335,9 +336,10 @@ TimeInfoBox::selection_changed ()
selection_start->set_off (false); selection_start->set_off (false);
selection_end->set_off (false); selection_end->set_off (false);
selection_length->set_off (false); selection_length->set_off (false);
selection_start->set (selection.time.start()); selection_start->set_time (selection.time.start_time());
selection_end->set (selection.time.end_sample()); selection_end->set_time (selection.time.end_time());
selection_length->set (selection.time.end_sample(), false, selection.time.start()); selection_length->set_is_duration (true, selection.time.start_time());
selection_length->set_duration (selection.time.start_time().distance (selection.time.end_time()));
} }
break; break;
@ -382,6 +384,6 @@ TimeInfoBox::punch_changed (Location* loc)
punch_start->set_off (false); punch_start->set_off (false);
punch_end->set_off (false); punch_end->set_off (false);
punch_start->set (loc->start()); punch_start->set_time (loc->start());
punch_end->set (loc->end()); punch_end->set_time (loc->end());
} }

View file

@ -1,21 +1,20 @@
/* /*
* Copyright (C) 2005-2017 Paul Davis <paul@linuxaudiosystems.com> Copyright (C) 2003-2004 Paul Davis
* Copyright (C) 2009-2012 Carl Hetherington <carl@carlh.net>
* Copyright (C) 2009-2012 David Robillard <d@drobilla.net> 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
* This program is free software; you can redistribute it and/or modify the Free Software Foundation; either version 2 of the License, or
* it under the terms of the GNU General Public License as published by (at your option) any later version.
* 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
* This program is distributed in the hope that it will be useful, MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* but WITHOUT ANY WARRANTY; without even the implied warranty of GNU General Public License for more details.
* 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
* You should have received a copy of the GNU General Public License along Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/ */
#include <algorithm> #include <algorithm>
@ -30,17 +29,17 @@
using namespace ARDOUR; using namespace ARDOUR;
using namespace PBD; using namespace PBD;
AudioRange& TimelineRange&
TimeSelection::operator[] (uint32_t which) TimeSelection::operator[] (uint32_t which)
{ {
for (std::list<AudioRange>::iterator i = begin(); i != end(); ++i) { for (std::list<TimelineRange>::iterator i = begin(); i != end(); ++i) {
if ((*i).id == which) { if ((*i).id == which) {
return *i; return *i;
} }
} }
fatal << string_compose (_("programming error: request for non-existent audio range (%1)!"), which) << endmsg; fatal << string_compose (_("programming error: request for non-existent audio range (%1)!"), which) << endmsg;
abort(); /*NOTREACHED*/ 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 bool
@ -49,16 +48,16 @@ TimeSelection::consolidate ()
bool changed = false; bool changed = false;
restart: restart:
for (std::list<AudioRange>::iterator a = begin(); a != end(); ++a) { for (std::list<TimelineRange>::iterator a = begin(); a != end(); ++a) {
for (std::list<AudioRange>::iterator b = begin(); b != end(); ++b) { for (std::list<TimelineRange>::iterator b = begin(); b != end(); ++b) {
if (&(*a) == &(*b)) { if (&(*a) == &(*b)) {
continue; continue;
} }
if (a->coverage (b->start, b->end) != Evoral::OverlapNone) { if (a->coverage (b->start(), b->end()) != Temporal::OverlapNone) {
a->start = std::min (a->start, b->start); a->set_start (std::min (a->start(), b->start()));
a->end = std::max (a->end, b->end); a->set_end (std::max (a->end(), b->end()));
erase (b); erase (b);
changed = true; changed = true;
goto restart; goto restart;
@ -70,43 +69,59 @@ TimeSelection::consolidate ()
} }
samplepos_t samplepos_t
TimeSelection::start () const TimeSelection::start_sample () const
{ {
if (empty()) { return start_time().sample ();
return 0;
}
samplepos_t first = max_samplepos;
for (std::list<AudioRange>::const_iterator i = begin(); i != end(); ++i) {
if ((*i).start < first) {
first = (*i).start;
}
}
return first;
} }
samplepos_t samplepos_t
TimeSelection::end_sample () const TimeSelection::end_sample () const
{ {
samplepos_t last = 0; return end_time().sample ();
/* XXX make this work like RegionSelection: no linear search needed */
for (std::list<AudioRange>::const_iterator i = begin(); i != end(); ++i) {
if ((*i).end > last) {
last = (*i).end;
}
}
return last;
} }
samplecnt_t samplecnt_t
TimeSelection::length() const TimeSelection::length_samples() const
{
return length().samples();
}
timepos_t
TimeSelection::start_time () const
{ {
if (empty()) { if (empty()) {
return 0; return 0;
} }
return end_sample() - start() + 1; timepos_t first = std::numeric_limits<timepos_t>::max();
for (std::list<TimelineRange>::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<timepos_t>::min();
for (std::list<TimelineRange>::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());
} }

View file

@ -1,21 +1,20 @@
/* /*
* Copyright (C) 2006-2017 Paul Davis <paul@linuxaudiosystems.com> Copyright (C) 2000-2020 Paul Davis
* Copyright (C) 2009-2011 David Robillard <d@drobilla.net>
* Copyright (C) 2009 Carl Hetherington <carl@carlh.net> 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
* This program is free software; you can redistribute it and/or modify the Free Software Foundation; either version 2 of the License, or
* it under the terms of the GNU General Public License as published by (at your option) any later version.
* 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
* This program is distributed in the hope that it will be useful, MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* but WITHOUT ANY WARRANTY; without even the implied warranty of GNU General Public License for more details.
* 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
* You should have received a copy of the GNU General Public License along Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*/ */
#ifndef __ardour_gtk_time_selection_h__ #ifndef __ardour_gtk_time_selection_h__
@ -28,14 +27,18 @@ namespace ARDOUR {
class RouteGroup; class RouteGroup;
} }
class TimeSelection : public std::list<ARDOUR::AudioRange> class TimeSelection : public std::list<ARDOUR::TimelineRange>
{ {
public: 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 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 (); bool consolidate ();
}; };