Audacity 3.2.0
Public Member Functions | Static Public Member Functions | Protected Member Functions | Private Member Functions | Private Attributes | List of all members
AudacityFileConfig Class Referencefinal

Our own specialisation of FileConfig. More...

#include <AudacityFileConfig.h>

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

Public Member Functions

bool Flush (bool bCurrentOnly) override
 
 ~AudacityFileConfig () override
 
bool RenameEntry (const wxString &oldName, const wxString &newName) override
 
bool RenameGroup (const wxString &oldName, const wxString &newName) override
 
bool DeleteEntry (const wxString &key, bool bDeleteGroupIfEmpty) override
 
bool DeleteGroup (const wxString &key) override
 
bool DeleteAll () override
 

Static Public Member Functions

static std::unique_ptr< AudacityFileConfigCreate (const wxString &appName={}, const wxString &vendorName={}, const wxString &localFilename={}, const wxString &globalFilename={}, long style=wxCONFIG_USE_LOCAL_FILE|wxCONFIG_USE_GLOBAL_FILE, const wxMBConv &conv=wxConvAuto())
 Require a call to this factory, to guarantee proper two-phase initialization. More...
 

Protected Member Functions

bool DoWriteString (const wxString &key, const wxString &szValue) override
 
bool DoWriteLong (const wxString &key, long lValue) override
 

Private Member Functions

 AudacityFileConfig (const wxString &appName, const wxString &vendorName, const wxString &localFilename, const wxString &globalFilename, long style, const wxMBConv &conv)
 Disallow direct constructor call, because a two-phase initialization is required. More...
 
void Init ()
 
void Warn () const
 

Private Attributes

bool mDirty {false}
 
const wxString mLocalFilename
 

Detailed Description

Our own specialisation of FileConfig.

Definition at line 19 of file AudacityFileConfig.h.

Constructor & Destructor Documentation

◆ ~AudacityFileConfig()

AudacityFileConfig::~AudacityFileConfig ( )
override

Definition at line 83 of file AudacityFileConfig.cpp.

84{
85 wxASSERT(mDirty == false);
86}

References mDirty.

◆ AudacityFileConfig()

AudacityFileConfig::AudacityFileConfig ( const wxString &  appName,
const wxString &  vendorName,
const wxString &  localFilename,
const wxString &  globalFilename,
long  style,
const wxMBConv &  conv 
)
private

Disallow direct constructor call, because a two-phase initialization is required.

Definition at line 24 of file AudacityFileConfig.cpp.

32: wxFileConfig{ appName, vendorName, localFilename, globalFilename, style, conv }
33, mLocalFilename(localFilename)
34{
35 // https://github.com/audacity/audacity/issues/6448 :
36 // We do not write environment variable names in the config files, and
37 // wxWidgets' implementation of environment variable expansion thinks a dollar
38 // sign at the beginning of a directory name is an environment variable - see
39 // https://github.com/wxWidgets/wxWidgets/issues/19214
40 SetExpandEnvVars(false);
41}
const wxString mLocalFilename

Member Function Documentation

◆ Create()

std::unique_ptr< AudacityFileConfig > AudacityFileConfig::Create ( const wxString &  appName = {},
const wxString &  vendorName = {},
const wxString &  localFilename = {},
const wxString &  globalFilename = {},
long  style = wxCONFIG_USE_LOCAL_FILE | wxCONFIG_USE_GLOBAL_FILE,
const wxMBConv &  conv = wxConvAuto() 
)
static

Require a call to this factory, to guarantee proper two-phase initialization.

Definition at line 88 of file AudacityFileConfig.cpp.

96{
97 // Private ctor means make_unique can't compile, so this verbosity:
98 auto result = std::unique_ptr<AudacityFileConfig>{
100 appName, vendorName, localFilename, globalFilename, style, conv } };
101 result->Init();
102 return result;
103}
#define safenew
Definition: MemoryX.h:10
Our own specialisation of FileConfig.

References safenew, and anonymous_namespace{AudacityDontAskAgainMessageDialog.cpp}::style.

Referenced by AudacityApp::InitPart2(), and anonymous_namespace{AudacityApp.cpp}::PopulatePreferences().

Here is the caller graph for this function:

◆ DeleteAll()

bool AudacityFileConfig::DeleteAll ( )
override

Definition at line 270 of file AudacityFileConfig.cpp.

271{
272 auto res = wxFileConfig::DeleteAll();
273 if (res)
274 {
275 mDirty = true;
276 }
277 return res;
278}

References mDirty.

◆ DeleteEntry()

bool AudacityFileConfig::DeleteEntry ( const wxString &  key,
bool  bDeleteGroupIfEmpty 
)
override

Definition at line 250 of file AudacityFileConfig.cpp.

251{
252 auto res = wxFileConfig::DeleteEntry(key, bDeleteGroupIfEmpty);
253 if (res)
254 {
255 mDirty = true;
256 }
257 return res;
258}
static const AudacityProject::AttachedObjects::RegisteredFactory key

References key, and mDirty.

◆ DeleteGroup()

bool AudacityFileConfig::DeleteGroup ( const wxString &  key)
override

Definition at line 260 of file AudacityFileConfig.cpp.

261{
262 auto res = wxFileConfig::DeleteGroup(key);
263 if (res)
264 {
265 mDirty = true;
266 }
267 return res;
268}

References key, and mDirty.

◆ DoWriteLong()

bool AudacityFileConfig::DoWriteLong ( const wxString &  key,
long  lValue 
)
overrideprotected

Definition at line 290 of file AudacityFileConfig.cpp.

291{
292 bool res = wxFileConfig::DoWriteLong(key, lValue);
293 if (res)
294 {
295 mDirty = true;
296 }
297 return res;
298}

References key, and mDirty.

◆ DoWriteString()

bool AudacityFileConfig::DoWriteString ( const wxString &  key,
const wxString &  szValue 
)
overrideprotected

Definition at line 280 of file AudacityFileConfig.cpp.

281{
282 bool res = wxFileConfig::DoWriteString(key, szValue);
283 if (res)
284 {
285 mDirty = true;
286 }
287 return res;
288}

References key, and mDirty.

◆ Flush()

bool AudacityFileConfig::Flush ( bool  bCurrentOnly)
override

Definition at line 105 of file AudacityFileConfig.cpp.

106{
107 if (!mDirty)
108 {
109 return true;
110 }
111
112 while (true)
113 {
114 FilePath backup = mLocalFilename + ".bkp";
115
116 if (!wxFileExists(backup) || (wxRemove(backup) == 0))
117 {
118 if (!wxFileExists(mLocalFilename) || (wxRename(mLocalFilename, backup) == 0))
119 {
120 wxFileOutputStream stream(mLocalFilename);
121 if (stream.IsOk())
122 {
123 if (Save(stream))
124 {
125 stream.Sync();
126 if (stream.IsOk() && stream.Close())
127 {
128 if (!wxFileExists(backup) || (wxRemove(backup) == 0))
129 {
130 mDirty = false;
131 return true;
132 }
133 }
134 }
135 }
136
137 if (wxFileExists(backup))
138 {
139 wxRemove(mLocalFilename);
140 wxRename(backup, mLocalFilename);
141 }
142 }
143 }
144
145 Warn();
146 }
147}
wxString FilePath
Definition: Project.h:21

References mDirty, mLocalFilename, and Warn().

Here is the call graph for this function:

◆ Init()

void AudacityFileConfig::Init ( )
private

Definition at line 43 of file AudacityFileConfig.cpp.

44{
45 // Prevent wxFileConfig from attempting a Flush() during object deletion. This happens
46 // because we don't use the wxFileConfig::Flush() method and so the wxFileConfig dirty
47 // flag never gets reset. During deletion, the dirty flag is checked and a Flush()
48 // performed. This can (and probably will) create bogus temporary files.
49 DisableAutoSave();
50
51 while (true)
52 {
53 bool canRead = false;
54 bool canWrite = false;
55 int fd;
56
57 fd = wxOpen(mLocalFilename, O_RDONLY, S_IREAD);
58 if (fd != -1 || errno == ENOENT)
59 {
60 canRead = true;
61 if (fd != -1)
62 {
63 wxClose(fd);
64 }
65 }
66
67 fd = wxOpen(mLocalFilename, O_WRONLY | O_CREAT, S_IWRITE);
68 if (fd != -1)
69 {
70 canWrite = true;
71 wxClose(fd);
72 }
73
74 if (canRead && canWrite)
75 {
76 break;
77 }
78
79 Warn();
80 }
81}

References mLocalFilename, and Warn().

Here is the call graph for this function:

◆ RenameEntry()

bool AudacityFileConfig::RenameEntry ( const wxString &  oldName,
const wxString &  newName 
)
override

Definition at line 230 of file AudacityFileConfig.cpp.

231{
232 auto res = wxFileConfig::RenameEntry(oldName, newName);
233 if (res)
234 {
235 mDirty = true;
236 }
237 return res;
238}

References mDirty.

◆ RenameGroup()

bool AudacityFileConfig::RenameGroup ( const wxString &  oldName,
const wxString &  newName 
)
override

Definition at line 240 of file AudacityFileConfig.cpp.

241{
242 auto res = wxFileConfig::RenameGroup(oldName, newName);
243 if (res)
244 {
245 mDirty = true;
246 }
247 return res;
248}

References mDirty.

◆ Warn()

void AudacityFileConfig::Warn ( ) const
private

Definition at line 149 of file AudacityFileConfig.cpp.

150{
151 wxDialogWrapper dlg(nullptr, wxID_ANY, XO("Audacity Configuration Error"));
152
153 ShuttleGui S(&dlg, eIsCreating);
154
155 wxButton *retryButton;
156 wxButton *quitButton;
157
158 S.SetBorder(5);
159 S.StartVerticalLay(wxEXPAND, 1);
160 {
161 S.SetBorder(15);
162 S.StartHorizontalLay(wxALIGN_RIGHT, 0);
163 {
164 S.AddFixedText(
165 XO("The following configuration file could not be accessed:\n\n"
166 "\t%s\n\n"
167 "This could be caused by many reasons, but the most likely are that "
168 "the disk is full or you do not have write permissions to the file. "
169 "\n\n"
170 "You can attempt to correct the issue and then click \"Retry\" to continue.\n\n"
171 "If you choose to \"Quit Audacity\", your project may be left in an unsaved "
172 "state which will be recovered the next time you open it.")
174 false,
175 500);
176 }
177 S.EndHorizontalLay();
178
179 S.SetBorder(5);
180 S.StartHorizontalLay(wxALIGN_RIGHT, 0);
181 {
182 // Can't use themed bitmap since the theme manager might not be
183 // initialized yet and it requires a configuration file.
184 wxButton *b = S.Id(wxID_HELP).AddBitmapButton(wxBitmap(Help_xpm));
185 b->SetToolTip( XO("Help").Translation() );
186 b->SetLabel(XO("Help").Translation()); // for screen readers
187
188 b = S.Id(wxID_CANCEL).AddButton(XXO("&Quit Audacity"));
189 b = S.Id(wxID_OK).AddButton(XXO("&Retry"));
190 dlg.SetAffirmativeId(wxID_OK);
191
192 b->SetDefault();
193 b->SetFocus();
194 }
195 S.EndHorizontalLay();
196 }
197 S.EndVerticalLay();
198
199 dlg.Layout();
200 dlg.GetSizer()->Fit(&dlg);
201 dlg.SetMinSize(dlg.GetSize());
202 dlg.Center();
203
204 auto onButton = [&](wxCommandEvent &e)
205 {
206 dlg.EndModal(e.GetId());
207 };
208
209 dlg.Bind(wxEVT_BUTTON, onButton);
210
211 switch (dlg.ShowModal())
212 {
213 case wxID_HELP:
214 // Can't use the HelpSystem since the theme manager may not
215 // yet be initialized and it requires a configuration file.
216 OpenInDefaultBrowser("https://" +
219 "Error:_Audacity_settings_file_unwritable");
220 break;
221
222 case wxID_CANCEL:
223 _exit(-1);
224 break;
225 }
226
227 dlg.Unbind(wxEVT_BUTTON, onButton);
228}
XO("Cut/Copy/Paste")
XXO("&Cut/Copy/Paste Toolbar")
@ eIsCreating
Definition: ShuttleGui.h:37
#define S(N)
Definition: ToChars.cpp:64
Abstract base class used in importing a file.
static const wxString HelpHostname
Definition: HelpSystem.h:96
static const wxString HelpServerHomeDir
Definition: HelpSystem.h:101
Derived from ShuttleGuiBase, an Audacity specific class for shuttling data to and from GUI.
Definition: ShuttleGui.h:640
bool OpenInDefaultBrowser(const wxString &url)
Open an URL in default browser.
Definition: BasicUI.cpp:246

References eIsCreating, HelpSystem::HelpHostname, HelpSystem::HelpServerHomeDir, mLocalFilename, BasicUI::OpenInDefaultBrowser(), S, XO(), and XXO().

Referenced by Flush(), and Init().

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

Member Data Documentation

◆ mDirty

bool AudacityFileConfig::mDirty {false}
private

◆ mLocalFilename

const wxString AudacityFileConfig::mLocalFilename
private

Definition at line 65 of file AudacityFileConfig.h.

Referenced by Flush(), Init(), and Warn().


The documentation for this class was generated from the following files: