文章目录
- 1、Qt窗口
- 2、菜单栏
- 设置快捷键
- 添加子菜单
- 添加分割线和菜单图标
- 3、工具栏 QToolBar
- 4、状态栏 QStatusBar
- 5、浮动窗口 QDockWidget
1、Qt窗口
QWidget,即控件,是窗口的一部分。在界面中创建控件组成界面时,Qt自动生成了窗口,QMainWindow。
从外到内,窗口标题,菜单栏,工具栏,铆接部件或子窗口(比如widget.cpp),中心控件,状态栏。
2、菜单栏
一个主窗口最多只有一个菜单栏。
菜单栏用QMenuBar类来实现,菜单用QMenu类来实现,菜单项用QAction类来实现。
创建一个窗口项目
main.cpp
#include "mainwindow.h"
#include <QApplication>
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
MainWindow w;
w.show();
return a.exec();
}
此时的w就是MainWindow类型了。ui文件中默认是这样的:
“在这里输入处”输入内容就是一个菜单,点击这个菜单,在这里输入,就创建菜单项。不过因为Qt Creator的bug,没办法正常用中文来输入,所以就在别的地方写好再复制过来。
此时是没有自动生成ui文件的,那用户就可以自己写,自己创建窗口对象;但如果自动生成了,用户再自己写,那么就会替换掉原本的对象,旧对象就不归Qt对象树管理,Qt也不会去释放它们,就能造成内存泄漏,除非关闭窗口。
代码创建菜单和菜单项
// mainwindow.h
class MainWindow : public QMainWindow
{
Q_OBJECT
public:
MainWindow(QWidget *parent = nullptr);
~MainWindow();
void handle();
private:
Ui::MainWindow *ui;
};
// mainwindow.cpp
#include <QDebug>
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
, ui(new Ui::MainWindow)
{
ui->setupUi(this);
// 创建菜单栏
QMenuBar* menuBar = new QMenuBar();
this->setMenuBar(menuBar);
// 自动生成了, 如下写法
// QMenuBar* menubar = this->menuBar();
// 创建菜单
QMenu* menu1 = new QMenu("文件");
QMenu* menu2 = new QMenu("编辑");
QMenu* menu3 = new QMenu("设置");
menuBar->addMenu(menu1);
menuBar->addMenu(menu2);
menuBar->addMenu(menu3);
// 添加菜单项
QAction* act1 = new QAction("打开");
QAction* act2 = new QAction("运行");
QAction* act3 = new QAction("调节大小");
menu1->addAction(act1);
menu2->addAction(act2);
menu3->addAction(act3);
// 菜单项被点击会触发信号triggered
// 菜单项槽函数
connect(act3, &QAction::triggered, this, &MainWindow::handle);
}
MainWindow::~MainWindow()
{
delete ui;
}
void MainWindow::handle()
{
qDebug() << "Act3";
}
设置快捷键
// 菜单
QMenu* menu3 = new QMenu("设置 (&T)");
// 菜单项
QAction* act3 = new QAction("调节大小 (&V)");
这样运行后,按一下alt,再按T就可以打开设置菜单了,按V就打印Act3了。不过这种是通用的,不是Qt做的。Qt用QShortCut来做快捷键,但上面的方法更简单。
添加子菜单
// 子菜单
QMenu* menu4 = new QMenu("打开目录");
menu1->addMenu(menu4);
QAction* act4 = new QAction("打开C盘");
menu4->addAction(act4);
添加分割线和菜单图标
分割线
QAction* act1 = new QAction("打开");
QAction* act2 = new QAction("运行");
QAction* act3 = new QAction("调节大小 (&V)");
menu1->addAction(act1);
menu1->addSeparator();
菜单图标,用qrc
// 菜单图标
QMenu* menu2 = new QMenu("编辑");
menu2->setIcon(QIcon(":/clouds.jpg"));
// 菜单项图标
QAction* act2 = new QAction("运行");
act2->setIcon(QIcon(":/ztk.jpg"));
3、工具栏 QToolBar
#include <QDebug>
#include <QToolBar>
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
, ui(new Ui::MainWindow)
{
ui->setupUi(this);
QToolBar* toolBar = new QToolBar();
// 菜单栏是set, 工具栏是add
// 菜单栏不能重复设置, 而工具栏只是添加
this->addToolBar(toolBar);
QAction* act1 = new QAction("保存");
QAction* act2 = new QAction("打开");
toolBar->addAction(act1);
toolBar->addAction(act2);
connect(act1, &QAction::triggered, this, &MainWindow::handle1);
connect(act2, &QAction::triggered, this, &MainWindow::handle2);
}
void MainWindow::handle1()
{
qDebug() << "Act1";
}
void MainWindow::handle2()
{
qDebug() << "Act2";
}
工具栏可以拖动。
如果给工具栏放上图标,也会替换掉文字。不过即使被替换掉了,文字还是会显示,会在鼠标悬停在对应位置上出现提示文字,这个提示我们可以自己设置。
act1->setToolTip("点击这里保存当前记录");
act1,act2,创建的菜单项不仅可以放到工具栏,也可以放到菜单栏,可以同时放置,释放时也不会重复释放,只要有一方释放了,另一方就不会进行释放。
创建多个工具栏,它们是从左到右依次排序的。
设置工具栏出现的初始位置,允许停放到哪些边缘,是否允许浮动,是否可以移动
QToolBar* toolBar1 = new QToolBar();
QToolBar* toolBar2 = new QToolBar();
// 菜单栏是set, 工具栏是add
// 菜单栏不能重复设置, 而工具栏只是添加
this->addToolBar(toolBar1);
this->addToolBar(Qt::RightToolBarArea, toolBar2);
toolBar2->setAllowedAreas(Qt::LeftToolBarArea | Qt::RightToolBarArea);
// 下面两个默认都为true
toolBar2->setFloatable(false);
toolBar2->setMovable(false);
4、状态栏 QStatusBar
#include <QDebug>
#include <QLabel>
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
, ui(new Ui::MainWindow)
{
ui->setupUi(this);
QStatusBar* statusBar = new QStatusBar();
// 无论状态栏是否被创建, 设置一下都没问题
this->setStatusBar(statusBar);
// 第二个参数表示多少ms后消息消失
//statusBar->showMessage("状态信息", 4000);
// 添加子控件
QLabel* label1 = new QLabel("Label");
// 另一个方法addPermanentWidget是从右到左添加
// 不上面的状态消息显示才会显示这个label
statusBar->addWidget(label1, 2);
QLabel* label2 = new QLabel("label");
// 第二个参数表示拉伸系数, 表示这个label占多少显示空间
statusBar->addWidget(label2, 1);
// 还可以加别的控件, 比如按钮, 进度条
}
5、浮动窗口 QDockWidget
#include <QDockWidget>
#include <QPushButton>
#include <QVBoxLayout>
dockWidget->setWindowTitle("浮动窗口");
// 添加子控件不能直接添加
// 先创建一个QWidget, 把子控件放到QWidget中
// 将QWidget放入浮动窗口中才能生效
QWidget* container = new QWidget();
dockWidget->setWidget(container);
QVBoxLayout* layout = new QVBoxLayout;
container->setLayout(layout);
QPushButton* button = new QPushButton("按钮");
layout->addWidget(button);
// 设置浮动窗口允许停靠的位置
dockWidget->setAllowedAreas(Qt::RightDockWidgetArea | Qt::TopDockWidgetArea);
结束。