Audacity 3.2.0
PlayableTrackControls.cpp
Go to the documentation of this file.
1/**********************************************************************
2
3Audacity: A Digital Audio Editor
4
5PlayableTrackControls.cpp
6
7Paul Licameli split from TrackInfo.cpp
8
9**********************************************************************/
11#include "PlayableTrack.h"
13#include "AColor.h"
14#include "../../ui/CommonTrackInfo.h"
15#include "../../../TrackPanelDrawingContext.h"
16#include "ViewInfo.h"
19
20#include <wx/dc.h>
21
22#include "RealtimeEffectList.h"
23
25
26namespace {
27
28void GetNarrowMuteHorizontalBounds( const wxRect & rect, wxRect &dest )
29{
30 dest.x = rect.x;
31 dest.width = rect.width / 2 + 1;
32}
33
34void GetNarrowSoloHorizontalBounds( const wxRect & rect, wxRect &dest )
35{
36 wxRect muteRect;
37 GetNarrowMuteHorizontalBounds( rect, muteRect );
38 dest.x = rect.x + muteRect.width;
39 dest.width = rect.width - muteRect.width + TitleSoloBorderOverlap;
40}
41
42void GetEffectsBounds( const wxRect & rect, wxRect &dest )
43{
44 constexpr int padding = 2;
45 dest.x = rect.x + padding;
46 dest.y = rect.y + padding;
47 dest.width = rect.width - padding * 2;
48 dest.height = rect.height - padding * 2;
49}
50
51void GetWideMuteSoloHorizontalBounds( const wxRect & rect, wxRect &dest )
52{
53 // Larger button, symmetrically placed intended.
54 // On windows this gives 15 pixels each side.
55 dest.width = rect.width - 2 * kTrackInfoBtnSize + 6;
56 dest.x = rect.x + kTrackInfoBtnSize -3;
57}
58
60( wxDC *dc, const wxRect &bev, const Track *pTrack, bool down,
61 bool WXUNUSED(captured),
62 bool solo, bool hit )
63{
64 //bev.Inflate(-1, -1);
65 bool selected = pTrack ? pTrack->GetSelected() : true;
66 auto pt = dynamic_cast<const PlayableTrack *>(pTrack);
67 bool value = pt ? (solo ? pt->GetSolo() : pt->GetMute()) : false;
68
69#if 0
70 AColor::MediumTrackInfo( dc, t->GetSelected());
71 if( solo )
72 {
73 if( pt && pt->GetSolo() )
74 {
75 AColor::Solo(dc, pt->GetSolo(), t->GetSelected());
76 }
77 }
78 else
79 {
80 if( pt && pt->GetMute() )
81 {
82 AColor::Mute(dc, pt->GetMute(), t->GetSelected(), pt->GetSolo());
83 }
84 }
85 //(solo) ? AColor::Solo(dc, t->GetSolo(), t->GetSelected()) :
86 // AColor::Mute(dc, t->GetMute(), t->GetSelected(), t->GetSolo());
87 dc->SetPen( *wxTRANSPARENT_PEN );//No border!
88 dc->DrawRectangle(bev);
89#endif
90
91 wxCoord textWidth, textHeight;
92 wxString str = (solo) ?
93 /* i18n-hint: This is on a button that will silence all the other tracks.*/
94 _("Solo") :
95 /* i18n-hint: This is on a button that will silence this track.*/
96 _("Mute");
97
99 *dc,
100 value == down,
101 bev,
102 selected, hit
103 );
104
106 dc->GetTextExtent(str, &textWidth, &textHeight);
107 dc->DrawText(str, bev.x + (bev.width - textWidth) / 2, bev.y + (bev.height - textHeight) / 2);
108}
109
111( wxDC *dc, const wxRect &bev, const Track *pTrack, bool down,
112 bool sel, bool hit )
113{
114 wxCoord textWidth, textHeight;
115
116 const auto str = _("Effects");
117
118 const auto selected = pTrack ? pTrack->GetSelected() : true;
119
120 AColor::ButtonStretch(*dc, !down, bev, selected, hit);
121
123 dc->GetTextExtent(str, &textWidth, &textHeight);
124 dc->DrawText(str, bev.x + (bev.width - textWidth) / 2, bev.y + (bev.height - textHeight) / 2);
125}
126
128( TrackPanelDrawingContext &context,
129 const wxRect &rect, const Track *pTrack )
130{
131 auto dc = &context.dc;
132 wxRect bev = rect;
134 auto target = dynamic_cast<MuteButtonHandle*>( context.target.get() );
135 bool hit = target && target->GetTrack().get() == pTrack;
136 bool captured = hit && target->IsDragging();
137 bool down = captured && bev.Contains( context.lastState.GetPosition());
138 MuteOrSoloDrawFunction( dc, bev, pTrack, down, captured, false, hit );
139}
140
142( TrackPanelDrawingContext &context,
143 const wxRect &rect, const Track *pTrack )
144{
145 auto dc = &context.dc;
146 wxRect bev = rect;
148 auto target = dynamic_cast<SoloButtonHandle*>( context.target.get() );
149 bool hit = target && target->GetTrack().get() == pTrack;
150 bool captured = hit && target->IsDragging();
151 bool down = captured && bev.Contains( context.lastState.GetPosition());
152 MuteOrSoloDrawFunction( dc, bev, pTrack, down, captured, true, hit );
153}
154
156( TrackPanelDrawingContext &context,
157 const wxRect &rect, const Track *pTrack )
158{
159 auto dc = &context.dc;
160
161 wxRect bev = rect;
162
164 {
165 auto target = dynamic_cast<MuteButtonHandle*>( context.target.get() );
166 bool hit = target && target->GetTrack().get() == pTrack;
167 bool captured = hit && target->IsDragging();
168 bool down = captured && bev.Contains( context.lastState.GetPosition());
169 MuteOrSoloDrawFunction( dc, bev, pTrack, down, captured, false, hit );
170 }
171
173 {
174 auto target = dynamic_cast<SoloButtonHandle*>( context.target.get() );
175 bool hit = target && target->GetTrack().get() == pTrack;
176 bool captured = hit && target->IsDragging();
177 bool down = captured && bev.Contains( context.lastState.GetPosition());
178 MuteOrSoloDrawFunction( dc, bev, pTrack, down, captured, true, hit );
179 }
180}
181
183( TrackPanelDrawingContext &context,
184 const wxRect &rect, const Track *pTrack )
185{
186 auto dc = &context.dc;
187
188 wxRect bev = rect;
189
190 GetEffectsBounds( rect, bev );
191 {
192 auto target = dynamic_cast<EffectsButtonHandle*>( context.target.get() );
193 bool hit = target && target->GetTrack().get() == pTrack;
194 bool captured = hit && target->IsDragging();
195 bool down = captured && bev.Contains( context.lastState.GetPosition());
196 EffectsDrawFunction( dc, bev, pTrack, down, captured, hit );
197 }
198}
199}
200
202(const wxRect & rect, wxRect & dest, bool solo,
203 const Track *pTrack)
204{
205 auto &trackControl = static_cast<const CommonTrackControls&>(
206 TrackControls::Get( *pTrack ) );
207 auto resultsM = TrackInfo::CalcItemY( trackControl.GetTCPLines(), TCPLine::kItemMute );
208 auto resultsS = TrackInfo::CalcItemY( trackControl.GetTCPLines(), TCPLine::kItemSolo );
209 dest.height = resultsS.second;
210
211 int yMute = resultsM.first;
212 int ySolo = resultsS.first;
213
214 bool bSameRow = ( yMute == ySolo );
215 bool bNarrow = bSameRow;
216
217 if( bNarrow )
218 {
219 if( solo )
220 GetNarrowSoloHorizontalBounds( rect, dest );
221 else
222 GetNarrowMuteHorizontalBounds( rect, dest );
223 }
224 else
226
227 if( bSameRow || !solo )
228 dest.y = rect.y + yMute;
229 else
230 dest.y = rect.y + ySolo;
231
232}
233
235(const wxRect & rect, wxRect & dest, const Track *pTrack)
236{
237 auto &trackControl = static_cast<const CommonTrackControls&>(
238 TrackControls::Get( *pTrack ) );
239 const auto resultsE = TrackInfo::CalcItemY( trackControl.GetTCPLines(), TCPLine::kItemEffects );
240 dest.x = rect.x;
241 dest.y = rect.y + resultsE.first;
242 dest.width = rect.width;
243 dest.height = resultsE.second;
244
245}
246
248{
249 static TCPLines playableTrackTCPLines;
250 static std::once_flag flag;
251 std::call_once( flag, []{
252 playableTrackTCPLines = CommonTrackInfo::StaticTCPLines();
253 playableTrackTCPLines.insert( playableTrackTCPLines.end(), {
254 { TCPLine::kItemMute | TCPLine::kItemSolo, kTrackInfoBtnSize + 1, 0,
255 MuteAndSoloDrawFunction },
256 } );
257 } );
258 return playableTrackTCPLines;
259}
260
262{
263 static TCPLines playableTrackTCPLines;
264 static std::once_flag flag;
265 std::call_once( flag, []{
266 playableTrackTCPLines = CommonTrackInfo::StaticTCPLines();
267 playableTrackTCPLines.insert( playableTrackTCPLines.end(), {
268 { TCPLine::kItemMute | TCPLine::kItemSolo, kTrackInfoBtnSize + 1, 0,
269 MuteAndSoloDrawFunction },
270 } );
271 playableTrackTCPLines.insert( playableTrackTCPLines.end(), {
272 { TCPLine::kItemEffects, kTrackEffectsBtnHeight + 1, 0,
273 EffectsDrawFunction },
274 } );
275 } );
276 return playableTrackTCPLines;
277}
std::vector< TrackInfo::TCPLine > TCPLines
static const int TitleSoloBorderOverlap
#define str(a)
#define _(s)
Definition: Internat.h:73
Extends Track with notions of mute and solo setting.
TrackInfo::TCPLine TCPLine
@ kTrackInfoBtnSize
Definition: ViewInfo.h:96
static std::once_flag flag
static void Solo(wxDC *dc, bool on, bool selected)
Definition: AColor.cpp:496
static void Bevel2(wxDC &dc, bool up, const wxRect &r, bool bSel=false, bool bHighlight=false)
Definition: AColor.cpp:292
static void Mute(wxDC *dc, bool on, bool selected, bool soloing)
Definition: AColor.cpp:481
static void MediumTrackInfo(wxDC *dc, bool selected)
Definition: AColor.cpp:427
static void ButtonStretch(wxDC &dc, bool up, const wxRect &r, bool selected=false, bool highlight=false)
Draw a button that fills a given rect.
Definition: AColor.cpp:283
std::shared_ptr< Track > GetTrack() const
Definition: ButtonHandle.h:30
static void GetEffectsRect(const wxRect &rect, wxRect &dest, const Track *pTrack)
static void GetMuteSoloRect(const wxRect &rect, wxRect &dest, bool solo, const Track *pTrack)
static const TCPLines & StaticWaveTCPLines()
static const TCPLines & StaticNoteTCPLines()
AudioTrack subclass that can also be audibly replayed by the program.
Definition: PlayableTrack.h:40
static TrackControls & Get(Track &track)
Abstract base class for an object holding data associated with points on a time axis.
Definition: Track.h:110
bool GetSelected() const
Selectedness is always the same for all channels of a group.
Definition: Track.cpp:78
AUDACITY_DLL_API const TCPLines & StaticTCPLines()
AUDACITY_DLL_API void SetTrackInfoFont(wxDC *dc)
Definition: TrackInfo.cpp:73
AUDACITY_DLL_API std::pair< int, int > CalcItemY(const TCPLines &lines, unsigned iItem)
Definition: TrackInfo.cpp:57
void GetEffectsBounds(const wxRect &rect, wxRect &dest)
void GetNarrowSoloHorizontalBounds(const wxRect &rect, wxRect &dest)
void WideMuteDrawFunction(TrackPanelDrawingContext &context, const wxRect &rect, const Track *pTrack)
void EffectsDrawFunction(TrackPanelDrawingContext &context, const wxRect &rect, const Track *pTrack)
void MuteAndSoloDrawFunction(TrackPanelDrawingContext &context, const wxRect &rect, const Track *pTrack)
void WideSoloDrawFunction(TrackPanelDrawingContext &context, const wxRect &rect, const Track *pTrack)
void MuteOrSoloDrawFunction(wxDC *dc, const wxRect &bev, const Track *pTrack, bool down, bool WXUNUSED(captured), bool solo, bool hit)
void GetNarrowMuteHorizontalBounds(const wxRect &rect, wxRect &dest)
void GetWideMuteSoloHorizontalBounds(const wxRect &rect, wxRect &dest)