diff --git a/libs/ardour/ardour/segment_descriptor.h b/libs/ardour/ardour/segment_descriptor.h new file mode 100644 index 0000000000..08fdd3ec57 --- /dev/null +++ b/libs/ardour/ardour/segment_descriptor.h @@ -0,0 +1,79 @@ +/* + * Copyright (C) 2021 Paul Davis + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + */ + +#ifndef __libardour_segment_descriptor_h__ +#define __libardour_segment_descriptor_h__ + +#include "temporal/timeline.h" +#include "temporal/tempo.h" + +namespace ARDOUR { + +/* An object that describes an extent (duration & position), along with a + * potentially expanding set of metadata about that extent (e.g. bpm, meter + * etc.) + */ + +class SegmentDescriptor { +public: + SegmentDescriptor (); + + /* This object does not use the tempo map to convert between time + * domains, since it describes things that are not (always) on the + * timeline. + */ + + Temporal::TimeDomain time_domain() const { return _time_domain; } + + void set_position (Temporal::samplepos_t); + void set_position (Temporal::Beats const &); + + void set_duration (Temporal::samplecnt_t); + void set_duration (Temporal::Beats const &); + + void set_extent (Temporal::samplepos_t pos, Temporal::samplecnt_t dur); + void set_extent (Temporal::Beats const & pos, Temporal::Beats const & dur); + + Temporal::timecnt_t extent() const; + Temporal::timepos_t position() const { return extent().position(); } + + Temporal::Tempo tempo() const { return _tempo; } + void set_tempo (Temporal::Tempo const&); + + Temporal::Meter meter() const { return _meter; } + void set_meter (Temporal::Meter const&); + +private: + Temporal::TimeDomain _time_domain; + + /* cannot use a union for these because Temporal::Beats has a + "non-trivial" constructor. + */ + + Temporal::samplepos_t _position_samples; + Temporal::Beats _position_beats; + Temporal::samplepos_t _duration_samples; + Temporal::Beats _duration_beats; + + Temporal::Tempo _tempo; + Temporal::Meter _meter; +}; + +} + +#endif /* __libardour_segment_descriptor_h__ */ diff --git a/libs/ardour/segment_descriptor.cc b/libs/ardour/segment_descriptor.cc new file mode 100644 index 0000000000..c2ba20ba27 --- /dev/null +++ b/libs/ardour/segment_descriptor.cc @@ -0,0 +1,109 @@ +/* + * Copyright (C) 2021 Paul Davis + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + */ + +#include "ardour/segment_descriptor.h" + +using namespace ARDOUR; +using namespace Temporal; + +SegmentDescriptor::SegmentDescriptor () + : _time_domain (AudioTime) + , _position_samples (0) + , _duration_samples (0) + , _tempo (120, 4) + , _meter (4, 4) +{ +} + +void +SegmentDescriptor::set_position (samplepos_t s) +{ + if (_time_domain != AudioTime) { + /* XXX error */ + return; + } + _position_samples = s; +} + +void +SegmentDescriptor::set_position (Temporal::Beats const & b) +{ + if (_time_domain != BeatTime) { + /* XXX error */ + return; + } + _position_beats = b; +} + +void +SegmentDescriptor::set_duration (samplepos_t s) +{ + if (_time_domain != AudioTime) { + /* XXX error */ + return; + } + _position_samples = s; +} + +void +SegmentDescriptor::set_duration (Temporal::Beats const & b) +{ + if (_time_domain != BeatTime) { + /* XXX error */ + return; + } + _duration_beats = b; +} + +void +SegmentDescriptor::set_extent (Temporal::Beats const & p, Temporal::Beats const & d) +{ + _time_domain = BeatTime; + _position_beats = p; + _duration_beats = d; +} + +void +SegmentDescriptor::set_extent (samplepos_t p, samplecnt_t d) +{ + _time_domain = AudioTime; + _position_samples = p; + _duration_samples = d; +} + +timecnt_t +SegmentDescriptor::extent() const +{ + if (_time_domain == BeatTime) { + return timecnt_t (_duration_beats, timepos_t (_position_beats)); + } + + return timecnt_t (_duration_samples, timepos_t (_position_samples)); +} + +void +SegmentDescriptor::set_tempo (Tempo const & t) +{ + _tempo = t; +} + +void +SegmentDescriptor::set_meter (Meter const & m) +{ + _meter = m; +} diff --git a/libs/ardour/wscript b/libs/ardour/wscript index 4be9caae82..9e721aee2c 100644 --- a/libs/ardour/wscript +++ b/libs/ardour/wscript @@ -208,6 +208,7 @@ libardour_sources = [ 'rt_tasklist.cc', 'scene_change.cc', 'search_paths.cc', + 'segment_descriptor.cc', 'selection.cc', 'send.cc', 'session.cc',