1 /********************************************************************** 2 3 Audacity: A Digital Audio Editor 4 5 WaveTrackView.h 6 7 Paul Licameli split from class WaveTrack 8 9 **********************************************************************/ 10 11 #ifndef __AUDACITY_WAVE_TRACK_VIEW__ 12 #define __AUDACITY_WAVE_TRACK_VIEW__ 13 14 #include "../../../ui/CommonTrackView.h" 15 #include "ClientData.h" 16 #include "SampleCount.h" 17 namespace WaveTrackViewConstants{ enum Display : int; } 18 struct WaveTrackSubViewType; 19 20 class CutlineHandle; 21 class TranslatableString; 22 class WaveTrack; 23 class WaveTrackView; 24 class WaveClip; 25 class WaveClipTrimHandle; 26 class ZoomInfo; 27 28 29 class TrackPanelResizeHandle; 30 class WaveTrackAffordanceHandle; 31 32 namespace { 33 class SubViewCloseHandle; 34 class SubViewAdjustHandle; 35 class SubViewRearrangeHandle; 36 } 37 38 class wxDC; 39 40 class AUDACITY_DLL_API WaveTrackSubView : public CommonTrackView 41 { 42 public: 43 44 using Display = WaveTrackViewConstants::Display; 45 using Type = WaveTrackSubViewType; 46 47 explicit 48 WaveTrackSubView( WaveTrackView &waveTrackView ); 49 50 virtual const Type &SubViewType() const = 0; 51 52 // For undo and redo purpose 53 // Empty abstract method to be inherited, for copying the spectral data in SpectrumSubView 54 virtual void CopyToSubView(WaveTrackSubView *destSubView) const; 55 56 std::pair< 57 bool, // if true, hit-testing is finished 58 std::vector<UIHandlePtr> 59 > DoDetailedHitTest( 60 const TrackPanelMouseState &state, 61 const AudacityProject *pProject, int currentTool, bool bMultiTool, 62 const std::shared_ptr<WaveTrack> &wt ); 63 64 protected: 65 static void DrawBoldBoundaries( 66 TrackPanelDrawingContext &context, const WaveTrack *track, 67 const wxRect &rect ); 68 69 std::weak_ptr<WaveTrackView> GetWaveTrackView() const; 70 71 std::vector<MenuItem> GetMenuItems( 72 const wxRect &rect, const wxPoint *pPosition, AudacityProject *pProject ) 73 override; 74 75 private: 76 std::weak_ptr<SubViewCloseHandle> mCloseHandle; 77 std::weak_ptr<TrackPanelResizeHandle> mResizeHandle; 78 std::weak_ptr<SubViewAdjustHandle> mAdjustHandle; 79 std::weak_ptr<SubViewRearrangeHandle> mRearrangeHandle; 80 std::weak_ptr<WaveClipTrimHandle> mClipTrimHandle; 81 std::weak_ptr<CutlineHandle> mCutlineHandle; 82 std::weak_ptr<WaveTrackView> mwWaveTrackView; 83 }; 84 85 struct WaveTrackSubViewPlacement { 86 int index; 87 float fraction; 88 }; 89 using WaveTrackSubViewPlacements = std::vector< WaveTrackSubViewPlacement >; 90 91 class WaveTrackView; 92 using WaveTrackSubViews = ClientData::Site< 93 WaveTrackView, WaveTrackSubView, ClientData::SkipCopying, std::shared_ptr 94 >; 95 96 class AUDACITY_DLL_API WaveTrackView final 97 : public CommonTrackView 98 , public WaveTrackSubViews 99 { 100 WaveTrackView( const WaveTrackView& ) = delete; 101 WaveTrackView &operator=( const WaveTrackView& ) = delete; 102 103 public: 104 static constexpr int kChannelSeparatorThickness{ 8 }; 105 106 using Display = WaveTrackViewConstants::Display; 107 108 static WaveTrackView &Get( WaveTrack &track ); 109 static const WaveTrackView &Get( const WaveTrack &track ); 110 111 explicit 112 WaveTrackView( const std::shared_ptr<Track> &pTrack ); 113 ~WaveTrackView() override; 114 115 // Preserve some view state too for undo/redo purposes 116 void CopyTo( Track &track ) const override; 117 118 std::shared_ptr<TrackVRulerControls> DoGetVRulerControls() override; 119 120 // CommonTrackView implementation 121 void Reparent( const std::shared_ptr<Track> &parent ) override; 122 123 static std::pair< 124 bool, // if true, hit-testing is finished 125 std::vector<UIHandlePtr> 126 > DoDetailedHitTest( 127 const TrackPanelMouseState &state, 128 const AudacityProject *pProject, int currentTool, bool bMultiTool, 129 const std::shared_ptr<WaveTrack> &wt, 130 CommonTrackView &view); 131 132 std::vector< WaveTrackSubView::Type > GetDisplays() const; 133 void SetDisplay(Display display, bool exclusive = true); 134 SavePlacements()135 const WaveTrackSubViewPlacements &SavePlacements() const 136 { return mPlacements; } RestorePlacements(const WaveTrackSubViewPlacements & placements)137 void RestorePlacements( const WaveTrackSubViewPlacements &placements ) 138 { mPlacements = placements; } 139 140 // Return true if successful. Fails if you try to toggle off the only 141 // sub-view. 142 bool ToggleSubView( Display id ); 143 144 // Get all the sub-views, in a sequence that is unspecified but in 145 // correspondence with the result of SavePlacements 146 std::vector< std::shared_ptr< WaveTrackSubView > > GetAllSubViews(); 147 148 // Return cached height of rect in last call of GetSubViews GetLastHeight()149 wxCoord GetLastHeight() const { return mLastHeight; } 150 GetMultiView()151 bool GetMultiView() const { return mMultiView; } SetMultiView(bool value)152 void SetMultiView( bool value ) { mMultiView = value; } 153 154 155 std::weak_ptr<WaveClip> GetSelectedClip(); 156 157 // Returns a visible subset of subviews, sorted in the same 158 // order as they are supposed to be displayed 159 160 161 // Get the visible sub-views, 162 // if rect is provided then result will contain 163 // y coordinate for each subview within this rect 164 Refinement GetSubViews(const wxRect* rect = nullptr); 165 166 unsigned CaptureKey 167 (wxKeyEvent& event, ViewInfo& viewInfo, wxWindow* pParent, 168 AudacityProject* project) override; 169 170 unsigned KeyDown(wxKeyEvent& event, ViewInfo& viewInfo, wxWindow* pParent, 171 AudacityProject* project) override; 172 173 unsigned Char 174 (wxKeyEvent& event, ViewInfo& viewInfo, wxWindow* pParent, 175 AudacityProject* project) override; 176 177 unsigned LoseFocus(AudacityProject *project) override; 178 179 static bool ClipDetailsVisible(const WaveClip& clip, const ZoomInfo& zoomInfo, const wxRect& viewRect); 180 static wxRect ClipHitTestArea(const WaveClip& clip, const ZoomInfo& zoomInfo, const wxRect& viewRect); 181 static bool HitTest(const WaveClip& clip, const ZoomInfo& zoomInfo, const wxRect& rect, const wxPoint& pos); 182 183 //FIXME: These functions do not push state to undo history 184 //because attempt to do so leads to a focus lose which, in 185 //turn finilizes text editing (state is saved after text 186 //editing was intentionally finished instead) 187 188 bool CutSelectedText(AudacityProject& project); 189 bool CopySelectedText(AudacityProject& project); 190 bool PasteText(AudacityProject& project); 191 bool SelectAllText(AudacityProject& project); 192 193 private: 194 void BuildSubViews() const; 195 void DoSetDisplay(Display display, bool exclusive = true); 196 bool SelectNextClip(ViewInfo& viewInfo, AudacityProject* project, bool forward); 197 198 // TrackPanelDrawable implementation 199 void Draw( 200 TrackPanelDrawingContext &context, 201 const wxRect &rect, unsigned iPass ) override; 202 203 std::vector<UIHandlePtr> DetailedHitTest 204 (const TrackPanelMouseState &state, 205 const AudacityProject *pProject, int currentTool, bool bMultiTool) 206 override; 207 208 // TrackView implementation 209 Refinement GetSubViews(const wxRect& rect) override; 210 211 protected: 212 std::shared_ptr<CommonTrackCell> GetAffordanceControls() override; 213 214 void DoSetMinimized( bool minimized ) override; 215 216 // Placements are in correspondence with the array of sub-views 217 // in the WaveTrackSubViews base class, though their sequence is 218 // unspecified and maybe different in different platforms. 219 WaveTrackSubViewPlacements mPlacements; 220 mutable wxCoord mLastHeight{}; 221 222 bool mMultiView{ false }; 223 224 private: 225 std::shared_ptr<CommonTrackCell> DoGetAffordance(const std::shared_ptr<Track>& track); 226 227 std::shared_ptr<CommonTrackCell> mpAffordanceCellControl; 228 229 std::weak_ptr<TrackPanelCell> mKeyEventDelegate; 230 231 std::weak_ptr<WaveTrackAffordanceHandle> mAffordanceHandle; 232 }; 233 234 // Helper for drawing routines 235 class SelectedRegion; 236 class WaveClip; 237 class ZoomInfo; 238 239 struct AUDACITY_DLL_API ClipParameters 240 { 241 // Do a bunch of calculations common to waveform and spectrum drawing. 242 ClipParameters 243 (bool spectrum, const WaveTrack *track, const WaveClip *clip, const wxRect &rect, 244 const SelectedRegion &selectedRegion, const ZoomInfo &zoomInfo); 245 246 double tOffset; 247 double rate; 248 double h; // absolute time of left edge of display 249 double tpre; // offset corrected time of left edge of display 250 double h1; 251 double tpost; // offset corrected time of right edge of display 252 253 // Calculate actual selection bounds so that t0 > 0 and t1 < the 254 // end of the track 255 double t0; 256 double t1; 257 258 double averagePixelsPerSample; 259 bool showIndividualSamples; 260 261 sampleCount ssel0; 262 sampleCount ssel1; 263 264 wxRect hiddenMid; 265 int hiddenLeftOffset; 266 267 wxRect mid; 268 int leftOffset; 269 270 // returns a clip rectangle restricted by viewRect, 271 // and with clipOffsetX - clip horizontal origin offset within view rect 272 static wxRect GetClipRect(const WaveClip& clip, const ZoomInfo& zoomInfo, const wxRect& viewRect, bool* outShowSamples = nullptr); 273 }; 274 275 #endif 276