From 9f63ab9931e6478472853bdda58da47ea29ac125 Mon Sep 17 00:00:00 2001 From: David Robillard Date: Sat, 2 Feb 2008 03:57:35 +0000 Subject: Merge with trunk R2978. git-svn-id: svn://localhost/ardour2/branches/3.0@2988 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/ardour/ardour/audioanalyser.h | 74 +++++++++++++++++++++++++++++++++ libs/ardour/ardour/audioregion.h | 24 ++++++++--- libs/ardour/ardour/audiosource.h | 17 +++++++- libs/ardour/ardour/cycles.h | 10 ----- libs/ardour/ardour/lv2_plugin.h | 45 ++++++++++++++++---- libs/ardour/ardour/midi_region.h | 8 +++- libs/ardour/ardour/midi_source.h | 11 ++++- libs/ardour/ardour/plugin_manager.h | 6 ++- libs/ardour/ardour/readable.h | 20 +++++++++ libs/ardour/ardour/region.h | 7 ++-- libs/ardour/ardour/region_factory.h | 2 +- libs/ardour/ardour/session.h | 3 ++ libs/ardour/ardour/source.h | 3 +- libs/ardour/ardour/tempo.h | 20 +++++++-- libs/ardour/ardour/transient_detector.h | 52 +++++++++++++++++++++++ 15 files changed, 264 insertions(+), 38 deletions(-) create mode 100644 libs/ardour/ardour/audioanalyser.h create mode 100644 libs/ardour/ardour/readable.h create mode 100644 libs/ardour/ardour/transient_detector.h (limited to 'libs/ardour/ardour') diff --git a/libs/ardour/ardour/audioanalyser.h b/libs/ardour/ardour/audioanalyser.h new file mode 100644 index 0000000000..dbd8a52d5a --- /dev/null +++ b/libs/ardour/ardour/audioanalyser.h @@ -0,0 +1,74 @@ +/* + Copyright (C) 2008 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + +*/ + +#ifndef __ardour_audioanalyser_h__ +#define __ardour_audioanalyser_h__ + +#include +#include +#include +#include +#include +#include + +namespace ARDOUR { + +class Readable; +class Session; + +class AudioAnalyser { + + public: + typedef Vamp::Plugin AnalysisPlugin; + typedef std::string AnalysisPluginKey; + + AudioAnalyser (float sample_rate, AnalysisPluginKey key); + virtual ~AudioAnalyser(); + + /* analysis object should provide a run method + that accepts a path to write the results to (optionally empty) + a Readable* to read data from + and a reference to a type-specific container to return the + results. + */ + + void reset (); + + protected: + float sample_rate; + AnalysisPlugin* plugin; + AnalysisPluginKey plugin_key; + + nframes64_t bufsize; + nframes64_t stepsize; + + int initialize_plugin (AnalysisPluginKey name, float sample_rate); + int analyse (const std::string& path, Readable*, uint32_t channel); + + /* instances of an analysis object will have this method called + whenever there are results to process. if out is non-null, + the data should be written to the stream it points to. + */ + + virtual int use_features (Vamp::Plugin::FeatureSet&, std::ostream*) = 0; +}; + +} /* namespace */ + +#endif /* __ardour_audioanalyser_h__ */ diff --git a/libs/ardour/ardour/audioregion.h b/libs/ardour/ardour/audioregion.h index b84d197c3f..2c5630aec0 100644 --- a/libs/ardour/ardour/audioregion.h +++ b/libs/ardour/ardour/audioregion.h @@ -21,6 +21,7 @@ #define __ardour_audio_region_h__ #include +#include #include #include @@ -75,6 +76,11 @@ class AudioRegion : public Region nframes_t offset, nframes_t cnt, uint32_t chan_n=0, double samples_per_unit= 1.0) const; + /* Readable interface */ + + virtual nframes64_t read (Sample*, nframes64_t pos, nframes64_t cnt, int channel) const; + virtual nframes64_t readable_length() const { return length(); } + virtual nframes_t read_at (Sample *buf, Sample *mixdown_buf, float *gain_buf, nframes_t position, nframes_t cnt, uint32_t chan_n = 0, @@ -128,12 +134,14 @@ class AudioRegion : public Region void resume_fade_in (); void resume_fade_out (); + int get_transients (std::vector&, bool force_new = false); + private: friend class RegionFactory; AudioRegion (boost::shared_ptr, nframes_t start, nframes_t length); AudioRegion (boost::shared_ptr, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags); - AudioRegion (SourceList &, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags); + AudioRegion (const SourceList &, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags); AudioRegion (boost::shared_ptr, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags); AudioRegion (boost::shared_ptr, const XMLNode&); AudioRegion (SourceList &, const XMLNode&); @@ -148,10 +156,11 @@ class AudioRegion : public Region void recompute_gain_at_start (); nframes_t _read_at (const SourceList&, Sample *buf, Sample *mixdown_buffer, - float *gain_buffer, nframes_t position, nframes_t cnt, - uint32_t chan_n = 0, - nframes_t read_frames = 0, - nframes_t skip_frames = 0) const; + float *gain_buffer, nframes_t position, nframes_t cnt, + uint32_t chan_n = 0, + nframes_t read_frames = 0, + nframes_t skip_frames = 0, + bool raw = false) const; void recompute_at_start (); void recompute_at_end (); @@ -178,6 +187,11 @@ class AudioRegion : public Region AudioRegion (boost::shared_ptr); int set_live_state (const XMLNode&, Change&, bool send); + + std::vector _transients; + bool valid_transients; + void invalidate_transients (); + void cleanup_transients (std::vector&); }; } /* namespace ARDOUR */ diff --git a/libs/ardour/ardour/audiosource.h b/libs/ardour/ardour/audiosource.h index 93708a5b07..b11174abe8 100644 --- a/libs/ardour/ardour/audiosource.h +++ b/libs/ardour/ardour/audiosource.h @@ -50,10 +50,20 @@ class AudioSource : public Source, public boost::enable_shared_from_this transients; + std::string get_transients_path() const; + protected: static bool _build_missing_peakfiles; static bool _build_peakfiles; @@ -134,6 +147,8 @@ class AudioSource : public Source, public boost::enable_shared_from_this -#else // Due to MacTypes.h and libgnomecanvasmm Rect conflict -typedef unsigned long long UInt64; - -extern UInt64 -AudioGetCurrentHostTime(); - -extern UInt64 -AudioConvertHostTimeToNanos(UInt64 inHostTime); -#endif typedef UInt64 cycles_t; static inline cycles_t get_cycles (void) diff --git a/libs/ardour/ardour/lv2_plugin.h b/libs/ardour/ardour/lv2_plugin.h index 40b3c669fa..777f285e9d 100644 --- a/libs/ardour/ardour/lv2_plugin.h +++ b/libs/ardour/ardour/lv2_plugin.h @@ -37,20 +37,21 @@ namespace ARDOUR { class AudioEngine; class Session; +struct LV2World; class LV2Plugin : public ARDOUR::Plugin { public: - LV2Plugin (ARDOUR::AudioEngine&, ARDOUR::Session&, SLV2Plugin plugin, nframes_t sample_rate); + LV2Plugin (ARDOUR::AudioEngine&, ARDOUR::Session&, ARDOUR::LV2World&, SLV2Plugin plugin, nframes_t sample_rate); LV2Plugin (const LV2Plugin &); ~LV2Plugin (); /* Plugin interface */ std::string unique_id() const; - const char* label() const { return slv2_plugin_get_name(_plugin); } - const char* name() const { return slv2_plugin_get_name(_plugin); } - const char* maker() const { return slv2_plugin_get_author_name(_plugin); } + const char* label() const { return slv2_value_as_string(_name); } + const char* name() const { return slv2_value_as_string(_name); } + const char* maker() const { return _author ? slv2_value_as_string(_author) : "Unknown"; } uint32_t parameter_count() const { return slv2_plugin_get_num_ports(_plugin); } float default_value (uint32_t port); nframes_t signal_latency() const; @@ -58,6 +59,9 @@ class LV2Plugin : public ARDOUR::Plugin float get_parameter (uint32_t port) const; int get_parameter_descriptor (uint32_t which, ParameterDescriptor&) const; uint32_t nth_parameter (uint32_t port, bool& ok) const; + + SLV2Plugin slv2_plugin() { return _plugin; } + SLV2Port slv2_port(uint32_t i) { return slv2_plugin_get_port_by_index(_plugin, i); } std::set automatable() const; @@ -105,29 +109,56 @@ class LV2Plugin : public ARDOUR::Plugin private: void* _module; + LV2World& _world; SLV2Plugin _plugin; - SLV2Template _template; + SLV2Value _name; + SLV2Value _author; SLV2Instance _instance; nframes_t _sample_rate; float* _control_data; float* _shadow_data; + float* _defaults; float* _latency_control_port; bool _was_activated; vector _port_is_input; - void init (SLV2Plugin plugin, nframes_t rate); + void init (LV2World& world, SLV2Plugin plugin, nframes_t rate); void run (nframes_t nsamples); void latency_compute_run (); }; + +/** The SLV2World, and various cached (as symbols, fast) URIs. + * + * This object represents everything ardour 'knows' about LV2 + * (ie understood extensions/features/etc) + */ +struct LV2World { + LV2World(); + ~LV2World(); + + SLV2World world; + SLV2Value input_class; + SLV2Value output_class; + SLV2Value audio_class; + SLV2Value control_class; + SLV2Value event_class; + SLV2Value in_place_broken; + SLV2Value integer; + SLV2Value toggled; + SLV2Value srate; +}; + + class LV2PluginInfo : public PluginInfo { public: - LV2PluginInfo (void* slv2_plugin);; + LV2PluginInfo (void* slv2_world, void* slv2_plugin);; ~LV2PluginInfo ();; static PluginInfoList discover (void* slv2_world); PluginPtr load (Session& session); + void* _lv2_world; void* _slv2_plugin; }; diff --git a/libs/ardour/ardour/midi_region.h b/libs/ardour/ardour/midi_region.h index 869436e423..50c6b8bce7 100644 --- a/libs/ardour/ardour/midi_region.h +++ b/libs/ardour/ardour/midi_region.h @@ -50,6 +50,10 @@ class MidiRegion : public Region ~MidiRegion(); boost::shared_ptr midi_source (uint32_t n=0) const; + + /* Stub Readable interface */ + virtual nframes64_t read (Sample*, nframes64_t pos, nframes64_t cnt, int channel) const { return 0; } + virtual nframes64_t readable_length() const { return length(); } nframes_t read_at (MidiRingBuffer& dst, nframes_t position, @@ -86,11 +90,11 @@ class MidiRegion : public Region MidiRegion (boost::shared_ptr, nframes_t start, nframes_t length); MidiRegion (boost::shared_ptr, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags); - MidiRegion (SourceList &, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags); + MidiRegion (const SourceList &, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags); MidiRegion (boost::shared_ptr, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags); MidiRegion (boost::shared_ptr); MidiRegion (boost::shared_ptr, const XMLNode&); - MidiRegion (SourceList &, const XMLNode&); + MidiRegion (const SourceList &, const XMLNode&); private: nframes_t _read_at (const SourceList&, MidiRingBuffer& dst, diff --git a/libs/ardour/ardour/midi_source.h b/libs/ardour/ardour/midi_source.h index c83debec3d..323fc8b5a1 100644 --- a/libs/ardour/ardour/midi_source.h +++ b/libs/ardour/ardour/midi_source.h @@ -49,8 +49,15 @@ class MidiSource : public Source MidiSource (Session& session, const XMLNode&); virtual ~MidiSource (); - virtual nframes_t read (MidiRingBuffer& dst, nframes_t start, nframes_t cnt, nframes_t stamp_offset) const; - virtual nframes_t write (MidiRingBuffer& src, nframes_t cnt); + /* Stub Readable interface */ + virtual nframes64_t read (Sample*, nframes64_t pos, nframes64_t cnt, int channel) const { return 0; } + virtual nframes64_t readable_length() const { return length(); } + virtual uint32_t n_channels () const { return 1; } + + // FIXME: integrate this with the Readable::read interface somehow + virtual nframes_t midi_read (MidiRingBuffer& dst, nframes_t start, nframes_t cnt, nframes_t stamp_offset) const; + virtual nframes_t midi_write (MidiRingBuffer& src, nframes_t cnt); + virtual void append_event_unlocked(const MidiEvent& ev) = 0; virtual void mark_for_remove() = 0; diff --git a/libs/ardour/ardour/plugin_manager.h b/libs/ardour/ardour/plugin_manager.h index dd50a079e3..892c8bd75a 100644 --- a/libs/ardour/ardour/plugin_manager.h +++ b/libs/ardour/ardour/plugin_manager.h @@ -28,7 +28,7 @@ #include #ifdef HAVE_SLV2 -#include +#include #endif namespace ARDOUR { @@ -40,6 +40,8 @@ class PluginManager { PluginManager (); ~PluginManager (); + /* realtime plugin APIs */ + ARDOUR::PluginInfoList &vst_plugin_info () { return _vst_plugin_info; } ARDOUR::PluginInfoList &ladspa_plugin_info () { return _ladspa_plugin_info; } ARDOUR::PluginInfoList &lv2_plugin_info () { return _lv2_plugin_info; } @@ -59,7 +61,7 @@ class PluginManager { ARDOUR::PluginInfoList _au_plugin_info; #ifdef HAVE_SLV2 - SLV2World _lv2_world; + LV2World* _lv2_world; #endif std::map rdf_type; diff --git a/libs/ardour/ardour/readable.h b/libs/ardour/ardour/readable.h new file mode 100644 index 0000000000..e072a1c95e --- /dev/null +++ b/libs/ardour/ardour/readable.h @@ -0,0 +1,20 @@ +#ifndef __ardour_readable_h__ +#define __ardour_readable_h__ + +#include + +namespace ARDOUR { + +class Readable { + public: + Readable () {} + virtual ~Readable() {} + + virtual nframes64_t read (Sample*, nframes64_t pos, nframes64_t cnt, int channel) const = 0; + virtual nframes64_t readable_length() const = 0; + virtual uint32_t n_channels () const = 0; +}; + +} + +#endif /* __ardour_readable_h__ */ diff --git a/libs/ardour/ardour/region.h b/libs/ardour/ardour/region.h index 76b41a04cb..da07c580b4 100644 --- a/libs/ardour/ardour/region.h +++ b/libs/ardour/ardour/region.h @@ -29,6 +29,7 @@ #include #include #include +#include class XMLNode; @@ -43,7 +44,7 @@ enum RegionEditState { EditChangesID = 2 }; -class Region : public Automatable, public boost::enable_shared_from_this +class Region : public Automatable, public boost::enable_shared_from_this, public Readable { public: typedef std::vector > SourceList; @@ -217,13 +218,13 @@ class Region : public Automatable, public boost::enable_shared_from_this Region (boost::shared_ptr src, nframes_t start, nframes_t length, const string& name, DataType type, layer_t = 0, Flag flags = DefaultFlags); - Region (SourceList& srcs, nframes_t start, nframes_t length, + Region (const SourceList& srcs, nframes_t start, nframes_t length, const string& name, DataType type, layer_t = 0, Flag flags = DefaultFlags); Region (boost::shared_ptr, nframes_t start, nframes_t length, const string& name, layer_t = 0, Flag flags = DefaultFlags); Region (boost::shared_ptr); Region (boost::shared_ptr src, const XMLNode&); - Region (SourceList& srcs, const XMLNode&); + Region (const SourceList& srcs, const XMLNode&); /* this one is for derived types of derived types */ diff --git a/libs/ardour/ardour/region_factory.h b/libs/ardour/ardour/region_factory.h index e6b9e5dde6..59749613ac 100644 --- a/libs/ardour/ardour/region_factory.h +++ b/libs/ardour/ardour/region_factory.h @@ -48,7 +48,7 @@ class RegionFactory { nframes_t length, std::string name, layer_t = 0, Region::Flag flags = Region::DefaultFlags, bool announce = true); static boost::shared_ptr create (boost::shared_ptr, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags, bool announce = true); - static boost::shared_ptr create (SourceList &, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags, bool announce = true); + static boost::shared_ptr create (const SourceList &, nframes_t start, nframes_t length, const string& name, layer_t = 0, Region::Flag flags = Region::DefaultFlags, bool announce = true); static boost::shared_ptr create (boost::shared_ptr); static boost::shared_ptr create (Session&, XMLNode&, bool); static boost::shared_ptr create (SourceList &, const XMLNode&); diff --git a/libs/ardour/ardour/session.h b/libs/ardour/ardour/session.h index c6b913b979..d27df2f7ea 100644 --- a/libs/ardour/ardour/session.h +++ b/libs/ardour/ardour/session.h @@ -261,6 +261,9 @@ class Session : public PBD::StatefulDestructible const SessionDirectory& session_directory () const { return *(_session_dir.get()); } std::string automation_dir () const; + std::string analysis_dir() const; + + int ensure_subdirs (); Glib::ustring peak_path (Glib::ustring) const; diff --git a/libs/ardour/ardour/source.h b/libs/ardour/ardour/source.h index aa8bc0ca1f..174e58c61b 100644 --- a/libs/ardour/ardour/source.h +++ b/libs/ardour/ardour/source.h @@ -30,13 +30,14 @@ #include #include #include +#include namespace ARDOUR { class Session; class Playlist; -class Source : public SessionObject +class Source : public SessionObject, public ARDOUR::Readable { public: Source (Session&, const std::string& name, DataType type); diff --git a/libs/ardour/ardour/tempo.h b/libs/ardour/ardour/tempo.h index 72f24c1054..dc49f5cdef 100644 --- a/libs/ardour/ardour/tempo.h +++ b/libs/ardour/ardour/tempo.h @@ -109,6 +109,9 @@ class MetricSection { public: MetricSection (const BBT_Time& start) : _start (start), _frame (0), _movable (true) {} + MetricSection (nframes_t start) + : _frame (start), _movable (true) {} + virtual ~MetricSection() {} const BBT_Time& start() const { return _start; } @@ -142,6 +145,8 @@ class MeterSection : public MetricSection, public Meter { public: MeterSection (const BBT_Time& start, double bpb, double note_type) : MetricSection (start), Meter (bpb, note_type) {} + MeterSection (nframes_t start, double bpb, double note_type) + : MetricSection (start), Meter (bpb, note_type) {} MeterSection (const XMLNode&); static const string xml_state_node_name; @@ -153,6 +158,8 @@ class TempoSection : public MetricSection, public Tempo { public: TempoSection (const BBT_Time& start, double qpm, double note_type) : MetricSection (start), Tempo (qpm, note_type) {} + TempoSection (nframes_t start, double qpm, double note_type) + : MetricSection (start), Tempo (qpm, note_type) {} TempoSection (const XMLNode&); static const string xml_state_node_name; @@ -165,7 +172,6 @@ typedef list Metrics; class TempoMap : public PBD::StatefulDestructible { public: - TempoMap (nframes_t frame_rate); ~TempoMap(); @@ -207,9 +213,14 @@ class TempoMap : public PBD::StatefulDestructible const Tempo& tempo_at (nframes_t); const Meter& meter_at (nframes_t); + const TempoSection& tempo_section_at (nframes_t); + void add_tempo(const Tempo&, BBT_Time where); void add_meter(const Meter&, BBT_Time where); + void add_tempo(const Tempo&, nframes_t where); + void add_meter(const Meter&, nframes_t where); + void move_tempo (TempoSection&, const BBT_Time& to); void move_meter (MeterSection&, const BBT_Time& to); @@ -267,6 +278,8 @@ class TempoMap : public PBD::StatefulDestructible Metric metric_at (nframes_t) const; void bbt_time_with_metric (nframes_t, BBT_Time&, const Metric&) const; + void change_existing_tempo_at (nframes_t, double bpm, double note_type); + sigc::signal StateChanged; private: @@ -280,8 +293,7 @@ class TempoMap : public PBD::StatefulDestructible BBT_Time last_bbt; mutable Glib::RWLock lock; - void timestamp_metrics (); - + void timestamp_metrics (bool use_bbt); nframes_t round_to_type (nframes_t fr, int dir, BBTPointType); @@ -298,7 +310,7 @@ class TempoMap : public PBD::StatefulDestructible nframes_t count_frames_between_metrics (const Meter&, const Tempo&, const BBT_Time&, const BBT_Time&) const; int move_metric_section (MetricSection&, const BBT_Time& to); - void do_insert (MetricSection* section); + void do_insert (MetricSection* section, bool with_bbt); }; }; /* namespace ARDOUR */ diff --git a/libs/ardour/ardour/transient_detector.h b/libs/ardour/ardour/transient_detector.h new file mode 100644 index 0000000000..c65bae3ed5 --- /dev/null +++ b/libs/ardour/ardour/transient_detector.h @@ -0,0 +1,52 @@ +/* + Copyright (C) 2008 Paul Davis + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + +*/ + +#ifndef __ardour_transient_detector_h__ +#define __ardour_transient_detector_h__ + +#include + +namespace ARDOUR { + +class AudioSource; +class Session; + +class TransientDetector : public AudioAnalyser +{ + + public: + TransientDetector (float sample_rate); + ~TransientDetector(); + + void set_threshold (float); + void set_sensitivity (float); + + float get_threshold () const; + float get_sensitivity () const; + + int run (const std::string& path, Readable*, uint32_t channel, std::vector& results); + + protected: + std::vector* current_results; + int use_features (Vamp::Plugin::FeatureSet&, std::ostream*); +}; + +} /* namespace */ + +#endif /* __ardour_audioanalyser_h__ */ -- cgit v1.2.3