diff --git a/src/Menus.cpp b/src/Menus.cpp index 06007c3d2..756fd2db6 100644 --- a/src/Menus.cpp +++ b/src/Menus.cpp @@ -199,7 +199,7 @@ namespace MenuTable { MenuItem::MenuItem( const Identifier &internalName, const TranslatableString &title_, BaseItemPtrs &&items_ ) -: ConcreteGroupItem< false, MenuVisitor >{ +: ConcreteGroupItem< false, ToolbarMenuVisitor >{ internalName, std::move( items_ ) }, title{ title_ } { wxASSERT( !title.empty() ); @@ -208,7 +208,7 @@ MenuItem::~MenuItem() {} ConditionalGroupItem::ConditionalGroupItem( const Identifier &internalName, Condition condition_, BaseItemPtrs &&items_ ) -: ConcreteGroupItem< false, MenuVisitor >{ +: ConcreteGroupItem< false, ToolbarMenuVisitor >{ internalName, std::move( items_ ) }, condition{ condition_ } { } @@ -240,6 +240,8 @@ CommandGroupItem::~CommandGroupItem() {} SpecialItem::~SpecialItem() {} +MenuSection::~MenuSection() {} + CommandHandlerFinder FinderScope::sFinder = [](AudacityProject &project) -> CommandHandlerObject & { // If this default finder function is reached, then FinderScope should @@ -1058,10 +1060,10 @@ namespace { using namespace MenuTable; -struct MenuItemVisitor : MenuVisitor +struct MenuItemVisitor : ToolbarMenuVisitor { MenuItemVisitor( AudacityProject &proj, CommandManager &man ) - : MenuVisitor(proj), manager( man ) {} + : ToolbarMenuVisitor(proj), manager( man ) {} void DoBeginGroup( GroupItem &item, const Path& ) override { @@ -1209,7 +1211,7 @@ void MenuCreator::CreateMenusAndCommands(AudacityProject &project) #endif } -void MenuManager::Visit( MenuVisitor &visitor ) +void MenuManager::Visit( ToolbarMenuVisitor &visitor ) { static const auto menuTree = MenuTable::Items( MenuPathStart ); Registry::Visit( visitor, menuTree.get(), &sRegistry() ); diff --git a/src/Menus.h b/src/Menus.h index 232757659..1bd5f2d71 100644 --- a/src/Menus.h +++ b/src/Menus.h @@ -54,7 +54,7 @@ public: PluginID mLastEffect{}; }; -struct MenuVisitor; +struct ToolbarMenuVisitor; class MenuManager final : public MenuCreator @@ -72,7 +72,7 @@ public: MenuManager &operator=( const MenuManager & ) PROHIBITED; ~MenuManager(); - static void Visit( MenuVisitor &visitor ); + static void Visit( ToolbarMenuVisitor &visitor ); static void ModifyUndoMenuItems(AudacityProject &project); static void ModifyToolbarMenus(AudacityProject &project); diff --git a/src/commands/CommandManager.h b/src/commands/CommandManager.h index 6eb9d661a..932c37400 100644 --- a/src/commands/CommandManager.h +++ b/src/commands/CommandManager.h @@ -667,9 +667,6 @@ namespace Registry { struct MenuVisitor : Registry::Visitor { - explicit MenuVisitor( AudacityProject &p ) : project{ p } {} - operator AudacityProject & () const { return project; } - // final overrides void BeginGroup( Registry::GroupItem &item, const Path &path ) final; void EndGroup( Registry::GroupItem &item, const Path& ) final; @@ -681,20 +678,25 @@ struct MenuVisitor : Registry::Visitor virtual void DoVisit( Registry::SingleItem &item, const Path &path ); virtual void DoSeparator(); - AudacityProject &project; - private: void MaybeDoSeparator(); std::vector firstItem; std::vector needSeparator; }; +struct ToolbarMenuVisitor : MenuVisitor +{ + explicit ToolbarMenuVisitor( AudacityProject &p ) : project{ p } {} + operator AudacityProject & () const { return project; } + AudacityProject &project; +}; + // Define items that populate tables that specifically describe menu trees namespace MenuTable { using namespace Registry; // Describes a main menu in the toolbar, or a sub-menu - struct MenuItem final : ConcreteGroupItem< false, MenuVisitor > { + struct MenuItem final : ConcreteGroupItem< false, ToolbarMenuVisitor > { // Construction from an internal name and a previously built-up // vector of pointers MenuItem( const Identifier &internalName, @@ -703,7 +705,7 @@ namespace MenuTable { template< typename... Args > MenuItem( const Identifier &internalName, const TranslatableString &title_, Args&&... args ) - : ConcreteGroupItem< false, MenuVisitor >{ + : ConcreteGroupItem< false, ToolbarMenuVisitor >{ internalName, std::forward(args)... } , title{ title_ } {} @@ -714,7 +716,8 @@ namespace MenuTable { // Collects other items that are conditionally shown or hidden, but are // always available to macro programming - struct ConditionalGroupItem final : ConcreteGroupItem< false, MenuVisitor > { + struct ConditionalGroupItem final + : ConcreteGroupItem< false, ToolbarMenuVisitor > { using Condition = std::function< bool() >; // Construction from an internal name and a previously built-up @@ -725,7 +728,7 @@ namespace MenuTable { template< typename... Args > ConditionalGroupItem( const Identifier &internalName, Condition condition_, Args&&... args ) - : ConcreteGroupItem< false, MenuVisitor >{ + : ConcreteGroupItem< false, ToolbarMenuVisitor >{ internalName, std::forward(args)... } , condition{ condition_ } {} @@ -839,18 +842,21 @@ namespace MenuTable { Appender fn; }; - template< bool Transparent > - struct MenuPart : ConcreteGroupItem< Transparent, MenuVisitor > + // This exists only so that dynamic_cast can find it + struct MenuSection { + virtual ~MenuSection(); + }; + + struct MenuPart : ConcreteGroupItem< false, ToolbarMenuVisitor >, MenuSection { template< typename... Args > explicit MenuPart( const Identifier &internalName, Args&&... args ) - : ConcreteGroupItem< Transparent, MenuVisitor >{ + : ConcreteGroupItem< false, ToolbarMenuVisitor >{ internalName, std::forward< Args >( args )... } {} }; - using MenuItems = MenuPart< true >; - using MenuSection = MenuPart< false >; + using MenuItems = ConcreteGroupItem< true, ToolbarMenuVisitor >; // The following, and Shared(), are the functions to use directly // in writing table definitions. @@ -874,9 +880,9 @@ namespace MenuTable { // It's not necessary that the sisters of sections be other sections, but it // might clarify the logical groupings. template< typename... Args > - inline std::unique_ptr< MenuSection > Section( + inline std::unique_ptr< MenuPart > Section( const Identifier &internalName, Args&&... args ) - { return std::make_unique< MenuSection >( + { return std::make_unique< MenuPart >( internalName, std::forward(args)... ); } // Menu items can be constructed two ways, as for group items diff --git a/src/menus/HelpMenus.cpp b/src/menus/HelpMenus.cpp index 597b1fe4a..993d1b5c8 100644 --- a/src/menus/HelpMenus.cpp +++ b/src/menus/HelpMenus.cpp @@ -380,9 +380,9 @@ void OnMenuTree(const CommandContext &context) auto &project = context.project; using namespace MenuTable; - struct MyVisitor : MenuVisitor + struct MyVisitor : ToolbarMenuVisitor { - using MenuVisitor::MenuVisitor; + using ToolbarMenuVisitor::ToolbarMenuVisitor; enum : unsigned { TAB = 3 }; void DoBeginGroup( GroupItem &item, const Path& ) override