Audacity  3.0.3
Track.h
Go to the documentation of this file.
1 /*!********************************************************************
2 
3  Audacity: A Digital Audio Editor
4 
5  @file Track.h
6  @brief declares abstract base class Track, TrackList, and iterators over TrackList
7 
8  Dominic Mazzoni
9 
10 **********************************************************************/
11 
12 #ifndef __AUDACITY_TRACK__
13 #define __AUDACITY_TRACK__
14 
15 
16 
17 
18 
19 #include <vector>
20 #include <list>
21 #include <functional>
22 #include <wx/event.h> // to inherit wxCommandEvent
23 #include <wx/longlong.h>
24 
25 #include "ClientData.h"
26 #include "SampleFormat.h"
27 #include "xml/XMLTagHandler.h"
28 
29 #ifdef __WXMSW__
30 #pragma warning(disable:4284)
31 #endif
32 
33 class wxTextFile;
34 class CommonTrackCell;
35 class Track;
36 class AudioTrack;
37 class PlayableTrack;
38 class ProjectSettings;
39 class LabelTrack;
40 class TimeTrack;
41 class WaveTrack;
42 class NoteTrack;
43 class AudacityProject;
44 
45 using TrackArray = std::vector< Track* >;
46 using WaveTrackArray = std::vector < std::shared_ptr< WaveTrack > > ;
47 using WaveTrackConstArray = std::vector < std::shared_ptr < const WaveTrack > >;
48 
49 using NoteTrackConstArray = std::vector < std::shared_ptr< const NoteTrack > >;
50 
51 class TrackList;
52 
53 using ListOfTracks = std::list< std::shared_ptr< Track > >;
54 
56 
59 std::pair< ListOfTracks::iterator, ListOfTracks* >;
60 
61 inline bool operator == (const TrackNodePointer &a, const TrackNodePointer &b)
62 { return a.second == b.second && a.first == b.first; }
63 
64 inline bool operator != (const TrackNodePointer &a, const TrackNodePointer &b)
65 { return !(a == b); }
66 
68 enum class TrackKind
69 {
70  None,
71  Wave,
72  Note,
73  Label,
74  Time,
75  Audio,
76  Playable,
77  All
78 };
79 
81 
83 constexpr bool CompatibleTrackKinds( TrackKind desired, TrackKind actual )
84 {
85  return
86  (desired == actual)
87  ||
88  (desired == TrackKind::All)
89  ||
90  (desired == TrackKind::Audio && actual == TrackKind::Wave)
91 #ifdef USE_MIDI
92  ||
93  (desired == TrackKind::Audio && actual == TrackKind::Note)
94 #endif
95  ||
96  (desired == TrackKind::Playable && actual == TrackKind::Wave)
97 #ifdef EXPERIMENTAL_MIDI_OUT
98  ||
99  (desired == TrackKind::Playable && actual == TrackKind::Note)
100 #endif
101  ;
102 }
103 
105 namespace TrackTyper {
106  template<typename, TrackKind> struct Pair;
108  using List = std::tuple<
116  // New classes can be added easily to this list
117  >;
119  template<typename...> struct Lookup {};
121  template<typename TrackType, TrackKind Here, typename... Rest>
122  struct Lookup< TrackType, std::tuple< Pair<TrackType, Here>, Rest... > > {
123  static constexpr TrackKind value() {
124  return Here;
125  }
126  };
128  template<typename TrackType, typename NotHere, typename... Rest>
129  struct Lookup< TrackType, std::tuple< NotHere, Rest... > > {
130  static constexpr TrackKind value() {
131  return Lookup< TrackType, std::tuple< Rest... > >::value();
132  }
133  };
134 };
135 
137 template<typename TrackType> constexpr TrackKind track_kind ()
138 {
139  using namespace TrackTyper;
141 }
142 
143 // forward declarations, so we can make them friends
144 template<typename T>
145  typename std::enable_if< std::is_pointer<T>::value, T >::type
146  track_cast(Track *track);
147 
148 template<typename T>
149  typename std::enable_if<
150  std::is_pointer<T>::value &&
151  std::is_const< typename std::remove_pointer< T >::type >::value,
152  T
153  >::type
154  track_cast(const Track *track);
155 
157 
164 class TrackId
165 {
166 public:
167  TrackId() : mValue(-1) {}
168  explicit TrackId (long value) : mValue(value) {}
169 
170  bool operator == (const TrackId &other) const
171  { return mValue == other.mValue; }
172 
173  bool operator != (const TrackId &other) const
174  { return mValue != other.mValue; }
175 
176  // Define this in case you want to key a std::map on TrackId
177  // The operator does not mean anything else
178  bool operator < (const TrackId &other) const
179  { return mValue < other.mValue; }
180 
181 private:
182  long mValue;
183 };
184 
186 struct AUDACITY_DLL_API TrackIntervalData {
188 };
189 
191 
193 public:
194 
196  ConstTrackInterval( double start, double end,
197  std::unique_ptr<TrackIntervalData> pExtra = {} )
198  : start{ start }, end{ end }, pExtra{ std::move( pExtra ) }
199  {
200  wxASSERT( start <= end );
201  }
202 
205 
206  double Start() const { return start; }
207  double End() const { return end; }
208  const TrackIntervalData *Extra() const { return pExtra.get(); }
209 
210 private:
211  double start, end;
212 protected:
213  // TODO C++17: use std::any instead
214  std::unique_ptr< TrackIntervalData > pExtra;
215 };
216 
218 
220 public:
222 
225 
226  TrackIntervalData *Extra() const { return pExtra.get(); }
227 };
228 
232 >;
233 
235 class AUDACITY_DLL_API Track /* not final */
236  : public XMLTagHandler
237  , public AttachedTrackObjects
238  , public std::enable_shared_from_this<Track> // see SharedPointer()
239 {
240  friend class TrackList;
241 
242  private:
244 
245  protected:
246  std::weak_ptr<TrackList> mList;
247 
250  int mIndex;
251  wxString mName;
252  wxString mDefaultName;
253 
254  private:
255  bool mSelected;
256 
257  protected:
258  bool mLinked;
259 
260  public:
261 
265 
266  static const auto LeftChannel = XMLValueChecker::LeftChannel;
267  static const auto RightChannel = XMLValueChecker::RightChannel;
268  static const auto MonoChannel = XMLValueChecker::MonoChannel;
269 
270  TrackId GetId() const { return mId; }
271  private:
272  void SetId( TrackId id ) { mId = id; }
273  public:
274 
275  // Given a bare pointer, find a shared_ptr. Undefined results if the track
276  // is not yet managed by a shared_ptr. Undefined results if the track is
277  // not really of the subclass. (That is, trusts the caller and uses static
278  // not dynamic casting.)
279  template<typename Subclass = Track>
280  inline std::shared_ptr<Subclass> SharedPointer()
281  {
282  // shared_from_this is injected into class scope by base class
283  // std::enable_shared_from_this<Track>
284  return std::static_pointer_cast<Subclass>( shared_from_this() );
285  }
286 
287  template<typename Subclass = const Track>
288  inline auto SharedPointer() const -> typename
289  std::enable_if<
290  std::is_const<Subclass>::value, std::shared_ptr<Subclass>
291  >::type
292  {
293  // shared_from_this is injected into class scope by base class
294  // std::enable_shared_from_this<Track>
295  return std::static_pointer_cast<Subclass>( shared_from_this() );
296  }
297 
298  // Static overloads of SharedPointer for when the pointer may be null
299  template<typename Subclass = Track>
300  static inline std::shared_ptr<Subclass> SharedPointer( Track *pTrack )
301  { return pTrack ? pTrack->SharedPointer<Subclass>() : nullptr; }
302 
303  template<typename Subclass = const Track>
304  static inline std::shared_ptr<Subclass> SharedPointer( const Track *pTrack )
305  { return pTrack ? pTrack->SharedPointer<Subclass>() : nullptr; }
306 
307  // Find anything registered with TrackList::RegisterPendingChangedTrack and
308  // not yet cleared or applied; if no such exists, return this track
309  std::shared_ptr<Track> SubstitutePendingChangedTrack();
310  std::shared_ptr<const Track> SubstitutePendingChangedTrack() const;
311 
312  // If this track is a pending changed track, return the corresponding
313  // original; else return this track
314  std::shared_ptr<const Track> SubstituteOriginalTrack() const;
315 
318  using Intervals = std::vector< Interval >;
320  using ConstIntervals = std::vector< ConstInterval >;
321 
323  virtual bool SupportsBasicEditing() const;
324 
325  using Holder = std::shared_ptr<Track>;
326 
328 
329  virtual Holder PasteInto( AudacityProject & ) const = 0;
330 
332 
335  virtual ConstIntervals GetIntervals() const;
336 
340  virtual Intervals GetIntervals();
341 
342  public:
343  mutable wxSize vrulerSize;
344 
345  // These are exposed only for the purposes of the TrackView class, to
346  // initialize the pointer on demand
347  const std::shared_ptr<CommonTrackCell> &GetTrackView();
348  void SetTrackView( const std::shared_ptr<CommonTrackCell> &pView );
349 
350  // These are exposed only for the purposes of the TrackControls class, to
351  // initialize the pointer on demand
352  const std::shared_ptr<CommonTrackCell> &GetTrackControls();
353  void SetTrackControls( const std::shared_ptr<CommonTrackCell> &pControls );
354 
355  // Return another, associated TrackPanelCell object that implements the
356 
357  int GetIndex() const;
358  void SetIndex(int index);
359 
360 public:
361  static void FinishCopy (const Track *n, Track *dest);
362 
363  // For use when loading a file. Return true if ok, else make repair
364  bool LinkConsistencyCheck();
365 
366  bool HasOwner() const { return static_cast<bool>(GetOwner());}
367 
368  std::shared_ptr<TrackList> GetOwner() const { return mList.lock(); }
369 
370 private:
371  Track *GetLink() const;
372  bool GetLinked () const { return mLinked; }
373 
374  friend WaveTrack; // WaveTrack needs to call SetLinked when reloading project
375  void SetLinked (bool l);
376 
377  void SetChannel(ChannelType c) { mChannel = c; }
378 private:
379  // No need yet to make this virtual
380  void DoSetLinked(bool l);
381 
383  TrackNodePointer GetNode() const;
385  void SetOwner
386  (const std::weak_ptr<TrackList> &list, TrackNodePointer node);
387 
388  // Keep in Track
389 
390  protected:
392  double mOffset;
393 
394  public:
395 
396  Track();
397  Track(const Track &orig);
398 
399  virtual ~ Track();
400 
401  void Init(const Track &orig);
402 
403  // public nonvirtual duplication function that invokes Clone():
404  virtual Holder Duplicate() const;
405 
406  // Called when this track is merged to stereo with another, and should
407  // take on some parameters of its partner.
408  virtual void Merge(const Track &orig);
409 
410  wxString GetName() const { return mName; }
411  void SetName( const wxString &n );
412  wxString GetDefaultName() const { return mDefaultName; }
413  void SetDefaultName( const wxString &n ) { mDefaultName = n; }
414 
415  bool GetSelected() const { return mSelected; }
416 
417  virtual void SetSelected(bool s);
418 
419  // The argument tells whether the last undo history state should be
420  // updated for the appearance change
421  void EnsureVisible( bool modifyState = false );
422 
423 public:
424 
425  virtual ChannelType GetChannel() const { return mChannel;}
426  virtual double GetOffset() const = 0;
427 
428  void Offset(double t) { SetOffset(GetOffset() + t); }
429  virtual void SetOffset (double o) { mOffset = o; }
430 
431  virtual void SetPan( float ){ ;}
432  virtual void SetPanFromChannelType(){ ;};
433 
434  // Create a NEW track and modify this track
435  // Return non-NULL or else throw
436  // May assume precondition: t0 <= t1
437  virtual Holder Cut(double WXUNUSED(t0), double WXUNUSED(t1)) = 0;
438 
439  // Create a NEW track and don't modify this track
440  // Return non-NULL or else throw
441  // Note that subclasses may want to distinguish tracks stored in a clipboard
442  // from those stored in a project
443  // May assume precondition: t0 <= t1
444  virtual Holder Copy
445  (double WXUNUSED(t0), double WXUNUSED(t1), bool forClipboard = true) const = 0;
446 
447  // May assume precondition: t0 <= t1
448  virtual void Clear(double WXUNUSED(t0), double WXUNUSED(t1)) = 0;
449 
450  virtual void Paste(double WXUNUSED(t), const Track * WXUNUSED(src)) = 0;
451 
452  // This can be used to adjust a sync-lock selected track when the selection
453  // is replaced by one of a different length.
454  virtual void SyncLockAdjust(double oldT1, double newT1);
455 
456  // May assume precondition: t0 <= t1
457  virtual void Silence(double WXUNUSED(t0), double WXUNUSED(t1)) = 0;
458 
459  // May assume precondition: t0 <= t1
460  virtual void InsertSilence(double WXUNUSED(t), double WXUNUSED(len)) = 0;
461 
462 private:
463  // Subclass responsibility implements only a part of Duplicate(), copying
464  // the track data proper (not associated data such as for groups and views):
465  virtual Holder Clone() const = 0;
466 
467  virtual TrackKind GetKind() const { return TrackKind::None; }
468 
469  template<typename T>
470  friend typename std::enable_if< std::is_pointer<T>::value, T >::type
471  track_cast(Track *track);
472  template<typename T>
473  friend typename std::enable_if<
474  std::is_pointer<T>::value &&
475  std::is_const< typename std::remove_pointer< T >::type >::value,
476  T
477  >::type
478  track_cast(const Track *track);
479 
480 public:
481  bool SameKindAs(const Track &track) const
482  { return GetKind() == track.GetKind(); }
483 
485  template < typename R = void >
486  using Continuation = std::function< R() >;
489 
490 private:
492  template< typename ...Params >
493  struct Executor{};
494 
496 
497  struct Dispatcher {
499  template< typename R, typename ConcreteType,
500  typename Function, typename ...Functions >
502  {
504  using Tail = Executor< R, ConcreteType, Functions... >;
506  enum : unsigned { SetUsed = Tail::SetUsed << 1 };
507 
509  R operator ()
510  (const Track *pTrack,
511  const Function &, const Functions &...functions)
512  { return Tail{}( pTrack, functions... ); }
513  };
514 
516  template< typename R, typename BaseClass, typename ConcreteType,
517  typename Function, typename ...Functions >
518  struct applicable1
519  {
521  enum : unsigned { SetUsed = 1u };
522 
524  R operator ()
525  (const Track *pTrack,
526  const Function &function, const Functions &...)
527  { return function( (BaseClass *)pTrack ); }
528  };
529 
531  template< typename R, typename BaseClass, typename ConcreteType,
532  typename Function, typename ...Functions >
533  struct applicable2
534  {
536  using Tail = Executor< R, ConcreteType, Functions... >;
538  enum : unsigned { SetUsed = (Tail::SetUsed << 1) | 1u };
539 
541  R operator ()
542  (const Track *pTrack, const Function &function,
543  const Functions &...functions)
544  {
545  auto continuation = Continuation<R>{ [&] {
546  return Tail{}( pTrack, functions... );
547  } };
548  return function( (BaseClass *)pTrack, continuation );
549  }
550  };
551 
553  template< typename ... > struct Switch {};
554 
556 
557  template< typename R, typename ConcreteType >
558  struct Switch< R, ConcreteType >
559  {
561  template< typename Function, typename ...Functions >
562  static auto test()
563  -> inapplicable< R, ConcreteType, Function, Functions... >;
564  };
565 
567 
568  template< typename R, typename ConcreteType,
569  typename BaseClass, typename ...BaseClasses >
570  struct Switch< R, ConcreteType, BaseClass, BaseClasses... >
571  {
573  using Retry = Switch< R, ConcreteType, BaseClasses... >;
574 
576 
578  template< typename Function, typename ...Functions >
579  static auto test( const void * )
580  -> decltype( Retry::template test< Function, Functions... >() );
581 
583 
586  template< typename Function, typename ...Functions >
587  static auto test( std::true_type * )
588  -> decltype(
589  (void) std::declval<Function>()
590  ( (BaseClass*)nullptr ),
591  applicable1< R, BaseClass, ConcreteType,
592  Function, Functions... >{}
593  );
594 
596 
600  template< typename Function, typename ...Functions >
601  static auto test( std::true_type * )
602  -> decltype(
603  (void) std::declval<Function>()
604  ( (BaseClass*)nullptr,
605  std::declval< Continuation<R> >() ),
606  applicable2< R, BaseClass, ConcreteType,
607  Function, Functions... >{}
608  );
609 
611  static constexpr bool Compatible = CompatibleTrackKinds(
612  track_kind<BaseClass>(), track_kind<ConcreteType>() );
614  template< typename Function, typename ...Functions >
615  static auto test()
616  -> decltype(
617  test< Function, Functions... >(
618  (std::integral_constant<bool, Compatible>*)nullptr) );
619  };
620  };
621 
623  template< typename R, typename ConcreteType >
624  struct Executor< R, ConcreteType >
625  {
627  enum : unsigned { SetUsed = 0 };
629  R operator () (const void *) { return R{}; }
630  };
631 
633  template< typename ConcreteType >
634  struct Executor< void, ConcreteType >
635  {
637  enum : unsigned { SetUsed = 0 };
639  void operator () (const void *) { }
640  };
641 
643 
644  template< typename R, typename ConcreteType,
645  typename Function, typename ...Functions >
646  struct Executor< R, ConcreteType, Function, Functions... >
647  : decltype(
648  Dispatcher::Switch< R, ConcreteType,
649  Track, AudioTrack, PlayableTrack,
650  WaveTrack, LabelTrack, TimeTrack,
651  NoteTrack >
652  ::template test<Function, Functions... >())
653  {};
654 
656 
657  template< typename R, typename ConcreteType,
658  typename Function, typename ...Functions >
659  struct Executor< R, const ConcreteType, Function, Functions... >
660  : decltype(
661  Dispatcher::Switch< R, ConcreteType,
662  const Track, const AudioTrack, const PlayableTrack,
663  const WaveTrack, const LabelTrack, const TimeTrack,
664  const NoteTrack >
665  ::template test<Function, Functions... >())
666  {};
667 
668 public:
669 
671 
689  template<
690  typename R = void,
691  typename ...Functions
692  >
693  R TypeSwitch( const Functions &...functions )
694  {
695  using WaveExecutor =
696  Executor< R, WaveTrack, Functions... >;
697  using NoteExecutor =
698  Executor< R, NoteTrack, Functions... >;
699  using LabelExecutor =
700  Executor< R, LabelTrack, Functions... >;
701  using TimeExecutor =
702  Executor< R, TimeTrack, Functions... >;
703  using DefaultExecutor =
705  enum { All = sizeof...( functions ) };
706 
707  static_assert(
708  (1u << All) - 1u ==
709  (WaveExecutor::SetUsed |
710  NoteExecutor::SetUsed |
711  LabelExecutor::SetUsed |
712  TimeExecutor::SetUsed),
713  "Uncallable case in Track::TypeSwitch"
714  );
715 
716  switch (GetKind()) {
717  case TrackKind::Wave:
718  return WaveExecutor{} (this, functions...);
719 #if defined(USE_MIDI)
720  case TrackKind::Note:
721  return NoteExecutor{} (this, functions...);
722 #endif
723  case TrackKind::Label:
724  return LabelExecutor{}(this, functions...);
725  case TrackKind::Time:
726  return TimeExecutor{} (this, functions...);
727  default:
728  return DefaultExecutor{} (this);
729  }
730  }
731 
735  template<
736  typename R = void,
737  typename ...Functions
738  >
739  R TypeSwitch(const Functions &...functions) const
740  {
741  using WaveExecutor =
742  Executor< R, const WaveTrack, Functions... >;
743  using NoteExecutor =
744  Executor< R, const NoteTrack, Functions... >;
745  using LabelExecutor =
746  Executor< R, const LabelTrack, Functions... >;
747  using TimeExecutor =
748  Executor< R, const TimeTrack, Functions... >;
749  using DefaultExecutor =
751  enum { All = sizeof...( functions ) };
752 
753  static_assert(
754  (1u << All) - 1u ==
755  (WaveExecutor::SetUsed |
756  NoteExecutor::SetUsed |
757  LabelExecutor::SetUsed |
758  TimeExecutor::SetUsed),
759  "Uncallable case in Track::TypeSwitch"
760  );
761 
762  switch (GetKind()) {
763  case TrackKind::Wave:
764  return WaveExecutor{} (this, functions...);
765 #if defined(USE_MIDI)
766  case TrackKind::Note:
767  return NoteExecutor{} (this, functions...);
768 #endif
769  case TrackKind::Label:
770  return LabelExecutor{}(this, functions...);
771  case TrackKind::Time:
772  return TimeExecutor{} (this, functions...);
773  default:
774  return DefaultExecutor{} (this);
775  }
776  }
777 
778  // XMLTagHandler callback methods -- NEW virtual for writing
779  virtual void WriteXML(XMLWriter &xmlFile) const = 0;
780 
781  // Returns true if an error was encountered while trying to
782  // open the track from XML
783  virtual bool GetErrorOpening() { return false; }
784 
785  virtual double GetStartTime() const = 0;
786  virtual double GetEndTime() const = 0;
787 
788  // Checks if sync-lock is on and any track in its sync-lock group is selected.
789  bool IsSyncLockSelected() const;
790 
791  // Send an event to listeners when state of the track changes
792  // To do: define values for the argument to distinguish different parts
793  // of the state, perhaps with wxNewId
794  void Notify( int code = -1 );
795 
796  // An always-true predicate useful for defining iterators
797  bool Any() const;
798 
799  // Frequently useful operands for + and -
800  bool IsSelected() const;
801  bool IsSelectedOrSyncLockSelected() const;
802  bool IsLeader() const;
803  bool IsSelectedLeader() const;
804 
805  // Cause this track and following ones in its TrackList to adjust
806  void AdjustPositions();
807 
808  // Serialize, not with tags of its own, but as attributes within a tag.
809  void WriteCommonXMLAttributes(
810  XMLWriter &xmlFile, bool includeNameAndSelected = true) const;
811 
812  // Return true iff the attribute is recognized.
813  bool HandleCommonXMLAttribute(const wxChar *attr, const wxChar *value);
814 
815 protected:
816  std::shared_ptr<CommonTrackCell> mpView;
817  std::shared_ptr<CommonTrackCell> mpControls;
818 };
819 
821 class AUDACITY_DLL_API AudioTrack /* not final */ : public Track
822 {
823 public:
825  : Track{} {}
826  AudioTrack(const Track &orig) : Track{ orig } {}
827 
828  // Serialize, not with tags of its own, but as attributes within a tag.
829  void WriteXMLAttributes(XMLWriter &WXUNUSED(xmlFile)) const {}
830 
831  // Return true iff the attribute is recognized.
832  bool HandleXMLAttribute(const wxChar * /*attr*/, const wxChar * /*value*/)
833  { return false; }
834 };
835 
837 class AUDACITY_DLL_API PlayableTrack /* not final */ : public AudioTrack
838 {
839 public:
841  : AudioTrack{} {}
842  PlayableTrack(const Track &orig) : AudioTrack{ orig } {}
843 
844  bool GetMute () const { return mMute; }
845  bool GetSolo () const { return mSolo; }
846  bool GetNotMute () const { return !mMute; }
847  bool GetNotSolo () const { return !mSolo; }
848  void SetMute (bool m);
849  void SetSolo (bool s);
850 
851  void Init( const PlayableTrack &init );
852  void Merge( const Track &init ) override;
853 
854  // Serialize, not with tags of its own, but as attributes within a tag.
855  void WriteXMLAttributes(XMLWriter &xmlFile) const;
856 
857  // Return true iff the attribute is recognized.
858  bool HandleXMLAttribute(const wxChar *attr, const wxChar *value);
859 
860 protected:
861  bool mMute { false };
862  bool mSolo { false };
863 };
864 
866 
873 template<typename T>
874  inline typename std::enable_if< std::is_pointer<T>::value, T >::type
876 {
877  using BareType = typename std::remove_pointer< T >::type;
878  if (track &&
879  CompatibleTrackKinds( track_kind<BareType>(), track->GetKind() ))
880  return reinterpret_cast<T>(track);
881  else
882  return nullptr;
883 }
884 
887 template<typename T>
888  inline typename std::enable_if<
889  std::is_pointer<T>::value &&
890  std::is_const< typename std::remove_pointer< T >::type >::value,
891  T
892  >::type
893  track_cast(const Track *track)
894 {
895  using BareType = typename std::remove_pointer< T >::type;
896  if (track &&
897  CompatibleTrackKinds( track_kind<BareType>(), track->GetKind() ))
898  return reinterpret_cast<T>(track);
899  else
900  return nullptr;
901 }
902 
903 template < typename TrackType > struct TrackIterRange;
904 
906 
913 template <
914  typename TrackType
915 > class TrackIter
916  : public ValueIterator< TrackType *, std::bidirectional_iterator_tag >
917 {
918 public:
920 
921  using FunctionType = std::function< bool(
922  typename std::add_pointer<
923  typename std::add_const<
924  typename std::remove_pointer<
925  TrackType
926  >::type
927  >::type
928  >::type
929  ) >;
930 
933  TrackNodePointer begin,
934  TrackNodePointer iter,
935  TrackNodePointer end,
936  FunctionType pred = {}
937  )
938  : mBegin( begin ), mIter( iter ), mEnd( end )
939  , mPred( std::move(pred) )
940  {
941  // Establish the class invariant
942  if (this->mIter != this->mEnd && !this->valid())
943  this->operator ++ ();
944  }
945 
947 
949  template < typename Predicate2 >
950  TrackIter Filter( const Predicate2 &pred2 ) const
951  {
952  return { this->mBegin, this->mIter, this->mEnd, pred2 };
953  }
954 
956 
958  template < typename TrackType2 >
959  auto Filter() const
960  -> typename std::enable_if<
961  std::is_base_of< TrackType, TrackType2 >::value &&
962  (!std::is_const<TrackType>::value ||
963  std::is_const<TrackType2>::value),
964  TrackIter< TrackType2 >
965  >::type
966  {
967  return { this->mBegin, this->mIter, this->mEnd, this->mPred };
968  }
969 
970  const FunctionType &GetPredicate() const
971  { return this->mPred; }
972 
974 
976  {
977  // Maintain the class invariant
978  if (this->mIter != this->mEnd) do
979  ++this->mIter.first;
980  while (this->mIter != this->mEnd && !this->valid() );
981  return *this;
982  }
983 
986  {
987  TrackIter result { *this };
988  this-> operator ++ ();
989  return result;
990  }
991 
993 
995  {
996  // Maintain the class invariant
997  do {
998  if (this->mIter == this->mBegin)
999  // Go circularly
1000  this->mIter = this->mEnd;
1001  else
1002  --this->mIter.first;
1003  } while (this->mIter != this->mEnd && !this->valid() );
1004  return *this;
1005  }
1006 
1009  {
1010  TrackIter result { *this };
1011  this->operator -- ();
1012  return result;
1013  }
1014 
1016 
1017  TrackType *operator * () const
1018  {
1019  if (this->mIter == this->mEnd)
1020  return nullptr;
1021  else
1022  // Other methods guarantee that the cast is correct
1023  // (provided no operations on the TrackList invalidated
1024  // underlying iterators or replaced the tracks there)
1025  return static_cast< TrackType * >( &**this->mIter.first );
1026  }
1027 
1030  long amount
1031  ) const
1032  {
1033  auto copy = *this;
1034  std::advance( copy, amount );
1035  return copy;
1036  }
1037 
1039  friend inline bool operator == (TrackIter a, TrackIter b)
1040  {
1041  // Assume the predicate is not stateful. Just compare the iterators.
1042  return
1043  a.mIter == b.mIter
1044  // Assume this too:
1045  // && a.mBegin == b.mBegin && a.mEnd == b.mEnd
1046  ;
1047  }
1048 
1050  friend inline bool operator != (TrackIter a, TrackIter b)
1051  {
1052  return !(a == b);
1053  }
1054 
1055 private:
1060  bool valid() const
1062  {
1063  // assume mIter != mEnd
1064  const auto pTrack = track_cast< TrackType * >( &**this->mIter.first );
1065  if (!pTrack)
1066  return false;
1067  return !this->mPred || this->mPred( pTrack );
1068  }
1069 
1072 
1078 };
1079 
1081 template <
1082  typename TrackType // Track or a subclass, maybe const-qualified
1084  : public IteratorRange< TrackIter< TrackType > >
1085 {
1087  ( const TrackIter< TrackType > &begin,
1088  const TrackIter< TrackType > &end )
1089  : IteratorRange< TrackIter< TrackType > >
1090  ( begin, end )
1091  {}
1092 
1093  // Conjoin the filter predicate with another predicate
1094  // Read + as "and"
1095  template< typename Predicate2 >
1096  TrackIterRange operator + ( const Predicate2 &pred2 ) const
1097  {
1098  const auto &pred1 = this->first.GetPredicate();
1099  using Function = typename TrackIter<TrackType>::FunctionType;
1100  const auto &newPred = pred1
1101  ? Function{ [=] (typename Function::argument_type track) {
1102  return pred1(track) && pred2(track);
1103  } }
1104  : Function{ pred2 };
1105  return {
1106  this->first.Filter( newPred ),
1107  this->second.Filter( newPred )
1108  };
1109  }
1110 
1111  // Specify the added conjunct as a pointer to member function
1112  // Read + as "and"
1113  template< typename R, typename C >
1114  TrackIterRange operator + ( R ( C ::* pmf ) () const ) const
1115  {
1116  return this->operator + ( std::mem_fn( pmf ) );
1117  }
1118 
1119  // Conjoin the filter predicate with the negation of another predicate
1120  // Read - as "and not"
1121  template< typename Predicate2 >
1122  TrackIterRange operator - ( const Predicate2 &pred2 ) const
1123  {
1124  using ArgumentType =
1125  typename TrackIterRange::iterator::FunctionType::argument_type;
1126  auto neg = [=] (ArgumentType track) { return !pred2( track ); };
1127  return this->operator + ( neg );
1128  }
1129 
1130  // Specify the negated conjunct as a pointer to member function
1131  // Read - as "and not"
1132  template< typename R, typename C >
1133  TrackIterRange operator - ( R ( C ::* pmf ) () const ) const
1134  {
1135  return this->operator + ( std::not1( std::mem_fn( pmf ) ) );
1136  }
1137 
1138  template< typename TrackType2 >
1140  {
1141  return {
1142  this-> first.template Filter< TrackType2 >(),
1143  this->second.template Filter< TrackType2 >()
1144  };
1145  }
1146 
1147  TrackIterRange StartingWith( const Track *pTrack ) const
1148  {
1149  auto newBegin = this->find( pTrack );
1150  // More careful construction is needed so that the independent
1151  // increment and decrement of each iterator in the NEW pair
1152  // has the expected behavior at boundaries of the range
1153  return {
1154  { newBegin.mIter, newBegin.mIter, this->second.mEnd,
1155  this->first.GetPredicate() },
1156  { newBegin.mIter, this->second.mIter, this->second.mEnd,
1157  this->second.GetPredicate() }
1158  };
1159  }
1160 
1161  TrackIterRange EndingAfter( const Track *pTrack ) const
1162  {
1163  const auto newEnd = this->reversal().find( pTrack ).base();
1164  // More careful construction is needed so that the independent
1165  // increment and decrement of each iterator in the NEW pair
1166  // has the expected behavior at boundaries of the range
1167  return {
1168  { this->first.mBegin, this->first.mIter, newEnd.mIter,
1169  this->first.GetPredicate() },
1170  { this->first.mBegin, newEnd.mIter, newEnd.mIter,
1171  this->second.GetPredicate() }
1172  };
1173  }
1174 
1175  // Exclude one given track
1176  TrackIterRange Excluding ( const TrackType *pExcluded ) const
1177  {
1178  return this->operator - (
1179  [=](const Track *pTrack){ return pExcluded == pTrack; } );
1180  }
1181 
1183  template< typename ...Functions >
1184  void Visit(const Functions &...functions)
1185  {
1186  for (auto track : *this)
1187  track->TypeSwitch(functions...);
1188  }
1189 
1191 
1192  template< typename Flag, typename ...Functions >
1193  void VisitWhile(Flag &flag, const Functions &...functions)
1194  {
1195  if ( flag ) for (auto track : *this) {
1196  track->TypeSwitch(functions...);
1197  if (!flag)
1198  break;
1199  }
1200  }
1201 };
1202 
1203 
1205 struct TrackListEvent : public wxCommandEvent
1206 {
1207  explicit
1209  wxEventType commandType,
1210  const std::weak_ptr<Track> &pTrack = {}, int code = -1)
1211  : wxCommandEvent{ commandType }
1212  , mpTrack{ pTrack }
1213  , mCode{ code }
1214  {}
1215 
1216  TrackListEvent( const TrackListEvent& ) = default;
1217 
1218  wxEvent *Clone() const override {
1219  // wxWidgets will own the event object
1220  return safenew TrackListEvent(*this); }
1221 
1222  std::weak_ptr<Track> mpTrack;
1223  int mCode;
1224 };
1225 
1227 wxDECLARE_EXPORTED_EVENT(AUDACITY_DLL_API,
1228  EVT_TRACKLIST_SELECTION_CHANGE, TrackListEvent);
1229 
1231 wxDECLARE_EXPORTED_EVENT(AUDACITY_DLL_API,
1232  EVT_TRACKLIST_TRACK_DATA_CHANGE, TrackListEvent);
1233 
1235 wxDECLARE_EXPORTED_EVENT(AUDACITY_DLL_API,
1236  EVT_TRACKLIST_TRACK_REQUEST_VISIBLE, TrackListEvent);
1237 
1239 
1240 wxDECLARE_EXPORTED_EVENT(AUDACITY_DLL_API,
1241  EVT_TRACKLIST_PERMUTED, TrackListEvent);
1242 
1244 wxDECLARE_EXPORTED_EVENT(AUDACITY_DLL_API,
1245  EVT_TRACKLIST_RESIZING, TrackListEvent);
1246 
1248 wxDECLARE_EXPORTED_EVENT(AUDACITY_DLL_API,
1249  EVT_TRACKLIST_ADDITION, TrackListEvent);
1250 
1252 
1253 wxDECLARE_EXPORTED_EVENT(AUDACITY_DLL_API,
1254  EVT_TRACKLIST_DELETION, TrackListEvent);
1255 
1259 class AUDACITY_DLL_API TrackList final
1260  : public wxEvtHandler
1261  , public ListOfTracks
1262  , public std::enable_shared_from_this<TrackList>
1263  , public ClientData::Base
1264 {
1265  // privatize this, make you use Add instead:
1266  using ListOfTracks::push_back;
1267 
1268  // privatize this, make you use Swap instead:
1269  using ListOfTracks::swap;
1270 
1271  // Disallow copy
1272  TrackList(const TrackList &that) = delete;
1273  TrackList &operator= (const TrackList&) = delete;
1274 
1275  // No need for move, disallow it
1276  TrackList(TrackList &&that) = delete;
1277  TrackList& operator= (TrackList&&) = delete;
1278 
1279  void clear() = delete;
1280 
1281  public:
1282  static TrackList &Get( AudacityProject &project );
1283  static const TrackList &Get( const AudacityProject &project );
1284 
1285  // Create an empty TrackList
1286  // Don't call directly -- use Create() instead
1287  explicit TrackList( AudacityProject *pOwner );
1288 
1289  // Create an empty TrackList
1290  static std::shared_ptr<TrackList> Create( AudacityProject *pOwner );
1291 
1292  // Move is defined in terms of Swap
1293  void Swap(TrackList &that);
1294 
1295  // Destructor
1296  virtual ~TrackList();
1297 
1298  // Find the owning project, which may be null
1299  AudacityProject *GetOwner() { return mOwner; }
1300  const AudacityProject *GetOwner() const { return mOwner; }
1301 
1302  // Iteration
1303 
1304  // Hide the inherited begin() and end()
1307  using value_type = Track *;
1308  iterator begin() { return Any().begin(); }
1309  iterator end() { return Any().end(); }
1310  const_iterator begin() const { return Any().begin(); }
1311  const_iterator end() const { return Any().end(); }
1312  const_iterator cbegin() const { return begin(); }
1313  const_iterator cend() const { return end(); }
1314 
1316  template < typename TrackType = Track >
1317  auto Find(Track *pTrack)
1319  {
1320  if (!pTrack || pTrack->GetOwner().get() != this)
1321  return EndIterator<TrackType>();
1322  else
1323  return MakeTrackIterator<TrackType>( pTrack->GetNode() );
1324  }
1325 
1327 
1328  template < typename TrackType = const Track >
1329  auto Find(const Track *pTrack) const
1330  -> typename std::enable_if< std::is_const<TrackType>::value,
1332  >::type
1333  {
1334  if (!pTrack || pTrack->GetOwner().get() != this)
1335  return EndIterator<TrackType>();
1336  else
1337  return MakeTrackIterator<TrackType>( pTrack->GetNode() );
1338  }
1339 
1340  // If the track is not an audio track, or not one of a group of channels,
1341  // return the track itself; else return the first channel of its group --
1342  // in either case as an iterator that will only visit other leader tracks.
1343  // (Generalizing away from the assumption of at most stereo)
1344  TrackIter< Track > FindLeader( Track *pTrack );
1345 
1347  FindLeader( const Track *pTrack ) const
1348  {
1349  return const_cast<TrackList*>(this)->
1350  FindLeader( const_cast<Track*>(pTrack) ).Filter< const Track >();
1351  }
1352 
1353 
1354  template < typename TrackType = Track >
1355  auto Any()
1357  {
1358  return Tracks< TrackType >();
1359  }
1360 
1361  template < typename TrackType = const Track >
1362  auto Any() const
1363  -> typename std::enable_if< std::is_const<TrackType>::value,
1364  TrackIterRange< TrackType >
1365  >::type
1366  {
1367  return Tracks< TrackType >();
1368  }
1369 
1370  // Abbreviating some frequently used cases
1371  template < typename TrackType = Track >
1372  auto Selected()
1374  {
1375  return Tracks< TrackType >( &Track::IsSelected );
1376  }
1377 
1378  template < typename TrackType = const Track >
1379  auto Selected() const
1380  -> typename std::enable_if< std::is_const<TrackType>::value,
1381  TrackIterRange< TrackType >
1382  >::type
1383  {
1384  return Tracks< TrackType >( &Track::IsSelected );
1385  }
1386 
1387 
1388  template < typename TrackType = Track >
1389  auto Leaders()
1391  {
1392  return Tracks< TrackType >( &Track::IsLeader );
1393  }
1394 
1395  template < typename TrackType = const Track >
1396  auto Leaders() const
1397  -> typename std::enable_if< std::is_const<TrackType>::value,
1398  TrackIterRange< TrackType >
1399  >::type
1400  {
1401  return Tracks< TrackType >( &Track::IsLeader );
1402  }
1403 
1404 
1405  template < typename TrackType = Track >
1408  {
1409  return Tracks< TrackType >( &Track::IsSelectedLeader );
1410  }
1411 
1412  template < typename TrackType = const Track >
1413  auto SelectedLeaders() const
1414  -> typename std::enable_if< std::is_const<TrackType>::value,
1415  TrackIterRange< TrackType >
1416  >::type
1417  {
1418  return Tracks< TrackType >( &Track::IsSelectedLeader );
1419  }
1420 
1421 
1422  template<typename TrackType>
1423  static auto SingletonRange( TrackType *pTrack )
1425  {
1426  return pTrack->GetOwner()->template Any<TrackType>()
1427  .StartingWith( pTrack ).EndingAfter( pTrack );
1428  }
1429 
1430 
1432  SyncLockGroup( Track *pTrack );
1433 
1435  SyncLockGroup( const Track *pTrack )
1436  {
1437  return SyncLockGroup(const_cast<Track*>(pTrack)).Filter<const Track>();
1438  }
1439 
1440 private:
1441  Track *DoAddToHead(const std::shared_ptr<Track> &t);
1442  Track *DoAdd(const std::shared_ptr<Track> &t);
1443 
1444  template< typename TrackType, typename InTrackType >
1447  {
1448  // Assume iterator filters leader tracks
1449  if (*iter1) {
1450  return {
1451  iter1.Filter( &Track::Any )
1452  .template Filter<TrackType>(),
1453  (++iter1).Filter( &Track::Any )
1454  .template Filter<TrackType>()
1455  };
1456  }
1457  else
1458  // empty range
1459  return {
1460  iter1.template Filter<TrackType>(),
1461  iter1.template Filter<TrackType>()
1462  };
1463  }
1464 
1465 public:
1466  // Find an iterator range of channels including the given track.
1467  template< typename TrackType >
1468  static auto Channels( TrackType *pTrack )
1470  {
1471  return Channels_<TrackType>( pTrack->GetOwner()->FindLeader(pTrack) );
1472  }
1473 
1474  friend class Track;
1475 
1477  void Permute(const std::vector<TrackNodePointer> &permutation);
1478 
1479  Track *FindById( TrackId id );
1480 
1482  template<typename TrackKind>
1483  TrackKind *AddToHead( const std::shared_ptr< TrackKind > &t )
1484  { return static_cast< TrackKind* >( DoAddToHead( t ) ); }
1485 
1486  template<typename TrackKind>
1487  TrackKind *Add( const std::shared_ptr< TrackKind > &t )
1488  { return static_cast< TrackKind* >( DoAdd( t ) ); }
1489 
1497  void GroupChannels(
1498  Track &track, size_t groupSize, bool resetChannels = true );
1499 
1502  ListOfTracks::value_type Replace(
1503  Track * t, const ListOfTracks::value_type &with);
1504 
1507 
1509  void Clear(bool sendEvent = true);
1510 
1511  bool CanMoveUp(Track * t) const;
1512  bool CanMoveDown(Track * t) const;
1513 
1514  bool MoveUp(Track * t);
1515  bool MoveDown(Track * t);
1516  bool Move(Track * t, bool up) { return up ? MoveUp(t) : MoveDown(t); }
1517 
1519  bool Contains(const Track * t) const;
1520 
1521  // Return non-null only if the weak pointer is not, and the track is
1522  // owned by this list; constant time.
1523  template <typename Subclass>
1524  std::shared_ptr<Subclass> Lock(const std::weak_ptr<Subclass> &wTrack)
1525  {
1526  auto pTrack = wTrack.lock();
1527  if (pTrack) {
1528  auto pList = pTrack->mList.lock();
1529  if (pTrack && this == pList.get())
1530  return pTrack;
1531  }
1532  return {};
1533  }
1534 
1535  bool empty() const;
1536  size_t size() const;
1537 
1538  double GetStartTime() const;
1539  double GetEndTime() const;
1540 
1541  double GetMinOffset() const;
1542 
1543 private:
1544 
1545  // Visit all tracks satisfying a predicate, mutative access
1546  template <
1547  typename TrackType = Track,
1548  typename Pred =
1550  >
1551  auto Tracks( const Pred &pred = {} )
1553  {
1554  auto b = getBegin(), e = getEnd();
1555  return { { b, b, e, pred }, { b, e, e, pred } };
1556  }
1557 
1558  // Visit all tracks satisfying a predicate, const access
1559  template <
1560  typename TrackType = const Track,
1561  typename Pred =
1563  >
1564  auto Tracks( const Pred &pred = {} ) const
1565  -> typename std::enable_if< std::is_const<TrackType>::value,
1567  >::type
1568  {
1569  auto b = const_cast<TrackList*>(this)->getBegin();
1570  auto e = const_cast<TrackList*>(this)->getEnd();
1571  return { { b, b, e, pred }, { b, e, e, pred } };
1572  }
1573 
1574  Track *GetPrev(Track * t, bool linked = false) const;
1575  Track *GetNext(Track * t, bool linked = false) const;
1576 
1577  std::pair<Track *, Track *> FindSyncLockGroup(Track *pMember) const;
1578 
1579  template < typename TrackType >
1582  {
1583  auto b = const_cast<TrackList*>(this)->getBegin();
1584  auto e = const_cast<TrackList*>(this)->getEnd();
1585  return { b, iter, e };
1586  }
1587 
1588  template < typename TrackType >
1590  EndIterator() const
1591  {
1592  auto e = const_cast<TrackList*>(this)->getEnd();
1593  return { e, e, e };
1594  }
1595 
1596  TrackIterRange< Track > EmptyRange() const;
1597 
1598  bool isNull(TrackNodePointer p) const
1599  { return (p.second == this && p.first == ListOfTracks::end())
1600  || (p.second == &mPendingUpdates && p.first == mPendingUpdates.end()); }
1602  { return { const_cast<TrackList*>(this)->ListOfTracks::end(),
1603  const_cast<TrackList*>(this)}; }
1605  { return { const_cast<TrackList*>(this)->ListOfTracks::begin(),
1606  const_cast<TrackList*>(this)}; }
1607 
1610  {
1611  if ( isNull(p) )
1612  return p;
1613  auto q = p;
1614  ++q.first;
1615  return q;
1616  }
1617 
1620  {
1621  if (p == getBegin())
1622  return getEnd();
1623  else {
1624  auto q = p;
1625  --q.first;
1626  return q;
1627  }
1628  }
1629 
1630  void RecalcPositions(TrackNodePointer node);
1631  void SelectionEvent( const std::shared_ptr<Track> &pTrack );
1632  void PermutationEvent(TrackNodePointer node);
1633  void DataEvent( const std::shared_ptr<Track> &pTrack, int code );
1634  void EnsureVisibleEvent(
1635  const std::shared_ptr<Track> &pTrack, bool modifyState );
1636  void DeletionEvent(TrackNodePointer node = {});
1637  void AdditionEvent(TrackNodePointer node);
1638  void ResizingEvent(TrackNodePointer node);
1639 
1640  void SwapNodes(TrackNodePointer s1, TrackNodePointer s2);
1641 
1642  // Nondecreasing during the session.
1643  // Nonpersistent.
1644  // Used to assign ids to added tracks.
1645  static long sCounter;
1646 
1647 public:
1648  using Updater = std::function< void(Track &dest, const Track &src) >;
1649  // Start a deferred update of the project.
1650  // The return value is a duplicate of the given track.
1651  // While ApplyPendingTracks or ClearPendingTracks is not yet called,
1652  // there may be other direct changes to the project that push undo history.
1653  // Meanwhile the returned object can accumulate other changes for a deferred
1654  // push, and temporarily shadow the actual project track for display purposes.
1655  // The Updater function, if not null, merges state (from the actual project
1656  // into the pending track) which is not meant to be overridden by the
1657  // accumulated pending changes.
1658  // To keep the display consistent, the Y and Height values, minimized state,
1659  // and Linked state must be copied, and this will be done even if the
1660  // Updater does not do it.
1661  // Pending track will have the same TrackId as the actual.
1662  // Pending changed tracks will not occur in iterations.
1663  std::shared_ptr<Track> RegisterPendingChangedTrack(
1664  Updater updater,
1665  Track *src
1666  );
1667 
1668  // Like the previous, but for a NEW track, not a replacement track. Caller
1669  // supplies the track, and there are no updates.
1670  // Pending track will have an unassigned TrackId.
1671  // Pending changed tracks WILL occur in iterations, always after actual
1672  // tracks, and in the sequence that they were added. They can be
1673  // distinguished from actual tracks by TrackId.
1674  void RegisterPendingNewTrack( const std::shared_ptr<Track> &pTrack );
1675 
1676  // Invoke the updaters of pending tracks. Pass any exceptions from the
1677  // updater functions.
1678  void UpdatePendingTracks();
1679 
1680  // Forget pending track additions and changes;
1681  // if requested, give back the pending added tracks.
1682  void ClearPendingTracks( ListOfTracks *pAdded = nullptr );
1683 
1684  // Change the state of the project.
1685  // Strong guarantee for project state in case of exceptions.
1686  // Will always clear the pending updates.
1687  // Return true if the state of the track list really did change.
1688  bool ApplyPendingTracks();
1689 
1690  bool HasPendingTracks() const;
1691 
1692 private:
1694 
1696 
1699  std::vector< Updater > mUpdaters;
1700 };
1701 
1702 #endif
XMLWriter
Base class for XMLFileWriter and XMLStringWriter that provides the general functionality for creating...
Definition: XMLWriter.h:23
TrackList::isNull
bool isNull(TrackNodePointer p) const
Definition: Track.h:1598
track_kind
constexpr TrackKind track_kind()
Metafunction from track subtype (as template parameter) to enum value.
Definition: Track.h:137
Init
Definition: ModuleManager.h:152
WaveTrackArray
std::vector< std::shared_ptr< WaveTrack > > WaveTrackArray
Definition: AudioIO.h:58
TrackIntervalData::~TrackIntervalData
virtual ~TrackIntervalData()
ConstTrackInterval::operator=
ConstTrackInterval & operator=(ConstTrackInterval &&)=default
WaveTrackConstArray
std::vector< std::shared_ptr< const WaveTrack > > WaveTrackConstArray
Definition: AudioIO.h:59
Track::SharedPointer
auto SharedPointer() const -> typename std::enable_if< std::is_const< Subclass >::value, std::shared_ptr< Subclass > >::type
Definition: Track.h:288
Track::mChannel
ChannelType mChannel
Definition: Track.h:391
TrackTyper
Metaprogramming enabling track_cast even when the subclasses are incomplete types.
Definition: Track.h:105
TrackList::EndIterator
TrackIter< TrackType > EndIterator() const
Definition: Track.h:1590
WaveTrack
A Track that contains audio waveform data.
Definition: WaveTrack.h:69
Track::GetDefaultName
wxString GetDefaultName() const
Definition: Track.h:412
Track::mOffset
double mOffset
Definition: Track.h:392
Track::SetId
void SetId(TrackId id)
Definition: Track.h:272
Track::Continuation
std::function< R() > Continuation
Type of arguments passed as optional second parameter to TypeSwitch() cases.
Definition: Track.h:486
PlayableTrack::PlayableTrack
PlayableTrack(const Track &orig)
Definition: Track.h:842
TrackList::Selected
auto Selected() const -> typename std::enable_if< std::is_const< TrackType >::value, TrackIterRange< TrackType > >::type
Definition: Track.h:1379
PlayableTrack::GetSolo
bool GetSolo() const
Definition: Track.h:845
Track::mSelected
bool mSelected
Definition: Track.h:255
PlayableTrack::GetMute
bool GetMute() const
Definition: Track.h:844
TrackKind::None
@ None
no class
ConstTrackInterval::ConstTrackInterval
ConstTrackInterval(double start, double end, std::unique_ptr< TrackIntervalData > pExtra={})
Definition: Track.h:196
flag
static std::once_flag flag
Definition: WaveformView.cpp:1125
TrackList::getEnd
TrackNodePointer getEnd() const
Definition: Track.h:1601
Track::GetEndTime
virtual double GetEndTime() const =0
TrackList::Lock
std::shared_ptr< Subclass > Lock(const std::weak_ptr< Subclass > &wTrack)
Definition: Track.h:1524
Track::GetName
wxString GetName() const
Definition: Track.h:410
Track::ConstIntervals
std::vector< ConstInterval > ConstIntervals
Definition: Track.h:320
TrackIter
Iterator over only members of a TrackList of the specified subtype, optionally filtered by a predicat...
Definition: Track.h:917
TrackId::operator==
bool operator==(const TrackId &other) const
Definition: Track.h:170
TrackList::SelectedLeaders
auto SelectedLeaders() const -> typename std::enable_if< std::is_const< TrackType >::value, TrackIterRange< TrackType > >::type
Definition: Track.h:1413
TrackKind::Playable
@ Playable
nonleaf
TrackIter::GetPredicate
const FunctionType & GetPredicate() const
Definition: Track.h:970
ValueIterator
std::iterator< Category, const Value, ptrdiff_t, void, const Value > ValueIterator
A convenience for defining iterators that return rvalue types, so that they cooperate correctly with ...
Definition: MemoryX.h:372
TrackList::Channels
static auto Channels(TrackType *pTrack) -> TrackIterRange< TrackType >
Definition: Track.h:1468
TrackList
A flat linked list of tracks supporting Add, Remove, Clear, and Contains, serialization of the list o...
Definition: Track.h:1264
ConstTrackInterval::End
double End() const
Definition: Track.h:207
TrackId::operator!=
bool operator!=(const TrackId &other) const
Definition: Track.h:173
Track::Dispatcher::Switch< R, ConcreteType >::test
static auto test() -> inapplicable< R, ConcreteType, Function, Functions... >
No BaseClass of ConcreteType is acceptable to Function.
Track::GetLinked
bool GetLinked() const
Definition: Track.h:372
TrackIntervalData
Optional extra information about an interval, appropriate to a subtype of Track.
Definition: Track.h:186
Track::Merge
virtual void Merge(const Track &orig)
Definition: Track.cpp:108
operator==
bool operator==(const TrackNodePointer &a, const TrackNodePointer &b)
Definition: Track.h:61
TrackList::Leaders
auto Leaders() const -> typename std::enable_if< std::is_const< TrackType >::value, TrackIterRange< TrackType > >::type
Definition: Track.h:1396
Track::SharedPointer
std::shared_ptr< Subclass > SharedPointer()
Definition: Track.h:280
Track::Cut
virtual Holder Cut(double WXUNUSED(t0), double WXUNUSED(t1))=0
IteratorRange
A convenience for use with range-for.
Definition: MemoryX.h:378
TrackListEvent::TrackListEvent
TrackListEvent(wxEventType commandType, const std::weak_ptr< Track > &pTrack={}, int code=-1)
Definition: Track.h:1208
Track::Dispatcher::applicable1
Second, nonrecursive case of metafunction, generates operator () that calls function without fallthro...
Definition: Track.h:519
TrackList::Tracks
auto Tracks(const Pred &pred={}) const -> typename std::enable_if< std::is_const< TrackType >::value, TrackIterRange< TrackType > >::type
Definition: Track.h:1564
Track::InsertSilence
virtual void InsertSilence(double WXUNUSED(t), double WXUNUSED(len))=0
TrackId::mValue
long mValue
Definition: Track.h:182
TrackList::TrackList
TrackList(TrackList &&that)=delete
ClientData::Site::size
size_t size() const
How many attachment pointers are in the Site.
Definition: ClientData.h:251
Track::GetOwner
std::shared_ptr< TrackList > GetOwner() const
Definition: Track.h:368
ClientData::Base
A convenient default parameter for class template Site.
Definition: ClientData.h:28
TrackTyper::Lookup< TrackType, std::tuple< NotHere, Rest... > >::value
static constexpr TrackKind value()
Definition: Track.h:130
TrackList::Add
TrackKind * Add(const std::shared_ptr< TrackKind > &t)
Definition: Track.h:1487
TrackList::Find
auto Find(Track *pTrack) -> TrackIter< TrackType >
Turn a pointer into a TrackIter (constant time); get end iterator if this does not own the track.
Definition: Track.h:1317
Track::SetPanFromChannelType
virtual void SetPanFromChannelType()
Definition: Track.h:432
LabelTrack
A LabelTrack is a Track that holds labels (LabelStruct).
Definition: LabelTrack.h:88
TrackIterRange::VisitWhile
void VisitWhile(Flag &flag, const Functions &...functions)
See Track::TypeSwitch.
Definition: Track.h:1193
Track::Paste
virtual void Paste(double WXUNUSED(t), const Track *WXUNUSED(src))=0
AudioTrack::HandleXMLAttribute
bool HandleXMLAttribute(const wxChar *, const wxChar *)
Definition: Track.h:832
Track::Any
bool Any() const
Definition: Track.cpp:361
Track::SharedPointer
static std::shared_ptr< Subclass > SharedPointer(Track *pTrack)
Definition: Track.h:300
AudioTrack::AudioTrack
AudioTrack(const Track &orig)
Definition: Track.h:826
Track::SetOffset
virtual void SetOffset(double o)
Definition: Track.h:429
TrackInterval
A start and an end time, and mutative access to optional extra information.
Definition: Track.h:219
TrackIterRange::TrackIterRange
TrackIterRange(const TrackIter< TrackType > &begin, const TrackIter< TrackType > &end)
Definition: Track.h:1087
ClientData.h
Utility ClientData::Site to register hooks into a host class that attach client data.
TrackInterval::Extra
TrackIntervalData * Extra() const
Definition: Track.h:226
TrackList::SelectedLeaders
auto SelectedLeaders() -> TrackIterRange< TrackType >
Definition: Track.h:1406
Track::Dispatcher::inapplicable
First, recursive case of metafunction, defers generation of operator ()
Definition: Track.h:502
Track::Dispatcher::Switch< R, ConcreteType, BaseClass, BaseClasses... >::test
static auto test() -> decltype(test< Function, Functions... >((std::integral_constant< bool, Compatible > *) nullptr))
undefined function used in decltype only to compute a type, using other overloads
Track::mDefaultName
wxString mDefaultName
Definition: Track.h:252
RefreshCode::EnsureVisible
@ EnsureVisible
Definition: RefreshCode.h:31
Track::mpControls
std::shared_ptr< CommonTrackCell > mpControls
Definition: Track.h:817
TrackList::MakeTrackIterator
TrackIter< TrackType > MakeTrackIterator(TrackNodePointer iter) const
Definition: Track.h:1581
ClientData::SkipCopying
@ SkipCopying
ignore the source and leave empty
Definition: ClientDataHelpers.h:34
TrackIterRange::Filter
TrackIterRange< TrackType2 > Filter() const
Definition: Track.h:1139
TrackListEvent::TrackListEvent
TrackListEvent(const TrackListEvent &)=default
TrackList::Track
friend class Track
Definition: Track.h:1474
TrackIter::TrackIter
TrackIter(TrackNodePointer begin, TrackNodePointer iter, TrackNodePointer end, FunctionType pred={})
Constructor, usually not called directly except by methods of TrackList.
Definition: Track.h:932
Track::mLinked
bool mLinked
Definition: Track.h:258
TrackList::end
iterator end()
Definition: Track.h:1309
TrackKind::All
@ All
the root class
TrackIterRange::Excluding
TrackIterRange Excluding(const TrackType *pExcluded) const
Definition: Track.h:1176
TrackIter::mPred
FunctionType mPred
Optional filter
Definition: Track.h:1077
PlayableTrack::GetNotMute
bool GetNotMute() const
Definition: Track.h:846
TrackList::Move
bool Move(Track *t, bool up)
Definition: Track.h:1516
Track::mName
wxString mName
Definition: Track.h:251
TrackList::end
const_iterator end() const
Definition: Track.h:1311
anonymous_namespace{ProjectSettings.cpp}::Notify
void Notify(AudacityProject &project, ProjectSettings::EventCode code)
Definition: ProjectSettings.cpp:24
Track::GetStartTime
virtual double GetStartTime() const =0
Track::Dispatcher::Switch< R, ConcreteType, BaseClass, BaseClasses... >::test
static auto test(std::true_type *) -> decltype((void) std::declval< Function >()((BaseClass *) nullptr, std::declval< Continuation< R > >()), applicable2< R, BaseClass, ConcreteType, Function, Functions... >
overload when upcast of ConcreteType* works, with sfinae'd return type
Definition: Track.h:601
TrackList::cend
const_iterator cend() const
Definition: Track.h:1313
TrackList::mUpdaters
std::vector< Updater > mUpdaters
This is in correspondence with mPendingUpdates.
Definition: Track.h:1699
Track::GetErrorOpening
virtual bool GetErrorOpening()
Definition: Track.h:783
Track::Track
Track()
Definition: Track.cpp:49
XMLValueChecker::LeftChannel
@ LeftChannel
Definition: XMLTagHandler.h:68
TrackId::operator<
bool operator<(const TrackId &other) const
Definition: Track.h:178
TrackList::mPendingUpdates
ListOfTracks mPendingUpdates
Shadow tracks holding append-recording in progress; need to put them into a list so that GetLink() wo...
Definition: Track.h:1697
Track::~ Track
virtual ~ Track()
Track::mList
std::weak_ptr< TrackList > mList
Definition: Track.h:246
TrackList::Updater
std::function< void(Track &dest, const Track &src) > Updater
Definition: Track.h:1648
AudioTrack::WriteXMLAttributes
void WriteXMLAttributes(XMLWriter &WXUNUSED(xmlFile)) const
Definition: Track.h:829
XMLTagHandler.h
Track::mId
TrackId mId
Identifies the track only in-session, not persistently.
Definition: Track.h:243
TrackIter::operator++
TrackIter & operator++()
Safe to call even when at the end.
Definition: Track.h:975
Track::GetId
TrackId GetId() const
Definition: Track.h:270
TrackKind::Time
@ Time
TrackListEvent
Notification of changes in individual tracks of TrackList, or of TrackList's composition.
Definition: Track.h:1206
TrackIter::valid
bool valid() const
Test satisfaction of the invariant, while initializing, incrementing, or decrementing.
Definition: Track.h:1061
Track::Offset
void Offset(double t)
Definition: Track.h:428
TrackKind::Audio
@ Audio
nonleaf
TrackIter::operator!=
friend bool operator!=(TrackIter a, TrackIter b)
Compares only current positions, assuming same beginnings and ends.
Definition: Track.h:1050
Track::Holder
std::shared_ptr< Track > Holder
Definition: Track.h:325
BasicUI::Get
Services * Get()
Fetch the global instance, or nullptr if none is yet installed.
Definition: BasicUI.cpp:26
Track::SetDefaultName
void SetDefaultName(const wxString &n)
Definition: Track.h:413
TrackList::mOwner
AudacityProject * mOwner
Definition: Track.h:1693
TrackIter::advance
TrackIter advance(long amount) const
This might be called operator + , but it's not constant-time as with a random access iterator.
Definition: Track.h:1029
operator!=
bool operator!=(const TrackNodePointer &a, const TrackNodePointer &b)
Definition: Track.h:64
TrackList::begin
iterator begin()
Definition: Track.h:1308
TrackIter::operator==
friend bool operator==(TrackIter a, TrackIter b)
Compares only current positions, assuming same beginnings and ends.
Definition: Track.h:1039
TrackIter::FunctionType
std::function< bool(typename std::add_pointer< typename std::add_const< typename std::remove_pointer< TrackType >::type >::type >::type) > FunctionType
Type of predicate taking pointer to const TrackType.
Definition: Track.h:929
ListOfTracks
std::list< std::shared_ptr< Track > > ListOfTracks
Definition: Track.h:53
Track::WaveTrack
friend WaveTrack
Definition: Track.h:374
XMLValueChecker::MonoChannel
@ MonoChannel
Definition: XMLTagHandler.h:70
TrackList::FindLeader
TrackIter< const Track > FindLeader(const Track *pTrack) const
Definition: Track.h:1347
Track::SameKindAs
bool SameKindAs(const Track &track) const
Definition: Track.h:481
TrackIter::Filter
auto Filter() const -> typename std::enable_if< std::is_base_of< TrackType, TrackType2 >::value &&(!std::is_const< TrackType >::value||std::is_const< TrackType2 >::value), TrackIter< TrackType2 > >::type
Return an iterator for a subclass of TrackType (and not removing const) with same predicate.
Definition: Track.h:959
Track::Silence
virtual void Silence(double WXUNUSED(t0), double WXUNUSED(t1))=0
Track::GetOffset
virtual double GetOffset() const =0
TrackTyper::Lookup
Variadic template implements metafunction with specializations, to associate enum values with types.
Definition: Track.h:119
Track::mpView
std::shared_ptr< CommonTrackCell > mpView
Definition: Track.h:816
TrackNodePointer
std::pair< ListOfTracks::iterator, ListOfTracks * > TrackNodePointer
Pairs a std::list iterator and a pointer to a list, for comparison purposes.
Definition: Track.h:59
TrackList::AddToHead
TrackKind * AddToHead(const std::shared_ptr< TrackKind > &t)
Add a Track, giving it a fresh id.
Definition: Track.h:1483
Track::GetKind
virtual TrackKind GetKind() const
Definition: Track.h:467
AudioTrack
Track subclass holding data representing sound (as notes, or samples, or ...)
Definition: Track.h:822
ConstTrackInterval
A start and an end time, and non-mutative access to optional extra information.
Definition: Track.h:192
NoteTrackConstArray
std::vector< std::shared_ptr< const NoteTrack > > NoteTrackConstArray
Definition: Track.h:49
Track::Clone
virtual Holder Clone() const =0
TrackIterRange::operator-
TrackIterRange operator-(const Predicate2 &pred2) const
Definition: Track.h:1122
ClientData::Site
Utility to register hooks into a host class that attach client data.
Definition: ClientData.h:220
CompatibleTrackKinds
constexpr bool CompatibleTrackKinds(TrackKind desired, TrackKind actual)
Compile-time function on enum values.
Definition: Track.h:83
wxDECLARE_EXPORTED_EVENT
wxDECLARE_EXPORTED_EVENT(AUDACITY_DLL_API, EVT_TRACKLIST_SELECTION_CHANGE, TrackListEvent)
Posted when the set of selected tracks changes.
Track::Fallthrough
Continuation<> Fallthrough
Type of arguments passed as optional second parameter to TypeSwitch<void>() cases.
Definition: Track.h:488
Track::IsSelected
bool IsSelected() const
Definition: Track.cpp:364
TrackTyper::Lookup< TrackType, std::tuple< Pair< TrackType, Here >, Rest... > >::value
static constexpr TrackKind value()
Definition: Track.h:123
TrackIter::Filter
TrackIter Filter(const Predicate2 &pred2) const
Return an iterator that replaces the predicate.
Definition: Track.h:950
TrackList::GetOwner
const AudacityProject * GetOwner() const
Definition: Track.h:1300
anonymous_namespace{NoteTrack.cpp}::swap
void swap(std::unique_ptr< Alg_seq > &a, std::unique_ptr< Alg_seq > &b)
Definition: NoteTrack.cpp:735
TrackList::Any
auto Any() const -> typename std::enable_if< std::is_const< TrackType >::value, TrackIterRange< TrackType > >::type
Definition: Track.h:1362
TrackId::TrackId
TrackId()
Definition: Track.h:167
ConstTrackInterval::Extra
const TrackIntervalData * Extra() const
Definition: Track.h:208
Track::IsSelectedLeader
bool IsSelectedLeader() const
Definition: Track.cpp:373
TrackIter::operator--
TrackIter & operator--()
Safe to call even when at the beginning.
Definition: Track.h:994
Track::Dispatcher::Switch< R, ConcreteType, BaseClass, BaseClasses... >::test
static auto test(const void *) -> decltype(Retry::template test< Function, Functions... >())
Catch-all overload of undefined function used in decltype only.
Track::SetChannel
void SetChannel(ChannelType c)
Definition: Track.h:377
PlayableTrack::GetNotSolo
bool GetNotSolo() const
Definition: Track.h:847
Track::SetPan
virtual void SetPan(float)
Definition: Track.h:431
TrackIterRange
Range between two TrackIters, usable in range-for statements, and with Visit member functions.
Definition: Track.h:1085
PlayableTrack
AudioTrack subclass that can also be audibly replayed by the program.
Definition: Track.h:838
TrackListEvent::Clone
wxEvent * Clone() const override
Definition: Track.h:1218
TrackList::getBegin
TrackNodePointer getBegin() const
Definition: Track.h:1604
TrackList::TrackList
TrackList(const TrackList &that)=delete
TrackTyper::List
std::tuple< Pair< Track, TrackKind::All >, Pair< AudioTrack, TrackKind::Audio >, Pair< PlayableTrack, TrackKind::Playable >, Pair< LabelTrack, TrackKind::Label >, Pair< NoteTrack, TrackKind::Note >, Pair< TimeTrack, TrackKind::Time >, Pair< WaveTrack, TrackKind::Wave > > List
Compile-time map from types to enum values.
Definition: Track.h:117
XMLTagHandler
This class is an interface which should be implemented by classes which wish to be able to load and s...
Definition: XMLTagHandler.h:80
Track::GetSelected
bool GetSelected() const
Definition: Track.h:415
Track::Intervals
std::vector< Interval > Intervals
Definition: Track.h:318
AudioTrack::AudioTrack
AudioTrack()
Definition: Track.h:824
Track::mIndex
int mIndex
0-based position of this track in its TrackList
Definition: Track.h:250
TrackIterRange::StartingWith
TrackIterRange StartingWith(const Track *pTrack) const
Definition: Track.h:1147
ConstTrackInterval::end
double end
Definition: Track.h:211
TrackKind
TrackKind
Enumerates all subclasses of Track (not just the leaf classes) and the None value.
Definition: Track.h:69
TrackList::GetOwner
AudacityProject * GetOwner()
Definition: Track.h:1299
id
int id
Definition: WaveTrackControls.cpp:590
TrackList::clear
void clear()=delete
ConstTrackInterval::pExtra
std::unique_ptr< TrackIntervalData > pExtra
Definition: Track.h:214
Track::WriteXML
virtual void WriteXML(XMLWriter &xmlFile) const =0
Track::TypeSwitch
R TypeSwitch(const Functions &...functions)
Use this function rather than testing track type explicitly and making down-casts.
Definition: Track.h:693
TrackId
An in-session identifier of track objects across undo states. It does not persist between sessions.
Definition: Track.h:165
TrackList::begin
const_iterator begin() const
Definition: Track.h:1310
TrackArray
std::vector< Track * > TrackArray
Definition: Track.h:45
AttachedTrackObjects
ClientData::Site< Track, ClientData::Base, ClientData::SkipCopying, std::shared_ptr > AttachedTrackObjects
Template generated base class for Track lets it host opaque UI related objects.
Definition: Track.h:232
TrackList::Leaders
auto Leaders() -> TrackIterRange< TrackType >
Definition: Track.h:1389
TrackList::sCounter
static long sCounter
Definition: Track.h:1645
Track
Abstract base class for an object holding data associated with points on a time axis.
Definition: Track.h:239
Track::IsLeader
bool IsLeader() const
Definition: Track.cpp:370
Track::SharedPointer
static std::shared_ptr< Subclass > SharedPointer(const Track *pTrack)
Definition: Track.h:304
Track::Init
void Init(const Track &orig)
Definition: Track.cpp:71
XMLValueChecker::ChannelType
ChannelType
Definition: XMLTagHandler.h:67
TrackInterval::operator=
TrackInterval & operator=(TrackInterval &&)=default
AudacityProject
The top-level handle to an Audacity project. It serves as a source of events that other objects can b...
Definition: Project.h:113
TrackKind::Wave
@ Wave
TrackList::Find
auto Find(const Track *pTrack) const -> typename std::enable_if< std::is_const< TrackType >::value, TrackIter< TrackType > >::type
Turn a pointer into a TrackIter (constant time); get end iterator if this does not own the track.
Definition: Track.h:1329
TrackList::getNext
TrackNodePointer getNext(TrackNodePointer p) const
Move an iterator to the next node, if any; else stay at end.
Definition: Track.h:1609
anonymous_namespace{EditMenus.cpp}::FinishCopy
void FinishCopy(const Track *n, const Track::Holder &dest, TrackList &list)
Definition: EditMenus.cpp:31
Track::GetChannel
virtual ChannelType GetChannel() const
Definition: Track.h:425
TrackList::getPrev
TrackNodePointer getPrev(TrackNodePointer p) const
Move an iterator to the previous node, if any; else wrap to end.
Definition: Track.h:1619
TrackInterval::TrackInterval
TrackInterval(TrackInterval &&)=default
TrackIterRange::Visit
void Visit(const Functions &...functions)
See Track::TypeSwitch.
Definition: Track.h:1184
Track::HasOwner
bool HasOwner() const
Definition: Track.h:366
Track::Clear
virtual void Clear(double WXUNUSED(t0), double WXUNUSED(t1))=0
TrackIterRange::operator+
TrackIterRange operator+(const Predicate2 &pred2) const
Definition: Track.h:1096
TrackList::Tracks
auto Tracks(const Pred &pred={}) -> TrackIterRange< TrackType >
Definition: Track.h:1551
TrackList::Channels_
static TrackIterRange< TrackType > Channels_(TrackIter< InTrackType > iter1)
Definition: Track.h:1446
TrackList::SyncLockGroup
static TrackIterRange< const Track > SyncLockGroup(const Track *pTrack)
Definition: Track.h:1435
ConstTrackInterval::start
double start
Definition: Track.h:211
TrackKind::Label
@ Label
TrackListEvent::mCode
int mCode
Definition: Track.h:1223
TrackIter::operator*
TrackType * operator*() const
Safe to call even when at the end.
Definition: Track.h:1017
TrackId::TrackId
TrackId(long value)
Definition: Track.h:168
XMLValueChecker::RightChannel
@ RightChannel
Definition: XMLTagHandler.h:69
TrackListEvent::mpTrack
std::weak_ptr< Track > mpTrack
Definition: Track.h:1222
PlayableTrack::PlayableTrack
PlayableTrack()
Definition: Track.h:840
ConstTrackInterval::Start
double Start() const
Definition: Track.h:206
TrackList::Any
auto Any() -> TrackIterRange< TrackType >
Definition: Track.h:1355
TrackList::SingletonRange
static auto SingletonRange(TrackType *pTrack) -> TrackIterRange< TrackType >
Definition: Track.h:1423
ActiveProjects::Remove
void Remove(const FilePath &path)
TrackIter::mEnd
TrackNodePointer mEnd
Allows end of iteration to be detected without comparison to other TrackIter.
Definition: Track.h:1076
Track::TypeSwitch
R TypeSwitch(const Functions &...functions) const
Use this function rather than testing track type explicitly and making down-casts.
Definition: Track.h:739
safenew
#define safenew
Definition: MemoryX.h:10
Track::Copy
virtual Holder Copy(double WXUNUSED(t0), double WXUNUSED(t1), bool forClipboard=true) const =0
TrackList::cbegin
const_iterator cbegin() const
Definition: Track.h:1312
TrackIterRange::EndingAfter
TrackIterRange EndingAfter(const Track *pTrack) const
Definition: Track.h:1161
Track::Dispatcher::Switch< R, ConcreteType, BaseClass, BaseClasses... >::test
static auto test(std::true_type *) -> decltype((void) std::declval< Function >()((BaseClass *) nullptr), applicable1< R, BaseClass, ConcreteType, Function, Functions... >
overload when upcast of ConcreteType* works, with sfinae'd return type
Definition: Track.h:587
Track::Dispatcher
Helper for recursive case of metafunction implementing Track::TypeSwitch.
Definition: Track.h:497
Track::PasteInto
virtual Holder PasteInto(AudacityProject &) const =0
Find or create the destination track for a paste, maybe in a different project.
track_cast
std::enable_if< std::is_pointer< T >::value, T >::type track_cast(Track *track)
Encapsulate the checked down-casting of track pointers.
Definition: Track.h:875
TrackIter::mBegin
TrackNodePointer mBegin
Allows end of reverse iteration to be detected without comparison to other TrackIter.
Definition: Track.h:1074
TrackList::Selected
auto Selected() -> TrackIterRange< TrackType >
Definition: Track.h:1372
TrackIter::mIter
TrackNodePointer mIter
Current position.
Definition: Track.h:1075
SampleFormat.h
TimeTrack
A kind of Track used to 'warp time'.
Definition: TimeTrack.h:24
NoteTrack
A Track that is used for Midi notes. (Somewhat old code).
Definition: NoteTrack.h:66
TrackTyper::Pair
Definition: Track.h:106
TrackKind::Note
@ Note
Track::Dispatcher::Switch
Variadic template implements metafunction with specializations, to choose among implementations of op...
Definition: Track.h:553
Track::Executor
Variadic template implements metafunction with specializations, to dispatch Track::TypeSwitch.
Definition: Track.h:493
CommonTrackCell
Definition: CommonTrackPanelCell.h:59
Track::Dispatcher::applicable2
Third, recursive case of metafunction, generates operator () that calls function with fallthrough.
Definition: Track.h:534
ProjectSettings
Holds various per-project settings values, including the sample rate, and sends events to the project...
Definition: ProjectSettings.h:54
Track::vrulerSize
wxSize vrulerSize
Definition: Track.h:343