Audacity 3.2.0
PluginMenus.cpp
Go to the documentation of this file.
1#include "../Benchmark.h"
2#include "../CommonCommandFlags.h"
3#include "../MenuCreator.h"
4#include "../PluginRegistrationDialog.h"
5#include "../ProjectWindows.h"
6#include "../commands/CommandDispatch.h"
7#include "../effects/EffectManager.h"
8#include "../effects/EffectUI.h"
9#include "../prefs/PrefsDialog.h"
10#include "../toolbars/SelectionBar.h"
11#include "../toolbars/ToolManager.h"
12#include "AudacityMessageBox.h"
13#include "AudioIO.h"
14#include "CommandContext.h"
15#include "CommandManager.h"
16#include "HelpSystem.h"
17#include "Journal.h"
18#include "MenuHelper.h"
19#include "PluginManager.h"
20#include "Prefs.h"
21#include "Project.h"
22#include "ProjectRate.h"
23#include "ProjectSnap.h"
25#include "RealtimeEffectPanel.h"
26#include "SampleTrack.h"
27#include "SyncLock.h"
28#include "TempDirectory.h"
29#include "TrackFocus.h"
30#include "UndoManager.h"
31#include "Viewport.h"
32#include "prefs/EffectsPrefs.h"
33
34// private helper classes and functions
35namespace {
36
37bool ShowManager(wxWindow *parent, int effectsCategory)
38{
39 PluginRegistrationDialog dlg(parent, effectsCategory);
40 return dlg.ShowModal() == wxID_OK;
41}
42
43void DoManagePluginsMenu(AudacityProject &project, int effectsCategory)
44{
45 auto &window = GetProjectFrame( project );
46 auto &pm = PluginManager::Get();
47 if (ShowManager(&window, effectsCategory))
49}
50
52{
53 auto &trackFocus = TrackFocus::Get(project);
54 auto &panel = RealtimeEffectPanel::Get(project);
55 if (panel.IsShown())
56 panel.HidePanel();
57 else if (auto pTrack = dynamic_cast<SampleTrack *>(trackFocus.Get()))
58 panel.ShowPanel(pTrack, true);
59}
60
61
62}
63
64namespace {
65
66// Menu handler functions
67
68void OnResetConfig(const CommandContext &context)
69{
70 auto &project = context.project;
71 auto &commandManager = CommandManager::Get(project);
72 commandManager.mLastAnalyzerRegistration = CommandManager::repeattypenone;
73 commandManager.mLastToolRegistration = CommandManager::repeattypenone;
74 commandManager.mLastGenerator = "";
75 commandManager.mLastEffect = "";
76 commandManager.mLastAnalyzer = "";
77 commandManager.mLastTool = "";
78
80
81 // Directory will be reset on next restart.
83
84 // There are many more things we could reset here.
85 // Beeds discussion as to which make sense to.
86 // Maybe in future versions?
87 // - Reset Effects
88 // - Reset Recording and Playback volumes
89 // - Reset Selection formats (and for spectral too)
90 // - Reset Play-at-speed speed to x1
91 // - Stop playback/recording and unapply pause.
92 // - Set Zoom sensibly.
96 gPrefs->Flush();
98
101
102 // These are necessary to preserve the newly correctly laid out toolbars.
103 // In particular the Device Toolbar ends up short on next restart,
104 // if they are left out.
105 gPrefs->Write(wxT("/PrefsVersion"), wxString(wxT(AUDACITY_PREFS_VERSION_STRING)));
106
107 // write out the version numbers to the prefs file for future checking
108 gPrefs->Write(wxT("/Version/Major"), AUDACITY_VERSION);
109 gPrefs->Write(wxT("/Version/Minor"), AUDACITY_RELEASE);
110 gPrefs->Write(wxT("/Version/Micro"), AUDACITY_REVISION);
111
112 gPrefs->Flush();
113
116
118 .SetRate(gPrefs->ReadDouble("/DefaultProjectSampleRate", 44100.0));
119}
120
122{
123 auto &project = context.project;
125}
126
127void OnEffect(const CommandContext &context)
128{
129 // using GET to interpret parameter as a PluginID
130 EffectUI::DoEffect(context.parameter.GET(), context, 0);
131}
132
133void OnManageEffects(const CommandContext &context)
134{
135 auto &project = context.project;
137}
138
140{
141 auto& project = context.project;
143}
144
145void OnAnalyzer2(wxCommandEvent& evt) { return; }
146
148{
149 auto& commandManager = CommandManager::Get(context.project);
150 auto lastEffect = commandManager.mLastGenerator;
151 if (!lastEffect.empty())
152 {
154 lastEffect, context, commandManager.mRepeatGeneratorFlags | EffectManager::kRepeatGen);
155 }
156}
157
159{
160 auto& commandManager = CommandManager::Get(context.project);
161 auto lastEffect = commandManager.mLastEffect;
162 if (!lastEffect.empty())
163 {
165 lastEffect, context, commandManager.mRepeatEffectFlags);
166 }
167}
168
170{
171 auto& commandManager = CommandManager::Get(context.project);
172 switch (commandManager.mLastAnalyzerRegistration) {
174 {
175 auto lastEffect = commandManager.mLastAnalyzer;
176 if (!lastEffect.empty())
177 {
179 lastEffect, context, commandManager.mRepeatAnalyzerFlags);
180 }
181 }
182 break;
185 commandManager.mLastAnalyzerRegisteredId);
186 break;
187 }
188}
189
191{
192 auto &project = context.project;
194}
195
196void OnManageTools(const CommandContext &context )
197{
198 auto &project = context.project;
200}
201
202void OnBenchmark(const CommandContext &context)
203{
204 auto &project = context.project;
205 CommandManager::Get(project).RegisterLastTool(context); //Register Run Benchmark as Last Tool
206 auto &window = GetProjectFrame( project );
207 ::RunBenchmark( &window, project);
208}
209
211{
212 auto &project = context.project;
213 auto &commandManager = CommandManager::Get( project );
214
215 auto gAudioIO = AudioIO::Get();
216 bool &setting = gAudioIO->mSimulateRecordingErrors;
217 commandManager.Check(wxT("SimulateRecordingErrors"), !setting);
218 setting = !setting;
219}
220
222{
223 auto &project = context.project;
224 auto &commandManager = CommandManager::Get( project );
225
226 auto gAudioIO = AudioIO::Get();
227 auto &setting = gAudioIO->mDetectUpstreamDropouts;
228 auto oldValue = setting.load(std::memory_order_relaxed);
229 commandManager.Check(wxT("DetectUpstreamDropouts"), !oldValue);
230 setting.store(!oldValue, std::memory_order_relaxed);
231}
232
234{
235 auto OnMessage =
236 /* i18n-hint a "journal" is a text file that records
237 the user's interactions with the application */
238 XO("A journal will be recorded after Audacity restarts.");
239 auto OffMessage =
240 /* i18n-hint a "journal" is a text file that records
241 the user's interactions with the application */
242 XO("No journal will be recorded after Audacity restarts.");
243
244 using namespace Journal;
245 bool enabled = RecordEnabled();
246 if ( SetRecordEnabled(!enabled) )
247 enabled = !enabled;
248 if ( enabled )
249 AudacityMessageBox( OnMessage );
250 else
251 AudacityMessageBox( OffMessage );
252}
253
254}
255
256// Menu definitions
257
258// Under /MenuBar
259using namespace MenuRegistry;
260
261namespace {
264 [](const AudacityProject &project){
265 return !CommandManager::Get( project ).mLastGenerator.empty();
266 }
267 }; return flag; }
268
270{
271 // All of this is a bit hacky until we can get more things connected into
272 // the plugin manager...sorry! :-(
273 static auto menu = std::shared_ptr{
274 Menu( wxT("Generate"), XXO("&Generate"),
275 Section( "Manage",
276 Command( wxT("ManageGenerators"), XXO("Plugin Manager"),
278 ),
279
280 Section("RepeatLast",
281 // Delayed evaluation:
283 {
284 const auto &lastGenerator =
286 TranslatableString buildMenuLabel;
287 if (!lastGenerator.empty())
288 buildMenuLabel = XO("Repeat %s")
289 .Format(EffectManager::Get().GetCommandName(lastGenerator));
290 else
291 buildMenuLabel = XO("Repeat Last Generator");
292
293 return Command(wxT("RepeatLastGenerator"), buildMenuLabel,
297 Options{}.IsGlobal());
298 }
299 ),
300
301 Section( "Generators",
302 // Delayed evaluation:
303 [](AudacityProject &) {
304 auto result = Items("");
306 *result,
310 &OnEffect);
311 return result;
312 }
313 )
314 ) };
315 return menu;
316}
317
318static const ReservedCommandFlag
320 [](const AudacityProject &project){
322 }
323}; return flag; } //lll
324
326
329 [](const AudacityProject &project) {
330 return !CommandManager::Get(project).mLastEffect.empty();
331 }
332 }; return flag;
333}
334
335static const ReservedCommandFlag&
337 [](const AudacityProject &project) {
338 auto& trackFocus = TrackFocus::Get(const_cast<AudacityProject&>(project));
339 return (trackFocus.Get() != nullptr);
340 }
341 };
342 return flag;
343}
344
346{
347 // All of this is a bit hacky until we can get more things connected into
348 // the plugin manager...sorry! :-(
349 static auto menu = std::shared_ptr { Menu(
350 wxT("Effect"), XXO("Effe&ct"),
351 Section(
352 "Manage", Command(
353 wxT("ManageEffects"), XXO("Plugin Manager"),
355
356 Section(
357 "RealtimeEffects",
358 Command(
359 wxT("AddRealtimeEffects"), XXO("Add Realtime Effects"),
361#if defined(__WXMSW__) || defined(__WXMAC__)
362 , Command(
363 wxT("GetMoreEffects"), XXO("Get more effects..."),
364 [](const CommandContext&) {
365 OpenInDefaultBrowser("https://www.musehub.com");
366 },
368#endif
369 ),
370 Section(
371 "RepeatLast",
372 // Delayed evaluation:
374 const auto &lastEffect = CommandManager::Get(project).mLastEffect;
375 TranslatableString buildMenuLabel;
376 if (!lastEffect.empty())
377 buildMenuLabel = XO("Repeat %s")
378 .Format( EffectManager::Get().GetCommandName(lastEffect) );
379 else
380 buildMenuLabel = XO("Repeat Last Effect");
381
382 return Command( wxT("RepeatLastEffect"), buildMenuLabel,
386 wxT("Ctrl+R") );
387 }),
388
389 Section(
390 "Effects",
391 // Delayed evaluation:
392 [](AudacityProject&) {
393 auto result = Items("");
395 *result,
399 &OnEffect);
400 return result;
401 })) };
402 return menu;
403}
404
406
409 [](const AudacityProject &project) {
412 return true;
414 }
415 }; return flag;
416}
417
419{
420 // All of this is a bit hacky until we can get more things connected into
421 // the plugin manager...sorry! :-(
422 static auto menu = std::shared_ptr{
423 Menu( wxT("Analyze"), XXO("&Analyze"),
424 Section( "Manage",
425 Command( wxT("ManageAnalyzers"), XXO("Plugin Manager"),
427 ),
428
429 Section("RepeatLast",
430 // Delayed evaluation:
432 {
433 const auto &lastAnalyzer =
435 TranslatableString buildMenuLabel;
436 if (!lastAnalyzer.empty())
437 buildMenuLabel = XO("Repeat %s")
438 .Format(EffectManager::Get().GetCommandName(lastAnalyzer));
439 else
440 buildMenuLabel = XO("Repeat Last Analyzer");
441
442 return Command(wxT("RepeatLastAnalyzer"), buildMenuLabel,
446 Options{}.IsGlobal());
447 }
448 ),
449
450 Section( "Analyzers",
451 Items( "Windows" ),
452
453 // Delayed evaluation:
454 [](AudacityProject &) {
455 auto result = Items("");
457 *result,
461 &OnEffect);
462 return result;
463 }
464 )
465 ) };
466 return menu;
467}
468
470
472{
473 static auto menu = std::shared_ptr{
474 Menu( wxT("Tools"), XXO("T&ools"),
475 Section( "Manage",
476 Command( wxT("ManageTools"), XXO("Plugin Manager"),
478
479 //Separator(),
480 ),
481
482 Section( "Other",
483 Command( wxT("ConfigReset"), XXO("Reset &Configuration"),
486
487 // PRL: team consensus for 2.2.0 was, we let end users have this diagnostic,
488 // as they used to in 1.3.x
489 //#ifdef IS_ALPHA
490 // TODO: What should we do here? Make benchmark a plug-in?
491 // Easy enough to do. We'd call it mod-self-test.
492 Command( wxT("Benchmark"), XXO("&Run Benchmark..."),
494 //#endif
495 ),
496
497 Section( "Tools",
498 // Delayed evaluation:
499 [](AudacityProject &) {
500 auto result = Items("");
502 *result,
506 &OnEffect);
507 return result;
508 }
509 )
510
511#ifdef IS_ALPHA
512 ,
513 Section( "",
514 Command( wxT("SimulateRecordingErrors"),
515 XXO("Simulate Recording Errors"),
519 [](AudacityProject&){
520 return AudioIO::Get()->mSimulateRecordingErrors; } ) ),
521 Command( wxT("DetectUpstreamDropouts"),
522 XXO("Detect Upstream Dropouts"),
526 [](AudacityProject&){
528 .load(std::memory_order_relaxed); } ) )
529 )
530#endif
531
532#if defined(IS_ALPHA) || defined(END_USER_JOURNALLING)
533 ,
534 Section( "",
535 Command( wxT("WriteJournal"),
536 /* i18n-hint a "journal" is a text file that records
537 the user's interactions with the application */
538 XXO("Write Journal"),
542 return Journal::RecordEnabled(); } ) )
543 )
544#endif
545
546 ) };
547 return menu;
548}
549
551
552}
wxT("CloseDown"))
int AudacityMessageBox(const TranslatableString &message, const TranslatableString &caption, long style, wxWindow *parent, int x, int y)
BoolSetting SoundActivatedRecord
Definition: AudioIO.cpp:3408
AttachedItem sAttachment1
AttachedItem sAttachment3
AttachedItem sAttachment2
void RunBenchmark(wxWindow *parent, AudacityProject &project)
Definition: Benchmark.cpp:91
constexpr CommandFlag AlwaysEnabledFlag
Definition: CommandFlag.h:34
const ReservedCommandFlag & AudioIONotBusyFlag()
const ReservedCommandFlag & TimeSelectedFlag()
const ReservedCommandFlag & WaveTracksSelectedFlag()
@ EffectTypeAnalyze
@ EffectTypeGenerate
@ EffectTypeTool
@ EffectTypeProcess
ChoiceSetting EffectsGroupBy
XO("Cut/Copy/Paste")
XXO("&Cut/Copy/Paste Toolbar")
audacity::BasicSettings * gPrefs
Definition: Prefs.cpp:68
void ResetPreferences()
Call this to reset preferences to an (almost)-"new" default state.
Definition: Prefs.cpp:253
#define AUDACITY_PREFS_VERSION_STRING
Definition: Prefs.h:39
void DoReloadPreferences(AudacityProject &project)
an object holding per-project preferred sample rate
AUDACITY_DLL_API wxFrame & GetProjectFrame(AudacityProject &project)
Get the top-level window associated with the project (as a wxFrame only, when you do not need to use ...
IntSetting SelectionToolbarMode
StringSetting SnapToSetting
Definition: SnapUtils.cpp:29
EnumSetting< SnapMode > SnapModeSetting
Definition: SnapUtils.cpp:31
BoolSetting SyncLockTracks
Definition: SyncLock.cpp:163
const auto project
static std::once_flag flag
The top-level handle to an Audacity project. It serves as a source of events that other objects can b...
Definition: Project.h:90
static AudioIO * Get()
Definition: AudioIO.cpp:126
bool mSimulateRecordingErrors
Definition: AudioIO.h:387
std::atomic< bool > mDetectUpstreamDropouts
Definition: AudioIO.h:391
wxString Read() const
Definition: Prefs.cpp:388
CommandContext provides additional information to an 'Apply()' command. It provides the project,...
CommandParameter parameter
AudacityProject & project
PluginID mLastGenerator
void RegisterLastTool(const CommandContext &context)
void DoRepeatProcess(const CommandContext &context, int)
static CommandManager & Get(AudacityProject &project)
PluginID mLastEffect
PluginID mLastAnalyzer
int mLastAnalyzerRegistration
static EffectManager & Get()
const wxString & GET() const
Explicit conversion to wxString, meant to be ugly-looking and demanding of a comment why it's correct...
Definition: Identifier.h:66
static void RebuildAllMenuBars()
static PluginManager & Get()
static ProjectRate & Get(AudacityProject &project)
Definition: ProjectRate.cpp:28
void SetRate(double rate)
Definition: ProjectRate.cpp:58
void SetSnapMode(SnapMode mode)
Definition: ProjectSnap.cpp:41
void SetSnapTo(Identifier snap)
Definition: ProjectSnap.cpp:59
static ProjectSnap & Get(AudacityProject &project)
Definition: ProjectSnap.cpp:27
static RealtimeEffectManager & Get(AudacityProject &project)
bool IsActive() const noexcept
To be called only from main thread.
static RealtimeEffectPanel & Get(AudacityProject &project)
Generates classes whose instances register items at construction.
Definition: Registry.h:388
bool Reset()
Reset to the default value.
Definition: Prefs.h:284
bool Read(T *pVar) const
overload of Read returning a boolean that is true if the value was previously defined *‍/
Definition: Prefs.h:207
static void OnResetToolBars(const CommandContext &context)
Track * Get()
Definition: TrackFocus.cpp:156
Holds a msgid for the translation catalog; may also bind format arguments.
void SetToDefaultSize()
Send a message to the main window PARENT of the viewport, to resize.
Definition: Viewport.cpp:765
static Viewport & Get(AudacityProject &project)
Definition: Viewport.cpp:33
virtual bool Flush() noexcept=0
double ReadDouble(const wxString &key, double defaultValue) const
virtual bool Write(const wxString &key, bool value)=0
bool OpenInDefaultBrowser(const wxString &url)
Open an URL in default browser.
Definition: BasicUI.cpp:246
AUDACITY_DLL_API bool DoEffect(const PluginID &ID, const CommandContext &context, unsigned flags)
'Repeat Last Effect'.
Definition: EffectUI.cpp:1148
FILES_API void UpdateDefaultPath(Operation op, const FilePath &path)
Facilities for recording and playback of sequences of user interaction.
bool SetRecordEnabled(bool value)
Definition: Journal.cpp:209
bool RecordEnabled()
Definition: Journal.cpp:204
void PopulateEffectsMenu(Group &menuItems, EffectType type, CommandFlag batchflags, const wxString &groupby, void(*onMenuCommand)(const CommandContext &), std::function< bool(const PluginDescriptor &)> pred={})
Definition: MenuHelper.cpp:563
constexpr auto Section
Definition: MenuRegistry.h:436
constexpr auto Items
Definition: MenuRegistry.h:427
constexpr auto Command
Definition: MenuRegistry.h:456
constexpr auto Menu
Items will appear in a main toolbar menu or in a sub-menu.
Definition: MenuRegistry.h:445
std::unique_ptr< detail::IndirectItem< Item > > Indirect(const std::shared_ptr< Item > &ptr)
A convenience function.
Definition: Registry.h:175
FILES_API const FilePath & DefaultTempDir()
void OnRepeatLastEffect(const CommandContext &context)
void OnWriteJournal(const CommandContext &)
const ReservedCommandFlag & HasLastEffectFlag()
void OnResetConfig(const CommandContext &context)
Definition: PluginMenus.cpp:68
bool ShowManager(wxWindow *parent, int effectsCategory)
Definition: PluginMenus.cpp:37
const ReservedCommandFlag & HasLastAnalyzerFlag()
static const ReservedCommandFlag & HasTrackFocusFlag()
void OnAnalyzer2(wxCommandEvent &evt)
void OnRepeatLastGenerator(const CommandContext &context)
void DoManageRealtimeEffectsSidePanel(AudacityProject &project)
Definition: PluginMenus.cpp:51
void OnRepeatLastAnalyzer(const CommandContext &context)
void OnEffect(const CommandContext &context)
static const ReservedCommandFlag & IsRealtimeNotActiveFlag()
void OnManageTools(const CommandContext &context)
void OnDetectUpstreamDropouts(const CommandContext &context)
void OnBenchmark(const CommandContext &context)
void OnManageEffects(const CommandContext &context)
void DoManagePluginsMenu(AudacityProject &project, int effectsCategory)
Definition: PluginMenus.cpp:43
void OnManageAnalyzers(const CommandContext &context)
void OnSimulateRecordingErrors(const CommandContext &context)
const ReservedCommandFlag & HasLastGeneratorFlag()
void OnAddRealtimeEffects(const CommandContext &context)
void OnManageGenerators(const CommandContext &context)
Options && IsGlobal() &&
Definition: MenuRegistry.h:56
Options && CheckTest(const CheckFn &fn) &&
Definition: MenuRegistry.h:74