简述

QSystemTrayIcon类为应用程序在系统托盘中提供一个图标。
现代操作系统通常在桌面上提供一个特殊的区域,称为系统托盘或通知区域,长时间运行的应用程序可以显示图标和短消息。

内容

详细描述

要检查系统托盘是否存在在用户的桌面上,调用QSystemTrayIcon::isSystemTrayAvailable()静态函数。
要添加系统托盘项,首先,需要创建一个QSystemTrayIcon对象,并调用setContextMenu()为图标提供上下文菜单,然后,调用show()使其在系统托盘中可见。状态通知消息(“气球消息”)可以在任何时候使用showMessage()来进行显示。
当用户激活托盘图标时,activated()信号会被发射。
只有在X11上时,当发出一个tooltip请求时,QSystemTrayIcon会接收一个QEvent::ToolTip类型的QHelpEvent事件。此外,QSystemTrayIcon会接收QEvent::Wheel类型的滚轮事件。这些都是不支持任何其它平台。

共有类型

  • 枚举QSystemTrayIcon::ActivationReason
    此枚举描述了系统托盘被激活的原因。
    | 常量 | 值 | 描述 | | :—-: | :—-: | :—-: | | QSystemTrayIcon::Unknown | 0 | 未知原因 | | QSystemTrayIcon::Context | 1 | 系统托盘的上下文菜单请求 | | QSystemTrayIcon::DoubleClick | 2 | 双击系统托盘 | | QSystemTrayIcon::Trigger | 3 | 单击系统托盘 | | QSystemTrayIcon::MiddleClick | 4 | 鼠标中键点击系统托盘 |

  • 枚举QSystemTrayIcon::MessageIcon
    此枚举描述了显示气球消息时所显示的图标。 | 常量 | 值 | 描述 | | :—-: | :—-: | :—-: | | QSystemTrayIcon::NoIcon | 0 | 无图标显示 | | QSystemTrayIcon::Information | 1 | 一个信息图标显示 | | QSystemTrayIcon::Warning | 2 | 一个标准的警告图标显示 | | QSystemTrayIcon::Critical | 3 | 一个严重的警告图标显示 |

共有函数

  • QMenu * contextMenu() const
    返回系统托盘的当前上下文菜单。
  • void setContextMenu(QMenu menu)
    设置指定菜单为系统托盘的上下文菜单。
    当用户通过点击鼠标请求系统托盘的上下文菜单时,菜单会弹出。
    在OS X中,一般转换为一个NSMenu,所以aboutToHide()信号不会发出。
    *注意:
    系统托盘菜单并不对菜单有所有权,必须确保在恰当的时候删除菜单,例如:创造一个具有合适父对象的菜单。
  • QRect QSystemTrayIcon::geometry() const
    返回系统托盘图标在屏幕上的几何坐标。
  • QIcon icon() const
  • void setIcon(const QIcon & icon)
    icon : QIcon
    这个属性保存了系统托盘的图标。
    在Windows中,系统任务栏图标的大小是16×16;X11中,首选大小为22x22。必要时该图标将被调整到合适大小。
  • void setToolTip(const QString & tip)
  • QString toolTip() const
    toolTip : QString
    这个属性保存了系统托盘的提示信息。
    在一些系统中,tooltip的长度是有限的,在必要时tooltip将被截断。
  • bool isVisible() const
    返回系统托盘是否可见。

    公有槽函数

  • void hide()
    隐藏系统托盘。

  • void setVisible(bool visible)
    设置系统托盘是否可见。
    设置为true或调用show()使系统托盘图标可见;设置为false或调用hide()隐藏它。
  • void show()
    显示系统托盘。
  • void showMessage(const QString & title, const QString & message, QSystemTrayIcon::MessageIcon icon = QSystemTrayIcon::Information, int millisecondsTimeoutHint = 10000)
    显示一个气球消息,使用所给出的标题、消息、图标和指定的时间,标题和消息必须是纯文本字符串。

消息可以被用户点击,当用户点击时发出messageClicked()信号 。

信号

  • void activated(QSystemTrayIcon::ActivationReason reason)
    当用户激活系统托盘图标,这个信号被发射。reason指定激活的原因, QSystemTrayIcon::ActivationReason列举了各种原因。
  • void messageClicked()
    当使用showMessage()显示的消息被用户点击时,此信号被发射。
    目前,这个信号不会在OS X中发射。

    静态共有函数

  • bool isSystemTrayAvailable() [static]
    如果系统托盘可用,返回true;否则,返回false。
    如果系统盘是当前不可用,但以后变为可用,若QSystemTrayIcon可见,它就会自动在系统托盘中添加条目。

  • bool supportsMessages() [static]
    如果系统托盘支持气球消息,则返回true;否则,返回false。

例子

头文件

  1. #ifndef WINDOW_H
  2. #define WINDOW_H
  3. #include <QSystemTrayIcon>
  4. #ifndef QT_NO_SYSTEMTRAYICON
  5. #include <QDialog>
  6. QT_BEGIN_NAMESPACE
  7. class QAction;
  8. class QCheckBox;
  9. class QComboBox;
  10. class QGroupBox;
  11. class QLabel;
  12. class QLineEdit;
  13. class QMenu;
  14. class QPushButton;
  15. class QSpinBox;
  16. class QTextEdit;
  17. QT_END_NAMESPACE
  18. class Window : public QDialog {
  19. Q_OBJECT
  20. public:
  21. Window();
  22. void setVisible(bool visible) override;
  23. protected:
  24. void closeEvent(QCloseEvent* event) override;
  25. private slots:
  26. void setIcon(int index);
  27. void iconActivated(QSystemTrayIcon::ActivationReason reason);
  28. void showMessage();
  29. void messageClicked();
  30. private:
  31. void createIconGroupBox();
  32. void createMessageGroupBox();
  33. void createActions();
  34. void createTrayIcon();
  35. QGroupBox* iconGroupBox;
  36. QLabel* iconLabel;
  37. QComboBox* iconComboBox;
  38. QCheckBox* showIconCheckBox;
  39. QGroupBox* messageGroupBox;
  40. QLabel* typeLabel;
  41. QLabel* durationLabel;
  42. QLabel* durationWarningLabel;
  43. QLabel* titleLabel;
  44. QLabel* bodyLabel;
  45. QComboBox* typeComboBox;
  46. QSpinBox* durationSpinBox;
  47. QLineEdit* titleEdit;
  48. QTextEdit* bodyEdit;
  49. QPushButton* showMessageButton;
  50. QAction* minimizeAction;
  51. QAction* maximizeAction;
  52. QAction* restoreAction;
  53. QAction* quitAction;
  54. QSystemTrayIcon* trayIcon;
  55. QMenu* trayIconMenu;
  56. };
  57. //! [0]
  58. #endif // QT_NO_SYSTEMTRAYICON
  59. #endif

实现

  1. #include "window.h"
  2. #ifndef QT_NO_SYSTEMTRAYICON
  3. #include <QAction>
  4. #include <QCheckBox>
  5. #include <QCloseEvent>
  6. #include <QComboBox>
  7. #include <QCoreApplication>
  8. #include <QGroupBox>
  9. #include <QLabel>
  10. #include <QLineEdit>
  11. #include <QMenu>
  12. #include <QMessageBox>
  13. #include <QPushButton>
  14. #include <QSpinBox>
  15. #include <QTextEdit>
  16. #include <QVBoxLayout>
  17. Window::Window()
  18. {
  19. createIconGroupBox();
  20. createMessageGroupBox();
  21. iconLabel->setMinimumWidth(durationLabel->sizeHint().width());
  22. createActions();
  23. createTrayIcon();
  24. connect(showMessageButton, &QAbstractButton::clicked, this, &Window::showMessage);
  25. connect(showIconCheckBox, &QAbstractButton::toggled, trayIcon, &QSystemTrayIcon::setVisible);
  26. connect(iconComboBox, QOverload<int>::of(&QComboBox::currentIndexChanged), this, &Window::setIcon);
  27. connect(trayIcon, &QSystemTrayIcon::messageClicked, this, &Window::messageClicked);
  28. connect(trayIcon, &QSystemTrayIcon::activated, this, &Window::iconActivated);
  29. QVBoxLayout* mainLayout = new QVBoxLayout;
  30. mainLayout->addWidget(iconGroupBox);
  31. mainLayout->addWidget(messageGroupBox);
  32. setLayout(mainLayout);
  33. iconComboBox->setCurrentIndex(1);
  34. trayIcon->show();
  35. setWindowTitle(tr("Systray"));
  36. resize(400, 300);
  37. }
  38. // 设置托盘菜单显隐状态
  39. void Window::setVisible(bool visible)
  40. {
  41. minimizeAction->setEnabled(visible);
  42. maximizeAction->setEnabled(!isMaximized());
  43. restoreAction->setEnabled(isMaximized() || !visible);
  44. QDialog::setVisible(visible);
  45. }
  46. // 关闭事件重写
  47. void Window::closeEvent(QCloseEvent* event)
  48. {
  49. #ifdef Q_OS_MACOS
  50. if (!event->spontaneous() || !isVisible()) {
  51. return;
  52. }
  53. #endif
  54. if (trayIcon->isVisible()) {
  55. QMessageBox::information(this, tr("Systray"),
  56. tr("The program will keep running in the "
  57. "system tray. To terminate the program, "
  58. "choose <b>Quit</b> in the context menu "
  59. "of the system tray entry."));
  60. hide();
  61. event->ignore();
  62. }
  63. }
  64. // 设置托盘图标
  65. void Window::setIcon(int index)
  66. {
  67. QIcon icon = iconComboBox->itemIcon(index);
  68. trayIcon->setIcon(icon);
  69. setWindowIcon(icon);
  70. trayIcon->setToolTip(iconComboBox->itemText(index));
  71. }
  72. // 托盘响应鼠标事件
  73. void Window::iconActivated(QSystemTrayIcon::ActivationReason reason)
  74. {
  75. switch (reason) {
  76. case QSystemTrayIcon::Trigger:
  77. case QSystemTrayIcon::DoubleClick:
  78. iconComboBox->setCurrentIndex((iconComboBox->currentIndex() + 1) % iconComboBox->count());
  79. break;
  80. case QSystemTrayIcon::MiddleClick:
  81. showMessage();
  82. break;
  83. default:;
  84. }
  85. }
  86. // 设置系统提示框
  87. void Window::showMessage()
  88. {
  89. showIconCheckBox->setChecked(true);
  90. int selectedIcon = typeComboBox->itemData(typeComboBox->currentIndex()).toInt();
  91. QSystemTrayIcon::MessageIcon msgIcon = QSystemTrayIcon::MessageIcon(selectedIcon);
  92. if (selectedIcon == -1) { // custom icon
  93. QIcon icon(iconComboBox->itemIcon(iconComboBox->currentIndex()));
  94. trayIcon->showMessage(titleEdit->text(), bodyEdit->toPlainText(), icon, durationSpinBox->value() * 1000);
  95. } else {
  96. trayIcon->showMessage(titleEdit->text(), bodyEdit->toPlainText(), msgIcon, durationSpinBox->value() * 1000);
  97. }
  98. }
  99. // 弹出提示(系统提示框点击后的弹窗)
  100. void Window::messageClicked()
  101. {
  102. QMessageBox::information(nullptr, tr("Systray"),
  103. tr("Sorry, I already gave what help I could.\nMaybe you should try asking a human?"));
  104. }
  105. // 创建布局
  106. void Window::createIconGroupBox()
  107. {
  108. iconGroupBox = new QGroupBox(tr("Tray Icon"));
  109. iconLabel = new QLabel("Icon:");
  110. iconComboBox = new QComboBox;
  111. iconComboBox->addItem(QIcon(":/images/bad.png"), tr("Bad"));
  112. iconComboBox->addItem(QIcon(":/images/heart.png"), tr("Heart"));
  113. iconComboBox->addItem(QIcon(":/images/trash.png"), tr("Trash"));
  114. showIconCheckBox = new QCheckBox(tr("Show icon"));
  115. showIconCheckBox->setChecked(true);
  116. QHBoxLayout* iconLayout = new QHBoxLayout;
  117. iconLayout->addWidget(iconLabel);
  118. iconLayout->addWidget(iconComboBox);
  119. iconLayout->addStretch();
  120. iconLayout->addWidget(showIconCheckBox);
  121. iconGroupBox->setLayout(iconLayout);
  122. }
  123. // 创建布局
  124. void Window::createMessageGroupBox()
  125. {
  126. messageGroupBox = new QGroupBox(tr("Balloon Message"));
  127. typeLabel = new QLabel(tr("Type:"));
  128. typeComboBox = new QComboBox;
  129. typeComboBox->addItem(tr("None"), QSystemTrayIcon::NoIcon);
  130. typeComboBox->addItem(style()->standardIcon(QStyle::SP_MessageBoxInformation), tr("Information"), QSystemTrayIcon::Information);
  131. typeComboBox->addItem(style()->standardIcon(QStyle::SP_MessageBoxWarning), tr("Warning"), QSystemTrayIcon::Warning);
  132. typeComboBox->addItem(style()->standardIcon(QStyle::SP_MessageBoxCritical), tr("Critical"), QSystemTrayIcon::Critical);
  133. typeComboBox->addItem(QIcon(), tr("Custom icon"), -1);
  134. typeComboBox->setCurrentIndex(1);
  135. durationLabel = new QLabel(tr("Duration:"));
  136. durationSpinBox = new QSpinBox;
  137. durationSpinBox->setRange(5, 60);
  138. durationSpinBox->setSuffix(" s");
  139. durationSpinBox->setValue(15);
  140. durationWarningLabel = new QLabel(tr("(some systems might ignore this "
  141. "hint)"));
  142. durationWarningLabel->setIndent(10);
  143. titleLabel = new QLabel(tr("Title:"));
  144. titleEdit = new QLineEdit(tr("Cannot connect to network"));
  145. bodyLabel = new QLabel(tr("Body:"));
  146. bodyEdit = new QTextEdit;
  147. bodyEdit->setPlainText(tr("Don't believe me. Honestly, I don't have a clue.\nClick this balloon for details."));
  148. showMessageButton = new QPushButton(tr("Show Message"));
  149. showMessageButton->setDefault(true);
  150. QGridLayout* messageLayout = new QGridLayout;
  151. messageLayout->addWidget(typeLabel, 0, 0);
  152. messageLayout->addWidget(typeComboBox, 0, 1, 1, 2);
  153. messageLayout->addWidget(durationLabel, 1, 0);
  154. messageLayout->addWidget(durationSpinBox, 1, 1);
  155. messageLayout->addWidget(durationWarningLabel, 1, 2, 1, 3);
  156. messageLayout->addWidget(titleLabel, 2, 0);
  157. messageLayout->addWidget(titleEdit, 2, 1, 1, 4);
  158. messageLayout->addWidget(bodyLabel, 3, 0);
  159. messageLayout->addWidget(bodyEdit, 3, 1, 2, 4);
  160. messageLayout->addWidget(showMessageButton, 5, 4);
  161. messageLayout->setColumnStretch(3, 1);
  162. messageLayout->setRowStretch(4, 1);
  163. messageGroupBox->setLayout(messageLayout);
  164. }
  165. // 托盘菜单绑定事件
  166. void Window::createActions()
  167. {
  168. minimizeAction = new QAction(tr("Mi&nimize"), this);
  169. connect(minimizeAction, &QAction::triggered, this, &QWidget::hide);
  170. maximizeAction = new QAction(tr("Ma&ximize"), this);
  171. connect(maximizeAction, &QAction::triggered, this, &QWidget::showMaximized);
  172. restoreAction = new QAction(tr("&Restore"), this);
  173. connect(restoreAction, &QAction::triggered, this, &QWidget::showNormal);
  174. quitAction = new QAction(tr("&Quit"), this);
  175. connect(quitAction, &QAction::triggered, qApp, &QCoreApplication::quit);
  176. }
  177. // 添加托盘菜单选项
  178. void Window::createTrayIcon()
  179. {
  180. trayIconMenu = new QMenu(this);
  181. trayIconMenu->addAction(minimizeAction);
  182. trayIconMenu->addAction(maximizeAction);
  183. trayIconMenu->addAction(restoreAction);
  184. trayIconMenu->addSeparator();
  185. trayIconMenu->addAction(quitAction);
  186. trayIcon = new QSystemTrayIcon(this);
  187. trayIcon->setContextMenu(trayIconMenu);
  188. }
  189. #endif

main函数

  1. #include <QApplication>
  2. #ifndef QT_NO_SYSTEMTRAYICON
  3. #include "window.h"
  4. #include <QMessageBox>
  5. int main(int argc, char* argv[])
  6. {
  7. Q_INIT_RESOURCE(systray);
  8. QCoreApplication::setAttribute(Qt::AA_UseHighDpiPixmaps);
  9. QApplication app(argc, argv);
  10. if (!QSystemTrayIcon::isSystemTrayAvailable()) {
  11. QMessageBox::critical(nullptr, QObject::tr("Systray"),
  12. QObject::tr("I couldn't detect any system tray "
  13. "on this system."));
  14. return 1;
  15. }
  16. QApplication::setQuitOnLastWindowClosed(false);
  17. Window window;
  18. window.show();
  19. return app.exec();
  20. }
  21. #else
  22. #include <QDebug>
  23. #include <QLabel>
  24. int main(int argc, char* argv[])
  25. {
  26. QApplication app(argc, argv);
  27. QString text("QSystemTrayIcon is not supported on this platform");
  28. QLabel* label = new QLabel(text);
  29. label->setWordWrap(true);
  30. label->show();
  31. qDebug() << text;
  32. app.exec();
  33. }
  34. #endif

图片

bad.png
bad.png
heart.png
heart.png
trash.png
trash.png

https://waleon.blog.csdn.net/article/details/52014110 Qt自带例子 Qt5.15\5.15.2\Src\qtbase\examples\widgets\desktop\systray