Audacity  2.3.1
Meter.h
Go to the documentation of this file.
1 /**********************************************************************
2 
3  Audacity: A Digital Audio Editor
4 
5  Meter.h
6 
7  Dominic Mazzoni
8 
9  VU Meter, for displaying recording/playback level
10 
11  This is a bunch of common code that can display many different
12  forms of VU meters and other displays.
13 
14 **********************************************************************/
15 
16 #ifndef __AUDACITY_METER__
17 #define __AUDACITY_METER__
18 
19 #include <wx/brush.h>
20 #include <wx/defs.h>
21 #include <wx/gdicmn.h>
22 #include <wx/string.h>
23 #include <wx/timer.h>
24 
25 #include "../SampleFormat.h"
26 #include "Ruler.h"
27 
28 #if wxUSE_ACCESSIBILITY
29 #include "WindowAccessible.h"
30 #endif
31 
32 class AudacityProject;
33 
34 // Event used to notify all meters of preference changes
35 wxDECLARE_EXPORTED_EVENT(AUDACITY_DLL_API,
36  EVT_METER_PREFERENCES_CHANGED, wxCommandEvent);
37 
38 // Increase this when we add support for multichannel meters
39 // (most of the code is already there)
40 const int kMaxMeterBars = 2;
41 
42 struct MeterBar {
43  bool vert;
44  wxRect b; // Bevel around bar
45  wxRect r; // True bar drawing area
46  float peak;
47  float rms;
48  float peakHold;
49  double peakHoldTime;
50  wxRect rClip;
51  bool clipping;
52  bool isclipping; //ANSWER-ME: What's the diff between these bools?! "clipping" vs "isclipping" is not clear.
54  float peakPeakHold;
55 };
56 
58 {
59  public:
60  int numFrames;
66 
67  /* neither constructor nor destructor do anything */
70  /* for debugging purposes, printing the values out is really handy */
72  wxString toString();
74  wxString toStringIfClipped();
75 };
76 
77 // Thread-safe queue of update messages
79 {
80  public:
81  explicit MeterUpdateQueue(size_t maxLen);
83 
84  bool Put(MeterUpdateMsg &msg);
85  bool Get(MeterUpdateMsg &msg);
86 
87  void Clear();
88 
89  private:
90  int mStart;
91  int mEnd;
92  size_t mBufferSize;
94 };
95 
96 class MeterAx;
97 
98 /********************************************************************/
102 class MeterPanel final : public wxPanelWrapper
103 {
104  DECLARE_DYNAMIC_CLASS(MeterPanel)
105 
106  public:
107  // These should be kept in the same order as they appear
108  // in the menu
109  enum Style {
113  MixerTrackCluster, // Doesn't show menu, icon, or L/R labels, but otherwise like VerticalStereo.
115  VerticalStereoCompact, // Narrower.
116  };
117 
118 
120  wxWindow* parent, wxWindowID id,
121  bool isInput,
122  const wxPoint& pos = wxDefaultPosition,
123  const wxSize& size = wxDefaultSize,
124  Style style = HorizontalStereo,
125  float fDecayRate = 60.0f);
126 
127  bool AcceptsFocus() const override { return s_AcceptsFocus; }
128  bool AcceptsFocusFromKeyboard() const override { return true; }
129 
130  void SetFocusFromKbd() override;
131 
132  void UpdatePrefs();
133  void Clear();
134 
135  Style GetStyle() const { return mStyle; }
136  Style GetDesiredStyle() const { return mDesiredStyle; }
137  void SetStyle(Style newStyle);
138 
144  void Reset(double sampleRate, bool resetClipping);
145 
168  void UpdateDisplay(unsigned numChannels,
169  int numFrames, float *sampleData);
170 
171  // Vaughan, 2010-11-29: This not currently used. See comments in MixerTrackCluster::UpdateMeter().
172  //void UpdateDisplay(int numChannels, int numFrames,
173  // // Need to make these double-indexed max and min arrays if we handle more than 2 channels.
174  // float* maxLeft, float* rmsLeft,
175  // float* maxRight, float* rmsRight,
176  // const size_t kSampleCount);
177 
183  bool IsMeterDisabled() const;
184 
185  float GetMaxPeak() const;
186 
187  bool IsClipping() const;
188 
189  void StartMonitoring();
190  void StopMonitoring();
191 
192  // These exist solely for the purpose of resetting the toolbars
193  struct State{ bool mSaved, mMonitoring, mActive; };
194  State SaveState();
195  void RestoreState(const State &state);
196 
197  int GetDBRange() const { return mDB ? mDBRange : -1; }
198 
199  private:
200  static bool s_AcceptsFocus;
201  struct Resetter { void operator () (bool *p) const { if(p) *p = false; } };
202  using TempAllowFocus = std::unique_ptr<bool, Resetter>;
203 
204  public:
206 
207  private:
208  //
209  // Event handlers
210  //
211  void OnErase(wxEraseEvent &evt);
212  void OnPaint(wxPaintEvent &evt);
213  void OnSize(wxSizeEvent &evt);
214  bool InIcon(wxMouseEvent *pEvent = nullptr) const;
215  void OnMouse(wxMouseEvent &evt);
216  void OnKeyDown(wxKeyEvent &evt);
217  void OnKeyUp(wxKeyEvent &evt);
218  void OnContext(wxContextMenuEvent &evt);
219  void OnSetFocus(wxFocusEvent &evt);
220  void OnKillFocus(wxFocusEvent &evt);
221 
222  void OnAudioIOStatus(wxCommandEvent &evt);
223 
224  void OnMeterUpdate(wxTimerEvent &evt);
225 
226  void HandleLayout(wxDC &dc);
227  void SetActiveStyle(Style style);
228  void SetBarAndClip(int iBar, bool vert);
229  void DrawMeterBar(wxDC &dc, MeterBar *meterBar);
230  void ResetBar(MeterBar *bar, bool resetClipping);
231  void RepaintBarsNow();
232  wxFont GetFont() const;
233 
234  //
235  // Pop-up menu
236  //
237  void ShowMenu(const wxPoint & pos);
238  void OnMonitor(wxCommandEvent &evt);
239  void OnPreferences(wxCommandEvent &evt);
240  void OnMeterPrefsUpdated(wxCommandEvent &evt);
241 
242  wxString Key(const wxString & key) const;
243 
246  wxTimer mTimer;
247 
248  int mWidth;
249  int mHeight;
250 
253 
254  bool mIsInput;
255 
258  bool mGradient;
259  bool mDB;
260  int mDBRange;
261  bool mDecay;
262  float mDecayRate; // dB/sec
263  bool mClip;
266  double mT;
267  double mRate;
269  long mMeterDisabled; //is used as a bool, needs long for easy gPrefs...
270 
272 
273  bool mActive;
274 
275  unsigned mNumBars;
277 
279 
280  std::unique_ptr<wxBitmap> mBitmap;
281  wxRect mIconRect;
282  wxPoint mLeftTextPos;
283  wxPoint mRightTextPos;
284  wxSize mLeftSize;
285  wxSize mRightSize;
286  std::unique_ptr<wxBitmap> mIcon;
287  wxPen mPen;
290  wxBrush mBrush;
291  wxBrush mRMSBrush;
292  wxBrush mClipBrush;
293  wxBrush mBkgndBrush;
296  wxString mLeftText;
297  wxString mRightText;
298 
300  wxRect mFocusRect;
301 #if defined(__WXMSW__)
302  bool mHadKeyDown;
303 #endif
304 
306 
307  friend class MeterAx;
308 
309  bool mHighlighted {};
310 
311  DECLARE_EVENT_TABLE()
312 };
313 
314 #if wxUSE_ACCESSIBILITY
315 
316 class MeterAx final : public WindowAccessible
317 {
318 public:
319  MeterAx(wxWindow * window);
320 
321  virtual ~ MeterAx();
322 
323  // Performs the default action. childId is 0 (the action for this object)
324  // or > 0 (the action for a child).
325  // Return wxACC_NOT_SUPPORTED if there is no default action for this
326  // window (e.g. an edit control).
327  wxAccStatus DoDefaultAction(int childId) override;
328 
329  // Retrieves the address of an IDispatch interface for the specified child.
330  // All objects must support this property.
331  wxAccStatus GetChild(int childId, wxAccessible** child) override;
332 
333  // Gets the number of children.
334  wxAccStatus GetChildCount(int* childCount) override;
335 
336  // Gets the default action for this object (0) or > 0 (the action for a child).
337  // Return wxACC_OK even if there is no action. actionName is the action, or the empty
338  // string if there is no action.
339  // The retrieved string describes the action that is performed on an object,
340  // not what the object does as a result. For example, a toolbar button that prints
341  // a document has a default action of "Press" rather than "Prints the current document."
342  wxAccStatus GetDefaultAction(int childId, wxString *actionName) override;
343 
344  // Returns the description for this object or a child.
345  wxAccStatus GetDescription(int childId, wxString *description) override;
346 
347  // Gets the window with the keyboard focus.
348  // If childId is 0 and child is NULL, no object in
349  // this subhierarchy has the focus.
350  // If this object has the focus, child should be 'this'.
351  wxAccStatus GetFocus(int *childId, wxAccessible **child) override;
352 
353  // Returns help text for this object or a child, similar to tooltip text.
354  wxAccStatus GetHelpText(int childId, wxString *helpText) override;
355 
356  // Returns the keyboard shortcut for this object or child.
357  // Return e.g. ALT+K
358  wxAccStatus GetKeyboardShortcut(int childId, wxString *shortcut) override;
359 
360  // Returns the rectangle for this object (id = 0) or a child element (id > 0).
361  // rect is in screen coordinates.
362  wxAccStatus GetLocation(wxRect& rect, int elementId) override;
363 
364  // Gets the name of the specified object.
365  wxAccStatus GetName(int childId, wxString *name) override;
366 
367  // Returns a role constant.
368  wxAccStatus GetRole(int childId, wxAccRole *role) override;
369 
370  // Gets a variant representing the selected children
371  // of this object.
372  // Acceptable values:
373  // - a null variant (IsNull() returns TRUE)
374  // - a list variant (GetType() == wxT("list"))
375  // - an integer representing the selected child element,
376  // or 0 if this object is selected (GetType() == wxT("long"))
377  // - a "void*" pointer to a wxAccessible child object
378  wxAccStatus GetSelections(wxVariant *selections) override;
379 
380  // Returns a state constant.
381  wxAccStatus GetState(int childId, long* state) override;
382 
383  // Returns a localized string representing the value for the object
384  // or child.
385  wxAccStatus GetValue(int childId, wxString* strValue) override;
386 
387 };
388 
389 #endif // wxUSE_ACCESSIBILITY
390 
391 #endif // __AUDACITY_METER__
float mDecayRate
Definition: Meter.h:262
MeterPanel(AudacityProject *, wxWindow *parent, wxWindowID id, bool isInput, const wxPoint &pos=wxDefaultPosition, const wxSize &size=wxDefaultSize, Style style=HorizontalStereo, float fDecayRate=60.0f)
Definition: Meter.cpp:211
float rms[kMaxMeterBars]
Definition: Meter.h:62
wxBrush mClipBrush
Definition: Meter.h:292
size_t mBufferSize
Definition: Meter.h:92
wxBrush mBrush
Definition: Meter.h:290
wxBrush mRMSBrush
Definition: Meter.h:291
void DrawMeterBar(wxDC &dc, MeterBar *meterBar)
Definition: Meter.cpp:1513
wxDECLARE_EXPORTED_EVENT(AUDACITY_DLL_API, EVT_METER_PREFERENCES_CHANGED, wxCommandEvent)
bool mGradient
Definition: Meter.h:258
wxRect r
Definition: Meter.h:45
wxPen mDisabledPen
Definition: Meter.h:288
void Clear()
Definition: Meter.cpp:335
void OnErase(wxEraseEvent &evt)
Definition: Meter.cpp:384
bool mClip
Definition: Meter.h:263
std::unique_ptr< bool, Resetter > TempAllowFocus
Definition: Meter.h:202
wxRect b
Definition: Meter.h:44
MeterBar mBar[kMaxMeterBars]
Definition: Meter.h:276
void OnMouse(wxMouseEvent &evt)
Definition: Meter.cpp:658
bool mIsFocused
Definition: Meter.h:299
void OnSetFocus(wxFocusEvent &evt)
Definition: Meter.cpp:802
wxString mRightText
Definition: Meter.h:297
int GetDBRange() const
Definition: Meter.h:197
void HandleLayout(wxDC &dc)
Definition: Meter.cpp:1190
friend class MeterAx
Definition: Meter.h:307
wxPen mPeakPeakPen
Definition: Meter.h:289
void StopMonitoring()
Definition: Meter.cpp:1798
bool AcceptsFocusFromKeyboard() const override
Definition: Meter.h:128
wxString Key(const wxString &key) const
Definition: Meter.cpp:2028
int tailPeakCount[kMaxMeterBars]
Definition: Meter.h:65
bool mMonitoring
Definition: Meter.h:271
MeterPanel is a panel that paints the meter used for monitoring or playback.
Definition: Meter.h:102
bool mDecay
Definition: Meter.h:261
bool clipping[kMaxMeterBars]
Definition: Meter.h:63
wxRect mFocusRect
Definition: Meter.h:300
bool vert
Definition: Meter.h:43
void OnContext(wxContextMenuEvent &evt)
Definition: Meter.cpp:723
int mDBRange
Definition: Meter.h:260
double mT
Definition: Meter.h:266
bool Get(MeterUpdateMsg &msg)
Definition: Meter.cpp:155
bool Put(MeterUpdateMsg &msg)
Definition: Meter.cpp:134
void OnKeyUp(wxKeyEvent &evt)
Definition: Meter.cpp:779
double mRate
Definition: Meter.h:267
int mRulerWidth
Definition: Meter.h:251
MeterUpdateQueue(size_t maxLen)
Definition: Meter.cpp:115
wxPoint mRightTextPos
Definition: Meter.h:283
An alternative to using wxWindowAccessible, which in wxWidgets 3.1.1 contained GetParent() which was ...
Style mDesiredStyle
Definition: Meter.h:257
int mHeight
Definition: Meter.h:249
void OnAudioIOStatus(wxCommandEvent &evt)
Definition: Meter.cpp:1805
AudacityProject provides the main window, with tools and tracks contained within it.
Definition: Project.h:174
wxRect rClip
Definition: Meter.h:50
void OnMonitor(wxCommandEvent &evt)
Definition: Meter.cpp:1883
float rms
Definition: Meter.h:47
void SetBarAndClip(int iBar, bool vert)
Definition: Meter.cpp:1147
int tailPeakCount
Definition: Meter.h:53
bool mAccSilent
Definition: Meter.h:305
unsigned mNumBars
Definition: Meter.h:275
int mNumPeakSamplesToClip
Definition: Meter.h:264
void OnPaint(wxPaintEvent &evt)
Definition: Meter.cpp:389
bool mMonitoring
Definition: Meter.h:193
Queue of MeterUpdateMsg used to feed the MeterPanel.
Definition: Meter.h:78
void OnMeterUpdate(wxTimerEvent &evt)
Definition: Meter.cpp:967
wxSize mRightSize
Definition: Meter.h:285
static bool s_AcceptsFocus
Definition: Meter.h:200
long mMeterDisabled
Definition: Meter.h:269
wxPen mPen
Definition: Meter.h:287
bool IsMeterDisabled() const
Find out if the level meter is disabled or not.
Definition: Meter.cpp:1773
wxTimer mTimer
Definition: Meter.h:246
float peak[kMaxMeterBars]
Definition: Meter.h:61
long mMeterRefreshRate
Definition: Meter.h:268
void UpdateDisplay(unsigned numChannels, int numFrames, float *sampleData)
Update the meters with a block of audio data.
Definition: Meter.cpp:886
void UpdatePrefs()
Definition: Meter.cpp:340
void OnSize(wxSizeEvent &evt)
Definition: Meter.cpp:645
bool isclipping
Definition: Meter.h:52
void RepaintBarsNow()
Definition: Meter.cpp:1496
AudacityProject * mProject
Definition: Meter.h:244
void SetStyle(Style newStyle)
Definition: Meter.cpp:814
void operator()(bool *p) const
Definition: Meter.h:201
wxString toStringIfClipped()
Only print meter updates if clipping may be happening.
Definition: Meter.cpp:98
double peakHoldTime
Definition: Meter.h:49
static TempAllowFocus TemporarilyAllowFocus()
Definition: Meter.cpp:2045
wxBrush mBkgndBrush
Definition: Meter.h:293
void ShowMenu(const wxPoint &pos)
Definition: Meter.cpp:1851
void OnMeterPrefsUpdated(wxCommandEvent &evt)
Definition: Meter.cpp:1888
void StartMonitoring()
Definition: Meter.cpp:1778
float peakPeakHold
Definition: Meter.h:54
void OnKeyDown(wxKeyEvent &evt)
Definition: Meter.cpp:742
bool mActive
Definition: Meter.h:273
Style GetDesiredStyle() const
Definition: Meter.h:136
float peakHold
Definition: Meter.h:48
MeterUpdateMsg()
Definition: Meter.h:68
Message used to update the MeterPanel.
Definition: Meter.h:57
void Reset(double sampleRate, bool resetClipping)
This method is thread-safe! Feel free to call from a different thread (like from an audio I/O callbac...
Definition: Meter.cpp:826
const int kMaxMeterBars
Definition: Meter.h:40
int numFrames
Definition: Meter.h:60
MeterUpdateQueue mQueue
Definition: Meter.h:245
void SetFocusFromKbd() override
Definition: Meter.cpp:2053
bool InIcon(wxMouseEvent *pEvent=nullptr) const
Definition: Meter.cpp:652
void RestoreState(const State &state)
Definition: Meter.cpp:1834
void OnKillFocus(wxFocusEvent &evt)
Definition: Meter.cpp:808
wxString toString()
Print out all the values in the meter update message.
Definition: Meter.cpp:81
const wxChar * name
Definition: Distortion.cpp:94
int mWidth
Definition: Meter.h:248
Used to display a Ruler.
Definition: Ruler.h:30
std::unique_ptr< wxBitmap > mIcon
Definition: Meter.h:286
int headPeakCount[kMaxMeterBars]
Definition: Meter.h:64
bool clipping
Definition: Meter.h:51
wxFont GetFont() const
Definition: Meter.cpp:1073
void OnPreferences(wxCommandEvent &evt)
Definition: Meter.cpp:1897
wxSize mLeftSize
Definition: Meter.h:284
double mPeakHoldDuration
Definition: Meter.h:265
float peak
Definition: Meter.h:46
bool mLayoutValid
Definition: Meter.h:278
wxBrush mDisabledBkgndBrush
Definition: Meter.h:294
Style mStyle
Definition: Meter.h:256
std::unique_ptr< wxBitmap > mBitmap
Definition: Meter.h:280
float GetMaxPeak() const
Definition: Meter.cpp:1063
Ruler mRuler
Definition: Meter.h:295
bool mIsInput
Definition: Meter.h:254
State SaveState()
Definition: Meter.cpp:1829
Style GetStyle() const
Definition: Meter.h:135
void SetActiveStyle(Style style)
Definition: Meter.cpp:1106
bool mHighlighted
Definition: Meter.h:309
ArrayOf< MeterUpdateMsg > mBuffer
Definition: Meter.h:93
wxPoint mLeftTextPos
Definition: Meter.h:282
void Clear()
Definition: Meter.cpp:126
bool IsClipping() const
Definition: Meter.cpp:1098
int mRulerHeight
Definition: Meter.h:252
bool AcceptsFocus() const override
Definition: Meter.h:127
wxString mLeftText
Definition: Meter.h:296
wxRect mIconRect
Definition: Meter.h:281
~MeterUpdateMsg()
Definition: Meter.h:69
A struct used by MeterPanel to hold the position of one bar.
Definition: Meter.h:42
void ResetBar(MeterBar *bar, bool resetClipping)
Definition: Meter.cpp:1083
bool mDB
Definition: Meter.h:259