Audacity  3.2.0
ShuttleGui.cpp
Go to the documentation of this file.
1 /**********************************************************************
2 
3  Audacity: A Digital Audio Editor
4 
5  ShuttleGui.cpp
6 
7  James Crook
8 
9  Audacity is free software.
10  This file is licensed under the wxWidgets license, see License.txt
11 
12 **********************************************************************//***************************************************************//***************************************************************//***************************************************************//******************************************************************/
94 
95 
96 
97 #include "ShuttleGui.h"
98 
99 
100 
101 #include "MemoryX.h"
102 #include "Prefs.h"
103 #include "ShuttlePrefs.h"
104 #include "Theme.h"
105 
106 #include <wx/setup.h> // for wxUSE_* macros
107 #include <wx/wx.h>
108 #include <wx/wxprec.h>
109 #include <wx/grid.h>
110 #include <wx/listctrl.h>
111 #include <wx/notebook.h>
112 #include <wx/simplebook.h>
113 #include <wx/treectrl.h>
114 #include <wx/spinctrl.h>
115 #include <wx/stattext.h>
116 #include <wx/bmpbuttn.h>
117 #include <wx/wrapsizer.h>
118 
119 #include "ComponentInterface.h"
120 #include "widgets/ReadOnlyText.h"
121 #include "widgets/wxPanelWrapper.h"
123 #include "AllThemeResources.h"
124 
125 #if wxUSE_ACCESSIBILITY
127 #endif
128 
130  wxWindow * pParent, teShuttleMode ShuttleMode, bool vertical, wxSize minSize )
131  : mpDlg{ pParent }
132 {
133  wxASSERT( (pParent != NULL ) || ( ShuttleMode != eIsCreating));
134  mpbOptionalFlag = nullptr;
135  mpParent = pParent;
136  mShuttleMode = ShuttleMode;
137  Init( vertical, minSize );
138 }
139 
141 {
142 }
143 
144 void ShuttleGuiBase::Init(bool vertical, wxSize minSize)
145 {
146  mpShuttle = NULL;
147  mpSizer = NULL;
148  mpWind = NULL;
149  mpSubSizer = NULL;
150 
151  mRadioSettingName = wxT("");
152  mRadioCount = -1;
153 
154  miBorder = 5;
155  miProp=0;
156  miPropSetByUser=-1;
157  miSizerProp=0;
158  mSizerDepth=-1;
159 
160  ResetId();
161 
162  miNoMatchSelector = 0;
163 
164  if( mShuttleMode != eIsCreating )
165  return;
166 
167  mpSizer = mpParent->GetSizer();
168 
169 #if 0
170  if( mpSizer == NULL )
171  {
172  wxWindow * pGrandParent = mpParent->GetParent();
173  if( pGrandParent )
174  {
175  mpSizer = pGrandParent->GetSizer();
176  }
177  }
178 #endif
179 
180  if( !mpSizer )
181  {
182  mpParent->SetSizer(
183  mpSizer = safenew wxBoxSizer(vertical ? wxVERTICAL : wxHORIZONTAL));
184  }
185  PushSizer();
186  mpSizer->SetMinSize(minSize);
187 }
188 
190 {
191  miIdSetByUser = -1;
192  miId = -1;
193  miIdNext = 3000;
194 }
195 
196 
197 int ShuttleGuiBase::GetBorder() const noexcept
198 {
199  return miBorder;
200 }
201 
204 {
205  if( mShuttleMode != eIsCreating )
206  return;
207  wxFlexGridSizer *pSizer = wxDynamicCast(mpSizer, wxFlexGridSizer);
208  wxASSERT( pSizer );
209  pSizer->AddGrowableCol( i, 1 );
210 }
211 
214 {
215  if( mShuttleMode != eIsCreating )
216  return;
217  wxFlexGridSizer *pSizer = wxDynamicCast(mpSizer, wxFlexGridSizer);
218  wxASSERT( pSizer );
219  pSizer->AddGrowableRow( i, 1 );
220 }
221 
222 
223 //---- Add Functions.
224 
226 {
227  // If creating, will be handled by an AddPrompt.
228  if( mShuttleMode == eIsCreating )
229  return;
230  //wxLogDebug( "Optionality: [%s] Id:%i (%i)", Prompt.c_str(), miId, miIdSetByUser ) ;
231  if( mpbOptionalFlag ){
232  bool * pVar = mpbOptionalFlag;
233  mpbOptionalFlag = nullptr;
234  TieCheckBox( Prompt, *pVar);
235  }
236 }
237 
239 void ShuttleGuiBase::AddPrompt(const TranslatableString &Prompt, int wrapWidth)
240 {
241  if( mShuttleMode != eIsCreating )
242  return;
243  //wxLogDebug( "Prompt: [%s] Id:%i (%i)", Prompt.c_str(), miId, miIdSetByUser ) ;
244  if( mpbOptionalFlag ){
245  bool * pVar = mpbOptionalFlag;
246  mpbOptionalFlag = nullptr;
247  TieCheckBox( {}, *pVar);
248  //return;
249  }
250  if( Prompt.empty() )
251  return;
252  miProp=1;
253  const auto translated = Prompt.Translation();
254  auto text = safenew wxStaticText(GetParent(), -1, translated, wxDefaultPosition, wxDefaultSize,
255  GetStyle( wxALIGN_RIGHT ));
256  mpWind = text;
257  if (wrapWidth > 0)
258  text->Wrap(wrapWidth);
259  mpWind->SetName(wxStripMenuCodes(translated)); // fix for bug 577 (NVDA/Narrator screen readers do not read static text in dialogs)
260  UpdateSizersCore( false, wxALL | wxALIGN_CENTRE_VERTICAL, true );
261 }
262 
264 void ShuttleGuiBase::AddUnits(const TranslatableString &Prompt, int wrapWidth)
265 {
266  if( Prompt.empty() )
267  return;
268  if( mShuttleMode != eIsCreating )
269  return;
270  miProp = 1;
271  const auto translated = Prompt.Translation();
272  auto text = safenew wxStaticText(GetParent(), -1, translated, wxDefaultPosition, wxDefaultSize,
273  GetStyle( wxALIGN_LEFT ));
274  mpWind = text;
275  if (wrapWidth > 0)
276  text->Wrap(wrapWidth);
277  mpWind->SetName(translated); // fix for bug 577 (NVDA/Narrator screen readers do not read static text in dialogs)
278  UpdateSizersCore( false, wxALL | wxALIGN_CENTRE_VERTICAL );
279 }
280 
282 void ShuttleGuiBase::AddTitle(const TranslatableString &Prompt, int wrapWidth)
283 {
284  if( Prompt.empty() )
285  return;
286  if( mShuttleMode != eIsCreating )
287  return;
288  const auto translated = Prompt.Translation();
289  auto text = safenew wxStaticText(GetParent(), -1, translated, wxDefaultPosition, wxDefaultSize,
290  GetStyle( wxALIGN_CENTRE ));
291  mpWind = text;
292  if (wrapWidth > 0)
293  text->Wrap(wrapWidth);
294  mpWind->SetName(translated); // fix for bug 577 (NVDA/Narrator screen readers do not read static text in dialogs)
295  UpdateSizers();
296 }
297 
300 wxWindow* ShuttleGuiBase::AddWindow(wxWindow* pWindow, int PositionFlags)
301 {
302  if( mShuttleMode != eIsCreating )
303  return pWindow;
304  mpWind = pWindow;
305  SetProportions( 0 );
306  UpdateSizersCore(false, PositionFlags | wxALL);
307  return pWindow;
308 }
309 
310 wxCheckBox * ShuttleGuiBase::AddCheckBox( const TranslatableString &Prompt, bool Selected)
311 {
312  HandleOptionality( Prompt );
313  auto realPrompt = Prompt.Translation();
314  if( mpbOptionalFlag )
315  {
316  AddPrompt( {} );
317  //realPrompt = wxT("");
318  }
319 
320  UseUpId();
321  if( mShuttleMode != eIsCreating )
322  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxCheckBox);
323  wxCheckBox * pCheckBox;
324  miProp=0;
325  mpWind = pCheckBox = safenew wxCheckBox(GetParent(), miId, realPrompt, wxDefaultPosition, wxDefaultSize,
326  GetStyle( 0 ));
327  pCheckBox->SetValue(Selected);
328  if (realPrompt.empty()) {
329  // NVDA 2018.3 does not read controls which are buttons, check boxes or radio buttons which have
330  // an accessibility name which is empty. Bug 1980.
331 #if wxUSE_ACCESSIBILITY
332  // so that name can be set on a standard control
333  pCheckBox->SetAccessible(safenew WindowAccessible(pCheckBox));
334 #endif
335  pCheckBox->SetName(wxT("\a")); // non-empty string which screen readers do not read
336  }
337  UpdateSizers();
338  return pCheckBox;
339 }
340 
344 wxCheckBox * ShuttleGuiBase::AddCheckBoxOnRight( const TranslatableString &Prompt, bool Selected)
345 {
346  HandleOptionality( Prompt );
347  AddPrompt( Prompt );
348  UseUpId();
349  if( mShuttleMode != eIsCreating )
350  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxCheckBox);
351  wxCheckBox * pCheckBox;
352  miProp=0;
353  mpWind = pCheckBox = safenew wxCheckBox(GetParent(), miId, wxT(""), wxDefaultPosition, wxDefaultSize,
354  GetStyle( 0 ));
355  pCheckBox->SetValue(Selected);
356  pCheckBox->SetName(Prompt.Stripped().Translation());
357  UpdateSizers();
358  return pCheckBox;
359 }
360 
362  const TranslatableString &Text, int PositionFlags, bool setDefault)
363 {
364  UseUpId();
365  if( mShuttleMode != eIsCreating )
366  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxButton);
367  wxButton * pBtn;
368  const auto translated = Text.Translation();
369  mpWind = pBtn = safenew wxButton(GetParent(), miId,
370  translated, wxDefaultPosition, wxDefaultSize,
371  GetStyle( 0 ) );
372  mpWind->SetName(wxStripMenuCodes(translated));
373  miProp=0;
374  UpdateSizersCore(false, PositionFlags | wxALL);
375  if (setDefault)
376  pBtn->SetDefault();
377  return pBtn;
378 }
379 
381  const wxBitmap &Bitmap, int PositionFlags, bool setDefault)
382 {
383  UseUpId();
384  if( mShuttleMode != eIsCreating )
385  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxBitmapButton);
386  wxBitmapButton * pBtn;
387  mpWind = pBtn = safenew wxBitmapButton(GetParent(), miId, Bitmap,
388  wxDefaultPosition, wxDefaultSize, GetStyle( wxBU_AUTODRAW ) );
389  pBtn->SetBackgroundColour(
390  wxColour( 246,246,243));
391 // wxSystemSettings::GetColour(wxSYS_COLOUR_BTNFACE));
392  miProp=0;
393  UpdateSizersCore(false, PositionFlags | wxALL);
394  if (setDefault)
395  pBtn->SetDefault();
396  return pBtn;
397 }
398 
400  const TranslatableStrings &choices, int Selected )
401 {
402  HandleOptionality( Prompt );
403  AddPrompt( Prompt );
404  UseUpId();
405  if( mShuttleMode != eIsCreating )
406  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxChoice);
407  wxChoice * pChoice;
408  miProp=0;
409 
410  mpWind = pChoice = safenew wxChoice(
411  GetParent(),
412  miId,
413  wxDefaultPosition,
414  wxDefaultSize,
415  transform_container<wxArrayString>(
416  choices, std::mem_fn( &TranslatableString::StrippedTranslation ) ),
417  GetStyle( 0 ) );
418 
419  pChoice->SetMinSize( { 180, -1 } );// Use -1 for 'default size' - Platform specific.
420 #ifdef __WXMAC__
421 #if wxUSE_ACCESSIBILITY
422  // so that name can be set on a standard control
423  mpWind->SetAccessible(safenew WindowAccessible(mpWind));
424 #endif
425 #endif
426  pChoice->SetName(Prompt.Stripped().Translation());
427  if ( Selected >= 0 && Selected < (int)choices.size() )
428  pChoice->SetSelection( Selected );
429 
430  UpdateSizers();
431  return pChoice;
432 }
433 
435  const TranslatableStrings &choices, const TranslatableString &Selected )
436 {
437  return AddChoice(
438  Prompt, choices, make_iterator_range( choices ).index( Selected ) );
439 }
440 
442  const TranslatableString &Str, bool bCenter, int wrapWidth)
443 {
444  const auto translated = Str.Translation();
445  UseUpId();
446  if( mShuttleMode != eIsCreating )
447  return;
448  auto text = safenew wxStaticText(GetParent(),
449  miId, translated, wxDefaultPosition, wxDefaultSize,
450  GetStyle( wxALIGN_LEFT ));
451  mpWind = text;
452  if ( wrapWidth > 0 )
453  text->Wrap( wrapWidth );
454  mpWind->SetName(wxStripMenuCodes(translated)); // fix for bug 577 (NVDA/Narrator screen readers do not read static text in dialogs)
455  if( bCenter )
456  {
457  miProp=1;
458  UpdateSizersC();
459  }
460  else
461  UpdateSizers();
462 }
463 
465  const TranslatableString &Str,
466  bool bCenter, int PositionFlags, int wrapWidth )
467 {
468  const auto translated = Str.Translation();
469  UseUpId();
470  if( mShuttleMode != eIsCreating )
471  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxStaticText);
472 
473  wxStaticText *pStatic;
474  auto text = pStatic = safenew wxStaticText(GetParent(), miId, translated,
475  wxDefaultPosition, wxDefaultSize,
476  GetStyle( wxALIGN_LEFT ));
477  mpWind = text;
478  if ( wrapWidth > 0 )
479  text->Wrap( wrapWidth );
480  mpWind->SetName(wxStripMenuCodes(translated)); // fix for bug 577 (NVDA/Narrator screen readers do not read static text in dialogs)
481  if( bCenter )
482  {
483  miProp=1;
484  if( PositionFlags )
485  UpdateSizersCore( false, PositionFlags );
486  else
487  UpdateSizersC();
488  }
489  else
490  if( PositionFlags )
491  UpdateSizersCore( false, PositionFlags );
492  else
493  UpdateSizers();
494  return pStatic;
495 }
496 
498  const TranslatableString &Caption, const wxString &Value)
499 {
500  const auto translated = Caption.Translation();
501  auto style = GetStyle( wxBORDER_NONE );
502  HandleOptionality( Caption );
503  mItem.miStyle = wxALIGN_CENTER_VERTICAL;
504  AddPrompt( Caption );
505  UseUpId();
506  if( mShuttleMode != eIsCreating )
507  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), ReadOnlyText);
508  ReadOnlyText * pReadOnlyText;
509  miProp=0;
510 
511  mpWind = pReadOnlyText = safenew ReadOnlyText(GetParent(), miId, Value,
512  wxDefaultPosition, wxDefaultSize, GetStyle( style ));
513  mpWind->SetName(wxStripMenuCodes(translated));
514  UpdateSizers();
515  return pReadOnlyText;
516 }
517 
519  const TranslatableString &Prompt,
520  const wxString &Selected, const wxArrayStringEx & choices )
521 {
522  const auto translated = Prompt.Translation();
523  HandleOptionality( Prompt );
524  AddPrompt( Prompt );
525  UseUpId();
526  if( mShuttleMode != eIsCreating )
527  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxComboBox);
528  wxComboBox * pCombo;
529  miProp=0;
530 
531  int n = choices.size();
532  if( n>50 ) n=50;
533  int i;
534  wxString Choices[50];
535  for(i=0;i<n;i++)
536  {
537  Choices[i] = choices[i];
538  }
539 
540  mpWind = pCombo = safenew wxComboBox(GetParent(), miId, Selected, wxDefaultPosition, wxDefaultSize,
541  n, Choices, GetStyle( 0 ));
542  mpWind->SetName(wxStripMenuCodes(translated));
543 
544  UpdateSizers();
545  return pCombo;
546 }
547 
548 
550  const TranslatableString &Prompt, int style, int selector, int initValue)
551 {
552  const auto translated = Prompt.Translation();
555  UseUpId();
556  if( mShuttleMode != eIsCreating )
557  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxRadioButton);
558  wxRadioButton * pRad;
559  mpWind = pRad = safenew wxRadioButton(GetParent(), miId, translated,
560  wxDefaultPosition, wxDefaultSize, GetStyle( style ) );
561  mpWind->SetName(wxStripMenuCodes(translated));
562  if ( style )
563  pRad->SetValue( true );
564  UpdateSizers();
565  pRad->SetValue( selector == initValue );
566  return pRad;
567 }
568 
570  const TranslatableString &Prompt, int selector, int initValue)
571 {
572  return DoAddRadioButton( Prompt, wxRB_GROUP, selector, initValue );
573 }
574 
576  const TranslatableString &Prompt, int selector, int initValue)
577 {
578  return DoAddRadioButton( Prompt, 0, selector, initValue );
579 }
580 
581 #ifdef __WXMAC__
582 void wxSliderWrapper::SetFocus()
583 {
584  // bypassing the override in wxCompositeWindow<wxSliderBase> which ends up
585  // doing nothing
586  return wxSliderBase::SetFocus();
587 }
588 #endif
589 
591  const TranslatableString &Prompt, int pos, int Max, int Min)
592 {
593  HandleOptionality( Prompt );
594  AddPrompt( Prompt );
595  UseUpId();
596  if( mShuttleMode != eIsCreating )
597  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxSlider);
598  wxSlider * pSlider;
600  pos, Min, Max,
601  wxDefaultPosition,
602  // Bug2289: On Linux at least, sliders like to be constructed with the
603  // proper size, not reassigned size later
604  ( ( mItem.mWindowSize == wxSize{} ) ? wxDefaultSize : mItem.mWindowSize ),
605  GetStyle( wxSL_HORIZONTAL | wxSL_LABELS | wxSL_AUTOTICKS )
606  );
607 #if wxUSE_ACCESSIBILITY
608  // so that name can be set on a standard control
609  mpWind->SetAccessible(safenew WindowAccessible(mpWind));
610 #endif
611  mpWind->SetName(wxStripMenuCodes(Prompt.Translation()));
612  miProp=1;
613  UpdateSizers();
614  return pSlider;
615 }
616 
618  const TranslatableString &Prompt, int Value, int Max, int Min)
619 {
620  const auto translated = Prompt.Translation();
621  HandleOptionality( Prompt );
622  AddPrompt( Prompt );
623  UseUpId();
624  if( mShuttleMode != eIsCreating )
625  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxSpinCtrl);
626  wxSpinCtrl * pSpinCtrl;
627  mpWind = pSpinCtrl = safenew wxSpinCtrl(GetParent(), miId,
628  wxEmptyString,
629  wxDefaultPosition, wxDefaultSize,
630  GetStyle( wxSP_VERTICAL | wxSP_ARROW_KEYS ),
631  Min, Max, Value
632  );
633  mpWind->SetName(wxStripMenuCodes(translated));
634  miProp=1;
635  UpdateSizers();
636  return pSpinCtrl;
637 }
638 
640  const TranslatableString &Caption, const wxString &Value, const int nChars)
641 {
642  const auto translated = Caption.Translation();
643  HandleOptionality( Caption );
644  AddPrompt( Caption );
645  UseUpId();
646  if( mShuttleMode != eIsCreating )
647  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxTextCtrl);
648  wxTextCtrl * pTextCtrl;
649  wxSize Size(wxDefaultSize);
650  if( nChars > 0 )
651  {
652  int width;
653  mpDlg->GetTextExtent( wxT("9"), &width, nullptr );
654  Size.SetWidth( nChars * width );
655  }
656  miProp=0;
657 
658 #ifdef EXPERIMENTAL_RIGHT_ALIGNED_TEXTBOXES
659  long flags = wxTE_RIGHT;
660 #else
661  long flags = wxTE_LEFT;
662 #endif
663 
664  mpWind = pTextCtrl = safenew wxTextCtrlWrapper(GetParent(), miId, Value,
665  wxDefaultPosition, Size, GetStyle( flags ));
666 #if wxUSE_ACCESSIBILITY
667  // so that name can be set on a standard control
668  mpWind->SetAccessible(safenew WindowAccessible(mpWind));
669 #endif
670  mpWind->SetName(wxStripMenuCodes(translated));
671  UpdateSizers();
672  return pTextCtrl;
673 }
674 
676  const TranslatableString &Caption, const wxString &Value, const int nChars)
677 {
678  const auto translated = Caption.Translation();
679  HandleOptionality( Caption );
680  AddPrompt( Caption );
681  UseUpId();
682  if( mShuttleMode != eIsCreating )
683  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxTextCtrl);
684  wxTextCtrl * pTextCtrl;
685  wxSize Size(wxDefaultSize);
686  if( nChars > 0 )
687  {
688  Size.SetWidth( nChars *5 );
689  }
690  miProp=0;
691 
692 #ifdef EXPERIMENTAL_RIGHT_ALIGNED_TEXTBOXES
693  long flags = wxTE_RIGHT;
694 #else
695  long flags = wxTE_LEFT;
696 #endif
697 
698  wxTextValidator Validator(wxFILTER_NUMERIC);
699  mpWind = pTextCtrl = safenew wxTextCtrl(GetParent(), miId, Value,
700  wxDefaultPosition, Size, GetStyle( flags ),
701  Validator // It's OK to pass this. It will be cloned.
702  );
703 #if wxUSE_ACCESSIBILITY
704  // so that name can be set on a standard control
705  mpWind->SetAccessible(safenew WindowAccessible(mpWind));
706 #endif
707  mpWind->SetName(wxStripMenuCodes(translated));
708  UpdateSizers();
709  return pTextCtrl;
710 }
711 
713 wxTextCtrl * ShuttleGuiBase::AddTextWindow(const wxString &Value)
714 {
715  UseUpId();
716  if( mShuttleMode != eIsCreating )
717  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxTextCtrl);
718  wxTextCtrl * pTextCtrl;
719  SetProportions( 1 );
720  mpWind = pTextCtrl = safenew wxTextCtrl(GetParent(), miId, Value,
721  wxDefaultPosition, wxDefaultSize, GetStyle( wxTE_MULTILINE ));
722 #if wxUSE_ACCESSIBILITY
723  // so that name can be set on a standard control
724  mpWind->SetAccessible(safenew WindowAccessible(mpWind));
725 #endif
726  UpdateSizers();
727  // Start off at start of window...
728  pTextCtrl->SetInsertionPoint( 0 );
729  pTextCtrl->ShowPosition( 0 );
730  return pTextCtrl;
731 }
732 
735  const TranslatableString &Prompt, const TranslatableString &Value)
736 {
737  HandleOptionality( Prompt );
738  AddPrompt( Prompt );
739  UseUpId();
740  if( mShuttleMode != eIsCreating )
741  return;
742 // return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wx);
743  miProp=0;
744  UpdateSizers();
745  miProp=0;
746  const auto translatedValue = Value.Translation();
747  mpWind = safenew wxStaticText(GetParent(), miId,
748  translatedValue, wxDefaultPosition, wxDefaultSize,
749  GetStyle( 0 ));
750  mpWind->SetName(translatedValue); // fix for bug 577 (NVDA/Narrator screen readers do not read static text in dialogs)
751  UpdateSizers();
752 }
753 
754 wxListBox * ShuttleGuiBase::AddListBox(const wxArrayStringEx &choices)
755 {
756  UseUpId();
757  if( mShuttleMode != eIsCreating )
758  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxListBox);
759  wxListBox * pListBox;
760  SetProportions( 1 );
761  mpWind = pListBox = safenew wxListBox(GetParent(), miId,
762  wxDefaultPosition, wxDefaultSize, choices, GetStyle(0));
763  pListBox->SetMinSize( wxSize( 120,150 ));
764  UpdateSizers();
765  return pListBox;
766 }
767 
768 
770 {
771  UseUpId();
772  if( mShuttleMode != eIsCreating )
773  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxGrid);
774  wxGrid * pGrid;
775  SetProportions( 1 );
776  mpWind = pGrid = safenew wxGrid(GetParent(), miId, wxDefaultPosition,
777  wxDefaultSize, GetStyle( wxWANTS_CHARS ));
778  pGrid->SetMinSize( wxSize( 120, 150 ));
779  UpdateSizers();
780  return pGrid;
781 }
782 
784  std::initializer_list<const ListControlColumn> columns,
785  long listControlStyles
786 )
787 {
788  UseUpId();
789  if( mShuttleMode != eIsCreating )
790  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxListCtrl);
791  wxListCtrl * pListCtrl;
792  SetProportions( 1 );
793  mpWind = pListCtrl = safenew wxListCtrl(GetParent(), miId,
794  wxDefaultPosition, wxDefaultSize, GetStyle( wxLC_ICON ));
795  pListCtrl->SetMinSize( wxSize( 120,150 ));
796  UpdateSizers();
797 
798  DoInsertListColumns( pListCtrl, listControlStyles, columns );
799 
800  return pListCtrl;
801 }
802 
804  std::initializer_list<const ListControlColumn> columns,
805  long listControlStyles
806 )
807 {
808  UseUpId();
809  if( mShuttleMode != eIsCreating )
810  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxListCtrl);
811  wxListCtrl * pListCtrl;
812  SetProportions( 1 );
813  mpWind = pListCtrl = safenew wxListCtrl(GetParent(), miId,
814  wxDefaultPosition, wxSize(230,120),//wxDefaultSize,
815  GetStyle( wxLC_REPORT | wxLC_HRULES | wxLC_VRULES | wxSUNKEN_BORDER ));
816 // pListCtrl->SetMinSize( wxSize( 120,150 ));
817  UpdateSizers();
818 
819  DoInsertListColumns( pListCtrl, listControlStyles, columns );
820 
821  return pListCtrl;
822 }
823 
825  wxListCtrl *pListCtrl,
826  long listControlStyles,
827  std::initializer_list<const ListControlColumn> columns )
828 {
829  // Old comment from HistoryWindow.cpp follows
830  // -- is it still correct for wxWidgets 3?
831 
832  // Do this BEFORE inserting the columns. On the Mac at least, the
833  // columns are deleted and later InsertItem()s will cause Audacity to crash.
834  for ( auto style = 1l; style <= listControlStyles; style <<= 1 )
835  if ( (style & listControlStyles) )
836  pListCtrl->SetSingleStyle(style, true);
837 
838  long iCol = 0;
839  bool dummyColumn =
840  columns.size() > 0 && begin(columns)->format == wxLIST_FORMAT_RIGHT;
841 
842  //A dummy first column, which is then deleted, is a workaround -
843  // under Windows the first column can't be right aligned.
844  if (dummyColumn)
845  pListCtrl->InsertColumn( iCol++, wxString{} );
846 
847  for (auto &column : columns)
848  pListCtrl->InsertColumn(
849  iCol++, column.heading.Translation(), column.format, column.width );
850 
851  if (dummyColumn)
852  pListCtrl->DeleteColumn( 0 );
853 }
854 
856 {
857  UseUpId();
858  if( mShuttleMode != eIsCreating )
859  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxTreeCtrl);
860  wxTreeCtrl * pTreeCtrl;
861  SetProportions( 1 );
862  mpWind = pTreeCtrl = safenew wxTreeCtrl(GetParent(), miId, wxDefaultPosition, wxDefaultSize,
863  GetStyle( wxTR_HAS_BUTTONS ));
864  pTreeCtrl->SetMinSize( wxSize( 120,650 ));
865  UpdateSizers();
866  return pTreeCtrl;
867 }
868 
869 void ShuttleGuiBase::AddIcon(wxBitmap *pBmp)
870 {
871  UseUpId();
872  if( mShuttleMode != eIsCreating )
873 // return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wx);
874  return;
875  wxBitmapButton * pBtn;
876  mpWind = pBtn = safenew wxBitmapButton(GetParent(), miId, *pBmp,
877  wxDefaultPosition, wxDefaultSize, GetStyle( wxBU_AUTODRAW ) );
878  pBtn->SetWindowStyle( wxBORDER_NONE );
879  pBtn->SetCanFocus(false);
880  UpdateSizersC();
881 }
882 
884 {
885  miPropSetByUser = iProp;
886  return *this;
887 }
888 
894 wxStaticBox * ShuttleGuiBase::StartStatic(const TranslatableString &Str, int iProp)
895 {
896  UseUpId();
897  if( mShuttleMode != eIsCreating )
898  return NULL;
899  auto translated = Str.Translation();
900  wxStaticBox * pBox = safenew wxStaticBoxWrapper(
901  GetParent(), miId, translated );
902  pBox->SetLabel( translated );
903  if (Str.empty()) {
904  // NVDA 2018.3 or later does not read the controls in a group box which has
905  // an accessibility name which is empty. Bug 2169.
906 #if wxUSE_ACCESSIBILITY
907  // so that name can be set on a standard control
908  pBox->SetAccessible(safenew WindowAccessible(pBox));
909 #endif
910  pBox->SetName(wxT("\a")); // non-empty string which screen readers do not read
911  }
912  else
913  pBox->SetName( wxStripMenuCodes( translated ) );
914  mpSubSizer = std::make_unique<wxStaticBoxSizer>(
915  pBox,
916  wxVERTICAL );
917  miSizerProp = iProp;
918  UpdateSizers();
919  mpParent = pBox;
920  return pBox;
921 }
922 
924 {
925  if( mShuttleMode != eIsCreating )
926  return;
927  PopSizer();
928  mpParent = mpParent->GetParent();
929 }
930 
939 wxScrolledWindow * ShuttleGuiBase::StartScroller(int iStyle)
940 {
941  UseUpId();
942  if( mShuttleMode != eIsCreating )
943  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxScrolledWindow);
944 
945  wxScrolledWindow * pScroller;
946  mpWind = pScroller = safenew wxScrolledWindow(GetParent(), miId, wxDefaultPosition, wxDefaultSize,
947  GetStyle( wxSUNKEN_BORDER ) );
948  pScroller->SetScrollRate( 20,20 );
949 
950  // This fools NVDA into not saying "Panel" when the dialog gets focus
951  pScroller->SetName(wxT("\a"));
952  pScroller->SetLabel(wxT("\a"));
953 
954  SetProportions( 1 );
955  if( iStyle==2 )
956  {
958  }
959  else
960  {
961  // mpWind->SetBackgroundColour(wxSystemSettings::GetColour(wxSYS_COLOUR_MENUBAR));
962  UpdateSizers(); // adds window in to current sizer.
963  }
964 
965  // create a sizer within the window...
966  mpParent = pScroller;
967  pScroller->SetSizer(mpSizer = safenew wxBoxSizer(wxVERTICAL));
968  PushSizer();
969  return pScroller;
970 }
971 
973 {
974  if( mShuttleMode != eIsCreating )
975  return;
976  wxSize ScrollSize = mpSizer->GetMinSize();
977  int yMin = ScrollSize.y+4;
978  int xMin = ScrollSize.x+4;
979  if( yMin > 400)
980  {
981  yMin = 400;
982  xMin+=50;// extra space for vertical scrollbar.
983  }
984 
985  mpParent->SetMinSize( wxSize(xMin, yMin) );
986 
987  PopSizer();
988  mpParent = mpParent->GetParent();
989 }
990 
991 wxPanel * ShuttleGuiBase::StartPanel(int iStyle)
992 {
993  UseUpId();
994  if( mShuttleMode != eIsCreating )
995  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxPanel);
996  wxPanel * pPanel;
997  mpWind = pPanel = safenew wxPanelWrapper( GetParent(), miId, wxDefaultPosition, wxDefaultSize,
998  GetStyle( wxNO_BORDER ));
999 
1000  if( iStyle != 0 )
1001  {
1002  mpWind->SetBackgroundColour(
1003  iStyle==1
1004  ? wxColour( 190,200,230) :
1005  wxSystemSettings::GetColour(wxSYS_COLOUR_WINDOW)
1006  );
1007  }
1008  SetProportions(0);
1009  miBorder=2;
1010  UpdateSizers(); // adds window in to current sizer.
1011 
1012  // create a sizer within the window...
1013  mpParent = pPanel;
1014  pPanel->SetSizer(mpSizer = safenew wxBoxSizer(wxVERTICAL));
1015  PushSizer();
1016  return pPanel;
1017 }
1018 
1020 {
1021  if( mShuttleMode != eIsCreating )
1022  return;
1023  PopSizer();
1024  mpParent = mpParent->GetParent();
1025 }
1026 
1028 {
1029  UseUpId();
1030  if( mShuttleMode != eIsCreating )
1031  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxNotebook);
1032  wxNotebook * pNotebook;
1033  mpWind = pNotebook = safenew wxNotebook(GetParent(),
1034  miId, wxDefaultPosition, wxDefaultSize, GetStyle( 0 ));
1035  SetProportions( 1 );
1036  UpdateSizers();
1037  mpParent = pNotebook;
1038  return pNotebook;
1039 }
1040 
1042 {
1043  //PopSizer();
1044  mpParent = mpParent->GetParent();
1045 }
1046 
1047 
1049 {
1050  UseUpId();
1051  if( mShuttleMode != eIsCreating )
1052  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxSimplebook);
1053  wxSimplebook * pNotebook;
1054  mpWind = pNotebook = safenew wxSimplebook(GetParent(),
1055  miId, wxDefaultPosition, wxDefaultSize, GetStyle( 0 ));
1056  SetProportions( 1 );
1057  UpdateSizers();
1058  mpParent = pNotebook;
1059  return pNotebook;
1060 }
1061 
1063 {
1064  //PopSizer();
1065  mpParent = mpParent->GetParent();
1066 }
1067 
1068 
1070  const TranslatableString & Name )
1071 {
1072  if( mShuttleMode != eIsCreating )
1073  return NULL;
1074 // return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wx);
1075  auto pNotebook = static_cast< wxBookCtrlBase* >( mpParent );
1077  const auto translated = Name.Translation();
1078  pPage->SetName(translated);
1079 
1080  pNotebook->AddPage(
1081  pPage,
1082  translated);
1083 
1084  SetProportions( 1 );
1085  mpParent = pPage;
1086  pPage->SetSizer(mpSizer = safenew wxBoxSizer(wxVERTICAL));
1087  PushSizer();
1088  // UpdateSizers();
1089  return pPage;
1090 }
1091 
1093 {
1094  if( mShuttleMode != eIsCreating )
1095  return;
1096  PopSizer();
1097  mpParent = mpParent->GetParent();
1098 }
1099 
1100 // Doxygen description is at the start of the file
1101 // this is a wxPanel with erase background disabled.
1102 class InvisiblePanel final : public wxPanelWrapper
1103 {
1104 public:
1106  wxWindow* parent,
1107  wxWindowID id = -1,
1108  const wxPoint& pos = wxDefaultPosition,
1109  const wxSize& size = wxDefaultSize,
1110  long style = wxTAB_TRAVERSAL ) :
1111  wxPanelWrapper( parent, id, pos, size, style )
1112  {
1113  };
1115  void OnPaint( wxPaintEvent &event );
1116  void OnErase(wxEraseEvent &/*evt*/){;};
1117  DECLARE_EVENT_TABLE()
1118 };
1119 
1120 
1121 BEGIN_EVENT_TABLE(InvisiblePanel, wxPanelWrapper)
1122 // EVT_PAINT(InvisiblePanel::OnPaint)
1123  EVT_ERASE_BACKGROUND( InvisiblePanel::OnErase)
1125 
1126 void InvisiblePanel::OnPaint( wxPaintEvent & WXUNUSED(event))
1127 {
1128  // Don't repaint my background.
1129  wxPaintDC dc(this);
1130  // event.Skip(); // swallow the paint event.
1131 }
1132 
1134 {
1135  UseUpId();
1136  if( mShuttleMode != eIsCreating )
1137  return wxDynamicCast(wxWindow::FindWindowById( miId, mpDlg), wxPanel);
1138  wxPanel * pPanel;
1139  mpWind = pPanel = safenew wxPanelWrapper(GetParent(), miId, wxDefaultPosition, wxDefaultSize,
1140  wxNO_BORDER);
1141 
1142  mpWind->SetBackgroundColour(
1143  wxSystemSettings::GetColour(wxSYS_COLOUR_BTNFACE)
1144  );
1145  SetProportions( 1 );
1146  miBorder=0;
1147  UpdateSizers(); // adds window in to current sizer.
1148 
1149  // create a sizer within the window...
1150  mpParent = pPanel;
1151  pPanel->SetSizer(mpSizer = safenew wxBoxSizer(wxVERTICAL));
1152  PushSizer();
1153  return pPanel;
1154 }
1155 
1157 {
1158  EndPanel();
1159 }
1160 
1161 
1168 void ShuttleGuiBase::StartHorizontalLay( int PositionFlags, int iProp)
1169 {
1170  if( mShuttleMode != eIsCreating )
1171  return;
1172  miSizerProp=iProp;
1173  mpSubSizer = std::make_unique<wxBoxSizer>( wxHORIZONTAL );
1174  // PRL: wxALL has no effect because UpdateSizersCore ignores border
1175  UpdateSizersCore( false, PositionFlags | wxALL );
1176 }
1177 
1179 {
1180  if( mShuttleMode != eIsCreating )
1181  return;
1182  PopSizer();
1183 }
1184 
1186 {
1187  if( mShuttleMode != eIsCreating )
1188  return;
1189  miSizerProp=iProp;
1190  mpSubSizer = std::make_unique<wxBoxSizer>( wxVERTICAL );
1191  UpdateSizers();
1192 }
1193 
1194 void ShuttleGuiBase::StartVerticalLay(int PositionFlags, int iProp)
1195 {
1196  if( mShuttleMode != eIsCreating )
1197  return;
1198  miSizerProp=iProp;
1199  mpSubSizer = std::make_unique<wxBoxSizer>( wxVERTICAL );
1200  // PRL: wxALL has no effect because UpdateSizersCore ignores border
1201  UpdateSizersCore( false, PositionFlags | wxALL );
1202 }
1203 
1205 {
1206  if( mShuttleMode != eIsCreating )
1207  return;
1208  PopSizer();
1209 }
1210 
1211 void ShuttleGuiBase::StartWrapLay(int PositionFlags, int iProp)
1212 {
1213  if (mShuttleMode != eIsCreating)
1214  return;
1215 
1216  miSizerProp = iProp;
1217  mpSubSizer = std::make_unique<wxWrapSizer>(wxHORIZONTAL, 0);
1218 
1219  UpdateSizersCore(false, PositionFlags | wxALL);
1220 }
1221 
1223 {
1224  if (mShuttleMode != eIsCreating)
1225  return;
1226 
1227  PopSizer();
1228 }
1229 
1230 void ShuttleGuiBase::StartMultiColumn(int nCols, int PositionFlags)
1231 {
1232  if( mShuttleMode != eIsCreating )
1233  return;
1234  mpSubSizer = std::make_unique<wxFlexGridSizer>( nCols );
1235  // PRL: wxALL has no effect because UpdateSizersCore ignores border
1236  UpdateSizersCore( false, PositionFlags | wxALL );
1237 }
1238 
1240 {
1241  if( mShuttleMode != eIsCreating )
1242  return;
1243  PopSizer();
1244 }
1245 
1248 void ShuttleGuiBase::DoDataShuttle( const wxString &Name, WrappedType & WrappedRef )
1249 {
1250  wxASSERT( mpShuttle );
1251  mpShuttle->TransferWrappedType( Name, WrappedRef );
1252 }
1253 
1254 //-----------------------------------------------------------------------//
1255 
1256 // We now have a group of tie functions which are generic in the type
1257 // they bind to (i.e. WrappedType).
1258 // The type specific versions are much shorter and are later
1259 // in this file.
1260 wxCheckBox * ShuttleGuiBase::DoTieCheckBox(const TranslatableString &Prompt, WrappedType & WrappedRef)
1261 {
1262  HandleOptionality( Prompt );
1263  // The Add function does a UseUpId(), so don't do it here in that case.
1264  if( mShuttleMode == eIsCreating )
1265  return AddCheckBox( Prompt, WrappedRef.ReadAsString() == wxT("true"));
1266 
1267  UseUpId();
1268 
1269  wxWindow * pWnd = wxWindow::FindWindowById( miId, mpDlg);
1270  wxCheckBox * pCheckBox = wxDynamicCast(pWnd, wxCheckBox);
1271 
1272  switch( mShuttleMode )
1273  {
1274  // IF setting internal storage from the controls.
1275  case eIsGettingMetadata:
1276  break;
1277  case eIsGettingFromDialog:
1278  {
1279  wxASSERT( pCheckBox );
1280  WrappedRef.WriteToAsBool( pCheckBox->GetValue() );
1281  }
1282  break;
1283  case eIsSettingToDialog:
1284  {
1285  wxASSERT( pCheckBox );
1286  pCheckBox->SetValue( WrappedRef.ReadAsBool() );
1287  }
1288  break;
1289  default:
1290  wxASSERT( false );
1291  break;
1292  }
1293  return pCheckBox;
1294 }
1295 
1297 {
1298  HandleOptionality( Prompt );
1299  // The Add function does a UseUpId(), so don't do it here in that case.
1300  if( mShuttleMode == eIsCreating )
1301  return AddCheckBoxOnRight( Prompt, WrappedRef.ReadAsString() == wxT("true"));
1302 
1303  UseUpId();
1304 
1305  wxWindow * pWnd = wxWindow::FindWindowById( miId, mpDlg);
1306  wxCheckBox * pCheckBox = wxDynamicCast(pWnd, wxCheckBox);
1307 
1308  switch( mShuttleMode )
1309  {
1310  // IF setting internal storage from the controls.
1311  case eIsGettingMetadata:
1312  break;
1313  case eIsGettingFromDialog:
1314  {
1315  wxASSERT( pCheckBox );
1316  WrappedRef.WriteToAsBool( pCheckBox->GetValue() );
1317  }
1318  break;
1319  case eIsSettingToDialog:
1320  {
1321  wxASSERT( pCheckBox );
1322  pCheckBox->SetValue( WrappedRef.ReadAsBool() );
1323  }
1324  break;
1325  default:
1326  wxASSERT( false );
1327  break;
1328  }
1329  return pCheckBox;
1330 }
1331 
1333  const TranslatableString &Prompt,
1334  WrappedType & WrappedRef, const int max, const int min )
1335 {
1336  HandleOptionality( Prompt );
1337  // The Add function does a UseUpId(), so don't do it here in that case.
1338  if( mShuttleMode == eIsCreating )
1339  return AddSpinCtrl( Prompt, WrappedRef.ReadAsInt(), max, min );
1340 
1341  UseUpId();
1342  wxSpinCtrl * pSpinCtrl=NULL;
1343 
1344  wxWindow * pWnd = wxWindow::FindWindowById( miId, mpDlg);
1345  pSpinCtrl = wxDynamicCast(pWnd, wxSpinCtrl);
1346 
1347  switch( mShuttleMode )
1348  {
1349  // IF setting internal storage from the controls.
1350  case eIsGettingMetadata:
1351  break;
1352  case eIsGettingFromDialog:
1353  {
1354  wxASSERT( pSpinCtrl );
1355  WrappedRef.WriteToAsInt( pSpinCtrl->GetValue() );
1356  }
1357  break;
1358  case eIsSettingToDialog:
1359  {
1360  wxASSERT( pSpinCtrl );
1361  pSpinCtrl->SetValue( WrappedRef.ReadAsInt() );
1362  }
1363  break;
1364  default:
1365  wxASSERT( false );
1366  break;
1367  }
1368  return pSpinCtrl;
1369 }
1370 
1372  const TranslatableString &Prompt, WrappedType & WrappedRef, const int nChars)
1373 {
1374  HandleOptionality( Prompt );
1375  // The Add function does a UseUpId(), so don't do it here in that case.
1376  if( mShuttleMode == eIsCreating )
1377  return AddTextBox( Prompt, WrappedRef.ReadAsString(), nChars );
1378 
1379  UseUpId();
1380  wxTextCtrl * pTextBox=NULL;
1381 
1382  wxWindow * pWnd = wxWindow::FindWindowById( miId, mpDlg);
1383  pTextBox = wxDynamicCast(pWnd, wxTextCtrl);
1384 
1385  switch( mShuttleMode )
1386  {
1387  // IF setting internal storage from the controls.
1388  case eIsGettingMetadata:
1389  break;
1390  case eIsGettingFromDialog:
1391  {
1392  wxASSERT( pTextBox );
1393  WrappedRef.WriteToAsString( pTextBox->GetValue() );
1394  }
1395  break;
1396  case eIsSettingToDialog:
1397  {
1398  wxASSERT( pTextBox );
1399  pTextBox->SetValue( WrappedRef.ReadAsString() );
1400  }
1401  break;
1402  default:
1403  wxASSERT( false );
1404  break;
1405  }
1406  return pTextBox;
1407 }
1408 
1410  const TranslatableString &Prompt, WrappedType & WrappedRef, const int nChars)
1411 {
1412  HandleOptionality( Prompt );
1413  // The Add function does a UseUpId(), so don't do it here in that case.
1414  if( mShuttleMode == eIsCreating )
1415  return AddNumericTextBox( Prompt, WrappedRef.ReadAsString(), nChars );
1416 
1417  UseUpId();
1418  wxTextCtrl * pTextBox=NULL;
1419 
1420  wxWindow * pWnd = wxWindow::FindWindowById( miId, mpDlg);
1421  pTextBox = wxDynamicCast(pWnd, wxTextCtrl);
1422 
1423  switch( mShuttleMode )
1424  {
1425  // IF setting internal storage from the controls.
1426  case eIsGettingMetadata:
1427  break;
1428  case eIsGettingFromDialog:
1429  {
1430  wxASSERT( pTextBox );
1431  WrappedRef.WriteToAsString( pTextBox->GetValue() );
1432  }
1433  break;
1434  case eIsSettingToDialog:
1435  {
1436  wxASSERT( pTextBox );
1437  pTextBox->SetValue( WrappedRef.ReadAsString() );
1438  }
1439  break;
1440  default:
1441  wxASSERT( false );
1442  break;
1443  }
1444  return pTextBox;
1445 }
1446 
1448  const TranslatableString &Prompt,
1449  WrappedType & WrappedRef, const int max, int min )
1450 {
1451  HandleOptionality( Prompt );
1452  // The Add function does a UseUpId(), so don't do it here in that case.
1453  if( mShuttleMode != eIsCreating )
1454  UseUpId();
1455  wxSlider * pSlider=NULL;
1456  switch( mShuttleMode )
1457  {
1458  case eIsCreating:
1459  {
1460  pSlider = AddSlider( Prompt, WrappedRef.ReadAsInt(), max, min );
1461  }
1462  break;
1463  // IF setting internal storage from the controls.
1464  case eIsGettingMetadata:
1465  break;
1466  case eIsGettingFromDialog:
1467  {
1468  wxWindow * pWnd = wxWindow::FindWindowById( miId, mpDlg);
1469  pSlider = wxDynamicCast(pWnd, wxSlider);
1470  wxASSERT( pSlider );
1471  WrappedRef.WriteToAsInt( pSlider->GetValue() );
1472  }
1473  break;
1474  case eIsSettingToDialog:
1475  {
1476  wxWindow * pWnd = wxWindow::FindWindowById( miId, mpDlg);
1477  pSlider = wxDynamicCast(pWnd, wxSlider);
1478  wxASSERT( pSlider );
1479  pSlider->SetValue( WrappedRef.ReadAsInt() );
1480  }
1481  break;
1482  default:
1483  wxASSERT( false );
1484  break;
1485  }
1486  return pSlider;
1487 }
1488 
1489 
1491  const TranslatableString &Prompt,
1492  int &Selected,
1493  const TranslatableStrings &choices )
1494 {
1495  HandleOptionality( Prompt );
1496 
1497  // The Add function does a UseUpId(), so don't do it here in that case.
1498  if( mShuttleMode != eIsCreating )
1499  UseUpId();
1500 
1501  wxChoice * pChoice=NULL;
1502  switch( mShuttleMode )
1503  {
1504  case eIsCreating:
1505  {
1506  pChoice = AddChoice( Prompt, choices, Selected );
1507  ShuttleGui::SetMinSize(pChoice, choices);
1508  }
1509  break;
1510  // IF setting internal storage from the controls.
1511  case eIsGettingMetadata:
1512  break;
1513  case eIsGettingFromDialog:
1514  {
1515  wxWindow * pWnd = wxWindow::FindWindowById( miId, mpDlg);
1516  pChoice = wxDynamicCast(pWnd, wxChoice);
1517  wxASSERT( pChoice );
1518  Selected = pChoice->GetSelection();
1519  }
1520  break;
1521  case eIsSettingToDialog:
1522  {
1523  wxWindow * pWnd = wxWindow::FindWindowById( miId, mpDlg);
1524  pChoice = wxDynamicCast(pWnd, wxChoice);
1525  wxASSERT( pChoice );
1526  pChoice->SetSelection( Selected );
1527  }
1528  break;
1529  default:
1530  wxASSERT( false );
1531  break;
1532  }
1533  return pChoice;
1534 }
1535 
1538 {
1539  wxASSERT( mRadioCount >= 0); // Did you remember to use StartRadioButtonGroup() ?
1540 
1541  EnumValueSymbol symbol;
1542  if (mRadioCount >= 0 && mRadioCount < (int)mRadioSymbols.size() )
1543  symbol = mRadioSymbols[ mRadioCount ];
1544 
1545  // In what follows, WrappedRef is used in read only mode, but we
1546  // don't have a 'read-only' version, so we copy to deal with the constness.
1547  auto Temp = symbol.Internal();
1548  wxASSERT( !Temp.empty() ); // More buttons than values?
1549 
1550  WrappedType WrappedRef( Temp );
1551 
1552  mRadioCount++;
1553 
1554  UseUpId();
1555  wxRadioButton * pRadioButton = NULL;
1556 
1557  switch( mShuttleMode )
1558  {
1559  case eIsCreating:
1560  {
1561  const auto &Prompt = symbol.Translation();
1562 
1563  mpWind = pRadioButton = safenew wxRadioButton(GetParent(), miId, Prompt,
1564  wxDefaultPosition, wxDefaultSize,
1565  (mRadioCount==1)?wxRB_GROUP:0);
1566 
1567  wxASSERT( WrappedRef.IsString() );
1568  wxASSERT( mRadioValue->IsString() );
1569  const bool value =
1570  (WrappedRef.ReadAsString() == mRadioValue->ReadAsString() );
1571  pRadioButton->SetValue( value );
1572 
1573  pRadioButton->SetName(wxStripMenuCodes(Prompt));
1574  UpdateSizers();
1575  }
1576  break;
1577  case eIsGettingMetadata:
1578  break;
1579  case eIsGettingFromDialog:
1580  {
1581  wxWindow * pWnd = wxWindow::FindWindowById( miId, mpDlg);
1582  pRadioButton = wxDynamicCast(pWnd, wxRadioButton);
1583  wxASSERT( pRadioButton );
1584  if( pRadioButton->GetValue() )
1585  mRadioValue->WriteToAsString( WrappedRef.ReadAsString() );
1586  }
1587  break;
1588  default:
1589  wxASSERT( false );
1590  break;
1591  }
1592  return pRadioButton;
1593 }
1594 
1597 {
1598  mRadioSymbols = Setting.GetSymbols();
1599 
1600  // Configure the generic type mechanism to use OUR string.
1601  mRadioValueString = Setting.Default().Internal();
1602  mRadioValue.emplace( mRadioValueString );
1603 
1604  // Now actually start the radio button group.
1605  mRadioSettingName = Setting.Key();
1606  mRadioCount = 0;
1607  if( mShuttleMode == eIsCreating )
1608  DoDataShuttle( Setting.Key(), *mRadioValue );
1609 }
1610 
1614 {
1615  // too few buttons?
1616  wxASSERT( mRadioCount == mRadioSymbols.size() );
1617 
1620  mRadioValue.reset();// Clear it out...
1621  mRadioSettingName = wxT("");
1622  mRadioCount = -1; // So we detect a problem.
1623  mRadioSymbols = {};
1624 }
1625 
1626 //-----------------------------------------------------------------------//
1627 //-- Now we are into type specific Tie() functions.
1628 //-- These are all 'one-step' tie functions.
1629 
1630 wxCheckBox * ShuttleGuiBase::TieCheckBox(const TranslatableString &Prompt, bool &Var)
1631 {
1632  WrappedType WrappedRef( Var );
1633  return DoTieCheckBox( Prompt, WrappedRef );
1634 }
1635 
1636 // See comment in AddCheckBoxOnRight() for why we have this variant.
1637 wxCheckBox * ShuttleGuiBase::TieCheckBoxOnRight(const TranslatableString &Prompt, bool &Var)
1638 {
1639  // Only does anything different if it's creating.
1640  WrappedType WrappedRef( Var );
1641  if( mShuttleMode == eIsCreating )
1642  return AddCheckBoxOnRight( Prompt, WrappedRef.ReadAsString() == wxT("true") );
1643  return DoTieCheckBox( Prompt, WrappedRef );
1644 }
1645 
1647  const TranslatableString &Prompt, int &Value, const int max, const int min )
1648 {
1649  WrappedType WrappedRef(Value);
1650  return DoTieSpinCtrl( Prompt, WrappedRef, max, min );
1651 }
1652 
1654  const TranslatableString &Prompt, wxString &Selected, const int nChars)
1655 {
1656  WrappedType WrappedRef(Selected);
1657  return DoTieTextBox( Prompt, WrappedRef, nChars );
1658 }
1659 
1661  const TranslatableString &Prompt, int &Selected, const int nChars)
1662 {
1663  WrappedType WrappedRef( Selected );
1664  return DoTieTextBox( Prompt, WrappedRef, nChars );
1665 }
1666 
1668  const TranslatableString &Prompt, double &Value, const int nChars)
1669 {
1670  WrappedType WrappedRef( Value );
1671  return DoTieTextBox( Prompt, WrappedRef, nChars );
1672 }
1673 
1675  const TranslatableString &Prompt, int &Value, const int nChars)
1676 {
1677  WrappedType WrappedRef( Value );
1678  return DoTieNumericTextBox( Prompt, WrappedRef, nChars );
1679 }
1680 
1682  const TranslatableString &Prompt, double &Value, const int nChars)
1683 {
1684  WrappedType WrappedRef( Value );
1685  return DoTieNumericTextBox( Prompt, WrappedRef, nChars );
1686 }
1687 
1689  const TranslatableString &Prompt, int &pos, const int max, const int min )
1690 {
1691  WrappedType WrappedRef( pos );
1692  return DoTieSlider( Prompt, WrappedRef, max, min );
1693 }
1694 
1696  const TranslatableString &Prompt,
1697  double &pos, const double max, const double min )
1698 {
1699  WrappedType WrappedRef( pos );
1700  return DoTieSlider( Prompt, WrappedRef, max, min );
1701 }
1702 
1704  const TranslatableString &Prompt,
1705  float &pos, const float fMin, const float fMax)
1706 {
1707  const float RoundFix=0.0000001f;
1708  int iVal=(pos-fMin+RoundFix)*100.0/(fMax-fMin);
1709  wxSlider * pWnd = TieSlider( Prompt, iVal, 100 );
1710  pos = iVal*(fMax-fMin)*0.01+fMin;
1711  return pWnd;
1712 }
1713 
1715  const TranslatableString &Prompt,
1716  float &pos, const float fMin, const float fMax)
1717 {
1718  int iVal=(pos-fMin)*100.0/(fMax-fMin);
1719 // if( mShuttleMode == eIsCreating )
1720 // {
1721 // return AddVSlider( Prompt, iVal, 100 );
1722 // }
1723  wxSlider * pWnd = TieSlider( Prompt, iVal, 100 );
1724  pos = iVal*(fMax-fMin)*0.01+fMin;
1725  return pWnd;
1726 }
1727 
1729  const TranslatableString &Prompt,
1730  TranslatableString &Selected,
1731  const TranslatableStrings &choices )
1732 {
1733  int Index = make_iterator_range( choices ).index( Selected );
1734  auto result = TieChoice( Prompt, Index, choices );
1735  if ( Index >= 0 && Index < choices.size() )
1736  Selected = choices[ Index ];
1737  else
1738  Selected = {};
1739  return result;
1740 }
1741 
1742 //-----------------------------------------------------------------------//
1743 
1744 // ShuttleGui utility functions to look things up in a list.
1745 // If not present, we use the configured default index value.
1746 
1747 //-----------------------------------------------------------------------//
1748 
1750 int ShuttleGuiBase::TranslateToIndex( const wxString &Value, const wxArrayStringEx &Choices )
1751 {
1752  int n = make_iterator_range( Choices ).index( Value );
1753  if( n == wxNOT_FOUND )
1755  miNoMatchSelector = 0;
1756  return n;
1757 }
1758 
1760 wxString ShuttleGuiBase::TranslateFromIndex( const int nIn, const wxArrayStringEx &Choices )
1761 {
1762  int n = nIn;
1763  if( n== wxNOT_FOUND )
1765  miNoMatchSelector = 0;
1766  if( n < (int)Choices.size() )
1767  {
1768  return Choices[n];
1769  }
1770  return wxT("");
1771 }
1772 
1773 //-----------------------------------------------------------------------//
1774 
1775 
1776 // ShuttleGui code uses the model that you read into program variables
1777 // and write out from program variables.
1778 
1779 // In programs like Audacity which don't use internal program variables
1780 // you have to do both steps in one go, using variants of the standard
1781 // 'Tie' functions which call the underlying Tie functions twice.
1782 
1783 //----------------------------------------------------------------------//
1784 
1785 
1818 bool ShuttleGuiBase::DoStep( int iStep )
1819 {
1820  // Get value and create
1821  if( mShuttleMode == eIsCreating )
1822  {
1823  return (iStep==1) || (iStep==2);
1824  }
1825  // Like creating, get the value and set.
1827  {
1828  return (iStep==1) || (iStep==2);
1829  }
1831  {
1832  return (iStep==2) || (iStep==3);
1833  }
1835  return iStep ==2;
1836  wxASSERT( false );
1837  return false;
1838 }
1839 
1840 
1844  const TranslatableString &Prompt,
1845  const BoolSetting &Setting)
1846 {
1847  wxCheckBox * pCheck=NULL;
1848 
1849  auto Value = Setting.GetDefault();
1850  WrappedType WrappedRef( Value );
1851  if( DoStep(1) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1852  if( DoStep(2) ) pCheck = DoTieCheckBox( Prompt, WrappedRef );
1853  if( DoStep(3) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1854 
1855  return pCheck;
1856 }
1857 
1861  const TranslatableString &Prompt,
1862  const BoolSetting & Setting)
1863 {
1864  wxCheckBox * pCheck=NULL;
1865 
1866  auto Value = Setting.GetDefault();
1867  WrappedType WrappedRef( Value );
1868  if( DoStep(1) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1869  if( DoStep(2) ) pCheck = DoTieCheckBoxOnRight( Prompt, WrappedRef );
1870  if( DoStep(3) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1871 
1872  return pCheck;
1873 }
1874 
1878  const TranslatableString &Prompt,
1879  const IntSetting & Setting,
1880  const int max,
1881  const int min)
1882 {
1883  wxSlider * pSlider=NULL;
1884 
1885  auto Value = Setting.GetDefault();
1886  WrappedType WrappedRef( Value );
1887  if( DoStep(1) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1888  if( DoStep(2) ) pSlider = DoTieSlider( Prompt, WrappedRef, max, min );
1889  if( DoStep(3) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1890 
1891  return pSlider;
1892 }
1893 
1897  const TranslatableString &Prompt,
1898  const IntSetting &Setting,
1899  const int max,
1900  const int min)
1901 {
1902  wxSpinCtrl * pSpinCtrl=NULL;
1903 
1904  auto Value = Setting.GetDefault();
1905  WrappedType WrappedRef( Value );
1906  if( DoStep(1) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1907  if( DoStep(2) ) pSpinCtrl = DoTieSpinCtrl( Prompt, WrappedRef, max, min );
1908  if( DoStep(3) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1909 
1910  return pSpinCtrl;
1911 }
1912 
1916  const TranslatableString & Prompt,
1917  const StringSetting & Setting,
1918  const int nChars)
1919 {
1920  wxTextCtrl * pText=(wxTextCtrl*)NULL;
1921 
1922  auto Value = Setting.GetDefault();
1923  WrappedType WrappedRef( Value );
1924  if( DoStep(1) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1925  if( DoStep(2) ) pText = DoTieTextBox( Prompt, WrappedRef, nChars );
1926  if( DoStep(3) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1927  return pText;
1928 }
1929 
1934  const TranslatableString & Prompt,
1935  const IntSetting &Setting,
1936  const int nChars)
1937 {
1938  wxTextCtrl * pText=(wxTextCtrl*)NULL;
1939 
1940  auto Value = Setting.GetDefault();
1941  WrappedType WrappedRef( Value );
1942  if( DoStep(1) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1943  if( DoStep(2) ) pText = DoTieNumericTextBox( Prompt, WrappedRef, nChars );
1944  if( DoStep(3) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1945  return pText;
1946 }
1947 
1952  const TranslatableString & Prompt,
1953  const DoubleSetting & Setting,
1954  const int nChars)
1955 {
1956  wxTextCtrl * pText=(wxTextCtrl*)NULL;
1957 
1958  auto Value = Setting.GetDefault();
1959  WrappedType WrappedRef( Value );
1960  if( DoStep(1) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1961  if( DoStep(2) ) pText = DoTieNumericTextBox( Prompt, WrappedRef, nChars );
1962  if( DoStep(3) ) DoDataShuttle( Setting.GetPath(), WrappedRef );
1963  return pText;
1964 }
1965 
1973  const TranslatableString &Prompt,
1974  const ChoiceSetting &choiceSetting )
1975 {
1976  // Do this to force any needed migrations first
1977  choiceSetting.Read();
1978 
1979  const auto &symbols = choiceSetting.GetSymbols();
1980  const auto &SettingName = choiceSetting.Key();
1981  const auto &Default = choiceSetting.Default().Internal();
1982  const auto &Choices = symbols.GetMsgids();
1983  const auto &InternalChoices = symbols.GetInternals();
1984 
1985  wxChoice * pChoice=(wxChoice*)NULL;
1986 
1987  int TempIndex=0;
1988 // int TempIndex = TranslateToIndex( Default, InternalChoices );
1989  wxString TempStr = Default;
1990  WrappedType WrappedRef( TempStr );
1991  // Get from prefs does 1 and 2.
1992  // Put to prefs does 2 and 3.
1993  if( DoStep(1) ) DoDataShuttle( SettingName, WrappedRef ); // Get Index from Prefs.
1994  if( DoStep(1) ) TempIndex = TranslateToIndex( TempStr, InternalChoices ); // To an index
1995  if( DoStep(2) ) pChoice = TieChoice( Prompt, TempIndex, Choices );
1996  if( DoStep(3) ) TempStr = TranslateFromIndex( TempIndex, InternalChoices ); // To a string
1997  if( DoStep(3) ) DoDataShuttle( SettingName, WrappedRef ); // Put into Prefs.
1998  return pChoice;
1999 }
2000 
2013  const TranslatableString &Prompt,
2014  const IntSetting & Setting,
2015  const TranslatableStrings & Choices,
2016  const std::vector<int> * pInternalChoices,
2017  int iNoMatchSelector)
2018 {
2019  auto fn = [](int arg){ return wxString::Format( "%d", arg ); };
2020 
2021  wxArrayStringEx InternalChoices;
2022  if ( pInternalChoices )
2023  InternalChoices =
2024  transform_container<wxArrayStringEx>(*pInternalChoices, fn);
2025  else
2026  for ( int ii = 0; ii < (int)Choices.size(); ++ii )
2027  InternalChoices.push_back( fn( ii ) );
2028 
2029 
2030  const auto Default = Setting.GetDefault();
2031 
2032  miNoMatchSelector = iNoMatchSelector;
2033 
2034  long defaultIndex;
2035  if ( pInternalChoices )
2036  defaultIndex = make_iterator_range( *pInternalChoices ).index( Default );
2037  else
2038  defaultIndex = Default;
2039  if ( defaultIndex < 0 || defaultIndex >= (int)Choices.size() )
2040  defaultIndex = -1;
2041 
2042  ChoiceSetting choiceSetting{
2043  Setting.GetPath(),
2044  {
2045  ByColumns,
2046  Choices,
2047  InternalChoices,
2048  },
2049  defaultIndex
2050  };
2051 
2052  return ShuttleGuiBase::TieChoice( Prompt, choiceSetting );
2053 }
2054 
2055 //------------------------------------------------------------------//
2056 
2057 // We're now into ShuttleGuiBase sizer and misc functions.
2058 
2066 {
2067  if( miIdSetByUser > 0)
2068  {
2069  miId = miIdSetByUser;
2070  miIdSetByUser = -1;
2071  return;
2072  }
2073  miId = miIdNext++;
2074 }
2075 
2077 {
2078  if( miPropSetByUser >=0 )
2079  {
2081  miPropSetByUser =-1;
2082  return;
2083  }
2084  miProp = Default;
2085 }
2086 
2087 
2089  wxWindow *pWind, wxWindow *pDlg )
2090 {
2091  if ( step == 0 ) {
2092  // Do these steps before adding the window to the sizer
2093  if( item.mUseBestSize )
2094  pWind->SetMinSize( pWind->GetBestSize() );
2095  else if( item.mHasMinSize )
2096  pWind->SetMinSize( item.mMinSize );
2097 
2098  if ( item.mWindowSize != wxSize{} )
2099  pWind->SetSize( item.mWindowSize );
2100  }
2101  else if ( step == 1) {
2102  // Apply certain other optional window attributes here
2103 
2104  if ( item.mValidatorSetter )
2105  item.mValidatorSetter( pWind );
2106 
2107  if ( !item.mToolTip.empty() )
2108  pWind->SetToolTip( item.mToolTip.Translation() );
2109 
2110  if ( !item.mName.empty() ) {
2111  pWind->SetName( item.mName.Stripped().Translation() );
2112 #ifndef __WXMAC__
2113  if (auto pButton = dynamic_cast< wxBitmapButton* >( pWind ))
2114  pButton->SetLabel( item.mName.Translation() );
2115 #endif
2116  }
2117 
2118  if ( !item.mNameSuffix.empty() )
2119  pWind->SetName(
2120  pWind->GetName() + " " + item.mNameSuffix.Translation() );
2121 
2122  if (item.mFocused)
2123  pWind->SetFocus();
2124 
2125  if (item.mDisabled)
2126  pWind->Enable( false );
2127 
2128  for (auto &pair : item.mRootConnections)
2129  pWind->Connect( pair.first, pair.second, nullptr, pDlg );
2130  }
2131 }
2132 
2133 
2134 void ShuttleGuiBase::UpdateSizersCore(bool bPrepend, int Flags, bool prompt)
2135 {
2136  if( mpWind && mpParent )
2137  {
2138  int useFlags = Flags;
2139 
2140  if ( !prompt && mItem.mWindowPositionFlags )
2141  // override the given Flags
2142  useFlags = mItem.mWindowPositionFlags;
2143 
2144  if (!prompt)
2145  ApplyItem( 0, mItem, mpWind, mpDlg );
2146 
2147  if( mpSizer){
2148  if( bPrepend )
2149  {
2150  mpSizer->Prepend(mpWind, miProp, useFlags, miBorder);
2151  }
2152  else
2153  {
2154  mpSizer->Add(mpWind, miProp, useFlags, miBorder);
2155  }
2156  }
2157 
2158  if (!prompt) {
2159  ApplyItem( 1, mItem, mpWind, mpDlg );
2160  // Reset to defaults
2161  mItem = {};
2162  }
2163  }
2164 
2165  if( mpSubSizer && mpSizer )
2166  {
2167  // When adding sizers into sizers, don't add a border.
2168  // unless it's a static box sizer.
2169  wxSizer *const pSubSizer = mpSubSizer.get();
2170  if (wxDynamicCast(pSubSizer, wxStaticBoxSizer))
2171  {
2172  mpSizer->Add( mpSubSizer.release(), miSizerProp, Flags , miBorder);
2173  }
2174  else
2175  {
2176  mpSizer->Add( mpSubSizer.release(), miSizerProp, Flags ,0);//miBorder);
2177  }
2178  mpSizer = pSubSizer;
2179  PushSizer();
2180  }
2181 
2182  mpWind = NULL;
2183  miProp = 0;
2184  miSizerProp =0;
2185 }
2186 
2187 // Sizer is added into parent sizer, and will expand/shrink.
2189 { UpdateSizersCore( false, wxEXPAND | wxALL );}
2190 
2191 // Sizer is added into parent sizer, centred
2193 { UpdateSizersCore( false, wxALIGN_CENTRE | wxALL );}
2194 
2195 // Sizer is added into parent sizer, and will expand/shrink.
2196 // added to start of sizer list.
2198 { UpdateSizersCore( true, wxEXPAND | wxALL );}
2199 
2201 {
2202  mSizerDepth--;
2203  wxASSERT( mSizerDepth >=0 );
2205 }
2206 
2208 {
2209  mSizerDepth++;
2210  wxASSERT( mSizerDepth < nMaxNestedSizers );
2212 }
2213 
2214 long ShuttleGuiBase::GetStyle( long style )
2215 {
2216  if( mItem.miStyle )
2217  style = mItem.miStyle;
2218  mItem.miStyle = 0;
2219  return style;
2220 }
2221 
2222 // A rarely used helper function that sets a pointer
2223 // ONLY if the value it is to be set to is non NULL.
2224 void SetIfCreated( wxChoice * &Var, wxChoice * Val )
2225 {
2226  if( Val != NULL )
2227  Var = Val;
2228 };
2229 void SetIfCreated( wxTextCtrl * &Var, wxTextCtrl * Val )
2230 {
2231  if( Val != NULL )
2232  Var = Val;
2233 };
2234 void SetIfCreated( wxStaticText *&Var, wxStaticText * Val )
2235 {
2236  if( Val != NULL )
2237  Var = Val;
2238 };
2239 
2240 #ifdef EXPERIMENTAL_TRACK_PANEL
2241 // Additional includes down here, to make it easier to split this into
2242 // two files at some later date.
2243 #include "../extnpanel-src/GuiWaveTrack.h"
2244 #endif
2245 
2247  wxWindow * pParent, teShuttleMode ShuttleMode, bool vertical, wxSize minSize)
2248  : ShuttleGuiBase( pParent, ShuttleMode, vertical, minSize )
2249 {
2250  if( ShuttleMode == eIsCreatingFromPrefs )
2251  {
2253  Init( vertical, minSize ); // Wasn't fully done in base constructor because it is only done when eIsCreating is set.
2254  }
2255  else if( ShuttleMode == eIsSavingToPrefs )
2256  {
2258  }
2259  else
2260  {
2261  return;
2262  }
2263 
2264  mpShuttle = std::make_unique<ShuttlePrefs>();
2265  // In this case the client is the GUI, so if creating we do want to
2266  // store in the client.
2267  mpShuttle->mbStoreInClient = (mShuttleMode == eIsCreating );
2268 };
2269 
2271 {
2272 }
2273 
2274 // Now we have Audacity specific shuttle functions.
2276 {
2277  miIdSetByUser = id;
2278  return *this;
2279 }
2280 
2282  mpbOptionalFlag = &bVar;
2283  return *this;
2284 };
2285 
2286 
2287 std::unique_ptr<wxSizer> CreateStdButtonSizer(wxWindow *parent, long buttons, wxWindow *extra)
2288 {
2289  wxASSERT(parent != NULL); // To justify safenew
2290 
2291  int margin;
2292  {
2293 #if defined(__WXMAC__)
2294  margin = 12;
2295 #elif defined(__WXGTK20__)
2296  margin = 12;
2297 #elif defined(__WXMSW__)
2298  wxButton b(parent, 0, wxEmptyString);
2299  margin = b.ConvertDialogToPixels(wxSize(2, 0)).x;
2300 #else
2301  wxButton b(parent, 0, wxEmptyString);
2302  margin = b->ConvertDialogToPixels(wxSize(4, 0)).x;
2303 #endif
2304  }
2305 
2306  wxButton *b = NULL;
2307  auto bs = std::make_unique<wxStdDialogButtonSizer>();
2308 
2309  const auto makeButton =
2310  [parent]( wxWindowID id, const wxString label = {} ) {
2311  auto result = safenew wxButton( parent, id, label );
2312  result->SetName( result->GetLabel() );
2313  return result;
2314  };
2315 
2316  if( buttons & eOkButton )
2317  {
2318  b = makeButton( wxID_OK );
2319  b->SetDefault();
2320  bs->AddButton( b );
2321  }
2322 
2323  if( buttons & eCancelButton )
2324  {
2325  bs->AddButton( makeButton( wxID_CANCEL ) );
2326  }
2327 
2328  if( buttons & eYesButton )
2329  {
2330  b = makeButton( wxID_YES );
2331  b->SetDefault();
2332  bs->AddButton( b );
2333  }
2334 
2335  if( buttons & eNoButton )
2336  {
2337  bs->AddButton( makeButton( wxID_NO ) );
2338  }
2339 
2340  if( buttons & eApplyButton )
2341  {
2342  b = makeButton( wxID_APPLY );
2343  b->SetDefault();
2344  bs->AddButton( b );
2345  }
2346 
2347  if( buttons & eCloseButton )
2348  {
2349  bs->AddButton( makeButton( wxID_CANCEL, XO("&Close").Translation() ) );
2350  }
2351 
2352 #if defined(__WXMSW__)
2353  // See below for explanation
2354  if( buttons & eHelpButton )
2355  {
2356  // Replace standard Help button with smaller icon button.
2357  // bs->AddButton(safenew wxButton(parent, wxID_HELP));
2358  b = safenew wxBitmapButton(parent, wxID_HELP, theTheme.Bitmap( bmpHelpIcon ));
2359  b->SetToolTip( XO("Help").Translation() );
2360  b->SetLabel(XO("Help").Translation()); // for screen readers
2361  b->SetName( b->GetLabel() );
2362  bs->AddButton( b );
2363  }
2364 #endif
2365 
2366  if (buttons & ePreviewButton)
2367  {
2368  bs->Add( makeButton( ePreviewID, XO("&Preview").Translation() ),
2369  0, wxALIGN_CENTER | wxLEFT | wxRIGHT, margin);
2370  }
2371  if (buttons & ePreviewDryButton)
2372  {
2373  bs->Add( makeButton( ePreviewDryID, XO("Dry Previe&w").Translation() ),
2374  0, wxALIGN_CENTER | wxLEFT | wxRIGHT, margin);
2375  bs->Add( 20, 0 );
2376  }
2377 
2378  if( buttons & eSettingsButton )
2379  {
2380  bs->Add( makeButton( eSettingsID, XO("&Settings").Translation() ),
2381  0, wxALIGN_CENTER | wxLEFT | wxRIGHT, margin);
2382  bs->Add( 20, 0 );
2383  }
2384 
2385  if( extra )
2386  {
2387  bs->Add( extra, 0, wxALIGN_CENTER | wxLEFT | wxRIGHT, margin );
2388  bs->Add( 40, 0 );
2389  }
2390 
2391  bs->AddStretchSpacer();
2392  bs->Realize();
2393 
2394  size_t lastLastSpacer = 0;
2395  size_t lastSpacer = 0;
2396  wxSizerItemList & list = bs->GetChildren();
2397  for( size_t i = 0, cnt = list.size(); i < cnt; i++ )
2398  {
2399  if( list[i]->IsSpacer() )
2400  {
2401  lastSpacer = i;
2402  }
2403  else
2404  {
2405  lastLastSpacer = lastSpacer;
2406  }
2407  }
2408 
2409  // Add any buttons that need to cuddle up to the right hand cluster
2410  if( buttons & eDebugButton )
2411  {
2412  b = makeButton( eDebugID, XO("Debu&g").Translation() );
2413  bs->Insert( ++lastLastSpacer, b, 0, wxALIGN_CENTER | wxLEFT | wxRIGHT, margin );
2414  }
2415 
2416 #if !defined(__WXMSW__)
2417  // Bug #2432: Couldn't find GTK guidelines, but Mac HIGs state:
2418  //
2419  // View style Help button position
2420  // Dialog with dismissal buttons (like OK and Cancel). Lower-left corner, vertically aligned with the dismissal buttons.
2421  // Dialog without dismissal buttons. Lower-left or lower-right corner.
2422  // Preference window or pane. Lower-left or lower-right corner.
2423  //
2424  // So, we're gonna cheat a little and use the lower-right corner.
2425  if( buttons & eHelpButton )
2426  {
2427  // Replace standard Help button with smaller icon button.
2428  // bs->AddButton(safenew wxButton(parent, wxID_HELP));
2429  b = safenew wxBitmapButton(parent, wxID_HELP, theTheme.Bitmap( bmpHelpIcon ));
2430  b->SetToolTip( XO("Help").Translation() );
2431  b->SetLabel(XO("Help").Translation()); // for screen readers
2432  b->SetName( b->GetLabel() );
2433  bs->Add( b, 0, wxALIGN_CENTER );
2434  }
2435 #endif
2436 
2437 
2438  auto s = std::make_unique<wxBoxSizer>( wxVERTICAL );
2439  s->Add( bs.release(), 1, wxEXPAND | wxALL, 7 );
2440  s->Add( 0, 3 ); // a little extra space
2441 
2442  return std::unique_ptr<wxSizer>{ s.release() };
2443 }
2444 
2445 void ShuttleGui::AddStandardButtons(long buttons, wxWindow *extra)
2446 {
2447  if( mShuttleMode != eIsCreating )
2448  return;
2449 
2450  StartVerticalLay( false );
2451 
2452  miSizerProp = false;
2453  mpSubSizer = CreateStdButtonSizer( mpParent, buttons, extra );
2454  UpdateSizers();
2455  PopSizer();
2456 
2457  EndVerticalLay();
2458 }
2459 
2460 wxSizerItem * ShuttleGui::AddSpace( int width, int height, int prop )
2461 {
2462  if( mShuttleMode != eIsCreating )
2463  return NULL;
2464 
2465 // SetProportions(0);
2466  // return mpSizer->Add( width, height, miProp);
2467 
2468  return mpSizer->Add( width, height, prop );
2469 }
2470 
2471 void ShuttleGui::SetMinSize( wxWindow *window, const TranslatableStrings & items )
2472 {
2473  SetMinSize( window,
2474  transform_container<wxArrayStringEx>(
2475  items, std::mem_fn( &TranslatableString::StrippedTranslation ) ) );
2476 }
2477 
2478 void ShuttleGui::SetMinSize( wxWindow *window, const wxArrayStringEx & items )
2479 {
2480  int maxw = 0;
2481 
2482  for( size_t i = 0; i < items.size(); i++ )
2483  {
2484  int x;
2485  int y;
2486 
2487  window->GetTextExtent(items[i], &x, &y );
2488  if( x > maxw )
2489  {
2490  maxw = x;
2491  }
2492  }
2493 
2494  // Would be nice to know the sizes of the button and borders, but this is
2495  // the best we can do for now.
2496 #if defined(__WXMAC__)
2497  maxw += 50;
2498 #elif defined(__WXMSW__)
2499  maxw += 50;
2500 #elif defined(__WXGTK__)
2501  maxw += 50;
2502 #else
2503  maxw += 50;
2504 #endif
2505 
2506  window->SetMinSize( { maxw, -1 } );
2507 }
2508 
2509 /*
2510 void ShuttleGui::SetMinSize( wxWindow *window, const std::vector<int> & items )
2511 {
2512  wxArrayStringEx strs;
2513 
2514  for( size_t i = 0; i < items.size(); i++ )
2515  {
2516  strs.Add( wxString::Format( wxT("%d"), items[i] ) );
2517  }
2518 
2519  SetMinSize( window, strs );
2520 }
2521 */
2522 
2524  const EnumValueSymbol strings[], size_t nStrings)
2525 {
2526  return transform_range<TranslatableStrings>(
2527  strings, strings + nStrings,
2528  std::mem_fn( &EnumValueSymbol::Msgid )
2529  );
2530 }
2531 
2532 TranslatableStrings Msgids( const std::vector<EnumValueSymbol> &strings )
2533 {
2534  return Msgids( strings.data(), strings.size() );
2535 }
size
size_t size
Definition: ffmpeg-2.3.6-single-header.h:412
ReadOnlyText.h
Init
Definition: ModuleManager.h:154
ShuttleGuiBase::StartRadioButtonGroup
void StartRadioButtonGroup(const ChoiceSetting &Setting)
Call this before any TieRadioButton calls.
Definition: ShuttleGui.cpp:1596
ReadOnlyText
Definition: ReadOnlyText.h:60
TranslatableString
Holds a msgid for the translation catalog; may also bind format arguments.
Definition: TranslatableString.h:32
ShuttleGuiBase::EndSimplebook
void EndSimplebook()
Definition: ShuttleGui.cpp:1062
label
TranslatableString label
Definition: TagsEditor.cpp:163
eIsCreating
@ eIsCreating
Definition: ShuttleGui.h:39
WrappedType::ReadAsString
wxString ReadAsString()
Definition: WrappedType.cpp:42
ShuttleGuiBase::Init
void Init(bool vertical, wxSize minSize)
Definition: ShuttleGui.cpp:144
TranslatableString::empty
bool empty() const
Definition: TranslatableString.h:72
ShuttleGuiBase::AddCheckBoxOnRight
wxCheckBox * AddCheckBoxOnRight(const TranslatableString &Prompt, bool Selected)
Definition: ShuttleGui.cpp:344
ShuttleGuiBase::AddChoice
wxChoice * AddChoice(const TranslatableString &Prompt, const TranslatableStrings &choices, int Selected=-1)
Definition: ShuttleGui.cpp:399
ShuttleGuiBase::EndRadioButtonGroup
void EndRadioButtonGroup()
Definition: ShuttleGui.cpp:1613
ShuttleGuiBase::StartVerticalLay
void StartVerticalLay(int iProp=1)
Definition: ShuttleGui.cpp:1185
wxSliderWrapper
wxSlider wxSliderWrapper
Definition: ShuttleGui.h:106
ShuttleGuiBase::AddCheckBox
wxCheckBox * AddCheckBox(const TranslatableString &Prompt, bool Selected)
Definition: ShuttleGui.cpp:310
make_iterator_range
IteratorRange< Iterator > make_iterator_range(const Iterator &i1, const Iterator &i2)
Definition: MemoryX.h:423
ShuttleGuiBase::DoTieSpinCtrl
wxSpinCtrl * DoTieSpinCtrl(const TranslatableString &Prompt, WrappedType &WrappedRef, const int max, const int min=0)
Definition: ShuttleGui.cpp:1332
ShuttleGui::SetMinSize
static void SetMinSize(wxWindow *window, const TranslatableStrings &items)
Definition: ShuttleGui.cpp:2471
ShuttleGuiBase::HandleOptionality
void HandleOptionality(const TranslatableString &Prompt)
Definition: ShuttleGui.cpp:225
ShuttleGuiBase::mRadioValue
std::optional< WrappedType > mRadioValue
The setting controlled by a group.
Definition: ShuttleGui.h:575
eIsGettingFromDialog
@ eIsGettingFromDialog
Definition: ShuttleGui.h:40
ComponentInterfaceSymbol::Translation
const wxString Translation() const
Definition: ComponentInterfaceSymbol.h:58
fn
static const auto fn
Definition: WaveformView.cpp:1122
IntSetting
Specialization of Setting for int.
Definition: Prefs.h:213
ShuttleGui::~ShuttleGui
~ShuttleGui(void)
Definition: ShuttleGui.cpp:2270
ShuttleGuiBase::EndWrapLay
void EndWrapLay()
Definition: ShuttleGui.cpp:1222
DialogDefinition::Item::mDisabled
bool mDisabled
Definition: ShuttleGui.h:235
ShuttleGuiBase::AddTitle
void AddTitle(const TranslatableString &Prompt, int wrapWidth=0)
Centred text string.
Definition: ShuttleGui.cpp:282
SettingBase::GetPath
const wxString & GetPath() const
Definition: Prefs.h:74
AllThemeResources.h
wxNotebookPage
wxWindow wxNotebookPage
Definition: ShuttleGui.h:62
TranslatableStrings
std::vector< TranslatableString > TranslatableStrings
Definition: TranslatableString.h:295
ShuttleGuiBase::UpdateSizersAtStart
void UpdateSizersAtStart()
Definition: ShuttleGui.cpp:2197
eHelpButton
@ eHelpButton
Definition: ShuttleGui.h:604
ChoiceSetting::Key
const wxString & Key() const
Definition: Prefs.h:285
ePreviewButton
@ ePreviewButton
Definition: ShuttleGui.h:605
ThemeBase::Bitmap
wxBitmap & Bitmap(int iIndex)
wxPanelWrapper
Definition: wxPanelWrapper.h:41
ShuttleGuiBase::miIdSetByUser
int miIdSetByUser
Definition: ShuttleGui.h:547
ShuttleGuiBase::DoTieCheckBoxOnRight
wxCheckBox * DoTieCheckBoxOnRight(const TranslatableString &Prompt, WrappedType &WrappedRef)
Definition: ShuttleGui.cpp:1296
ShuttleGuiBase::TieCheckBox
wxCheckBox * TieCheckBox(const TranslatableString &Prompt, bool &Var)
Definition: ShuttleGui.cpp:1630
ShuttleGuiBase::ApplyItem
static void ApplyItem(int step, const DialogDefinition::Item &item, wxWindow *pWind, wxWindow *pDlg)
Definition: ShuttleGui.cpp:2088
WrappedType::IsString
bool IsString()
Definition: WrappedType.cpp:35
ShuttleGuiBase::AddRadioButtonToGroup
wxRadioButton * AddRadioButtonToGroup(const TranslatableString &Prompt, int selector=1, int initValue=0)
Definition: ShuttleGui.cpp:575
ShuttleGuiBase::mpShuttle
std::unique_ptr< Shuttle > mpShuttle
Definition: ShuttleGui.h:533
WrappedType::WriteToAsBool
void WriteToAsBool(const bool InBool)
Definition: WrappedType.cpp:233
ShuttleGuiBase::TieSlider
wxSlider * TieSlider(const TranslatableString &Prompt, int &pos, const int max, const int min=0)
Definition: ShuttleGui.cpp:1688
BoolSetting
This specialization of Setting for bool adds a Toggle method to negate the saved value.
Definition: Prefs.h:203
ShuttleGuiBase::ShuttleGuiBase
ShuttleGuiBase(wxWindow *pParent, teShuttleMode ShuttleMode, bool vertical, wxSize minSize)
Definition: ShuttleGui.cpp:129
Validator
A Validator is an object which checks whether a wxVariant satisfies a certain criterion....
Definition: Validators.h:53
ShuttleGuiBase::EndNotebook
void EndNotebook()
Definition: ShuttleGui.cpp:1041
ShuttleGui::AddSpace
wxSizerItem * AddSpace(int width, int height, int prop=0)
Definition: ShuttleGui.cpp:2460
ShuttleGuiBase::TranslateToIndex
int TranslateToIndex(const wxString &Value, const wxArrayStringEx &Choices)
String-to-Index.
Definition: ShuttleGui.cpp:1750
ShuttleGuiBase::pSizerStack
wxSizer * pSizerStack[nMaxNestedSizers]
Definition: ShuttleGui.h:531
XO
#define XO(s)
Definition: Internat.h:31
wxPanelWrapper.h
ShuttleGuiBase::TieNumberAsChoice
virtual wxChoice * TieNumberAsChoice(const TranslatableString &Prompt, const IntSetting &Setting, const TranslatableStrings &Choices, const std::vector< int > *pInternalChoices=nullptr, int iNoMatchSelector=0)
Definition: ShuttleGui.cpp:2012
ShuttleGuiBase::mRadioValueString
wxString mRadioValueString
The index of this radio item. -1 for none.
Definition: ShuttleGui.h:577
WrappedType::ReadAsBool
bool ReadAsBool()
Definition: WrappedType.cpp:124
eDebugButton
@ eDebugButton
Definition: ShuttleGui.h:606
ShuttleGuiBase::EndMultiColumn
void EndMultiColumn()
Definition: ShuttleGui.cpp:1239
ShuttleGui::ShuttleGui
ShuttleGui(wxWindow *pParent, teShuttleMode ShuttleMode, bool vertical=true, wxSize minSize={ 250, 100 })
Definition: ShuttleGui.cpp:2246
ShuttleGuiBase::StartNotebookPage
wxNotebookPage * StartNotebookPage(const TranslatableString &Name)
Definition: ShuttleGui.cpp:1069
WrappedType::ReadAsInt
int ReadAsInt()
Definition: WrappedType.cpp:68
ShuttleGuiBase::DoTieTextBox
wxTextCtrl * DoTieTextBox(const TranslatableString &Prompt, WrappedType &WrappedRef, const int nChars)
Definition: ShuttleGui.cpp:1371
ShuttleGuiBase::DoInsertListColumns
void DoInsertListColumns(wxListCtrl *pListCtrl, long listControlStyles, std::initializer_list< const ListControlColumn > columns)
Definition: ShuttleGui.cpp:824
ShuttleGuiBase::EndNotebookPage
void EndNotebookPage()
Definition: ShuttleGui.cpp:1092
ShuttleGuiBase::AddListControl
wxListCtrl * AddListControl(std::initializer_list< const ListControlColumn > columns={}, long listControlStyles=0)
Definition: ShuttleGui.cpp:783
ShuttleGuiBase::mRadioSettingName
wxString mRadioSettingName
Definition: ShuttleGui.h:574
ShuttleGuiBase::StartPanel
wxPanel * StartPanel(int iStyle=0)
Definition: ShuttleGui.cpp:991
ComponentInterfaceSymbol::Msgid
const TranslatableString & Msgid() const
Definition: ComponentInterfaceSymbol.h:56
DialogDefinition::Item::mToolTip
TranslatableString mToolTip
Definition: ShuttleGui.h:217
ShuttleGuiBase::miSizerProp
int miSizerProp
Definition: ShuttleGui.h:539
eIsSettingToDialog
@ eIsSettingToDialog
Definition: ShuttleGui.h:41
wxArrayStringEx
Extend wxArrayString with move operations and construction and insertion fromstd::initializer_list.
Definition: wxArrayStringEx.h:18
ShuttleGuiBase::EndPanel
void EndPanel()
Definition: ShuttleGui.cpp:1019
ShuttleGuiBase::StartInvisiblePanel
wxPanel * StartInvisiblePanel()
Definition: ShuttleGui.cpp:1133
ePreviewDryID
@ ePreviewDryID
Definition: ShuttleGui.h:621
ComponentInterfaceSymbol
ComponentInterfaceSymbol pairs a persistent string identifier used internally with an optional,...
Definition: ComponentInterfaceSymbol.h:27
ShuttleGuiBase::DoTieSlider
wxSlider * DoTieSlider(const TranslatableString &Prompt, WrappedType &WrappedRef, const int max, const int min=0)
Definition: ShuttleGui.cpp:1447
eApplyButton
@ eApplyButton
Definition: ShuttleGui.h:609
ShuttleGui::Id
ShuttleGui & Id(int id)
Definition: ShuttleGui.cpp:2275
ShuttleGuiBase::TieTextBox
wxTextCtrl * TieTextBox(const TranslatableString &Caption, wxString &Value, const int nChars=0)
Definition: ShuttleGui.cpp:1653
ShuttleGuiBase::DoStep
bool DoStep(int iStep)
Definition: ShuttleGui.cpp:1818
ShuttleGuiBase::Prop
ShuttleGuiBase & Prop(int iProp)
Definition: ShuttleGui.cpp:883
StringSetting
Specialization of Setting for strings.
Definition: Prefs.h:227
ShuttleGuiBase::AddTree
wxTreeCtrl * AddTree()
Definition: ShuttleGui.cpp:855
ShuttleGuiBase::~ShuttleGuiBase
virtual ~ShuttleGuiBase()
Definition: ShuttleGui.cpp:140
ShuttleGuiBase::EndScroller
void EndScroller()
Definition: ShuttleGui.cpp:972
ShuttleGuiBase::GetBorder
int GetBorder() const noexcept
Definition: ShuttleGui.cpp:197
ShuttleGuiBase::miPropSetByUser
int miPropSetByUser
Definition: ShuttleGui.h:549
InvisiblePanel
An InvisiblePanel is a panel which does not repaint its own background.
Definition: ShuttleGui.cpp:1103
ePreviewID
@ ePreviewID
Definition: ShuttleGui.h:617
ShuttleGuiBase::AddSpinCtrl
wxSpinCtrl * AddSpinCtrl(const TranslatableString &Prompt, int Value, int Max, int Min)
Definition: ShuttleGui.cpp:617
ShuttleGuiBase::miBorder
int miBorder
Definition: ShuttleGui.h:541
ChoiceSetting
Definition: Prefs.h:269
ePreviewDryButton
@ ePreviewDryButton
Definition: ShuttleGui.h:608
DialogDefinition::Item::mWindowPositionFlags
int mWindowPositionFlags
Definition: ShuttleGui.h:226
DialogDefinition::Item::mName
TranslatableString mName
Definition: ShuttleGui.h:218
ShuttleGuiBase::AddIcon
void AddIcon(wxBitmap *pBmp)
Definition: ShuttleGui.cpp:869
ShuttleGuiBase::AddConstTextBox
void AddConstTextBox(const TranslatableString &Caption, const TranslatableString &Value)
Single line text box of fixed size.
Definition: ShuttleGui.cpp:734
wxTextCtrlWrapper
Definition: wxTextCtrlWrapper.h:23
eDebugID
@ eDebugID
Definition: ShuttleGui.h:619
ShuttleGuiBase::AddNumericTextBox
wxTextCtrl * AddNumericTextBox(const TranslatableString &Caption, const wxString &Value, const int nChars)
Definition: ShuttleGui.cpp:675
InvisiblePanel::OnErase
void OnErase(wxEraseEvent &)
Definition: ShuttleGui.cpp:1116
ComponentInterface.h
eCancelButton
@ eCancelButton
Definition: ShuttleGui.h:601
ShuttleGuiBase::mpSizer
wxSizer * mpSizer
Definition: ShuttleGui.h:554
ShuttleGuiBase::StartScroller
wxScrolledWindow * StartScroller(int iStyle=0)
Definition: ShuttleGui.cpp:939
ShuttleGuiBase::EndHorizontalLay
void EndHorizontalLay()
Definition: ShuttleGui.cpp:1178
eYesButton
@ eYesButton
Definition: ShuttleGui.h:602
DialogDefinition::Item::miStyle
long miStyle
Definition: ShuttleGui.h:223
ShuttleGuiBase::StartHorizontalLay
void StartHorizontalLay(int PositionFlags=wxALIGN_CENTRE, int iProp=1)
Definition: ShuttleGui.cpp:1168
wxTextCtrlWrapper.h
ShuttleGuiBase::AddTextBox
wxTextCtrl * AddTextBox(const TranslatableString &Caption, const wxString &Value, const int nChars)
Definition: ShuttleGui.cpp:639
ShuttleGuiBase::StartMultiColumn
void StartMultiColumn(int nCols, int PositionFlags=wxALIGN_LEFT)
Definition: ShuttleGui.cpp:1230
ShuttlePrefs.h
InvisiblePanel::InvisiblePanel
InvisiblePanel(wxWindow *parent, wxWindowID id=-1, const wxPoint &pos=wxDefaultPosition, const wxSize &size=wxDefaultSize, long style=wxTAB_TRAVERSAL)
Definition: ShuttleGui.cpp:1105
WrappedType
Used in type conversions, this wrapper for ints, strings, doubles and enums provides conversions betw...
Definition: WrappedType.h:31
ShuttleGuiBase::EndVerticalLay
void EndVerticalLay()
Definition: ShuttleGui.cpp:1204
ShuttleGuiBase::StartSimplebook
wxSimplebook * StartSimplebook()
Definition: ShuttleGui.cpp:1048
ShuttleGuiBase::miIdNext
int miIdNext
Definition: ShuttleGui.h:546
ShuttleGuiBase::ResetId
void ResetId()
Definition: ShuttleGui.cpp:189
ShuttleGuiBase::AddUnits
void AddUnits(const TranslatableString &Prompt, int wrapWidth=0)
Left aligned text string.
Definition: ShuttleGui.cpp:264
ShuttleGuiBase::AddFixedText
void AddFixedText(const TranslatableString &Str, bool bCenter=false, int wrapWidth=0)
Definition: ShuttleGui.cpp:441
ShuttleGuiBase::miProp
int miProp
Definition: ShuttleGui.h:542
Theme.h
ShuttleGuiBase::UpdateSizers
void UpdateSizers()
Definition: ShuttleGui.cpp:2188
ShuttleGuiBase::UpdateSizersC
void UpdateSizersC()
Definition: ShuttleGui.cpp:2192
ShuttleGuiBase::mpParent
wxWindow * mpParent
Definition: ShuttleGui.h:555
Setting
Class template adds default value, read, and write methods to CachingSetingBase.
Definition: Prefs.h:100
Setting::GetDefault
const T & GetDefault() const
Definition: Prefs.h:119
ShuttleGuiBase::PopSizer
void PopSizer()
Definition: ShuttleGui.cpp:2200
ShuttleGuiBase::PushSizer
void PushSizer()
Definition: ShuttleGui.cpp:2207
ShuttleGuiBase::GetParent
wxWindow * GetParent()
Definition: ShuttleGui.h:496
ShuttleGuiBase::mpbOptionalFlag
bool * mpbOptionalFlag
Definition: ShuttleGui.h:551
DialogDefinition::Item::mNameSuffix
TranslatableString mNameSuffix
Definition: ShuttleGui.h:219
ShuttleGuiBase::AddGrid
wxGrid * AddGrid()
Definition: ShuttleGui.cpp:769
ShuttleGuiBase::AddWindow
wxWindow * AddWindow(wxWindow *pWindow, int PositionFlags=wxALIGN_CENTRE)
Definition: ShuttleGui.cpp:300
WindowAccessible
An alternative to using wxWindowAccessible, which in wxWidgets 3.1.1 contained GetParent() which was ...
ShuttleGuiBase::AddRadioButton
wxRadioButton * AddRadioButton(const TranslatableString &Prompt, int selector=0, int initValue=0)
Definition: ShuttleGui.cpp:569
ShuttleGuiBase::TieNumericTextBox
wxTextCtrl * TieNumericTextBox(const TranslatableString &Prompt, int &Value, const int nChars=0)
Definition: ShuttleGui.cpp:1674
ShuttleGui.h
ShuttleGuiBase::TranslateFromIndex
wxString TranslateFromIndex(const int nIn, const wxArrayStringEx &Choices)
Index-to-String.
Definition: ShuttleGui.cpp:1760
Msgids
TranslatableStrings Msgids(const EnumValueSymbol strings[], size_t nStrings)
Convenience function often useful when adding choice controls.
Definition: ShuttleGui.cpp:2523
ChoiceSetting::GetSymbols
const EnumValueSymbols & GetSymbols() const
Definition: Prefs.h:287
ShuttleGuiBase::AddReadOnlyText
ReadOnlyText * AddReadOnlyText(const TranslatableString &Caption, const wxString &Value)
Definition: ShuttleGui.cpp:497
ShuttleGuiBase::AddSlider
wxSlider * AddSlider(const TranslatableString &Prompt, int pos, int Max, int Min=0)
Definition: ShuttleGui.cpp:590
theTheme
THEME_API Theme theTheme
Definition: Theme.cpp:82
ShuttleGuiBase::TieSpinCtrl
wxSpinCtrl * TieSpinCtrl(const TranslatableString &Prompt, int &Value, const int max, const int min=0)
Definition: ShuttleGui.cpp:1646
ShuttleGuiBase::UpdateSizersCore
void UpdateSizersCore(bool bPrepend, int Flags, bool prompt=false)
Definition: ShuttleGui.cpp:2134
ShuttleGuiBase::AddButton
wxButton * AddButton(const TranslatableString &Text, int PositionFlags=wxALIGN_CENTRE, bool setDefault=false)
Definition: ShuttleGui.cpp:361
ShuttleGuiBase::StartStatic
wxStaticBox * StartStatic(const TranslatableString &Str, int iProp=0)
Definition: ShuttleGui.cpp:894
ChoiceSetting::Read
wxString Read() const
Definition: Prefs.cpp:277
eIsSavingToPrefs
@ eIsSavingToPrefs
Definition: ShuttleGui.h:49
id
int id
Definition: WaveTrackControls.cpp:577
min
int min(int a, int b)
Definition: CompareAudioCommand.cpp:106
ShuttleGuiBase::mRadioCount
int mRadioCount
The wrapped value associated with the active radio button.
Definition: ShuttleGui.h:576
eIsGettingMetadata
@ eIsGettingMetadata
Definition: ShuttleGui.h:42
ShuttleGuiBase::miId
int miId
Definition: ShuttleGui.h:545
ShuttleGuiBase::UseUpId
void UseUpId()
Definition: ShuttleGui.cpp:2065
ShuttleGuiBase::SetProportions
void SetProportions(int Default)
Definition: ShuttleGui.cpp:2076
WindowAccessible.h
eOkButton
@ eOkButton
Definition: ShuttleGui.h:600
ChoiceSetting::Default
const EnumValueSymbol & Default() const
Definition: Prefs.cpp:269
ShuttleGuiBase::mShuttleMode
teShuttleMode mShuttleMode
Used in choices to determine which item to use on no match.
Definition: ShuttleGui.h:537
ShuttleGuiBase::TieVSlider
wxSlider * TieVSlider(const TranslatableString &Prompt, float &pos, const float fMin, const float fMax)
Definition: ShuttleGui.cpp:1714
ShuttleGuiBase::mpWind
wxWindow * mpWind
Definition: ShuttleGui.h:556
ShuttleGuiBase::AddListControlReportMode
wxListCtrl * AddListControlReportMode(std::initializer_list< const ListControlColumn > columns={}, long listControlStyles=0)
Definition: ShuttleGui.cpp:803
MemoryX.h
eCloseButton
@ eCloseButton
Definition: ShuttleGui.h:610
ShuttleGuiBase::AddBitmapButton
wxBitmapButton * AddBitmapButton(const wxBitmap &Bitmap, int PositionFlags=wxALIGN_CENTRE, bool setDefault=false)
Definition: ShuttleGui.cpp:380
ShuttleGuiBase::TieIntegerTextBox
virtual wxTextCtrl * TieIntegerTextBox(const TranslatableString &Prompt, const IntSetting &Setting, const int nChars)
Definition: ShuttleGui.cpp:1933
ShuttleGuiBase::DoTieNumericTextBox
wxTextCtrl * DoTieNumericTextBox(const TranslatableString &Prompt, WrappedType &WrappedRef, const int nChars)
Definition: ShuttleGui.cpp:1409
TranslatableString::StrippedTranslation
wxString StrippedTranslation() const
Definition: TranslatableString.h:201
DialogDefinition::Item::mUseBestSize
bool mUseBestSize
Definition: ShuttleGui.h:232
ShuttleGuiBase::miNoMatchSelector
int miNoMatchSelector
Definition: ShuttleGui.h:535
ComponentInterfaceSymbol::Internal
const wxString & Internal() const
Definition: ComponentInterfaceSymbol.h:55
ShuttleGuiBase::mSizerDepth
int mSizerDepth
Definition: ShuttleGui.h:540
ShuttleGuiBase::DoDataShuttle
void DoDataShuttle(const wxString &Name, WrappedType &WrappedRef)
Definition: ShuttleGui.cpp:1248
DialogDefinition::Item
Definition: ShuttleGui.h:111
ShuttleGuiBase::AddTextWindow
wxTextCtrl * AddTextWindow(const wxString &Value)
Multiline text box that grows.
Definition: ShuttleGui.cpp:713
ShuttleGuiBase::GetStyle
long GetStyle(long Style)
Definition: ShuttleGui.cpp:2214
ShuttleGuiBase::mItem
DialogDefinition::Item mItem
Definition: ShuttleGui.h:582
ShuttleGui::AddStandardButtons
void AddStandardButtons(long buttons=eOkButton|eCancelButton, wxWindow *extra=NULL)
Definition: ShuttleGui.cpp:2445
WrappedType::WriteToAsString
void WriteToAsString(const wxString &InStr)
Definition: WrappedType.cpp:152
DialogDefinition::Item::mHasMinSize
bool mHasMinSize
Definition: ShuttleGui.h:231
ShuttleGuiBase::mRadioSymbols
std::vector< EnumValueSymbol > mRadioSymbols
Definition: ShuttleGui.h:573
ShuttleGuiBase::TieRadioButton
wxRadioButton * TieRadioButton()
This function must be within a StartRadioButtonGroup - EndRadioButtonGroup pair.
Definition: ShuttleGui.cpp:1537
wxStaticBoxWrapper
wxStaticBox wxStaticBoxWrapper
Definition: ShuttleGui.h:105
Prefs.h
ShuttleGuiBase::AddPrompt
void AddPrompt(const TranslatableString &Prompt, int wrapWidth=0)
Right aligned text string.
Definition: ShuttleGui.cpp:239
TranslatableString::Translation
wxString Translation() const
Definition: TranslatableString.h:79
ByColumns
ByColumns_t ByColumns
Definition: Prefs.cpp:415
eIsCreatingFromPrefs
@ eIsCreatingFromPrefs
Definition: ShuttleGui.h:48
ShuttleGuiBase::AddVariableText
wxStaticText * AddVariableText(const TranslatableString &Str, bool bCenter=false, int PositionFlags=0, int wrapWidth=0)
Definition: ShuttleGui.cpp:464
ShuttleGui::Optional
ShuttleGui & Optional(bool &bVar)
Definition: ShuttleGui.cpp:2281
ShuttleGuiBase::DoTieCheckBox
wxCheckBox * DoTieCheckBox(const TranslatableString &Prompt, WrappedType &WrappedRef)
Definition: ShuttleGui.cpp:1260
DialogDefinition::Item::mRootConnections
std::vector< std::pair< wxEventType, wxObjectEventFunction > > mRootConnections
Definition: ShuttleGui.h:221
DialogDefinition::Item::mFocused
bool mFocused
Definition: ShuttleGui.h:234
TranslatableString::Stripped
TranslatableString Stripped(unsigned options=MenuCodes) const
non-mutating, constructs another TranslatableString object
Definition: TranslatableString.h:198
ShuttleGuiBase::EndStatic
void EndStatic()
Definition: ShuttleGui.cpp:923
ShuttleGuiBase::StartWrapLay
void StartWrapLay(int PositionFlags=wxEXPAND, int iProp=0)
Definition: ShuttleGui.cpp:1211
safenew
#define safenew
Definition: MemoryX.h:10
ShuttleGuiBase::StartNotebook
wxNotebook * StartNotebook()
Definition: ShuttleGui.cpp:1027
ShuttleGuiBase::mpDlg
wxWindow *const mpDlg
Definition: ShuttleGui.h:530
ShuttleGuiBase::SetStretchyCol
void SetStretchyCol(int i)
Used to modify an already placed FlexGridSizer to make a column stretchy.
Definition: ShuttleGui.cpp:203
WrappedType::WriteToAsInt
void WriteToAsInt(const int InInt)
Definition: WrappedType.cpp:181
eSettingsID
@ eSettingsID
Definition: ShuttleGui.h:620
DialogDefinition::Item::mMinSize
wxSize mMinSize
Definition: ShuttleGui.h:230
ShuttleGuiBase::AddListBox
wxListBox * AddListBox(const wxArrayStringEx &choices)
Definition: ShuttleGui.cpp:754
ShuttleGuiBase::EndInvisiblePanel
void EndInvisiblePanel()
Definition: ShuttleGui.cpp:1156
ShuttleGuiBase::mpSubSizer
std::unique_ptr< wxSizer > mpSubSizer
Definition: ShuttleGui.h:553
eSettingsButton
@ eSettingsButton
Definition: ShuttleGui.h:607
END_EVENT_TABLE
END_EVENT_TABLE()
ShuttleGuiBase::TieChoice
wxChoice * TieChoice(const TranslatableString &Prompt, TranslatableString &Selected, const TranslatableStrings &choices)
Definition: ShuttleGui.cpp:1728
ShuttleGuiBase::SetStretchyRow
void SetStretchyRow(int i)
Used to modify an already placed FlexGridSizer to make a row stretchy.
Definition: ShuttleGui.cpp:213
ShuttleGuiBase::TieCheckBoxOnRight
wxCheckBox * TieCheckBoxOnRight(const TranslatableString &Prompt, bool &Var)
Definition: ShuttleGui.cpp:1637
DoubleSetting
Specialization of Setting for double.
Definition: Prefs.h:220
ShuttleGuiBase::DoAddRadioButton
wxRadioButton * DoAddRadioButton(const TranslatableString &Prompt, int style, int selector, int initValue)
Unwrapped string value.
Definition: ShuttleGui.cpp:549
ShuttleGuiBase::AddCombo
wxComboBox * AddCombo(const TranslatableString &Prompt, const wxString &Selected, const wxArrayStringEx &choices)
Definition: ShuttleGui.cpp:518
ShuttleGuiBase
Base class for shuttling data to and from a GUI.
Definition: ShuttleGui.h:242
eNoButton
@ eNoButton
Definition: ShuttleGui.h:603
DialogDefinition::Item::mWindowSize
wxSize mWindowSize
Definition: ShuttleGui.h:228
teShuttleMode
teShuttleMode
Definition: ShuttleGui.h:38
SetIfCreated
void SetIfCreated(wxChoice *&Var, wxChoice *Val)
Definition: ShuttleGui.cpp:2224
InvisiblePanel::OnPaint
void OnPaint(wxPaintEvent &event)
Definition: ShuttleGui.cpp:1126
DialogDefinition::Item::mValidatorSetter
std::function< void(wxWindow *) > mValidatorSetter
Definition: ShuttleGui.h:216
InvisiblePanel::~InvisiblePanel
~InvisiblePanel()
Definition: ShuttleGui.cpp:1114
ShuttleGui
Derived from ShuttleGuiBase, an Audacity specific class for shuttling data to and from GUI.
Definition: ShuttleGui.h:631
CreateStdButtonSizer
std::unique_ptr< wxSizer > CreateStdButtonSizer(wxWindow *parent, long buttons, wxWindow *extra)
Definition: ShuttleGui.cpp:2287
nMaxNestedSizers
const int nMaxNestedSizers
Definition: ShuttleGui.h:35