X-Git-Url: https://git.carlh.net/gitweb/?a=blobdiff_plain;f=libs%2Fardour%2Fardour%2Fmidi_playlist.h;h=f784b7317723d89bb9e57f2ee1548b830823278e;hb=e5a181c323243a03338f5a9934a5df254986370d;hp=99d0b983216ed0c0597bce3e2f1e2702e0c468d7;hpb=60da662affe9ade1db4ecb988006a1293cce49b4;p=ardour.git diff --git a/libs/ardour/ardour/midi_playlist.h b/libs/ardour/ardour/midi_playlist.h index 99d0b98321..f784b73177 100644 --- a/libs/ardour/ardour/midi_playlist.h +++ b/libs/ardour/ardour/midi_playlist.h @@ -23,57 +23,116 @@ #include #include +#include + #include "ardour/ardour.h" -#include "ardour/playlist.h" +#include "ardour/midi_cursor.h" +#include "ardour/midi_model.h" #include "ardour/midi_state_tracker.h" +#include "ardour/note_fixer.h" +#include "ardour/playlist.h" +#include "evoral/Note.hpp" #include "evoral/Parameter.hpp" +namespace Evoral { +template class EventSink; +class Beats; +} + namespace ARDOUR { -class Session; +class BeatsSamplesConverter; +class MidiChannelFilter; class MidiRegion; +class Session; class Source; + template class MidiRingBuffer; -class MidiPlaylist : public ARDOUR::Playlist +class LIBARDOUR_API MidiPlaylist : public ARDOUR::Playlist { public: MidiPlaylist (Session&, const XMLNode&, bool hidden = false); MidiPlaylist (Session&, std::string name, bool hidden = false); MidiPlaylist (boost::shared_ptr other, std::string name, bool hidden = false); - MidiPlaylist (boost::shared_ptr other, framepos_t start, framecnt_t cnt, - std::string name, bool hidden = false); + + /** This constructor does NOT notify others (session) */ + MidiPlaylist (boost::shared_ptr other, + samplepos_t start, + samplecnt_t cnt, + std::string name, + bool hidden = false); ~MidiPlaylist (); - framecnt_t read (Evoral::EventSink& buf, - framepos_t start, framecnt_t cnt, uint32_t chan_n = 0); + /** Read a range from the playlist into an event sink. + * + * @param buf Destination for events. + * @param start First sample of read range. + * @param cnt Number of samples in read range. + * @param loop_range If non-null, all event times will be mapped into this loop range. + * @param chan_n Must be 0 (this is the audio-style "channel", where each + * channel is backed by a separate region, not MIDI channels, which all + * exist in the same region and are not handled here). + * @return The number of samples read (time, not an event count). + */ + samplecnt_t read (Evoral::EventSink& buf, + samplepos_t start, + samplecnt_t cnt, + Evoral::Range* loop_range, + uint32_t chan_n = 0, + MidiChannelFilter* filter = NULL); int set_state (const XMLNode&, int version); bool destroy_region (boost::shared_ptr); + void _split_region (boost::shared_ptr, const MusicSample& position); void set_note_mode (NoteMode m) { _note_mode = m; } std::set contained_automation(); - void clear_note_trackers (); + /** Handle a region edit during read. + * + * This must be called before the command is applied to the model. Events + * are injected into the playlist output to compensate for edits to active + * notes and maintain coherent output and tracker state. + */ + void region_edited(boost::shared_ptr region, + const MidiModel::NoteDiffCommand* cmd); + + /** Clear all note trackers. */ + void reset_note_trackers (); + + /** Resolve all pending notes and clear all note trackers. + * + * @param dst Sink to write note offs to. + * @param time Time stamp of all written note offs. + */ + void resolve_note_trackers (Evoral::EventSink& dst, samplepos_t time); protected: - void remove_dependents (boost::shared_ptr region); + void region_going_away (boost::weak_ptr region); private: - void dump () const; + typedef Evoral::Note Note; + typedef Evoral::Event Event; - bool region_changed (const PBD::PropertyChange&, boost::shared_ptr); + struct RegionTracker : public boost::noncopyable { + MidiCursor cursor; ///< Cursor (iterator and read state) + MidiStateTracker tracker; ///< Active note tracker + NoteFixer fixer; ///< Edit compensation + }; - NoteMode _note_mode; + typedef std::map< Region*, boost::shared_ptr > NoteTrackers; - typedef std::map NoteTrackers; - NoteTrackers _note_trackers; + void dump () const; + NoteTrackers _note_trackers; + NoteMode _note_mode; + samplepos_t _read_end; }; } /* namespace ARDOUR */