Audacity  3.0.3
Prefs.h
Go to the documentation of this file.
1 /**********************************************************************
2 
3  Audacity: A Digital Audio Editor
4 
5  Prefs.h
6 
7  Dominic Mazzoni
8  Markus Meyer
9 
10  Audacity uses wxWidgets' wxFileConfig class to handle preferences.
11  In Audacity versions prior to 1.3.1, it used wxConfig, which would
12  store the prefs in a platform-dependent way (e.g. in the registry
13  on Windows). Now it always stores the settings in a configuration file
14  in the Audacity Data Directory.
15 
16  Every time we read a preference, we need to specify the default
17  value for that preference, to be used if the preference hasn't
18  been set before.
19 
20  So, to avoid code duplication, we provide functions in this file
21  to read and write preferences which have a nonobvious default
22  value, so that if we later want to change this value, we only
23  have to change it in one place.
24 
25  See Prefs.cpp for a (complete?) list of preferences we keep
26  track of...
27 
28 **********************************************************************/
29 #ifndef __AUDACITY_PREFS__
30 #define __AUDACITY_PREFS__
31 
32 // Increment this every time the prefs need to be reset
33 // the first part (before the r) indicates the version the reset took place
34 // the second part (after the r) indicates the number of times the prefs have been reset within the same version
35 #define AUDACITY_PREFS_VERSION_STRING "1.1.1r1"
36 
37 #include <functional>
38 
40 #include "wxArrayStringEx.h"
41 #include "FileConfig.h"
42 
43 #include <memory>
44 #include <wx/event.h> // to declare custom event types
45 
46 class wxFileName;
47 
48 PREFERENCES_API void InitPreferences( std::unique_ptr<FileConfig> uPrefs );
50 
54 PREFERENCES_API void ResetPreferences();
55 PREFERENCES_API void FinishPreferences();
56 
57 extern PREFERENCES_API FileConfig *gPrefs;
58 extern int gMenusDirty;
59 
60 
61 struct ByColumns_t{};
62 extern PREFERENCES_API ByColumns_t ByColumns;
63 
65 /* The constructors are non-explicit for convenience */
66 class PREFERENCES_API SettingBase
67 {
68 public:
69  SettingBase( const char *path ) : mPath{ path } {}
70  SettingBase( const wxChar *path ) : mPath{ path } {}
71  SettingBase( const wxString &path ) : mPath{ path } {}
72 
73  wxConfigBase *GetConfig() const;
74 
75  const wxString &GetPath() const { return mPath; }
76 
78  bool Delete();
79 
80 protected:
81  SettingBase( const SettingBase& ) = default;
83 };
84 
86 template< typename T >
88 {
89 public:
90  explicit CachingSettingBase( const SettingBase &path )
91  : SettingBase{ path } {}
92 protected:
93  CachingSettingBase( const CachingSettingBase & ) = default;
94  mutable T mCurrentValue{};
95  mutable bool mValid{false};
96 };
97 
99 template< typename T >
100 class Setting : public CachingSettingBase< T >
101 {
102 public:
104 
105  using DefaultValueFunction = std::function< T() >;
106 
108  Setting( const SettingBase &path, const T &defaultValue )
109  : CachingSettingBase< T >{ path }
110  , mDefaultValue{ defaultValue }
111  {}
112 
114  Setting( const SettingBase &path, DefaultValueFunction function )
115  : CachingSettingBase< T >{ path }
116  , mFunction{ function }
117  {}
118 
119 
120  const T& GetDefault() const
121  {
122  if ( mFunction )
124  return mDefaultValue;
125  }
126 
128  bool Read( T *pVar ) const
129  {
130  return ReadWithDefault( pVar, GetDefault() );
131  }
132 
134  bool ReadWithDefault( T *pVar, const T& defaultValue ) const
135  {
136  if ( pVar )
137  *pVar = defaultValue;
138  if ( pVar && this->mValid ) {
139  *pVar = this->mCurrentValue;
140  return true;
141  }
142  const auto config = this->GetConfig();
143  if ( pVar && config ) {
144  if ((this->mValid = config->Read( this->mPath, &this->mCurrentValue )))
145  *pVar = this->mCurrentValue;
146  return this->mValid;
147  }
148  return (this->mValid = false);
149  }
150 
152 
154  T Read() const
155  {
156  return ReadWithDefault( GetDefault() );
157  }
158 
160 
162  T ReadWithDefault( const T &defaultValue ) const
163  {
164  const auto config = this->GetConfig();
165  return config
166  ? ( this->mValid = true, this->mCurrentValue =
167  config->ReadObject( this->mPath, defaultValue ) )
168  : T{};
169  }
170 
172  bool Write( const T &value )
173  {
174  const auto config = this->GetConfig();
175  if ( config ) {
176  this->mCurrentValue = value;
177  return DoWrite();
178  }
179  return false;
180  }
181 
183  bool Reset()
184  {
185  return Write( GetDefault() );
186  }
187 
188 protected:
190 
191  bool DoWrite( )
192  {
193  const auto config = this->GetConfig();
194  return this->mValid =
195  config ? config->Write( this->mPath, this->mCurrentValue ) : false;
196  }
197 
198  mutable T mDefaultValue{};
200 };
201 
203 class BoolSetting final : public Setting< bool >
204 {
205 public:
206  using Setting::Setting;
207 
209  bool Toggle();
210 };
211 
213 class IntSetting final : public Setting< int >
214 {
215 public:
216  using Setting::Setting;
217 };
218 
220 class DoubleSetting final : public Setting< double >
221 {
222 public:
223  using Setting::Setting;
224 };
225 
227 class StringSetting final : public Setting< wxString >
228 {
229 public:
230  using Setting::Setting;
231 };
232 
234 
238 class PREFERENCES_API EnumValueSymbols : public std::vector< EnumValueSymbol >
239 {
240 public:
241  EnumValueSymbols() = default;
242  EnumValueSymbols( std::initializer_list<EnumValueSymbol> symbols )
243  : vector( symbols )
244  {}
245 
246  // columnwise constructor; arguments must have same size
247  // (Implicit constructor takes initial tag argument to avoid unintended
248  // overload resolution to the inherited constructor taking
249  // initializer_list, in the case that each column has exactly two strings)
251  ByColumns_t,
252  const TranslatableStrings &msgids,
253  wxArrayStringEx internals
254  );
255 
256  const TranslatableStrings &GetMsgids() const;
257  const wxArrayStringEx &GetInternals() const;
258 
259 private:
262 };
263 
266 class PREFERENCES_API ChoiceSetting
267 {
268 public:
270  const SettingBase &key,
271  EnumValueSymbols symbols,
272  long defaultSymbol = -1
273  )
274  : mKey{ key.GetPath() }
275 
276  , mSymbols{ std::move( symbols ) }
277 
278  , mDefaultSymbol{ defaultSymbol }
279  {
280  wxASSERT( defaultSymbol < (long)mSymbols.size() );
281  }
282 
283  const wxString &Key() const { return mKey; }
284  const EnumValueSymbol &Default() const;
285  const EnumValueSymbols &GetSymbols() const { return mSymbols; }
286 
287  wxString Read() const;
288 
289  // new direct use is discouraged but it may be needed in legacy code:
290  // use a default in case the preference is not defined, which may not be
291  // the default-default stored in this object.
292  wxString ReadWithDefault( const wxString & ) const;
293 
294  bool Write( const wxString &value ); // you flush gPrefs afterward
295 
296  void SetDefault( long value );
297 
298 protected:
299  size_t Find( const wxString &value ) const;
300  virtual void Migrate( wxString& );
301 
302  const wxString mKey;
303 
305 
306  // stores an internal value
307  mutable bool mMigrated { false };
308 
310 };
311 
316 class PREFERENCES_API EnumSettingBase : public ChoiceSetting
317 {
318 public:
320  const SettingBase &key,
321  EnumValueSymbols symbols,
322  long defaultSymbol,
323 
324  std::vector<int> intValues, // must have same size as symbols
325  const wxString &oldKey = {}
326  );
327 
328 protected:
329 
330  // Read and write the encoded values
331  int ReadInt() const;
332 
333  // new direct use is discouraged but it may be needed in legacy code:
334  // use a default in case the preference is not defined, which may not be
335  // the default-default stored in this object.
336  int ReadIntWithDefault( int defaultValue ) const;
337 
338  bool WriteInt( int code ); // you flush gPrefs afterward
339 
340  size_t FindInt( int code ) const;
341  void Migrate( wxString& ) override;
342 
343 private:
344  std::vector<int> mIntValues;
345  const wxString mOldKey;
346 };
347 
349 template< typename Enum >
351 {
352 public:
353 
355  const SettingBase &key,
356  EnumValueSymbols symbols,
357  long defaultSymbol,
358 
359  std::vector< Enum > values, // must have same size as symbols
360  const wxString &oldKey = {}
361  )
362  : EnumSettingBase{
363  key, symbols, defaultSymbol,
364  { values.begin(), values.end() },
365  oldKey
366  }
367  {}
368 
369  // Wrap ReadInt() and ReadIntWithDefault() and WriteInt()
370  Enum ReadEnum() const
371  { return static_cast<Enum>( ReadInt() ); }
372 
373  // new direct use is discouraged but it may be needed in legacy code:
374  // use a default in case the preference is not defined, which may not be
375  // the default-default stored in this object.
376  Enum ReadEnumWithDefault( Enum defaultValue ) const
377  {
378  auto integer = static_cast<int>(defaultValue);
379  return static_cast<Enum>( ReadIntWithDefault( integer ) );
380  }
381 
382  bool WriteEnum( Enum value )
383  { return WriteInt( static_cast<int>( value ) ); }
384 
385 };
386 
388 class PREFERENCES_API PrefsListener
389 {
390 public:
392 
399  static void Broadcast(int id = 0);
400 
401  PrefsListener();
402  virtual ~PrefsListener();
403 
404  // Called when all preferences should be updated.
405  virtual void UpdatePrefs() = 0;
406 
407 protected:
408  // Called when only selected preferences are to be updated.
409  // id is some value generated by wxNewId() that identifies the portion
410  // of preferences.
411  // Default function does nothing.
412  virtual void UpdateSelectedPrefs( int id );
413 
414 private:
415  struct Impl;
416  std::unique_ptr<Impl> mpImpl;
417 };
418 
422 PREFERENCES_API
423 wxString WarningDialogKey(const wxString &internalDialogName);
424 
429 struct PREFERENCES_API PreferenceInitializer {
431  virtual ~PreferenceInitializer();
432  virtual void operator () () = 0;
433 
434  static void ReinitializeAll();
435 };
436 
437 // Special extra-sticky settings
438 extern PREFERENCES_API BoolSetting DefaultUpdatesCheckingFlag;
439 
440 #endif
SettingBase
Base class for settings objects. It holds a configuration key path.
Definition: Prefs.h:67
CachingSettingBase::CachingSettingBase
CachingSettingBase(const SettingBase &path)
Definition: Prefs.h:90
Setting::DoWrite
bool DoWrite()
Write cached value to config and return true if successful.
Definition: Prefs.h:191
Setting::ReadWithDefault
T ReadWithDefault(const T &defaultValue) const
new direct use is discouraged but it may be needed in legacy code
Definition: Prefs.h:162
IntSetting
Specialization of Setting for int.
Definition: Prefs.h:214
SettingBase::GetPath
const wxString & GetPath() const
Definition: Prefs.h:75
EnumSettingBase
Definition: Prefs.h:317
EnumSettingBase::mIntValues
std::vector< int > mIntValues
Definition: Prefs.h:344
TranslatableStrings
std::vector< TranslatableString > TranslatableStrings
Definition: TranslatableString.h:295
ChoiceSetting::ChoiceSetting
ChoiceSetting(const SettingBase &key, EnumValueSymbols symbols, long defaultSymbol=-1)
Definition: Prefs.h:269
ChoiceSetting::Key
const wxString & Key() const
Definition: Prefs.h:283
gPrefs
PREFERENCES_API FileConfig * gPrefs
Definition: Prefs.cpp:70
EnumValueSymbols::EnumValueSymbols
EnumValueSymbols()=default
Setting::Write
bool Write(const T &value)
Write value to config and return true if successful.
Definition: Prefs.h:172
SettingBase::SettingBase
SettingBase(const wxChar *path)
Definition: Prefs.h:70
WarningDialogKey
PREFERENCES_API wxString WarningDialogKey(const wxString &internalDialogName)
Definition: Prefs.cpp:409
BoolSetting
This specialization of Setting for bool adds a Toggle method to negate the saved value.
Definition: Prefs.h:204
FileConfig.h
EnumSetting::EnumSetting
EnumSetting(const SettingBase &key, EnumValueSymbols symbols, long defaultSymbol, std::vector< Enum > values, const wxString &oldKey={})
Definition: Prefs.h:354
CachingSettingBase::CachingSettingBase
CachingSettingBase(const CachingSettingBase &)=default
EnumValueSymbols::EnumValueSymbols
EnumValueSymbols(std::initializer_list< EnumValueSymbol > symbols)
Definition: Prefs.h:242
ComponentInterfaceSymbol.h
wxArrayStringEx
Extend wxArrayString with move operations and construction and insertion fromstd::initializer_list.
Definition: wxArrayStringEx.h:18
EnumValueSymbols::mMsgids
TranslatableStrings mMsgids
Definition: Prefs.h:260
ComponentInterfaceSymbol
ComponentInterfaceSymbol pairs a persistent string identifier used internally with an optional,...
Definition: ComponentInterfaceSymbol.h:27
Setting::Read
bool Read(T *pVar) const
overload of Read returning a boolean that is true if the value was previously defined *‍/
Definition: Prefs.h:128
PrefsListener
A listener notified of changes in preferences.
Definition: Prefs.h:389
SettingBase::mPath
const RegistryPath mPath
Definition: Prefs.h:82
EnumValueSymbols
Definition: Prefs.h:239
StringSetting
Specialization of Setting for strings.
Definition: Prefs.h:228
ByColumns_t
Definition: Prefs.h:61
SettingBase::SettingBase
SettingBase(const SettingBase &)=default
ChoiceSetting
Definition: Prefs.h:267
Setting::Setting
Setting(const SettingBase &path, const T &defaultValue)
Usual overload supplies a default value.
Definition: Prefs.h:108
Setting::Read
T Read() const
overload of Read, always returning a value
Definition: Prefs.h:154
EnumSettingBase::mOldKey
const wxString mOldKey
Definition: Prefs.h:345
SettingBase::SettingBase
SettingBase(const wxString &path)
Definition: Prefs.h:71
gMenusDirty
int gMenusDirty
Definition: Prefs.cpp:71
Setting
Class template adds default value, read, and write methods to CachingSetingBase.
Definition: Prefs.h:101
Setting::GetDefault
const T & GetDefault() const
Definition: Prefs.h:120
EnumSetting::ReadEnumWithDefault
Enum ReadEnumWithDefault(Enum defaultValue) const
Definition: Prefs.h:376
ChoiceSetting::mDefaultSymbol
long mDefaultSymbol
Definition: Prefs.h:309
ByColumns
PREFERENCES_API ByColumns_t ByColumns
Definition: Prefs.cpp:414
Setting::ReadWithDefault
bool ReadWithDefault(T *pVar, const T &defaultValue) const
overload of ReadWithDefault returning a boolean that is true if the value was previously defined *‍/
Definition: Prefs.h:134
ChoiceSetting::GetSymbols
const EnumValueSymbols & GetSymbols() const
Definition: Prefs.h:285
ActiveProjects::Find
wxString Find(const FilePath &path)
CachingSettingBase::mCurrentValue
T mCurrentValue
Definition: Prefs.h:94
InitPreferences
PREFERENCES_API void InitPreferences(std::unique_ptr< FileConfig > uPrefs)
Definition: Prefs.cpp:196
ChoiceSetting::mKey
const wxString mKey
Definition: Prefs.h:302
RegistryPath
wxString RegistryPath
Definition: Identifier.h:218
EnumValueSymbols::mInternals
wxArrayStringEx mInternals
Definition: Prefs.h:261
FileConfig
Definition: FileConfig.h:22
anonymous_namespace{ProjectSerializer.cpp}::ReadInt
static const auto ReadInt
Definition: ProjectSerializer.cpp:179
wxArrayStringEx.h
Setting::mDefaultValue
T mDefaultValue
Definition: Prefs.h:198
PrefsListener::Impl
Definition: Prefs.cpp:85
Setting::Setting
Setting(const SettingBase &path, DefaultValueFunction function)
This overload causes recomputation of the default each time it is needed.
Definition: Prefs.h:114
SettingBase::SettingBase
SettingBase(const char *path)
Definition: Prefs.h:69
EnumSetting::ReadEnum
Enum ReadEnum() const
Definition: Prefs.h:370
Read
gPrefs Read(wxT("/GUI/VerticalZooming"), &bVZoom, false)
key
static const AudacityProject::AttachedObjects::RegisteredFactory key
Definition: CommandManager.cpp:197
Setting::mFunction
const DefaultValueFunction mFunction
Definition: Prefs.h:199
ChoiceSetting::Migrate
virtual void Migrate(wxString &)
Definition: Prefs.cpp:307
CachingSettingBase::mValid
bool mValid
Definition: Prefs.h:95
anonymous_namespace{ProjectSerializer.cpp}::WriteInt
static const auto WriteInt
Definition: ProjectSerializer.cpp:168
SettingBase::GetConfig
wxConfigBase * GetConfig() const
Definition: Prefs.cpp:443
FinishPreferences
PREFERENCES_API void FinishPreferences()
Definition: Prefs.cpp:222
Setting::Reset
bool Reset()
Reset to the default value.
Definition: Prefs.h:183
BoolSetting::Toggle
bool Toggle()
Write the negation of the previous value, and then return the current value.
Definition: Prefs.cpp:454
EnumSetting
Adapts EnumSettingBase to a particular enumeration type.
Definition: Prefs.h:351
PrefsListener::UpdatePrefs
virtual void UpdatePrefs()=0
DefaultUpdatesCheckingFlag
PREFERENCES_API BoolSetting DefaultUpdatesCheckingFlag
Definition: Prefs.cpp:65
PrefsListener::mpImpl
std::unique_ptr< Impl > mpImpl
Definition: Prefs.h:415
ResetPreferences
PREFERENCES_API void ResetPreferences()
Call this to reset preferences to an (almost)-"new" default state.
Definition: Prefs.cpp:203
PreferenceInitializer
Definition: Prefs.h:429
values
const wxChar * values
Definition: Equalization.cpp:472
ChoiceSetting::mSymbols
const EnumValueSymbols mSymbols
Definition: Prefs.h:304
DoubleSetting
Specialization of Setting for double.
Definition: Prefs.h:221
EnumSetting::WriteEnum
bool WriteEnum(Enum value)
Definition: Prefs.h:382
CachingSettingBase
Class template adds an in-memory cache of a value to SettingBase.
Definition: Prefs.h:88
Setting::DefaultValueFunction
std::function< T() > DefaultValueFunction
Definition: Prefs.h:105