From f6e56961463c398a0c6a3465158fce4cf547dd09 Mon Sep 17 00:00:00 2001 From: Paul Licameli Date: Wed, 9 Jan 2019 11:27:32 -0500 Subject: [PATCH] Most functions defining menus compute once and cache the result... ... Except a few where project or plugin manager state or preferences are needed to compute the items, so evaluation is delayed, often inside lambdas Comment "Delayed evaluation" wherever there are exceptions --- src/Menus.cpp | 52 +++++++-------- src/menus/ClipMenus.cpp | 24 ++++--- src/menus/EditMenus.cpp | 21 ++++--- src/menus/ExtraMenus.cpp | 113 +++++++++++++++++---------------- src/menus/FileMenus.cpp | 8 ++- src/menus/HelpMenus.cpp | 13 ++-- src/menus/LabelMenus.cpp | 11 ++-- src/menus/NavigationMenus.cpp | 16 +++-- src/menus/PluginMenus.cpp | 115 +++++++++++++++++++++------------- src/menus/SelectMenus.cpp | 55 +++++++++------- src/menus/ToolbarMenus.cpp | 17 ++--- src/menus/TrackMenus.cpp | 21 ++++--- src/menus/TransportMenus.cpp | 40 +++++++----- src/menus/ViewMenus.cpp | 13 ++-- src/menus/WindowMenus.cpp | 22 ++++--- src/prefs/GUIPrefs.cpp | 4 ++ src/tracks/ui/Scrubbing.cpp | 68 +++++++++++--------- src/tracks/ui/Scrubbing.h | 2 +- 18 files changed, 354 insertions(+), 261 deletions(-) diff --git a/src/Menus.cpp b/src/Menus.cpp index 251b070a6..19b6d5bfa 100644 --- a/src/Menus.cpp +++ b/src/Menus.cpp @@ -275,45 +275,45 @@ void VisitItem( AudacityProject &project, MenuTable::BaseItem *pItem ) /// changes in configured preferences - for example changes in key-bindings /// affect the short-cut key legend that appears beside each command, -MenuTable::BaseItemPtr FileMenu( AudacityProject& ); +MenuTable::BaseItemSharedPtr FileMenu(); -MenuTable::BaseItemPtr EditMenu( AudacityProject& ); +MenuTable::BaseItemSharedPtr EditMenu(); -MenuTable::BaseItemPtr SelectMenu( AudacityProject& ); +MenuTable::BaseItemSharedPtr SelectMenu(); -MenuTable::BaseItemPtr ViewMenu( AudacityProject& ); +MenuTable::BaseItemSharedPtr ViewMenu(); -MenuTable::BaseItemPtr TransportMenu( AudacityProject& ); +MenuTable::BaseItemSharedPtr TransportMenu(); -MenuTable::BaseItemPtr TracksMenu( AudacityProject& ); +MenuTable::BaseItemSharedPtr TracksMenu(); -MenuTable::BaseItemPtr GenerateMenu( AudacityProject& ); -MenuTable::BaseItemPtr EffectMenu( AudacityProject& ); -MenuTable::BaseItemPtr AnalyzeMenu( AudacityProject& ); -MenuTable::BaseItemPtr ToolsMenu( AudacityProject& ); +MenuTable::BaseItemSharedPtr GenerateMenu(); +MenuTable::BaseItemSharedPtr EffectMenu(); +MenuTable::BaseItemSharedPtr AnalyzeMenu(); +MenuTable::BaseItemSharedPtr ToolsMenu(); -MenuTable::BaseItemPtr WindowMenu( AudacityProject& ); +MenuTable::BaseItemSharedPtr WindowMenu(); -MenuTable::BaseItemPtr ExtraMenu( AudacityProject& ); +MenuTable::BaseItemSharedPtr ExtraMenu(); -MenuTable::BaseItemPtr HelpMenu( AudacityProject& ); +MenuTable::BaseItemSharedPtr HelpMenu(); // Table of menu factories. // TODO: devise a registration system instead. static const auto menuTree = MenuTable::Items( - FileMenu - , EditMenu - , SelectMenu - , ViewMenu - , TransportMenu - , TracksMenu - , GenerateMenu - , EffectMenu - , AnalyzeMenu - , ToolsMenu - , WindowMenu - , ExtraMenu - , HelpMenu + FileMenu() + , EditMenu() + , SelectMenu() + , ViewMenu() + , TransportMenu() + , TracksMenu() + , GenerateMenu() + , EffectMenu() + , AnalyzeMenu() + , ToolsMenu() + , WindowMenu() + , ExtraMenu() + , HelpMenu() ); void MenuCreator::CreateMenusAndCommands(AudacityProject &project) diff --git a/src/menus/ClipMenus.cpp b/src/menus/ClipMenus.cpp index ae7deba59..3c2d91cad 100644 --- a/src/menus/ClipMenus.cpp +++ b/src/menus/ClipMenus.cpp @@ -823,12 +823,13 @@ static CommandHandlerObject &findCommandHandler(AudacityProject &) { #define FN(X) (& ClipActions::Handler :: X) -MenuTable::BaseItemPtr ClipSelectMenu( AudacityProject& ) +MenuTable::BaseItemSharedPtr ClipSelectMenu() { using namespace MenuTable; using Options = CommandManager::Options; - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("Clip B&oundaries"), Command( wxT("SelPrevClipBoundaryToCursor"), XXO("Pre&vious Clip Boundary to Cursor"), @@ -844,15 +845,17 @@ MenuTable::BaseItemPtr ClipSelectMenu( AudacityProject& ) Command( wxT("SelNextClip"), XXO("N&ext Clip"), FN(OnSelectNextClip), WaveTracksExistFlag, Options{ wxT("Alt+."), XO("Select Next Clip") } ) - ) ); + ) ) }; + return menu; } -MenuTable::BaseItemPtr ClipCursorItems( AudacityProject & ) +MenuTable::BaseItemSharedPtr ClipCursorItems() { using namespace MenuTable; using Options = CommandManager::Options; - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr items{ + FinderScope( findCommandHandler ).Eval( Items( Command( wxT("CursPrevClipBoundary"), XXO("Pre&vious Clip Boundary"), FN(OnCursorPrevClipBoundary), @@ -862,20 +865,23 @@ MenuTable::BaseItemPtr ClipCursorItems( AudacityProject & ) FN(OnCursorNextClipBoundary), WaveTracksExistFlag, Options{}.LongName( XO("Cursor to Next Clip Boundary") ) ) - ) ); + ) ) }; + return items; } -MenuTable::BaseItemPtr ExtraClipCursorItems( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraClipCursorItems() { using namespace MenuTable; - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr items{ + FinderScope( findCommandHandler ).Eval( Items( Command( wxT("ClipLeft"), XXO("Clip L&eft"), FN(OnClipLeft), TracksExistFlag | TrackPanelHasFocus, wxT("\twantKeyup") ), Command( wxT("ClipRight"), XXO("Clip Rig&ht"), FN(OnClipRight), TracksExistFlag | TrackPanelHasFocus, wxT("\twantKeyup") ) - ) ); + ) ) }; + return items; } #undef FN diff --git a/src/menus/EditMenus.cpp b/src/menus/EditMenus.cpp index abe3690c2..dad5410cd 100644 --- a/src/menus/EditMenus.cpp +++ b/src/menus/EditMenus.cpp @@ -997,7 +997,7 @@ static CommandHandlerObject &findCommandHandler(AudacityProject &) { #define FN(X) (& EditActions::Handler :: X) -MenuTable::BaseItemPtr LabelEditMenus( AudacityProject &project ); +MenuTable::BaseItemSharedPtr LabelEditMenus(); const ReservedCommandFlag CutCopyAvailableFlag{ @@ -1024,7 +1024,7 @@ const ReservedCommandFlag cutCopyOptions() }; -MenuTable::BaseItemPtr EditMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr EditMenu() { using namespace MenuTable; using Options = CommandManager::Options; @@ -1051,7 +1051,8 @@ MenuTable::BaseItemPtr EditMenu( AudacityProject & ) #endif ; - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&Edit"), Command( wxT("Undo"), XXO("&Undo"), FN(OnUndo), AudioIONotBusyFlag | UndoAvailableFlag, wxT("Ctrl+Z") ), @@ -1132,7 +1133,7 @@ MenuTable::BaseItemPtr EditMenu( AudacityProject & ) ////////////////////////////////////////////////////////////////////////// - LabelEditMenus, + LabelEditMenus(), Command( wxT("EditMetaData"), XXO("&Metadata..."), FN(OnEditMetadata), AudioIONotBusyFlag ), @@ -1145,17 +1146,18 @@ MenuTable::BaseItemPtr EditMenu( AudacityProject & ) Command( wxT("Preferences"), XXO("Pre&ferences..."), FN(OnPreferences), AudioIONotBusyFlag, prefKey ) - ) ); + ) ) }; + return menu; } -MenuTable::BaseItemPtr ExtraEditMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraEditMenu() { using namespace MenuTable; using Options = CommandManager::Options; static const auto flags = AudioIONotBusyFlag | TracksSelectedFlag | TimeSelectedFlag; - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&Edit"), Command( wxT("DeleteKey"), XXO("&Delete Key"), FN(OnDelete), (flags | NoAutoSelect), @@ -1163,7 +1165,8 @@ MenuTable::BaseItemPtr ExtraEditMenu( AudacityProject & ) Command( wxT("DeleteKey2"), XXO("Delete Key&2"), FN(OnDelete), (flags | NoAutoSelect), wxT("Delete") ) - ) ); + ) ) }; + return menu; } auto canSelectAll = [](const AudacityProject &project){ diff --git a/src/menus/ExtraMenus.cpp b/src/menus/ExtraMenus.cpp index 18ebc3e75..860b3708a 100644 --- a/src/menus/ExtraMenus.cpp +++ b/src/menus/ExtraMenus.cpp @@ -138,62 +138,68 @@ static CommandHandlerObject &findCommandHandler(AudacityProject &) { // Imported menu item definitions -MenuTable::BaseItemPtr ExtraEditMenu( AudacityProject & ); -MenuTable::BaseItemPtr ExtraSelectionMenu( AudacityProject & ); -MenuTable::BaseItemPtr ExtraCursorMenu( AudacityProject & ); -MenuTable::BaseItemPtr ExtraSeekMenu( AudacityProject & ); -MenuTable::BaseItemPtr ExtraToolsMenu( AudacityProject & ); -MenuTable::BaseItemPtr ExtraTransportMenu( AudacityProject & ); -MenuTable::BaseItemPtr ExtraPlayAtSpeedMenu( AudacityProject & ); -MenuTable::BaseItemPtr ExtraTrackMenu( AudacityProject & ); -MenuTable::BaseItemPtr ExtraScriptablesIMenu( AudacityProject & ); -MenuTable::BaseItemPtr ExtraScriptablesIIMenu( AudacityProject & ); -MenuTable::BaseItemPtr ExtraWindowItems( AudacityProject & ); -MenuTable::BaseItemPtr ExtraGlobalCommands( AudacityProject & ); -MenuTable::BaseItemPtr ExtraFocusMenu( AudacityProject & ); -MenuTable::BaseItemPtr ExtraMenu( AudacityProject& ); -MenuTable::BaseItemPtr ExtraMixerMenu( AudacityProject & ); -MenuTable::BaseItemPtr ExtraDeviceMenu( AudacityProject & ); +MenuTable::BaseItemSharedPtr ExtraEditMenu(); +MenuTable::BaseItemSharedPtr ExtraSelectionMenu(); +MenuTable::BaseItemSharedPtr ExtraCursorMenu(); +MenuTable::BaseItemSharedPtr ExtraSeekMenu(); +MenuTable::BaseItemSharedPtr ExtraToolsMenu(); +MenuTable::BaseItemSharedPtr ExtraTransportMenu(); +MenuTable::BaseItemSharedPtr ExtraPlayAtSpeedMenu(); +MenuTable::BaseItemSharedPtr ExtraTrackMenu(); +MenuTable::BaseItemSharedPtr ExtraScriptablesIMenu(); +MenuTable::BaseItemSharedPtr ExtraScriptablesIIMenu(); +MenuTable::BaseItemSharedPtr ExtraWindowItems(); +MenuTable::BaseItemSharedPtr ExtraGlobalCommands(); +MenuTable::BaseItemSharedPtr ExtraFocusMenu(); +MenuTable::BaseItemSharedPtr ExtraMenu(); +MenuTable::BaseItemSharedPtr ExtraMixerMenu(); +MenuTable::BaseItemSharedPtr ExtraDeviceMenu(); MenuTable::BaseItemPtr ExtraMiscItems( AudacityProject & ); -// Table of menu factories. -// TODO: devise a registration system instead. -static const std::shared_ptr extraItems = MenuTable::Items( - ExtraTransportMenu - , ExtraToolsMenu - , ExtraMixerMenu - , ExtraEditMenu - , ExtraPlayAtSpeedMenu - , ExtraSeekMenu - , ExtraDeviceMenu - , ExtraSelectionMenu - - , MenuTable::Separator() - - , ExtraGlobalCommands - , ExtraFocusMenu - , ExtraCursorMenu - , ExtraTrackMenu - , ExtraScriptablesIMenu - , ExtraScriptablesIIMenu - , ExtraMiscItems -); - -MenuTable::BaseItemPtr ExtraMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraMenu() { using namespace MenuTable; + + // Table of menu factories. + // TODO: devise a registration system instead. + static BaseItemSharedPtr extraItems{ + Items( + ExtraTransportMenu() + , ExtraToolsMenu() + , ExtraMixerMenu() + , ExtraEditMenu() + , ExtraPlayAtSpeedMenu() + , ExtraSeekMenu() + , ExtraDeviceMenu() + , ExtraSelectionMenu() + + , MenuTable::Separator() + + , ExtraGlobalCommands() + , ExtraFocusMenu() + , ExtraCursorMenu() + , ExtraTrackMenu() + , ExtraScriptablesIMenu() + , ExtraScriptablesIIMenu() + + // Delayed evaluation: + , ExtraMiscItems + ) }; + static const auto pred = []{ return gPrefs->ReadBool(wxT("/GUI/ShowExtraMenus"), false); }; - static const auto factory = - [](AudacityProject &){ return extraItems; }; - return ConditionalItems( pred, Menu( XO("Ext&ra"), factory ) ); + static BaseItemSharedPtr menu{ + ConditionalItems( + pred, Menu( XO("Ext&ra"), extraItems ) ) + }; + return menu; } -MenuTable::BaseItemPtr ExtraMixerMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraMixerMenu() { using namespace MenuTable; - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("Mi&xer"), Command( wxT("OutputGain"), XXO("Ad&just Playback Volume..."), FN(OnOutputGain), AlwaysEnabledFlag ), @@ -207,14 +213,15 @@ MenuTable::BaseItemPtr ExtraMixerMenu( AudacityProject & ) FN(OnInputGainInc), AlwaysEnabledFlag ), Command( wxT("InputGainDec"), XXO("D&ecrease Recording Volume"), FN(OnInputGainDec), AlwaysEnabledFlag ) - ) ); + ) ) }; + return menu; } -MenuTable::BaseItemPtr ExtraDeviceMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraDeviceMenu() { using namespace MenuTable; - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("De&vice"), Command( wxT("InputDevice"), XXO("Change &Recording Device..."), FN(OnInputDevice), @@ -227,7 +234,8 @@ MenuTable::BaseItemPtr ExtraDeviceMenu( AudacityProject & ) Command( wxT("InputChannels"), XXO("Change Recording Cha&nnels..."), FN(OnInputChannels), AudioIONotBusyFlag, wxT("Shift+N") ) - ) ); + ) ) }; + return menu; } MenuTable::BaseItemPtr ExtraMiscItems( AudacityProject &project ) @@ -244,7 +252,6 @@ MenuTable::BaseItemPtr ExtraMiscItems( AudacityProject &project ) ; // Not a menu. - return FinderScope( findCommandHandler ).Eval( Items( // Accel key is not bindable. @@ -254,7 +261,7 @@ MenuTable::BaseItemPtr ExtraMiscItems( AudacityProject &project ) Options{ key }.CheckState( GetProjectFrame( project ).wxTopLevelWindow::IsFullScreen() ) ), - ExtraWindowItems + ExtraWindowItems() ) ); } diff --git a/src/menus/FileMenus.cpp b/src/menus/FileMenus.cpp index 13de72199..130d526ab 100644 --- a/src/menus/FileMenus.cpp +++ b/src/menus/FileMenus.cpp @@ -551,12 +551,13 @@ static CommandHandlerObject &findCommandHandler(AudacityProject &) { #define FN(X) (& FileActions::Handler :: X) -MenuTable::BaseItemPtr FileMenu( AudacityProject& ) +MenuTable::BaseItemSharedPtr FileMenu() { using namespace MenuTable; using Options = CommandManager::Options; - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&File"), /*i18n-hint: "New" is an action (verb) to create a NEW project*/ Command( wxT("New"), XXO("&New"), FN(OnNew), @@ -698,7 +699,8 @@ MenuTable::BaseItemPtr FileMenu( AudacityProject& ) /* i18n-hint: (verb) It's item on a menu. */ Command( wxT("Exit"), XXO("E&xit"), FN(OnExit), AlwaysEnabledFlag, wxT("Ctrl+Q") ) - ) ); + ) ) }; + return menu; } #undef FN diff --git a/src/menus/HelpMenus.cpp b/src/menus/HelpMenus.cpp index cd3d5aac3..d81a1f528 100644 --- a/src/menus/HelpMenus.cpp +++ b/src/menus/HelpMenus.cpp @@ -420,15 +420,11 @@ static CommandHandlerObject &findCommandHandler(AudacityProject &) { #define FN(X) (& HelpActions::Handler :: X) -MenuTable::BaseItemPtr HelpMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr HelpMenu() { -#ifdef __WXMAC__ - wxApp::s_macHelpMenuTitleName = _("&Help"); -#endif - using namespace MenuTable; - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&Help"), // QuickFix menu item not in Audacity 2.3.1 whilst we discuss further. #ifdef EXPERIMENTAL_DA @@ -480,7 +476,8 @@ MenuTable::BaseItemPtr HelpMenu( AudacityProject & ) #endif Command( wxT("About"), XXO("&About Audacity..."), FN(OnAbout), AlwaysEnabledFlag ) - ) ); + ) ) }; + return menu; } #undef FN diff --git a/src/menus/LabelMenus.cpp b/src/menus/LabelMenus.cpp index 21a72b3b7..cc509fb93 100644 --- a/src/menus/LabelMenus.cpp +++ b/src/menus/LabelMenus.cpp @@ -561,7 +561,7 @@ static CommandHandlerObject &findCommandHandler(AudacityProject &) { #define FN(X) (& LabelEditActions::Handler :: X) -MenuTable::BaseItemPtr LabelEditMenus( AudacityProject & ) +MenuTable::BaseItemSharedPtr LabelEditMenus() { using namespace MenuTable; using Options = CommandManager::Options; @@ -574,10 +574,10 @@ MenuTable::BaseItemPtr LabelEditMenus( AudacityProject & ) // Returns TWO menus. - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menus{ + FinderScope( findCommandHandler ).Eval( Items( - + Menu( XO("&Labels"), Command( wxT("EditLabels"), XXO("&Edit Labels..."), FN(OnEditLabels), AudioIONotBusyFlag ), @@ -654,7 +654,8 @@ MenuTable::BaseItemPtr LabelEditMenus( AudacityProject & ) wxT("Alt+Shift+J") ) ) // second menu - ) ); // two menus + ) ) }; // two menus + return menus; } #undef FN diff --git a/src/menus/NavigationMenus.cpp b/src/menus/NavigationMenus.cpp index 60572531e..c5732058f 100644 --- a/src/menus/NavigationMenus.cpp +++ b/src/menus/NavigationMenus.cpp @@ -555,13 +555,14 @@ static CommandHandlerObject &findCommandHandler(AudacityProject &project) { #define FN(X) (& NavigationActions::Handler :: X) -MenuTable::BaseItemPtr ExtraGlobalCommands( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraGlobalCommands() { // Ceci n'est pas un menu using namespace MenuTable; using Options = CommandManager::Options; - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr items{ + FinderScope( findCommandHandler ).Eval( Items( Command( wxT("PrevWindow"), XXO("Move Backward Through Active Windows"), FN(OnPrevWindow), AlwaysEnabledFlag, @@ -569,15 +570,17 @@ MenuTable::BaseItemPtr ExtraGlobalCommands( AudacityProject & ) Command( wxT("NextWindow"), XXO("Move Forward Through Active Windows"), FN(OnNextWindow), AlwaysEnabledFlag, Options{ wxT("Alt+F6") }.IsGlobal() ) - ) ); + ) ) }; + return items; } -MenuTable::BaseItemPtr ExtraFocusMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraFocusMenu() { using namespace MenuTable; static const auto FocusedTracksFlags = TracksExistFlag | TrackPanelHasFocus; - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("F&ocus"), Command( wxT("PrevFrame"), XXO("Move &Backward from Toolbars to Tracks"), FN(OnPrevFrame), @@ -601,7 +604,8 @@ MenuTable::BaseItemPtr ExtraFocusMenu( AudacityProject & ) FocusedTracksFlags, wxT("Return") ), Command( wxT("ToggleAlt"), XXO("Toggle Focuse&d Track"), FN(OnToggle), FocusedTracksFlags, wxT("NUMPAD_ENTER") ) - ) ); + ) ) }; + return menu; } #undef FN diff --git a/src/menus/PluginMenus.cpp b/src/menus/PluginMenus.cpp index f44bde730..319ed0ebe 100644 --- a/src/menus/PluginMenus.cpp +++ b/src/menus/PluginMenus.cpp @@ -741,13 +741,14 @@ MenuTable::BaseItemPtrs PopulateMacrosMenu( CommandFlag flags ) // Menu definitions -MenuTable::BaseItemPtr GenerateMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr GenerateMenu() { using namespace MenuTable; // All of this is a bit hacky until we can get more things connected into // the plugin manager...sorry! :-( - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&Generate"), #ifdef EXPERIMENTAL_EFFECT_MANAGEMENT Command( wxT("ManageGenerators"), XXO("Add / Remove Plug-ins..."), @@ -757,11 +758,15 @@ MenuTable::BaseItemPtr GenerateMenu( AudacityProject & ) #endif - Items( PopulateEffectsMenu( + // Delayed evaluation: + [](AudacityProject &) + { return Items( PopulateEffectsMenu( EffectTypeGenerate, AudioIONotBusyFlag, - AudioIONotBusyFlag) ) - ) ); + AudioIONotBusyFlag) + ); } + ) ) }; + return menu; } const ReservedCommandFlag @@ -771,21 +776,14 @@ const ReservedCommandFlag } }; //lll -MenuTable::BaseItemPtr EffectMenu( AudacityProject &project ) +MenuTable::BaseItemSharedPtr EffectMenu() { using namespace MenuTable; // All of this is a bit hacky until we can get more things connected into // the plugin manager...sorry! :-( - const auto &lastEffect = MenuManager::Get(project).mLastEffect; - TranslatableString buildMenuLabel; - if (!lastEffect.empty()) - buildMenuLabel = XO("Repeat %s") - .Format( EffectManager::Get().GetCommandName(lastEffect) ); - else - buildMenuLabel = XO("Repeat Last Effect"); - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("Effe&ct"), #ifdef EXPERIMENTAL_EFFECT_MANAGEMENT Command( wxT("ManageEffects"), XXO("Add / Remove Plug-ins..."), @@ -794,28 +792,47 @@ MenuTable::BaseItemPtr EffectMenu( AudacityProject &project ) Separator(), #endif - Command( wxT("RepeatLastEffect"), buildMenuLabel, - FN(OnRepeatLastEffect), - AudioIONotBusyFlag | TimeSelectedFlag | - WaveTracksSelectedFlag | HasLastEffectFlag, - wxT("Ctrl+R") ), + + // Delayed evaluation: + [](AudacityProject &project) + { + const auto &lastEffect = MenuManager::Get(project).mLastEffect; + TranslatableString buildMenuLabel; + if (!lastEffect.empty()) + buildMenuLabel = XO("Repeat %s") + .Format( EffectManager::Get().GetCommandName(lastEffect) ); + else + buildMenuLabel = XO("Repeat Last Effect"); + + return Command( wxT("RepeatLastEffect"), buildMenuLabel, + FN(OnRepeatLastEffect), + AudioIONotBusyFlag | TimeSelectedFlag | + WaveTracksSelectedFlag | HasLastEffectFlag, + wxT("Ctrl+R"), findCommandHandler ); + }, Separator(), - Items( PopulateEffectsMenu( + // Delayed evaluation: + [](AudacityProject &) + { return Items( PopulateEffectsMenu( EffectTypeProcess, AudioIONotBusyFlag | TimeSelectedFlag | WaveTracksSelectedFlag, - IsRealtimeNotActiveFlag ) ) - ) ); + IsRealtimeNotActiveFlag ) + ); } + + ) ) }; + return menu; } -MenuTable::BaseItemPtr AnalyzeMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr AnalyzeMenu() { using namespace MenuTable; // All of this is a bit hacky until we can get more things connected into // the plugin manager...sorry! :-( - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&Analyze"), #ifdef EXPERIMENTAL_EFFECT_MANAGEMENT Command( wxT("ManageAnalyzers"), XXO("Add / Remove Plug-ins..."), @@ -831,19 +848,24 @@ MenuTable::BaseItemPtr AnalyzeMenu( AudacityProject & ) Command( wxT("PlotSpectrum"), XXO("Plot Spectrum..."), FN(OnPlotSpectrum), AudioIONotBusyFlag | WaveTracksSelectedFlag | TimeSelectedFlag ), - Items( PopulateEffectsMenu( + // Delayed evaluation: + [](AudacityProject&) + { return Items( PopulateEffectsMenu( EffectTypeAnalyze, AudioIONotBusyFlag | TimeSelectedFlag | WaveTracksSelectedFlag, - IsRealtimeNotActiveFlag ) ) - ) ); + IsRealtimeNotActiveFlag ) + ); } + ) ) }; + return menu; } -MenuTable::BaseItemPtr ToolsMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ToolsMenu() { using namespace MenuTable; using Options = CommandManager::Options; - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("T&ools"), #ifdef EXPERIMENTAL_EFFECT_MANAGEMENT @@ -865,7 +887,9 @@ MenuTable::BaseItemPtr ToolsMenu( AudacityProject & ) Separator(), - Items( PopulateMacrosMenu( AudioIONotBusyFlag ) ) + // Delayed evaluation: + [](AudacityProject&) + { return Items( PopulateMacrosMenu( AudioIONotBusyFlag ) ); } ), Separator(), @@ -884,10 +908,13 @@ MenuTable::BaseItemPtr ToolsMenu( AudacityProject & ) Separator(), - Items( PopulateEffectsMenu( + // Delayed evaluation: + [](AudacityProject&) + { return Items( PopulateEffectsMenu( EffectTypeTool, AudioIONotBusyFlag, - AudioIONotBusyFlag ) ) + AudioIONotBusyFlag ) + ); } #ifdef IS_ALPHA , @@ -909,19 +936,20 @@ MenuTable::BaseItemPtr ToolsMenu( AudacityProject & ) [](AudacityProject&){ return AudioIO::Get()->mDetectUpstreamDropouts; } ) ) #endif - ) ); + ) ) }; + return menu; } -MenuTable::BaseItemPtr ExtraScriptablesIMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraScriptablesIMenu() { using namespace MenuTable; // These are the more useful to VI user Scriptables. - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( // i18n-hint: Scriptables are commands normally used from Python, Perl etc. Menu( XO("Script&ables I"), - // Note that the PLUGIN_SYMBOL must have a space between words, + // Note that the PLUGIN_SYMBOL must have a space between words, // whereas the short-form used here must not. // (So if you did write "CompareAudio" for the PLUGIN_SYMBOL name, then // you would have to use "Compareaudio" here.) @@ -957,15 +985,17 @@ MenuTable::BaseItemPtr ExtraScriptablesIMenu( AudacityProject & ) AudioIONotBusyFlag ), Command( wxT("SetProject"), XXO("Set Project..."), FN(OnAudacityCommand), AudioIONotBusyFlag ) - ) ); + ) ) }; + return menu; } -MenuTable::BaseItemPtr ExtraScriptablesIIMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraScriptablesIIMenu() { using namespace MenuTable; // Less useful to VI users. - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("Scripta&bles II"), Command( wxT("Select"), XXO("Select..."), FN(OnAudacityCommand), AudioIONotBusyFlag ), @@ -996,7 +1026,8 @@ MenuTable::BaseItemPtr ExtraScriptablesIIMenu( AudacityProject & ) Command( wxT("Screenshot"), XXO("Screenshot (short format)..."), FN(OnAudacityCommand), AudioIONotBusyFlag ) - ) ); + ) ) }; + return menu; } #undef FN diff --git a/src/menus/SelectMenus.cpp b/src/menus/SelectMenus.cpp index 396119491..3d7191bdc 100644 --- a/src/menus/SelectMenus.cpp +++ b/src/menus/SelectMenus.cpp @@ -1028,14 +1028,14 @@ static CommandHandlerObject &findCommandHandler(AudacityProject &project) { #define FN(X) (& SelectActions::Handler :: X) -MenuTable::BaseItemPtr ClipSelectMenu( AudacityProject& ); +MenuTable::BaseItemSharedPtr ClipSelectMenu(); -MenuTable::BaseItemPtr SelectMenu( AudacityProject& ) +MenuTable::BaseItemSharedPtr SelectMenu() { using namespace MenuTable; using Options = CommandManager::Options; - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( /* i18n-hint: (verb) It's an item on a menu. */ Menu( XO("&Select"), Command( wxT("SelectAll"), XXO("&All"), FN(OnSelectAll), @@ -1113,7 +1113,7 @@ MenuTable::BaseItemPtr SelectMenu( AudacityProject& ) ////////////////////////////////////////////////////////////////////////// - ClipSelectMenu, + ClipSelectMenu(), ////////////////////////////////////////////////////////////////////////// @@ -1135,14 +1135,15 @@ MenuTable::BaseItemPtr SelectMenu( AudacityProject& ) Command( wxT("ZeroCross"), XXO("At &Zero Crossings"), FN(OnZeroCrossing), TracksSelectedFlag, Options{ wxT("Z"), XO("Select Zero Crossing") } ) - ) ); + ) ) }; + return menu; } -MenuTable::BaseItemPtr ExtraSelectionMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraSelectionMenu() { using namespace MenuTable; - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&Selection"), Command( wxT("SnapToOff"), XXO("Snap-To &Off"), FN(OnSnapToOff), AlwaysEnabledFlag ), @@ -1176,12 +1177,13 @@ MenuTable::BaseItemPtr ExtraSelectionMenu( AudacityProject & ) FN(OnSelContractRight), TracksExistFlag | TrackPanelHasFocus, wxT("Ctrl+Shift+Left\twantKeyup") ) - ) ); + ) ) }; + return menu; } -MenuTable::BaseItemPtr ClipCursorItems( AudacityProject & ); +MenuTable::BaseItemSharedPtr ClipCursorItems(); -MenuTable::BaseItemPtr CursorMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr CursorMenu() { using namespace MenuTable; using Options = CommandManager::Options; @@ -1192,7 +1194,8 @@ MenuTable::BaseItemPtr CursorMenu( AudacityProject & ) // GA: 'Skip to' moves the viewpoint to center of the track and preserves the // selection. 'Cursor to' does neither. 'Center at' might describe it better // than 'Skip'. - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&Cursor to"), Command( wxT("CursSelStart"), XXO("Selection Star&t"), FN(OnCursorSelStart), @@ -1212,7 +1215,7 @@ MenuTable::BaseItemPtr CursorMenu( AudacityProject & ) TracksSelectedFlag, Options{ wxT("K"), XO("Cursor to Track End") } ), - ClipCursorItems, + ClipCursorItems(), Command( wxT("CursProjectStart"), XXO("&Project Start"), FN(OnSkipStart), @@ -1221,16 +1224,18 @@ MenuTable::BaseItemPtr CursorMenu( AudacityProject & ) Command( wxT("CursProjectEnd"), XXO("Project E&nd"), FN(OnSkipEnd), CanStopFlags, Options{ wxT("End"), XO("Cursor to Project End") } ) - ) ); + ) ) }; + return menu; } -MenuTable::BaseItemPtr ExtraClipCursorItems( AudacityProject & ); +MenuTable::BaseItemSharedPtr ExtraClipCursorItems(); -MenuTable::BaseItemPtr ExtraCursorMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraCursorMenu() { using namespace MenuTable; - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&Cursor"), Command( wxT("CursorLeft"), XXO("Cursor &Left"), FN(OnCursorLeft), TracksExistFlag | TrackPanelHasFocus, @@ -1251,15 +1256,16 @@ MenuTable::BaseItemPtr ExtraCursorMenu( AudacityProject & ) FN(OnCursorLongJumpRight), TracksExistFlag | TrackPanelHasFocus, wxT("Shift+.") ), - ExtraClipCursorItems - ) ); + ExtraClipCursorItems() + ) ) }; + return menu; } -MenuTable::BaseItemPtr ExtraSeekMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraSeekMenu() { using namespace MenuTable; - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("See&k"), Command( wxT("SeekLeftShort"), XXO("Short Seek &Left During Playback"), FN(OnSeekLeftShort), AudioIOBusyFlag, wxT("Left\tallowDup") ), @@ -1270,7 +1276,8 @@ MenuTable::BaseItemPtr ExtraSeekMenu( AudacityProject & ) FN(OnSeekLeftLong), AudioIOBusyFlag, wxT("Shift+Left\tallowDup") ), Command( wxT("SeekRightLong"), XXO("Long Seek Rig&ht During Playback"), FN(OnSeekRightLong), AudioIOBusyFlag, wxT("Shift+Right\tallowDup") ) - ) ); + ) ) }; + return menu; } #undef FN diff --git a/src/menus/ToolbarMenus.cpp b/src/menus/ToolbarMenus.cpp index d070aaebf..711e097bc 100644 --- a/src/menus/ToolbarMenus.cpp +++ b/src/menus/ToolbarMenus.cpp @@ -253,14 +253,15 @@ static CommandHandlerObject &findCommandHandler(AudacityProject &) { #define FN(X) (& ToolbarActions::Handler :: X) -MenuTable::BaseItemPtr ToolbarsMenu( AudacityProject& ) +MenuTable::BaseItemSharedPtr ToolbarsMenu() { using namespace MenuTable; using Options = CommandManager::Options; static const auto checkOff = Options{}.CheckState( false ); - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&Toolbars"), /* i18n-hint: (verb)*/ Command( wxT("ResetToolbars"), XXO("Reset Toolb&ars"), @@ -330,14 +331,15 @@ MenuTable::BaseItemPtr ToolbarsMenu( AudacityProject& ) XXO("Spe&ctral Selection Toolbar"), FN(OnShowSpectralSelectionToolBar), AlwaysEnabledFlag, checkOff ) #endif - ) ); + ) ) }; + return menu; } -MenuTable::BaseItemPtr ExtraToolsMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraToolsMenu() { using namespace MenuTable; - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("T&ools"), Command( wxT("SelectTool"), XXO("&Selection Tool"), FN(OnSelectTool), AlwaysEnabledFlag, wxT("F1") ), @@ -355,7 +357,8 @@ MenuTable::BaseItemPtr ExtraToolsMenu( AudacityProject & ) AlwaysEnabledFlag, wxT("A") ), Command( wxT("NextTool"), XXO("&Next Tool"), FN(OnNextTool), AlwaysEnabledFlag, wxT("D") ) - ) ); + ) ) }; + return menu; } #undef FN diff --git a/src/menus/TrackMenus.cpp b/src/menus/TrackMenus.cpp index e894bba5a..834d4431f 100644 --- a/src/menus/TrackMenus.cpp +++ b/src/menus/TrackMenus.cpp @@ -1276,13 +1276,14 @@ static CommandHandlerObject &findCommandHandler(AudacityProject &) { #define FN(X) (& TrackActions::Handler :: X) -MenuTable::BaseItemPtr TracksMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr TracksMenu() { // Tracks Menu (formerly Project Menu) using namespace MenuTable; using Options = CommandManager::Options; - - return FinderScope( findCommandHandler ).Eval( + + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&Tracks"), Menu( XO("Add &New"), Command( wxT("NewMonoTrack"), XXO("&Mono Track"), FN(OnNewWaveTrack), @@ -1373,7 +1374,7 @@ MenuTable::BaseItemPtr TracksMenu( AudacityProject & ) Separator(), - // Alignment commands using selection or zero + // Alignment commands using selection or zero CommandGroup(wxT("Align"), alignLabels, FN(OnAlign), AudioIONotBusyFlag | TracksSelectedFlag), @@ -1427,14 +1428,15 @@ MenuTable::BaseItemPtr TracksMenu( AudacityProject & ) Options{}.CheckTest( wxT("/GUI/SyncLockTracks"), false ) ) #endif - ) ); + ) ) }; + return menu; } -MenuTable::BaseItemPtr ExtraTrackMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraTrackMenu() { using namespace MenuTable; - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&Track"), Command( wxT("TrackPan"), XXO("Change P&an on Focused Track..."), FN(OnTrackPan), @@ -1479,7 +1481,8 @@ MenuTable::BaseItemPtr ExtraTrackMenu( AudacityProject & ) Command( wxT("TrackMoveBottom"), XXO("Move Focused Track to &Bottom"), FN(OnTrackMoveBottom), AudioIONotBusyFlag | TrackPanelHasFocus | TracksExistFlag ) - ) ); + ) ) }; + return menu; } #undef FN diff --git a/src/menus/TransportMenus.cpp b/src/menus/TransportMenus.cpp index 79f7940f5..609c7f3b9 100644 --- a/src/menus/TransportMenus.cpp +++ b/src/menus/TransportMenus.cpp @@ -968,9 +968,9 @@ static CommandHandlerObject &findCommandHandler(AudacityProject &) { #define FN(X) (& TransportActions::Handler :: X) -MenuTable::BaseItemPtr CursorMenu( AudacityProject& ); +MenuTable::BaseItemSharedPtr CursorMenu(); -MenuTable::BaseItemPtr TransportMenu( AudacityProject &project ) +MenuTable::BaseItemSharedPtr TransportMenu() { using namespace MenuTable; using Options = CommandManager::Options; @@ -980,7 +980,8 @@ MenuTable::BaseItemPtr TransportMenu( AudacityProject &project ) static const auto CanStopFlags = AudioIONotBusyFlag | CanStopAudioStreamFlag; - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( /* i18n-hint: 'Transport' is the name given to the set of controls that play, record, pause etc. */ Menu( XO("Tra&nsport"), @@ -1000,10 +1001,13 @@ MenuTable::BaseItemPtr TransportMenu( AudacityProject &project ) /* i18n-hint: (verb)*/ Command( wxT("Record1stChoice"), XXO("&Record"), FN(OnRecord), CanStopFlags, wxT("R") ), + // The OnRecord2ndChoice function is: if normal record records beside, // it records below, if normal record records below, it records beside. // TODO: Do 'the right thing' with other options like TimerRecord. - Command( wxT("Record2ndChoice"), + // Delayed evaluation in case gPrefs is not yet defined + [](const AudacityProject&) + { return Command( wxT("Record2ndChoice"), // Our first choice is bound to R (by default) // and gets the prime position. // We supply the name for the 'other one' here. @@ -1011,8 +1015,9 @@ MenuTable::BaseItemPtr TransportMenu( AudacityProject &project ) (gPrefs->ReadBool("/GUI/PreferNewTrackRecord", false) ? XO("&Append Record") : XO("Record &New Track")), FN(OnRecord2ndChoice), CanStopFlags, - wxT("Shift+R") - ), + wxT("Shift+R"), + findCommandHandler + ); }, Command( wxT("TimerRecord"), XXO("&Timer Record..."), FN(OnTimerRecord), CanStopFlags, wxT("Shift+T") ), @@ -1034,7 +1039,7 @@ MenuTable::BaseItemPtr TransportMenu( AudacityProject &project ) // Scrubbing sub-menu Scrubber::Menu(), - CursorMenu, + CursorMenu(), Separator(), @@ -1085,14 +1090,15 @@ MenuTable::BaseItemPtr TransportMenu( AudacityProject &project ) AudioIONotBusyFlag | CanStopAudioStreamFlag, checkOff ) #endif ) - ) ); + ) ) }; + return menu; } -MenuTable::BaseItemPtr ExtraTransportMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraTransportMenu() { using namespace MenuTable; - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("T&ransport"), // PlayStop is already in the menus. /* i18n-hint: (verb) Start playing audio*/ @@ -1135,14 +1141,15 @@ MenuTable::BaseItemPtr ExtraTransportMenu( AudacityProject & ) Command(wxT("KeyboardScrubForwards"), XXO("Scrub For&wards"), FN(OnKeyboardScrubForwards), CaptureNotBusyFlag | CanStopAudioStreamFlag, wxT("I\twantKeyup")) - ) ); + ) ) }; + return menu; } -MenuTable::BaseItemPtr ExtraPlayAtSpeedMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraPlayAtSpeedMenu() { using namespace MenuTable; - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&Play-at-Speed"), /* i18n-hint: 'Normal Play-at-Speed' doesn't loop or cut preview. */ Command( wxT("PlayAtSpeed"), XXO("Normal Pl&ay-at-Speed"), @@ -1167,7 +1174,8 @@ MenuTable::BaseItemPtr ExtraPlayAtSpeedMenu( AudacityProject & ) Command( wxT("MoveToNextLabel"), XXO("Move to &Next Label"), FN(OnMoveToNextLabel), CaptureNotBusyFlag | TrackPanelHasFocus, wxT("Alt+Right") ) - ) ); + ) ) }; + return menu; } #undef FN diff --git a/src/menus/ViewMenus.cpp b/src/menus/ViewMenus.cpp index e6e0878a2..75e6d20b2 100644 --- a/src/menus/ViewMenus.cpp +++ b/src/menus/ViewMenus.cpp @@ -432,16 +432,17 @@ static CommandHandlerObject &findCommandHandler(AudacityProject &project) { #define FN(X) (& ViewActions::Handler :: X) -MenuTable::BaseItemPtr ToolbarsMenu( AudacityProject& ); +MenuTable::BaseItemSharedPtr ToolbarsMenu(); -MenuTable::BaseItemPtr ViewMenu( AudacityProject& ) +MenuTable::BaseItemSharedPtr ViewMenu() { using namespace MenuTable; using Options = CommandManager::Options; static const auto checkOff = Options{}.CheckState( false ); - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&View"), Menu( XO("&Zoom"), Command( wxT("ZoomIn"), XXO("Zoom &In"), FN(OnZoomIn), @@ -532,7 +533,7 @@ MenuTable::BaseItemPtr ViewMenu( AudacityProject& ) ////////////////////////////////////////////////////////////////////////// - ToolbarsMenu, + ToolbarsMenu(), Separator(), @@ -547,7 +548,9 @@ MenuTable::BaseItemPtr ViewMenu( AudacityProject& ) Command( wxT("ShowEffectsRack"), XXO("Show Effects Rack"), FN(OnShowEffectsRack), AlwaysEnabledFlag, checkOff ) #endif - ) ); + ) ) }; + return menu; + } #undef FN diff --git a/src/menus/WindowMenus.cpp b/src/menus/WindowMenus.cpp index 02ed69a5d..43199dd96 100644 --- a/src/menus/WindowMenus.cpp +++ b/src/menus/WindowMenus.cpp @@ -118,14 +118,14 @@ static CommandHandlerObject &findCommandHandler(AudacityProject &) { #define FN(X) (& WindowActions::Handler :: X) -MenuTable::BaseItemPtr WindowMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr WindowMenu() { ////////////////////////////////////////////////////////////////////////// // poor imitation of the Mac Windows Menu ////////////////////////////////////////////////////////////////////////// using namespace MenuTable; - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr menu{ + FinderScope( findCommandHandler ).Eval( Menu( XO("&Window"), /* i18n-hint: Standard Macintosh Window menu item: Make (the current * window) shrink to an icon on the dock */ @@ -142,21 +142,23 @@ MenuTable::BaseItemPtr WindowMenu( AudacityProject & ) * windows un-hidden */ Command( wxT("MacBringAllToFront"), XXO("&Bring All to Front"), FN(OnMacBringAllToFront), AlwaysEnabledFlag ) - ) ); + ) ) }; + return menu; } -MenuTable::BaseItemPtr ExtraWindowItems( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraWindowItems() { using namespace MenuTable; - - return FinderScope( findCommandHandler ).Eval( + static BaseItemSharedPtr items{ + FinderScope( findCommandHandler ).Eval( Items( /* i18n-hint: Shrink all project windows to icons on the Macintosh tooldock */ Command( wxT("MacMinimizeAll"), XXO("Minimize All Projects"), FN(OnMacMinimizeAll), AlwaysEnabledFlag, wxT("Ctrl+Alt+M") ) - ) ); + ) ) }; + return items; } #undef FN @@ -164,12 +166,12 @@ MenuTable::BaseItemPtr ExtraWindowItems( AudacityProject & ) #else // Not WXMAC. Stub functions. -MenuTable::BaseItemPtr WindowMenu( AudacityProject & ) +MenuTable::BaseItemSharedPtr WindowMenu() { return nullptr; } -MenuTable::BaseItemPtr ExtraWindowItems( AudacityProject & ) +MenuTable::BaseItemSharedPtr ExtraWindowItems() { return nullptr; } diff --git a/src/prefs/GUIPrefs.cpp b/src/prefs/GUIPrefs.cpp index b9f50b63c..0f0fc684a 100644 --- a/src/prefs/GUIPrefs.cpp +++ b/src/prefs/GUIPrefs.cpp @@ -360,6 +360,10 @@ wxString GUIPrefs::SetLang( const wxString & lang ) // we're not using them yet... using future1 = decltype( XO("Master Gain Control") ); +#ifdef __WXMAC__ + wxApp::s_macHelpMenuTitleName = _("&Help"); +#endif + return result; } diff --git a/src/tracks/ui/Scrubbing.cpp b/src/tracks/ui/Scrubbing.cpp index 638d6246d..ffb576711 100644 --- a/src/tracks/ui/Scrubbing.cpp +++ b/src/tracks/ui/Scrubbing.cpp @@ -258,7 +258,7 @@ static const ReservedCommandFlag HasWaveDataFlag{ HasWaveDataPred }; // jkc namespace { - const struct MenuItem { + struct MenuItem { CommandID name; TranslatableString label; TranslatableString status; @@ -268,7 +268,11 @@ namespace { bool (Scrubber::*StatusTest)() const; const TranslatableString &GetStatus() const { return status; } - } menuItems[] = { + }; + using MenuItems = std::vector< MenuItem >; + const MenuItems &menuItems() + { + static MenuItems theItems{ /* i18n-hint: These commands assist the user in finding a sound by ear. ... "Scrubbing" is variable-speed playback, ... "Seeking" is normal speed playback but with skips, ... @@ -287,13 +291,13 @@ namespace { AlwaysEnabledFlag, &Scrubber::OnToggleScrubRuler, false, &Scrubber::ShowsBar, }, + }; + return theItems; }; - enum { nMenuItems = sizeof(menuItems) / sizeof(*menuItems) }; - inline const MenuItem &FindMenuItem(bool seek) { - return *std::find_if(menuItems, menuItems + nMenuItems, + return *std::find_if(menuItems().begin(), menuItems().end(), [=](const MenuItem &item) { return seek == item.seek; } @@ -1055,7 +1059,7 @@ BEGIN_EVENT_TABLE(Scrubber, wxEvtHandler) EVT_MENU(CMD_ID + 2, THUNK(OnToggleScrubRuler)) END_EVENT_TABLE() -static_assert(nMenuItems == 3, "wrong number of items"); +//static_assert(menuItems().size() == 3, "wrong number of items"); static auto sPlayAtSpeedStatus = XO("Playing at Speed"); @@ -1101,7 +1105,7 @@ registeredStatusWidthFunction{ if ( field == stateStatusBarField ) { TranslatableStrings strings; // Note that Scrubbing + Paused is not allowed. - for (const auto &item : menuItems) + for (const auto &item : menuItems()) strings.push_back( item.GetStatus() ); strings.push_back( XO("%s Paused.").Format( sPlayAtSpeedStatus ) @@ -1121,36 +1125,44 @@ bool Scrubber::CanScrub() const HasWaveDataPred( *mProject ); } -MenuTable::BaseItemPtr Scrubber::Menu() +MenuTable::BaseItemSharedPtr Scrubber::Menu() { + using namespace MenuTable; using Options = CommandManager::Options; - auto scope = MenuTable::FinderScope( + static BaseItemSharedPtr menu { + FinderScope( [](AudacityProject &project) -> CommandHandlerObject& - { return Scrubber::Get( project ); } ); - - MenuTable::BaseItemPtrs ptrs; - for (const auto &item : menuItems) { - ptrs.push_back( MenuTable::Command( item.name, item.label, - item.memFn, - item.flags, - item.StatusTest - ? // a checkmark item - Options{}.CheckTest( [&item](AudacityProject &project){ - return ( Scrubber::Get(project).*(item.StatusTest) )(); } ) - : // not a checkmark item - Options{} - ) ); - } - - return MenuTable::Menu( XO("Scru&bbing"), std::move( ptrs ) ); + { return Scrubber::Get( project ); } + ).Eval( + MenuTable::Menu( + XO("Scru&bbing"), + []{ + BaseItemPtrs ptrs; + for (const auto &item : menuItems()) { + ptrs.push_back( MenuTable::Command( item.name, item.label, + item.memFn, + item.flags, + item.StatusTest + ? // a checkmark item + Options{}.CheckTest( [&item](AudacityProject &project){ + return ( Scrubber::Get(project).*(item.StatusTest) )(); } ) + : // not a checkmark item + Options{} + ) ); + } + return ptrs; + }() + ) ) }; + + return menu; } void Scrubber::PopulatePopupMenu(wxMenu &menu) { int id = CMD_ID; auto &cm = CommandManager::Get( *mProject ); - for (const auto &item : menuItems) { + for (const auto &item : menuItems()) { if (cm.GetEnabled(item.name)) { auto test = item.StatusTest; menu.Append(id, item.label.Translation(), wxString{}, @@ -1165,7 +1177,7 @@ void Scrubber::PopulatePopupMenu(wxMenu &menu) void Scrubber::CheckMenuItems() { auto &cm = CommandManager::Get( *mProject ); - for (const auto &item : menuItems) { + for (const auto &item : menuItems()) { auto test = item.StatusTest; if (test) cm.Check(item.name, (this->*test)()); diff --git a/src/tracks/ui/Scrubbing.h b/src/tracks/ui/Scrubbing.h index 08d818cfe..9be0ea08c 100644 --- a/src/tracks/ui/Scrubbing.h +++ b/src/tracks/ui/Scrubbing.h @@ -118,7 +118,7 @@ public: bool CanScrub() const; // For the toolbar - static MenuTable::BaseItemPtr Menu(); + static MenuTable::BaseItemSharedPtr Menu(); // For popup void PopulatePopupMenu(wxMenu &menu);