本页内容

QMenu Class

QMenu 类提供了一个菜单控件,可用于菜单栏、上下文菜单和其他弹出菜单。更多内容...

头文件: #include <QMenu>
CMake: find_package(Qt6 REQUIRED COMPONENTS Widgets)
target_link_libraries(mytarget PRIVATE Qt6::Widgets)
qmake: QT += widgets
继承自: QWidget

属性

公共函数

QMenu(QWidget *parent = nullptr)
QMenu(const QString &title, QWidget *parent = nullptr)
virtual ~QMenu()
QAction *actionAt(const QPoint &pt) const
QRect actionGeometry(QAction *act) const
QAction *activeAction() const
QAction *addMenu(QMenu *menu)
QMenu *addMenu(const QString &title)
QMenu *addMenu(const QIcon &icon, const QString &title)
QAction *addSection(const QString &text)
QAction *addSection(const QIcon &icon, const QString &text)
QAction *addSeparator()
void clear()
QAction *defaultAction() const
QAction *exec()
QAction *exec(const QPoint &p, QAction *action = nullptr)
void hideTearOffMenu()
QIcon icon() const
QAction *insertMenu(QAction *before, QMenu *menu)
QAction *insertSection(QAction *before, const QString &text)
QAction *insertSection(QAction *before, const QIcon &icon, const QString &text)
QAction *insertSeparator(QAction *before)
bool isEmpty() const
bool isTearOffEnabled() const
bool isTearOffMenuVisible() const
QAction *menuAction() const
void popup(const QPoint &p, QAction *atAction = nullptr)
bool separatorsCollapsible() const
void setActiveAction(QAction *act)
void setAsDockMenu()
void setDefaultAction(QAction *act)
void setIcon(const QIcon &icon)
void setSeparatorsCollapsible(bool collapse)
void setTearOffEnabled(bool)
void setTitle(const QString &title)
void setToolTipsVisible(bool visible)
void showTearOffMenu(const QPoint &pos)
void showTearOffMenu()
QString title() const
NSMenu *toNSMenu()
bool toolTipsVisible() const

重新实现的公共函数

virtual QSize sizeHint() const override

信号

void aboutToHide()
void aboutToShow()
void hovered(QAction *action)
void triggered(QAction *action)

静态公共成员

QAction *exec(const QList<QAction *> &actions, const QPoint &pos, QAction *at = nullptr, QWidget *parent = nullptr)
QMenu *menuInAction(const QAction *action)

受保护函数

int columnCount() const
virtual void initStyleOption(QStyleOptionMenuItem *option, const QAction *action) const

重新实现的受保护函数

virtual void actionEvent(QActionEvent *e) override
virtual void changeEvent(QEvent *e) override
virtual void enterEvent(QEnterEvent *) override
virtual bool event(QEvent *e) override
virtual bool focusNextPrevChild(bool next) override
virtual void hideEvent(QHideEvent *) override
virtual void keyPressEvent(QKeyEvent *e) override
virtual void leaveEvent(QEvent *) override
virtual void mouseMoveEvent(QMouseEvent *e) override
virtual void mousePressEvent(QMouseEvent *e) override
virtual void mouseReleaseEvent(QMouseEvent *e) override
virtual void paintEvent(QPaintEvent *e) override
virtual void timerEvent(QTimerEvent *e) override
virtual void wheelEvent(QWheelEvent *e) override

详细说明

包含多个操作项的菜单

菜单控件是一种选择菜单。它可以是菜单栏中的下拉菜单,也可以是独立的上下文菜单。当下拉菜单显示时,用户点击相应项目或按下指定的快捷键,菜单栏便会显示该菜单。使用QMenuBar::addMenu()将菜单插入到菜单栏中。 上下文菜单通常通过某些特殊的键盘键或右键单击来调用。它们既可以通过 `popup()` 异步执行,也可以通过 `exec()` 同步执行。菜单还可以通过响应按钮点击来调用;这些菜单除了调用方式不同外,与上下文菜单完全相同。

操作

一个菜单由一组操作项组成。可通过 addAction()、addActions() 和insertAction() 函数添加操作项。操作项以垂直方式显示,并通过QStyle 进行渲染。此外,操作项可以包含文本标签、绘制在最左侧的可选图标,以及诸如“Ctrl+X”之类的快捷键序列。

可通过actions() 获取菜单中现有的操作项。

操作项分为四类:分隔符、显示子菜单的操作、控件以及执行特定操作的操作项。分隔符通过addSeparator()插入,子菜单通过addMenu()插入,其余所有项均被视为操作项。

插入操作项时,通常需要指定一个接收器和一个槽。每当该操作项被triggered()时,接收器都会收到通知。此外,QMenu还提供了两个信号:triggered()和hovered(),它们会向QAction 发出触发菜单的信号。

使用clear() 可以清除菜单,使用removeAction() 可以删除单个操作项。

QMenu 还可以提供一个可拆分菜单。可拆分菜单是一个顶级窗口,其中包含该菜单的副本。这使得用户能够将常用菜单“拆分”出来,并将其放置在屏幕上的方便位置。 若希望某个菜单具备此功能,请使用setTearOffEnabled() 插入一个可分离句柄。使用可分离菜单时,请注意该概念在 Microsoft Windows 中通常不被采用,因此部分用户可能不熟悉。建议改用QToolBar 。

可以通过 `QWidgetAction ` 类将小部件插入菜单。该类的实例用于容纳小部件,并通过接受 `QAction` 参数的 `addAction()` 重载方法将其插入菜单。如果 `QWidgetAction ` 触发了 `triggered()` 信号,菜单将关闭。

警告:要使 QMenu 在屏幕上可见,应使用exec() 或popup(),而不是show() 或setVisible()。若要隐藏或禁用菜单栏中的菜单,或隐藏/禁用将其作为子菜单添加到其他菜单中的菜单,请改用menuAction() 的相应属性。

在 macOS 上使用基于 Cocoa 构建的 Qt 时的 QMenu

QMenu 只能在菜单/菜单栏中插入一次。后续的插入操作将无效,或导致菜单项处于禁用状态。

请参阅“菜单”示例,了解如何在应用程序中使用QMenuBar 和 QMenu。

重要的继承函数:addAction()、removeAction()、clear()、addSeparator() 和addMenu()。

另请参阅《 QMenuBar 》和“菜单示例”。

属性文档

icon : QIcon

该属性存储菜单的图标

这相当于menuAction()对象的QAction::icon 属性。

默认情况下,如果未显式设置图标,则该属性包含一个空图标。

访问函数:

QIcon icon() const
void setIcon(const QIcon &icon)

separatorsCollapsible : bool

此属性用于控制是否应将连续的分隔符折叠

此属性指定菜单中连续的分隔符是否应在视觉上折叠为一个。菜单开头或结尾的分隔符也会被隐藏。

默认情况下,此属性值为true 。

访问函数:

bool separatorsCollapsible() const
void setSeparatorsCollapsible(bool collapse)

tearOffEnabled : bool

该属性表示菜单是否支持撕下功能

当值为 true 时,菜单中包含一个特殊的“分离”选项(通常显示为菜单顶部的虚线),触发该选项时会创建菜单的副本。

这个“分离”后的副本位于一个单独的窗口中。它包含与原始菜单相同的菜单项,但不含分离控点。

默认情况下,此属性的值为false 。

访问函数:

bool isTearOffEnabled() const
void setTearOffEnabled(bool)

title : QString

该属性用于指定菜单的标题

这相当于menuAction()对象的QAction::text 属性。

默认情况下,该属性包含一个空字符串。

访问函数:

QString title() const
void setTitle(const QString &title)

toolTipsVisible : bool

此属性用于控制菜单操作的工具提示是否应显示

该属性用于指定操作菜单项是否显示其工具提示。

默认情况下,此属性的值为false 。

访问函数:

bool toolTipsVisible() const
void setToolTipsVisible(bool visible)

成员函数文档

[explicit] QMenu::QMenu(QWidget *parent = nullptr)

创建一个父级为parent 的菜单。

尽管弹出菜单始终是顶级控件,但如果传入了父控件,则当该父控件被销毁时,弹出菜单也会被删除(与其他任何QObject 一样)。

[explicit] QMenu::QMenu(const QString &title, QWidget *parent = nullptr)

创建一个包含title 和parent 的菜单。

尽管弹出菜单始终是顶级小部件,但如果传入了父级对象,当该父级对象被销毁时,弹出菜单也将被删除(与任何其他QObject 相同)。

另请参阅 title 。

[virtual noexcept] QMenu::~QMenu()

关闭菜单。

[signal] void QMenu::aboutToHide()

该信号是在菜单从用户视图中隐藏之前发出的。

另请参阅 aboutToShow() 和hide()。

[signal] void QMenu::aboutToShow()

该信号是在向用户显示菜单之前发出的。

另请参阅 aboutToHide() 和show()。

QAction *QMenu::actionAt(const QPoint &pt) const

返回位于 `pt` 处的项目;如果该处没有项目,则返回 `nullptr `。

[override virtual protected] void QMenu::actionEvent(QActionEvent *e)

重写了:QWidget::actionEvent(QActionEvent *event)。

QRect QMenu::actionGeometry(QAction *act) const

返回操作act 的几何信息。

QAction *QMenu::activeAction() const

返回当前选中的操作;如果当前没有选中的操作,则返回nullptr 。

另请参阅 setActiveAction()。

QAction *QMenu::addMenu(QMenu *menu)

此便捷函数将menu 作为子菜单添加到该菜单中。它返回menu 的menuAction()。该菜单不会获取menu 的所有权。

另请参阅 QWidget::addAction() 和QMenu::menuAction()。

QMenu *QMenu::addMenu(const QString &title)

将一个新的QMenu (其title )追加到菜单中。该菜单将接管该菜单的所有权。返回新的菜单。

另请参阅 QWidget::addAction() 和QMenu::menuAction()。

QMenu *QMenu::addMenu(const QIcon &icon, const QString &title)

将一个包含icon 和title 的新QMenu 项追加到菜单中。该菜单将接管该菜单的所有权。返回新的菜单。

另请参阅 QWidget::addAction() 和QMenu::menuAction()。

QAction *QMenu::addSection(const QString &text)

此便捷函数会创建一个新的分区操作,即一个QAction::isSeparator()返回true、同时具有text 提示的操作,并将该新操作添加到此菜单的操作列表中。它返回新创建的操作。

提示的渲染效果取决于样式和平台。控件样式可以在渲染分节时使用其中的文本信息,也可以选择忽略该信息,将分节渲染为简单的分隔符。

QMenu 该方法将接管返回的QAction 的所有权。

另请参阅 QWidget::addAction()。

QAction *QMenu::addSection(const QIcon &icon, const QString &text)

此便捷函数会创建一个新的分区操作,即一个QAction::isSeparator()返回true,同时具有text 和icon 提示的操作,并将该新操作添加到此菜单的操作列表中。它返回新创建的操作。

提示信息的渲染效果取决于样式和平台。控件样式可以在渲染分区时使用其中的文本和图标信息,也可以选择忽略这些信息,将分区渲染为简单的分隔符。

QMenu 该函数将接管返回的 `QAction` 的所有权。

另请参阅 QWidget::addAction()。

QAction *QMenu::addSeparator()

此便捷函数会创建一个新的分隔符操作,即一个QAction::isSeparator()返回true的操作,并将该新操作添加到此菜单的操作列表中。它返回新创建的操作。

QMenu 获取返回的 `QAction` 的所有权。

另请参阅 QWidget::addAction()。

[override virtual protected] void QMenu::changeEvent(QEvent *e)

重写了:QWidget::changeEvent(QEvent *event)。

void QMenu::clear()

删除菜单中的所有操作。属于该菜单且未在其他小部件中显示的操作将被删除。

另请参阅 removeAction()。

[protected] int QMenu::columnCount() const

如果菜单无法完全显示在屏幕上,它会自动调整布局以适应屏幕。具体采用何种布局取决于系统风格(例如,在 Windows 系统上会采用多栏布局)。

该函数返回所需的列数。

QAction *QMenu::defaultAction() const

返回当前的默认操作。

另请参阅 setDefaultAction()。

[override virtual protected] void QMenu::enterEvent(QEnterEvent *)

重写了:QWidget::enterEvent(QEnterEvent *event)。

[override virtual protected] bool QMenu::event(QEvent *e)

重写了:QWidget::event(QEvent *event)。

QAction *QMenu::exec()

同步执行此菜单。

这相当于exec(pos()) 。

该方法会返回在弹出菜单或其子菜单中被触发的QAction ,若未触发任何项目(通常是因为用户按下了Esc键),则返回nullptr 。

在大多数情况下,您需要自行指定位置,例如当前鼠标位置:

exec(QCursor::pos());

或对齐到某个控件:

exec(somewidget.mapToGlobal(QPoint(0,0)));

或响应于QMouseEvent *e:

exec(e->globalPosition().toPoint());

QAction *QMenu::exec(const QPoint &p, QAction *action = nullptr)

同步执行此菜单。

弹出菜单,使操作action 位于指定的全局位置p 。要将控件的本地坐标转换为全局坐标,请使用QWidget::mapToGlobal()。

该方法返回在弹出菜单或其子菜单中被触发的QAction ,若未触发任何项目(通常是因为用户按下了 Esc 键),则返回nullptr 。

请注意,所有信号都会照常发出。如果你将QAction 连接到一个slot并调用菜单的exec(),则既可以通过信号-槽连接获得结果,也可以通过exec()的返回值获得结果。

常见用法是将菜单定位在当前鼠标位置:

exec(QCursor::pos());

或与某个控件对齐:

exec(somewidget.mapToGlobal(QPoint(0, 0)));

或响应QMouseEvent 事件:*e:

exec(e->globalPosition().toPoint());

使用 exec() 或popup() 定位菜单时,请注意不能依赖菜单当前的size() 值。出于性能考虑,菜单仅在必要时才会调整其大小。 因此,在许多情况下,显示前后的尺寸会有所不同。建议改用sizeHint(),该函数会根据菜单的当前内容计算出正确的尺寸。

这是一个重载函数。

另请参阅 popup() 和QWidget::mapToGlobal()。

[static] QAction *QMenu::exec(const QList<QAction *> &actions, const QPoint &pos, QAction *at = nullptr, QWidget *parent = nullptr)

同步执行菜单。

菜单的操作由actions 列表指定。菜单将弹出,使得指定的操作at 出现在全局位置pos 处。 如果未指定at ,则菜单将显示在位置pos 处。parent 是菜单的父控件;当仅凭pos 无法确定菜单应显示的位置时(例如,存在多个桌面或父控件嵌入在QGraphicsView 中),指定父控件可提供上下文信息。

该函数返回被触发的QAction ,该项位于弹出菜单或其子菜单之一中;若未触发任何项目(通常是因为用户按下了Esc键),则返回nullptr 。

这等同于:

QMenu menu;
QAction *at = actions[0]; // Assumes actions is not empty
for (QAction *a : std::as_const(actions))
    menu.addAction(a);
menu.exec(pos, at);

这是一个重载函数。

另请参阅 popup() 和QWidget::mapToGlobal()。

[override virtual protected] bool QMenu::focusNextPrevChild(bool next)

重新实现了:QWidget::focusNextPrevChild (bool next)。

[override virtual protected] void QMenu::hideEvent(QHideEvent *)

重写了:QWidget::hideEvent(QHideEvent *event)。

void QMenu::hideTearOffMenu()

此函数将强制隐藏被撕下的菜单,使其从用户的桌面上消失。

另请参阅 showTearOffMenu()、isTearOffMenuVisible(),以及isTearOffEnabled()。

[signal] void QMenu::hovered(QAction *action)

当菜单操作被高亮显示时,会发出此信号;action 是触发该信号发出的操作。

通常,该信号用于更新状态信息。

另请参阅 triggered() 和QAction::hovered()。

[virtual protected] void QMenu::initStyleOption(QStyleOptionMenuItem *option, const QAction *action) const

使用此菜单中的值以及action 中的信息初始化option 。当子类需要一个QStyleOptionMenuItem ,但又不想自己填写所有信息时,此方法非常有用。

另请参阅 QStyleOption::initFrom() 和QMenuBar::initStyleOption()。

QAction *QMenu::insertMenu(QAction *before, QMenu *menu)

该便捷函数会在操作before 之前插入menu ,并返回菜单menuAction()。

另请参阅 QWidget::insertAction() 和addMenu()。

QAction *QMenu::insertSection(QAction *before, const QString &text)

此便捷函数会创建一个新的标题操作,即一个QAction::isSeparator()返回true,同时具有text 提示的操作。该函数将新创建的操作插入到此菜单的操作列表中,位置在操作before 之前,并返回该操作。

提示的渲染效果取决于样式和平台。控件样式可以在渲染分区时使用其中的文本信息,也可以选择忽略该信息,将分区渲染为简单的分隔符。

QMenu 该函数将接管返回的 `QAction` 的所有权。

另请参阅 QWidget::insertAction() 和addSection()。

QAction *QMenu::insertSection(QAction *before, const QIcon &icon, const QString &text)

此便捷函数会创建一个新的标题操作,即一个QAction::isSeparator()返回true,同时具有text 和icon 提示的操作。该函数将新创建的操作插入到此菜单的操作列表中,位置在操作before 之前,并返回该操作。

提示信息的渲染效果取决于样式和平台。控件样式可以在渲染分区时使用其中的文本和图标信息,也可以选择忽略这些信息,将分区渲染为简单的分隔符。

QMenu 该函数将接管返回的 `QAction` 的所有权。

另请参阅 QWidget::insertAction() 和addSection()。

QAction *QMenu::insertSeparator(QAction *before)

此便捷函数会创建一个新的分隔符操作,即一个其QAction::isSeparator()方法返回true的操作。该函数会将新创建的操作插入到该菜单的操作列表中,位置在操作before 之前,并返回该操作。

QMenu 接管返回的 `QAction` 的所有权。

另请参阅 QWidget::insertAction() 和addSeparator()。

bool QMenu::isEmpty() const

如果菜单中未插入任何可见的操作,则返回true ;否则返回false。

另请参阅 QWidget::actions()。

bool QMenu::isTearOffMenuVisible() const

当菜单被撕下时,会显示第二个菜单,以在新窗口中展示菜单内容。当菜单处于此模式且可见时,返回true ;否则返回false。

另请参阅 showTearOffMenu()、hideTearOffMenu() 和isTearOffEnabled()。

[override virtual protected] void QMenu::keyPressEvent(QKeyEvent *e)

重写了:QWidget::keyPressEvent(QKeyEvent *event)。

[override virtual protected] void QMenu::leaveEvent(QEvent *)

重写了:QWidget::leaveEvent(QEvent *event)。

返回与该菜单关联的操作。

返回action 所包含的菜单;如果action 不包含菜单,则返回nullptr 。

在控件应用程序中,包含菜单的操作可用于创建带有子菜单的菜单项,或插入到工具栏中以创建带有弹出菜单的按钮。

[override virtual protected] void QMenu::mouseMoveEvent(QMouseEvent *e)

重写了:QWidget::mouseMoveEvent(QMouseEvent *event)。

[override virtual protected] void QMenu::mousePressEvent(QMouseEvent *e)

重写了:QWidget::mousePressEvent(QMouseEvent *event)。

[override virtual protected] void QMenu::mouseReleaseEvent(QMouseEvent *e)

重写了:QWidget::mouseReleaseEvent(QMouseEvent *event)。

[override virtual protected] void QMenu::paintEvent(QPaintEvent *e)

重写了:QWidget::paintEvent(QPaintEvent *event)。

显示菜单,使操作atAction 位于指定的全局位置p 。要将控件的本地坐标转换为全局坐标,请使用QWidget::mapToGlobal()。

使用exec() 或 popup() 定位菜单时,请注意不能依赖菜单当前的size() 值。 出于性能考虑,菜单仅在必要时调整其大小,因此在许多情况下,显示前后的尺寸会有所不同。建议改用sizeHint(),该方法会根据菜单的当前内容计算出正确尺寸。

另请参阅 QWidget::mapToGlobal() 和exec()。

void QMenu::setActiveAction(QAction *act)

将当前选中的操作设置为“act ”。

另请参阅 activeAction()。

void QMenu::setAsDockMenu()

将此菜单设置为通过按住 Option 键并单击应用程序 Dock 图标来调用的 Dock 菜单。仅在 macOS 上可用。

void QMenu::setDefaultAction(QAction *act)

这将默认操作设置为act 。根据当前的QStyle ,默认操作可能会有视觉提示。默认操作通常表示发生拖放操作时将默认执行什么操作。

另请参阅 defaultAction()。

void QMenu::showTearOffMenu(const QPoint &pos)

该函数将强制显示被剥离的菜单,使其出现在用户桌面的指定全局位置pos 。

另请参阅 hideTearOffMenu()、isTearOffMenuVisible() 和isTearOffEnabled()。

void QMenu::showTearOffMenu()

此函数将强制显示被撕下的菜单,使其出现在用户桌面上鼠标光标下方。

这是一个重载函数。

另请参阅 hideTearOffMenu()、isTearOffMenuVisible() 和isTearOffEnabled()。

[override virtual] QSize QMenu::sizeHint() const

重新实现了属性QWidget::sizeHint 的访问函数。

[override virtual protected] void QMenu::timerEvent(QTimerEvent *e)

重写了:QObject::timerEvent(QTimerEvent *event)。

NSMenu *QMenu::toNSMenu()

返回该菜单的原生 NSMenu 对象。仅在 macOS 上可用。

注意:Qt 会为原生菜单设置委托。如果您需要设置自己的委托,请确保保存原始委托,并将所有调用转发给它。

[signal] void QMenu::triggered(QAction *action)

当此菜单中的某个操作被触发时,会发出此信号。

action 是导致该信号发出的操作。

通常,你会将每个菜单操作的triggered()信号连接到其自身的自定义槽,但有时你会希望将多个操作连接到一个槽,例如,当你有一组密切相关的操作时,如“左对齐”、“居中”、“右对齐”。

注意:此 信号是在层次结构中的主父级菜单上发出的。因此,只需将父级菜单连接到一个槽,子菜单则无需连接。

另请参阅 hovered() 和QAction::triggered()。

[override virtual protected] void QMenu::wheelEvent(QWheelEvent *e)

重写了:QWidget::wheelEvent(QWheelEvent *event)。

© 2026 The Qt Company Ltd. Documentation contributions included herein are the copyrights of their respective owners. The documentation provided herein is licensed under the terms of the GNU Free Documentation License version 1.3 as published by the Free Software Foundation. Qt and respective logos are trademarks of The Qt Company Ltd. in Finland and/or other countries worldwide. All other trademarks are property of their respective owners.