Audacity  3.0.3
Public Member Functions | Public Attributes | Private Member Functions | Private Attributes | List of all members
MixerTrackCluster Class Referencefinal

#include <MixerBoard.h>

Inheritance diagram for MixerTrackCluster:
[legend]
Collaboration diagram for MixerTrackCluster:
[legend]

Public Member Functions

 MixerTrackCluster (wxWindow *parent, MixerBoard *grandParent, AudacityProject *project, const std::shared_ptr< PlayableTrack > &pTrack, const wxPoint &pos=wxDefaultPosition, const wxSize &size=wxDefaultSize)
 
virtual ~MixerTrackCluster ()
 
WaveTrackGetWave () const
 
WaveTrackGetRight () const
 
void HandleResize ()
 
void HandleSliderGain (const bool bWantPushState=false)
 
void HandleSliderPan (const bool bWantPushState=false)
 
void ResetMeter (const bool bResetClipping)
 
void UpdateForStateChange ()
 
void UpdateMeter (const double t0, const double t1)
 
- Public Member Functions inherited from wxPanelWrapper
 wxPanelWrapper ()
 
 wxPanelWrapper (wxWindow *parent, wxWindowID winid=wxID_ANY, const wxPoint &pos=wxDefaultPosition, const wxSize &size=wxDefaultSize, long style=wxTAB_TRAVERSAL|wxNO_BORDER, const TranslatableString &name=XO("Panel"))
 
bool Create (wxWindow *parent, wxWindowID winid=wxID_ANY, const wxPoint &pos=wxDefaultPosition, const wxSize &size=wxDefaultSize, long style=wxTAB_TRAVERSAL|wxNO_BORDER, const TranslatableString &name=XO("Panel"))
 
void SetLabel (const TranslatableString &label)
 
void SetName (const TranslatableString &name)
 
void SetToolTip (const TranslatableString &toolTip)
 
void SetName ()
 
- Public Member Functions inherited from wxTabTraversalWrapper< wxPanel >
 wxTabTraversalWrapper (Args &&... args)
 
 wxTabTraversalWrapper (const wxTabTraversalWrapper &)=delete
 
 wxTabTraversalWrapper (wxTabTraversalWrapper &&)=delete
 
wxTabTraversalWrapperoperator= (const wxTabTraversalWrapper &)=delete
 
wxTabTraversalWrapperoperator= (wxTabTraversalWrapper &&)=delete
 

Public Attributes

std::shared_ptr< PlayableTrackmTrack
 

Private Member Functions

wxColour GetTrackColor ()
 
void HandleSelect (bool bShiftDown, bool bControlDown)
 
void OnKeyEvent (wxKeyEvent &event)
 
void OnMouseEvent (wxMouseEvent &event)
 
void OnPaint (wxPaintEvent &evt)
 
void OnButton_MusicalInstrument (wxCommandEvent &event)
 
void OnSlider_Gain (wxCommandEvent &event)
 
void OnSlider_Pan (wxCommandEvent &event)
 
void OnButton_Mute (wxCommandEvent &event)
 
void OnButton_Solo (wxCommandEvent &event)
 

Private Attributes

MixerBoardmMixerBoard
 
AudacityProjectmProject
 
auStaticTextmStaticText_TrackName
 
wxBitmapButton * mBitmapButton_MusicalInstrument
 
AButtonmToggleButton_Mute
 
AButtonmToggleButton_Solo
 
MixerTrackSlidermSlider_Pan
 
MixerTrackSlidermSlider_Gain
 
wxWeakRef< MeterPanelmMeter
 

Detailed Description

Definition at line 75 of file MixerBoard.h.

Constructor & Destructor Documentation

◆ MixerTrackCluster()

MixerTrackCluster::MixerTrackCluster ( wxWindow *  parent,
MixerBoard grandParent,
AudacityProject project,
const std::shared_ptr< PlayableTrack > &  pTrack,
const wxPoint &  pos = wxDefaultPosition,
const wxSize &  size = wxDefaultSize 
)

Definition at line 172 of file MixerBoard.cpp.

177 : wxPanelWrapper(parent, -1, pos, size)
178 , mTrack{ pTrack }
179 {
180  mMixerBoard = grandParent;
181  mProject = project;
182  wxASSERT( pTrack );
183 
184  SetName( Verbatim( mTrack->GetName() ) );
185 
186  //this->SetBackgroundColour(wxSystemSettings::GetColour(wxSYS_COLOUR_3DFACE));
187  this->SetBackgroundColour( theTheme.Colour( clrMedium ) );
188  // Not sure why, but sizers weren't getting offset vertically,
189  // probably because not using wxDefaultPosition,
190  // so positions are calculated explicitly below, and sizers code was removed.
191  // (Still available in Audacity_UmixIt branch off 1.2.6.)
192 
193  // track name
194  wxPoint ctrlPos(kDoubleInset, kDoubleInset);
195  wxSize ctrlSize(size.GetWidth() - kQuadrupleInset, TRACK_NAME_HEIGHT);
197  safenew auStaticText(this, mTrack->GetName());
198  //v Useful when different tracks are different colors, but not now.
199  // mStaticText_TrackName->SetBackgroundColour(this->GetTrackColor());
200  mStaticText_TrackName->SetForegroundColour(theTheme.Colour(clrMedium));
201  mStaticText_TrackName->SetForegroundColour(theTheme.Colour(clrTrackPanelText));
202  mStaticText_TrackName->SetSize( ctrlSize );
203  mStaticText_TrackName->SetPosition( ctrlPos );
204 
205 
206  // gain and velocity sliders at left (both in same place)
207  ctrlPos.x = kDoubleInset;
208  ctrlPos.y += TRACK_NAME_HEIGHT + kDoubleInset;
209  const int nGainSliderHeight =
210  size.GetHeight() - ctrlPos.y - kQuadrupleInset;
211  ctrlSize.Set(kLeftSideStackWidth - kQuadrupleInset, nGainSliderHeight);
212 
213  mSlider_Gain =
215  this, ID_SLIDER_GAIN,
216  /* i18n-hint: title of the Gain slider, used to adjust the volume */
217  XO("Gain"),
218  ctrlPos, ctrlSize,
220  .Style( DB_SLIDER )
221  .Orientation( wxVERTICAL ));
222  mSlider_Gain->SetName(_("Gain"));
223 
224 #ifdef EXPERIMENTAL_MIDI_OUT
225  mSlider_Velocity =
227  this, ID_SLIDER_VELOCITY,
228  /* i18n-hint: title of the MIDI Velocity slider */
229  XO("Velocity"),
230  ctrlPos, ctrlSize,
232  .Style( VEL_SLIDER )
233  .Orientation( wxVERTICAL ));
234  mSlider_Velocity->SetName(_("Velocity"));
235 #endif
236 
237  // other controls and meter at right
238 
239  // musical instrument image
240  ctrlPos.x += kLeftSideStackWidth + kInset; // + kInset to center it in right side stack
242  wxBitmap* bitmap = mMixerBoard->GetMusicalInstrumentBitmap(mTrack.get());
243  wxASSERT(bitmap);
245  safenew wxBitmapButton(this, ID_BITMAPBUTTON_MUSICAL_INSTRUMENT, *bitmap,
246  ctrlPos, ctrlSize,
247  wxBU_AUTODRAW, wxDefaultValidator,
248  _("Musical Instrument"));
249  mBitmapButton_MusicalInstrument->SetName(_("Musical Instrument"));
250 
251 
252  // pan slider
253  ctrlPos.x -= kInset; // Remove inset for instrument, so Pan is at leftmost of left side stack.
255  ctrlSize.Set(kRightSideStackWidth, PAN_HEIGHT);
256 
257  // The width of the pan slider must be odd (don't ask).
258  if (!(ctrlSize.x & 1))
259  ctrlSize.x--;
260 
261  mSlider_Pan =
263  this, ID_SLIDER_PAN,
264  /* i18n-hint: Title of the Pan slider, used to move the sound left or right */
265  XO("Pan"),
266  ctrlPos, ctrlSize,
268  mSlider_Pan->SetName(_("Pan"));
269 
270  // mute/solo buttons stacked below Pan slider
271  ctrlPos.y += PAN_HEIGHT + kDoubleInset;
275  ctrlPos, ctrlSize,
279  true); // toggle button
280  mToggleButton_Mute->SetName(_("Mute"));
282  1,
286 
287  ctrlPos.y += MUTE_SOLO_HEIGHT;
290  ctrlPos, ctrlSize,
294  true); // toggle button
295  mToggleButton_Solo->SetName(_("Solo"));
296  bool bSoloNone = ProjectSettings::Get( *mProject ).IsSoloNone();
297  mToggleButton_Solo->Show(!bSoloNone);
298 
299 
300  // meter
301  ctrlPos.y += (bSoloNone ? 0 : MUTE_SOLO_HEIGHT) + kDoubleInset;
302  const int nMeterHeight =
303  nGainSliderHeight -
306  (MUTE_SOLO_HEIGHT + (bSoloNone ? 0 : MUTE_SOLO_HEIGHT) + kDoubleInset);
307  ctrlSize.Set(kRightSideStackWidth, nMeterHeight);
308 
309  mMeter.Release();
310  if (GetWave()) {
311  mMeter =
312  safenew MeterPanel(mProject, // AudacityProject* project,
313  this, -1, // wxWindow* parent, wxWindowID id,
314  false, // bool isInput
315  ctrlPos, ctrlSize, // const wxPoint& pos = wxDefaultPosition, const wxSize& size = wxDefaultSize,
316  MeterPanel::MixerTrackCluster); // Style style = HorizontalStereo,
317  mMeter->SetName(XO("Signal Level Meter"));
318  }
319 
320  #if wxUSE_TOOLTIPS
321  mStaticText_TrackName->SetToolTip(mTrack->GetName());
322  mToggleButton_Mute->SetToolTip(XO("Mute"));
323  mToggleButton_Solo->SetToolTip(XO("Solo"));
324  if (GetWave())
325  mMeter->SetToolTip(XO("Signal Level Meter"));
326  #endif // wxUSE_TOOLTIPS
327 
329 
330  #ifdef __WXMAC__
331  wxSizeEvent event(GetSize(), GetId());
332  event.SetEventObject(this);
333  GetEventHandler()->ProcessEvent(event);
334  #endif
335 }

◆ ~MixerTrackCluster()

virtual MixerTrackCluster::~MixerTrackCluster ( )
inlinevirtual

Definition at line 83 of file MixerBoard.h.

83 {}

Member Function Documentation

◆ GetRight()

WaveTrack * MixerTrackCluster::GetRight ( ) const

Definition at line 342 of file MixerBoard.cpp.

343 {
344  // TODO: more-than-two-channels
345  auto left = GetWave();
346  if (left) {
347  auto channels = TrackList::Channels(left);
348  if ( channels.size() > 1 )
349  return * ++ channels.first;
350  }
351  return nullptr;
352 }

References TrackList::Channels(), and GetWave().

Referenced by HandleSliderGain(), HandleSliderPan(), and UpdateMeter().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ GetTrackColor()

wxColour MixerTrackCluster::GetTrackColor ( )
private

Definition at line 669 of file MixerBoard.cpp.

670 {
671  return wxColour(102, 255, 102); // same as Meter playback color
672 }

◆ GetWave()

WaveTrack * MixerTrackCluster::GetWave ( ) const

Definition at line 337 of file MixerBoard.cpp.

338 {
339  return dynamic_cast< WaveTrack * >( mTrack.get() );
340 }

References mTrack.

Referenced by GetRight(), HandleSliderGain(), HandleSliderPan(), ResetMeter(), UpdateForStateChange(), and UpdateMeter().

Here is the caller graph for this function:

◆ HandleResize()

void MixerTrackCluster::HandleResize ( )

Definition at line 373 of file MixerBoard.cpp.

374 {
375  wxSize scrolledWindowClientSize = this->GetParent()->GetClientSize();
376  const int newClusterHeight =
377  scrolledWindowClientSize.GetHeight() - kDoubleInset - // nClusterHeight from MixerBoard::UpdateTrackClusters
378  wxSystemSettings::GetMetric(wxSYS_HSCROLL_Y) + // wxScrolledWindow::GetClientSize doesn't account for its scrollbar size.
379  kDoubleInset;
380 
381  this->SetSize(-1, newClusterHeight);
382 
383  // Change only the heights of mSlider_Gain and mMeter.
384  // But update shown status of mToggleButton_Solo, which affects top of mMeter.
385  const int nGainSliderHeight =
386  newClusterHeight -
387  (kInset + // margin above mStaticText_TrackName
388  TRACK_NAME_HEIGHT + kDoubleInset) - // mStaticText_TrackName + margin
389  kQuadrupleInset; // margin below gain slider
390  mSlider_Gain->SetSize(-1, nGainSliderHeight);
391 #ifdef EXPERIMENTAL_MIDI_OUT
392  mSlider_Velocity->SetSize(-1, nGainSliderHeight);
393 #endif
394 
395  bool bSoloNone = ProjectSettings::Get( *mProject ).IsSoloNone();
396 
397  mToggleButton_Solo->Show(!bSoloNone);
398 
399  const int nRequiredHeightAboveMeter =
402  MUTE_SOLO_HEIGHT + (bSoloNone ? 0 : MUTE_SOLO_HEIGHT) + kDoubleInset;
403  const int nMeterY =
404  kDoubleInset + // margin at top
406  nRequiredHeightAboveMeter;
407  const int nMeterHeight = nGainSliderHeight - nRequiredHeightAboveMeter;
408  if (mMeter)
409  mMeter->SetSize(-1, nMeterY, -1, nMeterHeight);
410 }

References ProjectSettings::Get(), anonymous_namespace{wxWidgetsBasicUI.cpp}::GetParent(), ProjectSettings::IsSoloNone(), kDoubleInset, kInset, kQuadrupleInset, mMeter, mSlider_Gain, mToggleButton_Solo, MUSICAL_INSTRUMENT_HEIGHT_AND_WIDTH, MUTE_SOLO_HEIGHT, PAN_HEIGHT, and TRACK_NAME_HEIGHT.

Here is the call graph for this function:

◆ HandleSelect()

void MixerTrackCluster::HandleSelect ( bool  bShiftDown,
bool  bControlDown 
)
private

Definition at line 677 of file MixerBoard.cpp.

678 {
680  mTrack.get(), bShiftDown, bControlDown, true);
681 }

References SelectUtilities::DoListSelection(), mProject, and mTrack.

Referenced by OnButton_MusicalInstrument(), and OnMouseEvent().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ HandleSliderGain()

void MixerTrackCluster::HandleSliderGain ( const bool  bWantPushState = false)

Definition at line 412 of file MixerBoard.cpp.

413 {
414  float fValue = mSlider_Gain->Get();
415  if (GetWave())
416  GetWave()->SetGain(fValue);
417  if (GetRight())
418  GetRight()->SetGain(fValue);
419 
420  // Update the TrackPanel correspondingly.
421  TrackPanel::Get( *mProject ).RefreshTrack(mTrack.get());
422  if (bWantPushState)
424  .PushState(XO("Moved gain slider"), XO("Gain"), UndoPush::CONSOLIDATE );
425 }

References CONSOLIDATE, ProjectHistory::Get(), TrackPanel::Get(), ASlider::Get(), GetRight(), GetWave(), mProject, mSlider_Gain, mTrack, ProjectHistory::PushState(), TrackPanel::RefreshTrack(), WaveTrack::SetGain(), and XO.

Referenced by MixerTrackSlider::OnMouseEvent(), and OnSlider_Gain().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ HandleSliderPan()

void MixerTrackCluster::HandleSliderPan ( const bool  bWantPushState = false)

Definition at line 443 of file MixerBoard.cpp.

444 {
445  float fValue = mSlider_Pan->Get();
446  if (GetWave()) // test in case track is a NoteTrack
447  GetWave()->SetPan(fValue);
448  if (GetRight())
449  GetRight()->SetPan(fValue);
450 
451  // Update the TrackPanel correspondingly.
452  TrackPanel::Get( *mProject ).RefreshTrack(mTrack.get());
453 
454  if (bWantPushState)
456  .PushState(XO("Moved pan slider"), XO("Pan"),
458 }

References CONSOLIDATE, ProjectHistory::Get(), TrackPanel::Get(), ASlider::Get(), GetRight(), GetWave(), mProject, mSlider_Pan, mTrack, ProjectHistory::PushState(), TrackPanel::RefreshTrack(), WaveTrack::SetPan(), and XO.

Referenced by MixerTrackSlider::OnMouseEvent(), and OnSlider_Pan().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ OnButton_MusicalInstrument()

void MixerTrackCluster::OnButton_MusicalInstrument ( wxCommandEvent &  event)
private

Definition at line 718 of file MixerBoard.cpp.

719 {
720  const auto &state = ::wxGetMouseState();
721  this->HandleSelect(state.ShiftDown(), state.ControlDown());
722 }

References HandleSelect().

Here is the call graph for this function:

◆ OnButton_Mute()

void MixerTrackCluster::OnButton_Mute ( wxCommandEvent &  event)
private

Definition at line 756 of file MixerBoard.cpp.

757 {
760  mToggleButton_Mute->SetAlternateIdx(mTrack->GetSolo() ? 1 : 0);
761 
762  // Update the TrackPanel correspondingly.
763  if (ProjectSettings::Get(*mProject).IsSoloSimple())
764  ProjectWindow::Get( *mProject ).RedrawProject();
765  else
766  // Update only the changed track.
767  TrackPanel::Get( *mProject ).RefreshTrack(mTrack.get());
768 }

References TrackUtilities::DoTrackMute(), ProjectSettings::Get(), ProjectWindow::Get(), TrackPanel::Get(), ProjectSettings::IsSoloSimple(), mProject, mToggleButton_Mute, mTrack, ProjectWindow::RedrawProject(), TrackPanel::RefreshTrack(), AButton::SetAlternateIdx(), and AButton::WasShiftDown().

Here is the call graph for this function:

◆ OnButton_Solo()

void MixerTrackCluster::OnButton_Solo ( wxCommandEvent &  event)
private

Definition at line 770 of file MixerBoard.cpp.

771 {
774  bool bIsSolo = mTrack->GetSolo();
775  mToggleButton_Mute->SetAlternateIdx(bIsSolo ? 1 : 0);
776 
777  // Update the TrackPanel correspondingly.
778  // Bug 509: Must repaint all, as many tracks can change with one Solo change.
779  ProjectWindow::Get( *mProject ).RedrawProject();
780 }

References TrackUtilities::DoTrackSolo(), ProjectWindow::Get(), mProject, mToggleButton_Mute, mToggleButton_Solo, mTrack, ProjectWindow::RedrawProject(), AButton::SetAlternateIdx(), and AButton::WasShiftDown().

Here is the call graph for this function:

◆ OnKeyEvent()

void MixerTrackCluster::OnKeyEvent ( wxKeyEvent &  event)
private

◆ OnMouseEvent()

void MixerTrackCluster::OnMouseEvent ( wxMouseEvent &  event)
private

Definition at line 683 of file MixerBoard.cpp.

684 {
685  if (event.ButtonUp())
686  this->HandleSelect(event.ShiftDown(), event.ControlDown());
687  else
688  event.Skip();
689 }

References HandleSelect().

Here is the call graph for this function:

◆ OnPaint()

void MixerTrackCluster::OnPaint ( wxPaintEvent &  evt)
private

Definition at line 691 of file MixerBoard.cpp.

692 {
694 
695  auto selected = mTrack->GetSelected();
696 
697  wxColour col = theTheme.Colour(selected ? clrTrackInfoSelected : clrTrackInfo) ;
698  SetBackgroundColour( col );
699  if (mMeter)
700  mMeter->SetBackgroundColour( col );
701  mStaticText_TrackName->SetBackgroundColour( col );
704 
705  wxPaintDC dc(this);
706 
707  AColor::MediumTrackInfo(&dc, selected);
708  dc.DrawRectangle(this->GetClientRect());
709 
710  wxSize clusterSize = this->GetSize();
711  wxRect bev(0, 0, clusterSize.GetWidth() - 1, clusterSize.GetHeight() - 1);
712 
713  //bev.Inflate(-1, -1);
714  AColor::Bevel(dc, true, bev);// same bevel whether selected or not.
715 }

References AColor::Bevel(), ThemeBase::Colour(), AColor::MediumTrackInfo(), mMeter, mSlider_Gain, mSlider_Pan, mStaticText_TrackName, mTrack, ASlider::SetBackgroundColour(), theTheme, and UpdateForStateChange().

Here is the call graph for this function:

◆ OnSlider_Gain()

void MixerTrackCluster::OnSlider_Gain ( wxCommandEvent &  event)
private

Definition at line 724 of file MixerBoard.cpp.

725 {
726  this->HandleSliderGain();
727 }

References HandleSliderGain().

Here is the call graph for this function:

◆ OnSlider_Pan()

void MixerTrackCluster::OnSlider_Pan ( wxCommandEvent &  event)
private

Definition at line 751 of file MixerBoard.cpp.

752 {
753  this->HandleSliderPan();
754 }

References HandleSliderPan().

Here is the call graph for this function:

◆ ResetMeter()

void MixerTrackCluster::ResetMeter ( const bool  bResetClipping)

Definition at line 460 of file MixerBoard.cpp.

461 {
462  if (mMeter)
463  mMeter->Reset(GetWave()->GetRate(), bResetClipping);
464 }

References anonymous_namespace{TimeTrack.cpp}::GetRate(), GetWave(), and mMeter.

Referenced by UpdateMeter().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ UpdateForStateChange()

void MixerTrackCluster::UpdateForStateChange ( )

Definition at line 468 of file MixerBoard.cpp.

469 {
470  const wxString newName = mTrack->GetName();
471  if (newName != GetName()) {
472  SetName( Verbatim( newName ) );
473  mStaticText_TrackName->SetLabel(newName);
474  mStaticText_TrackName->SetName(newName);
475 #if wxUSE_TOOLTIPS
476  mStaticText_TrackName->SetToolTip(newName);
477 #endif
478  mBitmapButton_MusicalInstrument->SetBitmapLabel(
480  }
481 
482  mToggleButton_Mute->SetAlternateIdx(mTrack->GetSolo() ? 1 : 0);
483  if (mTrack->GetMute())
485  else
487 
488  bool bIsSolo = mTrack->GetSolo();
489  if (bIsSolo)
491  else
493  mToggleButton_Mute->SetAlternateIdx(bIsSolo ? 1 : 0);
494 
495  if (!GetWave())
496  mSlider_Pan->Hide();
497  else
498  mSlider_Pan->Set(GetWave()->GetPan());
499 
500  if (!GetWave())
501  mSlider_Gain->Hide();
502  else
503  mSlider_Gain->Set(GetWave()->GetGain());
504 
505 #ifdef EXPERIMENTAL_MIDI_OUT
506  if (!GetNote())
507  mSlider_Velocity->Hide();
508  else
509  mSlider_Velocity->Set(GetNote()->GetVelocity());
510 #endif
511 }

References MixerBoard::GetMusicalInstrumentBitmap(), GetWave(), mBitmapButton_MusicalInstrument, mMixerBoard, mSlider_Gain, mSlider_Pan, mStaticText_TrackName, mToggleButton_Mute, mToggleButton_Solo, mTrack, AButton::PopUp(), AButton::PushDown(), ASlider::Set(), AButton::SetAlternateIdx(), wxPanelWrapper::SetName(), and Verbatim().

Referenced by OnPaint().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ UpdateMeter()

void MixerTrackCluster::UpdateMeter ( const double  t0,
const double  t1 
)

Definition at line 513 of file MixerBoard.cpp.

514 {
515  // NoteTracks do not (currently) register on meters. It would probably be
516  // a good idea to display 16 channel "active" lights rather than a meter
517  if (!GetWave())
518  return;
519 
520  if ((t0 < 0.0) || (t1 < 0.0) || (t0 >= t1) || // bad time value or nothing to show
521  ((mMixerBoard->HasSolo() || mTrack->GetMute()) && !mTrack->GetSolo())
522  )
523  {
524  //v Vaughan, 2011-02-25: Moved the update back to TrackPanel::OnTimer() as it helps with
525  // playback issues reported by Bill and noted on Bug 258, so no assert.
526  // Vaughan, 2011-02-04: Now that we're updating all meters from audacityAudioCallback,
527  // this causes an assert if you click Mute while playing, because ResetMeter() resets
528  // the timer, and wxTimerbase says that can only be done from main thread --
529  // but it seems to work fine.
530  this->ResetMeter(false);
531  return;
532  }
533 
534  // Vaughan, 2010-11-27:
535  // This commented out code is flawed. Mistaken understanding of "frame" vs "window".
536  // Caused me to override MeterPanel::UpdateDisplay().
537  // But I think it's got a good idea, of calling WaveTracks' GetMinMax and GetRMS
538  // instead of passing in all the data and asking the meter to derive peak and rms.
539  // May be worth revisiting as I think it should perform better, because it uses the min/max/rms
540  // stored in sample blocks, rather than calculating them, but for now, changing it to use the
541  // original MeterPanel::UpdateDisplay(). New code is below the previous (now commented out).
542  //
543  //const size_t kFramesPerBuffer = 4;
544  //float min; // dummy, since it's not shown in meters
545  //Floats maxLeft{kFramesPerBuffer};
546  //Floats rmsLeft{kFramesPerBuffer};
547  //Floats maxRight{kFramesPerBuffer};
548  //Floats rmsRight{kFramesPerBuffer};
549  //
550  //#ifdef EXPERIMENTAL_MIDI_OUT
551  // bool bSuccess = (GetWave() != nullptr);
552  //#else
553  // bool bSuccess = true;
554  //#endif
555 
556  //const double dFrameInterval = (t1 - t0) / (double)kFramesPerBuffer;
557  //double dFrameT0 = t0;
558  //double dFrameT1 = t0 + dFrameInterval;
559  //int i = 0;
560  //while (bSuccess && (i < kFramesPerBuffer))
561  //{
562  // bSuccess &=
563  // mTrack->GetMinMax(&min, &(maxLeft[i]), dFrameT0, dFrameT1) &&
564  // mTrack->GetRMS(&(rmsLeft[i]), dFrameT0, dFrameT1);
565  // if (bSuccess && mRightTrack)
566  // bSuccess &=
567  // mRightTrack->GetMinMax(&min, &(maxRight[i]), dFrameT0, dFrameT1) &&
568  // mRightTrack->GetRMS(&(rmsRight[i]), dFrameT0, dFrameT1);
569  // else
570  // {
571  // // Mono: Start with raw values same as left.
572  // // To be modified by bWantPostFadeValues and channel pan/gain.
573  // maxRight[i] = maxLeft[i];
574  // rmsRight[i] = rmsLeft[i];
575  // }
576  // dFrameT0 += dFrameInterval;
577  // dFrameT1 += dFrameInterval;
578  // i++;
579  //}
580  //
581  //const bool bWantPostFadeValues = true; //v Turn this into a checkbox on MixerBoard? For now, always true.
582  //if (bSuccess && bWantPostFadeValues)
583  //if (bSuccess)
584  //{
585  // for (i = 0; i < kFramesPerBuffer; i++)
586  // {
587  // float gain = mTrack->GetChannelGain(0);
588  // maxLeft[i] *= gain;
589  // rmsLeft[i] *= gain;
590  // if (mRightTrack)
591  // gain = mRightTrack->GetChannelGain(1);
592  // maxRight[i] *= gain;
593  // rmsRight[i] *= gain;
594  // }
595  // if ( mMeter ) mMeter->UpdateDisplay(
596  // 2, // If mono, show left track values in both meters, as in MeterToolBar, rather than nChannels.
597  // kFramesPerBuffer,
598  // maxLeft, rmsLeft,
599  // maxRight, rmsRight,
600  // mTrack->TimeToLongSamples(t1 - t0));
601  //}
602  //
603 
604  const auto pTrack = GetWave();
605  auto startSample = (sampleCount)((pTrack->GetRate() * t0) + 0.5);
606  auto scnFrames = (sampleCount)((pTrack->GetRate() * (t1 - t0)) + 0.5);
607 
608  // Expect that the difference of t1 and t0 is the part of a track played
609  // in about 1/20 second (ticks of TrackPanel timer), so this won't overflow
610  auto nFrames = scnFrames.as_size_t();
611 
612  Floats tempFloatsArray{ nFrames };
613  decltype(tempFloatsArray) meterFloatsArray;
614  // Don't throw on read error in this drawing update routine
615  bool bSuccess = pTrack->GetFloats(tempFloatsArray.get(),
616  startSample, nFrames, fillZero, false);
617  if (bSuccess)
618  {
619  // We always pass a stereo sample array to the meter, as it shows 2 channels.
620  // Mono shows same in both meters.
621  // Since we're not mixing, need to duplicate same signal for "right" channel in mono case.
622  meterFloatsArray = Floats{ 2 * nFrames };
623 
624  // Interleave for stereo. Left/mono first.
625  for (unsigned int index = 0; index < nFrames; index++)
626  meterFloatsArray[2 * index] = tempFloatsArray[index];
627 
628  if (GetRight())
629  // Again, don't throw
630  bSuccess = GetRight()->GetFloats(tempFloatsArray.get(),
631  startSample, nFrames, fillZero, false);
632 
633  if (bSuccess)
634  // Interleave right channel, or duplicate same signal for "right" channel in mono case.
635  for (unsigned int index = 0; index < nFrames; index++)
636  meterFloatsArray[(2 * index) + 1] = tempFloatsArray[index];
637  }
638 
639  //const bool bWantPostFadeValues = true; //v Turn this into a checkbox on MixerBoard? For now, always true.
640  //if (bSuccess && bWantPostFadeValues)
641  if (bSuccess)
642  {
643  //vvv Need to apply envelope, too? See Mixer::MixSameRate.
644  float gain = pTrack->GetChannelGain(0);
645  for (unsigned int index = 0; index < nFrames; index++)
646  meterFloatsArray[2 * index] *= gain;
647  if (GetRight())
648  gain = GetRight()->GetChannelGain(1);
649  else
650  gain = pTrack->GetChannelGain(1);
651  for (unsigned int index = 0; index < nFrames; index++)
652  meterFloatsArray[(2 * index) + 1] *= gain;
653  // Clip to [-1.0, 1.0] range.
654  for (unsigned int index = 0; index < 2 * nFrames; index++)
655  if (meterFloatsArray[index] < -1.0)
656  meterFloatsArray[index] = -1.0;
657  else if (meterFloatsArray[index] > 1.0)
658  meterFloatsArray[index] = 1.0;
659 
660  if (mMeter)
661  mMeter->UpdateDisplay(2, nFrames, meterFloatsArray.get());
662  }
663  else
664  this->ResetMeter(false);
665 }

References fillZero, WaveTrack::GetChannelGain(), WaveTrack::GetFloats(), GetRight(), GetWave(), MixerBoard::HasSolo(), mMeter, mMixerBoard, mTrack, and ResetMeter().

Here is the call graph for this function:

Member Data Documentation

◆ mBitmapButton_MusicalInstrument

wxBitmapButton* MixerTrackCluster::mBitmapButton_MusicalInstrument
private

Definition at line 136 of file MixerBoard.h.

Referenced by UpdateForStateChange().

◆ mMeter

wxWeakRef<MeterPanel> MixerTrackCluster::mMeter
private

Definition at line 144 of file MixerBoard.h.

Referenced by HandleResize(), OnPaint(), ResetMeter(), and UpdateMeter().

◆ mMixerBoard

MixerBoard* MixerTrackCluster::mMixerBoard
private

Definition at line 131 of file MixerBoard.h.

Referenced by UpdateForStateChange(), and UpdateMeter().

◆ mProject

AudacityProject* MixerTrackCluster::mProject
private

◆ mSlider_Gain

MixerTrackSlider* MixerTrackCluster::mSlider_Gain
private

Definition at line 140 of file MixerBoard.h.

Referenced by HandleResize(), HandleSliderGain(), OnPaint(), and UpdateForStateChange().

◆ mSlider_Pan

MixerTrackSlider* MixerTrackCluster::mSlider_Pan
private

Definition at line 139 of file MixerBoard.h.

Referenced by HandleSliderPan(), OnPaint(), and UpdateForStateChange().

◆ mStaticText_TrackName

auStaticText* MixerTrackCluster::mStaticText_TrackName
private

Definition at line 135 of file MixerBoard.h.

Referenced by OnPaint(), and UpdateForStateChange().

◆ mToggleButton_Mute

AButton* MixerTrackCluster::mToggleButton_Mute
private

Definition at line 137 of file MixerBoard.h.

Referenced by OnButton_Mute(), OnButton_Solo(), and UpdateForStateChange().

◆ mToggleButton_Solo

AButton* MixerTrackCluster::mToggleButton_Solo
private

Definition at line 138 of file MixerBoard.h.

Referenced by HandleResize(), OnButton_Solo(), and UpdateForStateChange().

◆ mTrack

std::shared_ptr<PlayableTrack> MixerTrackCluster::mTrack

The documentation for this class was generated from the following files:
MixerTrackCluster::GetRight
WaveTrack * GetRight() const
Definition: MixerBoard.cpp:342
MixerBoard::mImageMuteOver
std::unique_ptr< wxImage > mImageMuteOver
Definition: MixerBoard.h:243
kRightSideStackWidth
const int kRightSideStackWidth
Definition: MixerBoard.cpp:143
MUSICAL_INSTRUMENT_HEIGHT_AND_WIDTH
const int MUSICAL_INSTRUMENT_HEIGHT_AND_WIDTH
Definition: MixerBoard.cpp:138
ASlider::Get
float Get(bool convert=true)
Definition: ASlider.cpp:1742
MixerTrackCluster::HandleSliderPan
void HandleSliderPan(const bool bWantPushState=false)
Definition: MixerBoard.cpp:443
WaveTrack
A Track that contains audio waveform data.
Definition: WaveTrack.h:69
MixerBoard::mImageMuteDisabled
std::unique_ptr< wxImage > mImageMuteDisabled
Definition: MixerBoard.h:245
kQuadrupleInset
const int kQuadrupleInset
Definition: MixerBoard.cpp:135
kDoubleInset
const int kDoubleInset
Definition: MixerBoard.cpp:133
MixerBoard::mImageSoloDown
std::unique_ptr< wxImage > mImageSoloDown
Definition: MixerBoard.h:245
MixerTrackCluster::ResetMeter
void ResetMeter(const bool bResetClipping)
Definition: MixerBoard.cpp:460
MixerTrackCluster::mProject
AudacityProject * mProject
Definition: MixerBoard.h:132
AButton
A wxButton with mouse-over behaviour.
Definition: AButton.h:25
MixerBoard::GetMusicalInstrumentBitmap
wxBitmap * GetMusicalInstrumentBitmap(const Track *pTrack)
Definition: MixerBoard.cpp:1078
ASlider::Set
void Set(float value)
Definition: ASlider.cpp:1747
ASlider::SetBackgroundColour
bool SetBackgroundColour(const wxColour &colour) override
Definition: ASlider.cpp:1627
AButton::PopUp
void PopUp()
Definition: AButton.cpp:605
TrackList::Channels
static auto Channels(TrackType *pTrack) -> TrackIterRange< TrackType >
Definition: Track.h:1484
VEL_SLIDER
#define VEL_SLIDER
Definition: ASlider.h:37
AButton::WasShiftDown
bool WasShiftDown()
Definition: AButton.cpp:561
TrackPanel::Get
static TrackPanel & Get(AudacityProject &project)
Definition: TrackPanel.cpp:227
XO
#define XO(s)
Definition: Internat.h:31
MixerBoard::mImageSoloUp
std::unique_ptr< wxImage > mImageSoloUp
Definition: MixerBoard.h:245
MixerTrackCluster::mStaticText_TrackName
auStaticText * mStaticText_TrackName
Definition: MixerBoard.h:135
ProjectSettings::Get
static ProjectSettings & Get(AudacityProject &project)
Definition: ProjectSettings.cpp:41
ProjectWindow::Get
static ProjectWindow & Get(AudacityProject &project)
Definition: ProjectWindow.cpp:535
ASlider::Options
Definition: ASlider.h:238
MixerTrackCluster::mSlider_Gain
MixerTrackSlider * mSlider_Gain
Definition: MixerBoard.h:140
MixerTrackCluster::mToggleButton_Mute
AButton * mToggleButton_Mute
Definition: MixerBoard.h:137
fillZero
@ fillZero
Definition: SampleFormat.h:54
TrackUtilities::DoTrackSolo
void DoTrackSolo(AudacityProject &project, Track *t, bool exclusive)
Definition: TrackUtilities.cpp:112
PAN_SLIDER
#define PAN_SLIDER
Definition: ASlider.h:34
MixerTrackCluster::mMixerBoard
MixerBoard * mMixerBoard
Definition: MixerBoard.h:131
MUTE_SOLO_HEIGHT
const int MUTE_SOLO_HEIGHT
Definition: MixerBoard.cpp:139
MixerBoard::mMuteSoloWidth
int mMuteSoloWidth
Definition: MixerBoard.h:247
ID_TOGGLEBUTTON_MUTE
@ ID_TOGGLEBUTTON_MUTE
Definition: MixerBoard.cpp:153
AButton::SetAlternateImages
void SetAlternateImages(unsigned idx, ImageRoll up, ImageRoll over, ImageRoll down, ImageRoll overDown, ImageRoll dis)
Definition: AButton.cpp:304
ID_TOGGLEBUTTON_SOLO
@ ID_TOGGLEBUTTON_SOLO
Definition: MixerBoard.cpp:154
MixerTrackCluster::mMeter
wxWeakRef< MeterPanel > mMeter
Definition: MixerBoard.h:144
MeterPanel::MixerTrackCluster
@ MixerTrackCluster
Definition: MeterPanel.h:107
MixerTrackCluster::GetWave
WaveTrack * GetWave() const
Definition: MixerBoard.cpp:337
MixerBoard::mImageSoloDisabled
std::unique_ptr< wxImage > mImageSoloDisabled
Definition: MixerBoard.h:245
anonymous_namespace{TimeTrack.cpp}::GetRate
double GetRate()
Definition: TimeTrack.cpp:175
AButton::SetAlternateIdx
void SetAlternateIdx(unsigned idx)
Definition: AButton.cpp:320
AButton::PushDown
void PushDown()
Definition: AButton.cpp:597
WaveTrack::SetGain
void SetGain(float newGain)
Definition: WaveTrack.cpp:474
DB_SLIDER
#define DB_SLIDER
Definition: ASlider.h:33
kLeftSideStackWidth
const int kLeftSideStackWidth
Definition: MixerBoard.cpp:142
MixerTrackCluster::UpdateForStateChange
void UpdateForStateChange()
Definition: MixerBoard.cpp:468
ID_BITMAPBUTTON_MUSICAL_INSTRUMENT
@ ID_BITMAPBUTTON_MUSICAL_INSTRUMENT
Definition: MixerBoard.cpp:147
TRACK_NAME_HEIGHT
const int TRACK_NAME_HEIGHT
Definition: MixerBoard.cpp:137
AColor::MediumTrackInfo
static void MediumTrackInfo(wxDC *dc, bool selected)
Definition: AColor.cpp:344
MixerBoard::mImageMuteUp
std::unique_ptr< wxImage > mImageMuteUp
Definition: MixerBoard.h:243
ProjectHistory::PushState
void PushState(const TranslatableString &desc, const TranslatableString &shortDesc)
Definition: ProjectHistory.cpp:90
wxPanelWrapper::SetName
void SetName()
Definition: wxPanelWrapper.cpp:61
AColor::Bevel
static void Bevel(wxDC &dc, bool up, const wxRect &r)
Definition: AColor.cpp:191
auStaticText
is like wxStaticText, except it can be themed. wxStaticText can't be.
Definition: Theme.h:183
MixerBoard::mImageMuteDown
std::unique_ptr< wxImage > mImageMuteDown
Definition: MixerBoard.h:243
ProjectSettings::IsSoloSimple
bool IsSoloSimple() const
Definition: ProjectSettings.h:128
MixerTrackCluster::mBitmapButton_MusicalInstrument
wxBitmapButton * mBitmapButton_MusicalInstrument
Definition: MixerBoard.h:136
TrackUtilities::DoTrackMute
void DoTrackMute(AudacityProject &project, Track *t, bool exclusive)
Definition: TrackUtilities.cpp:64
WaveTrack::SetPan
void SetPan(float newPan) override
Definition: WaveTrack.cpp:487
_
#define _(s)
Definition: Internat.h:75
sampleCount
Positions or offsets within audio files need a wide type.
Definition: SampleCount.h:18
MixerBoard::mImageSoloOver
std::unique_ptr< wxImage > mImageSoloOver
Definition: MixerBoard.h:245
MixerTrackCluster::mSlider_Pan
MixerTrackSlider * mSlider_Pan
Definition: MixerBoard.h:139
MeterPanel
MeterPanel is a panel that paints the meter used for monitoring or playback.
Definition: MeterPanel.h:97
wxPanelWrapper::wxPanelWrapper
wxPanelWrapper()
Definition: wxPanelWrapper.h:44
Verbatim
TranslatableString Verbatim(wxString str)
Require calls to the one-argument constructor to go through this distinct global function name.
Definition: TranslatableString.h:321
UndoPush::CONSOLIDATE
@ CONSOLIDATE
ThemeBase::Colour
wxColour & Colour(int iIndex)
Definition: Theme.cpp:1197
PAN_HEIGHT
const int PAN_HEIGHT
Definition: MixerBoard.cpp:140
kInset
const int kInset
Definition: MixerBoard.cpp:132
MixerTrackCluster::HandleSelect
void HandleSelect(bool bShiftDown, bool bControlDown)
Definition: MixerBoard.cpp:677
AButton::SetToolTip
void SetToolTip(const TranslatableString &toolTip)
Definition: AButton.cpp:269
theTheme
AUDACITY_DLL_API Theme theTheme
Definition: Theme.cpp:203
ProjectSettings::IsSoloNone
bool IsSoloNone() const
Definition: ProjectSettings.h:129
WaveTrack::GetChannelGain
float GetChannelGain(int channel) const
Definition: WaveTrack.cpp:500
ProjectWindow::RedrawProject
void RedrawProject(const bool bForceWaveTracks=false)
Definition: ProjectWindow.cpp:710
SelectUtilities::DoListSelection
void DoListSelection(AudacityProject &project, Track *t, bool shift, bool ctrl, bool modifyState)
Definition: SelectUtilities.cpp:113
anonymous_namespace{wxWidgetsBasicUI.cpp}::GetParent
wxWindow * GetParent(const BasicUI::WindowPlacement &placement)
Definition: wxWidgetsBasicUI.cpp:39
MixerTrackCluster::HandleSliderGain
void HandleSliderGain(const bool bWantPushState=false)
Definition: MixerBoard.cpp:412
MixerTrackSlider
Definition: MixerBoard.h:39
safenew
#define safenew
Definition: MemoryX.h:10
MixerBoard::HasSolo
bool HasSolo()
Definition: MixerBoard.cpp:1122
WaveTrack::GetFloats
bool GetFloats(float *buffer, sampleCount start, size_t len, fillFormat fill=fillZero, bool mayThrow=true, sampleCount *pNumWithinClips=nullptr) const
Retrieve samples from a track in floating-point format, regardless of the storage format.
Definition: WaveTrack.h:265
ArrayOf< float >
ID_SLIDER_GAIN
@ ID_SLIDER_GAIN
Definition: MixerBoard.cpp:149
MixerTrackCluster::mToggleButton_Solo
AButton * mToggleButton_Solo
Definition: MixerBoard.h:138
TrackPanel::RefreshTrack
void RefreshTrack(Track *trk, bool refreshbacking=true)
Definition: TrackPanel.cpp:755
ProjectHistory::Get
static ProjectHistory & Get(AudacityProject &project)
Definition: ProjectHistory.cpp:26
MixerTrackCluster::mTrack
std::shared_ptr< PlayableTrack > mTrack
Definition: MixerBoard.h:128
ASlider::Options::Style
Options & Style(int s)
Definition: ASlider.h:250
ID_SLIDER_PAN
@ ID_SLIDER_PAN
Definition: MixerBoard.cpp:148