#include <glibmm/threads.h>
#include "pbd/undo.h"
+#include "pbd/enum_convert.h"
#include "pbd/stateful.h"
#include "pbd/statefuldestructible.h"
class Meter;
class TempoMap;
+// Find a better place for these
+LIBARDOUR_API bool bbt_time_to_string (const Timecode::BBT_Time& bbt, std::string& str);
+LIBARDOUR_API bool string_to_bbt_time (const std::string& str, Timecode::BBT_Time& bbt);
+
/** Tempo, the speed at which musical time progresses (BPM). */
class LIBARDOUR_API Tempo {
public:
*/
virtual XMLNode& get_state() const = 0;
+ virtual int set_state (const XMLNode&, int version);
+
PositionLockStyle position_lock_style () const { return _position_lock_style; }
void set_position_lock_style (PositionLockStyle ps) { _position_lock_style = ps; }
bool is_tempo () const { return _is_tempo; }
framepos_t frame_at_minute (const double& time) const;
double minute_at_frame (const framepos_t& frame) const;
+protected:
+ void add_state_to_node (XMLNode& node) const;
+
private:
double _pulse;
}
const Timecode::BBT_Time& bbt() const { return _bbt; }
- const double& beat () const { return _beat; }
+ const double& beat () const { return _beat; }
void set_beat (double beat) { _beat = beat; }
private:
};
TempoSection (const double& pulse, const double& minute, Tempo tempo, PositionLockStyle pls, framecnt_t sr)
- : MetricSection (pulse, minute, pls, true, sr), Tempo (tempo), _c (0.0), _active (true), _locked_to_meter (false) {}
+ : MetricSection (pulse, minute, pls, true, sr), Tempo (tempo), _c (0.0), _active (true), _locked_to_meter (false), _clamped (false) {}
TempoSection (const XMLNode&, const framecnt_t sample_rate);
bool locked_to_meter () const { return _locked_to_meter; }
void set_locked_to_meter (bool yn) { _locked_to_meter = yn; }
+ bool clamped () const { return _clamped; }
+ void set_clamped (bool yn) { _clamped = yn; }
+
Tempo tempo_at_minute (const double& minute) const;
double minute_at_ntpm (const double& ntpm, const double& pulse) const;
framepos_t frame_at_pulse (const double& pulse) const;
Timecode::BBT_Time legacy_bbt () { return _legacy_bbt; }
- bool legacy_end () { return _legacy_end; }
private:
this enables us to keep the tempo change at the same relative
position within the bar if/when the meter changes.
*/
+
double _c;
bool _active;
bool _locked_to_meter;
+ bool _clamped;
Timecode::BBT_Time _legacy_bbt;
- bool _legacy_end;
};
typedef std::list<MetricSection*> Metrics;
{
public:
TempoMap (framecnt_t frame_rate);
- TempoMap (TempoMap const &);
~TempoMap();
TempoMap& operator= (TempoMap const &);
};
struct BBTPoint {
- framepos_t frame;
Meter meter;
Tempo tempo;
- double c;
+ framepos_t frame;
uint32_t bar;
uint32_t beat;
+ double qn;
BBTPoint (const MeterSection& m, const Tempo& t, framepos_t f,
- uint32_t b, uint32_t e, double func_c)
- : frame (f), meter (m.divisions_per_bar(), m.note_divisor()), tempo (t.note_types_per_minute(), t.note_type(), t.end_note_types_per_minute()), c (func_c), bar (b), beat (e) {}
+ uint32_t b, uint32_t e, double qnote)
+ : meter (m), tempo (t), frame (f), bar (b), beat (e), qn (qnote) {}
Timecode::BBT_Time bbt() const { return Timecode::BBT_Time (bar, beat, 0); }
operator Timecode::BBT_Time() const { return bbt(); }
const MeterSection& meter_section_at_frame (framepos_t frame) const;
const MeterSection& meter_section_at_beat (double beat) const;
+ TempoSection* previous_tempo_section (TempoSection*) const;
+ TempoSection* next_tempo_section (TempoSection*) const;
+
/** add a tempo section locked to pls. ignored values will be set in recompute_tempi()
* @param pulse pulse position of new section. ignored if pls == AudioTime
* @param frame frame position of new section. ignored if pls == MusicTime
void gui_set_tempo_position (TempoSection*, const framepos_t& frame, const int& sub_num);
void gui_set_meter_position (MeterSection*, const framepos_t& frame);
- bool gui_change_tempo (TempoSection*, const Tempo& bpm, bool change_end);
+ bool gui_change_tempo (TempoSection*, const Tempo& bpm);
void gui_stretch_tempo (TempoSection* tempo, const framepos_t frame, const framepos_t end_frame);
void gui_stretch_tempo_end (TempoSection* tempo, const framepos_t frame, const framepos_t end_frame);
bool gui_twist_tempi (TempoSection* first, const Tempo& bpm, const framepos_t frame, const framepos_t end_frame);
void fix_legacy_end_session();
private:
+ /* prevent copy construction */
+ TempoMap (TempoMap const&);
+
+ TempoSection* previous_tempo_section_locked (const Metrics& metrics, TempoSection*) const;
+ TempoSection* next_tempo_section_locked (const Metrics& metrics, TempoSection*) const;
double beat_at_minute_locked (const Metrics& metrics, const double& minute) const;
double minute_at_beat_locked (const Metrics& metrics, const double& beat) const;
bool remove_tempo_locked (const TempoSection&);
bool remove_meter_locked (const MeterSection&);
- TempoSection* copy_metrics_and_point (const Metrics& metrics, Metrics& copy, TempoSection* section);
- MeterSection* copy_metrics_and_point (const Metrics& metrics, Metrics& copy, MeterSection* section);
+ TempoSection* copy_metrics_and_point (const Metrics& metrics, Metrics& copy, TempoSection* section) const;
+ MeterSection* copy_metrics_and_point (const Metrics& metrics, Metrics& copy, MeterSection* section) const;
};
}; /* namespace ARDOUR */
LIBARDOUR_API std::ostream& operator<< (std::ostream&, const ARDOUR::Tempo&);
LIBARDOUR_API std::ostream& operator<< (std::ostream&, const ARDOUR::MetricSection&);
+namespace PBD {
+ DEFINE_ENUM_CONVERT (ARDOUR::TempoSection::Type)
+}
+
#endif /* __ardour_tempo_h__ */