Qt 5.14.2 学习记录 —— 십칠 窗口和菜单

devtools/2025/1/21 10:26:12/

文章目录

  • 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_OBJECTpublic: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);// 下面两个默认都为truetoolBar2->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是从右到左添加// 不上面的状态消息显示才会显示这个labelstatusBar->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);

结束。


http://www.ppmy.cn/devtools/152321.html

相关文章

Leiden算法一种用于社区检测的图聚类算法

Leiden算法是一种用于社区检测的图聚类算法&#xff0c;其灵感来源于Louvain算法&#xff0c;但进行了多项改进以提高社区划分的质量和效率。Leiden算法由荷兰莱顿大学的研究人员在2018年提出&#xff0c;旨在解决Louvain算法在某些情况下可能出现的不连通社区问题&#xff0c;…

Linux之网络套接字

Linux之网络套接字 一.IP地址和端口号二.TCP和UDP协议2.1网络字节序 三.socket编程的常见API四.模拟实现UDP服务器和客户端五.模拟实现TCP服务器和客户端 一.IP地址和端口号 在了解了网络相关的基础知识之后我们知道了数据在计算机中传输的流程并且发现IP地址在其中占据了确定…

深入了解Text2SQL开源项目(Chat2DB、SQL Chat 、Wren AI 、Vanna)

深入了解Text2SQL开源项目&#xff08;Chat2DB、SQL Chat 、Wren AI 、Vanna&#xff09; 前言 1.Chat2DB2.SQL Chat3.Wren AI4.Vanna 前言 在数据驱动决策的时代&#xff0c;将自然语言查询转化为结构化查询语言&#xff08;SQL&#xff09;的能力变得日益重要。无论是小型…

Centos7搭建PHP项目,环境(Apache+PHP7.4+Mysql5.7)

###项目地址 商城系统&#xff08;PC.小程序.APP.架构SaaS&#xff09;当PHP遇上了Java&#xff0c;还来个GO: ???本仓库同时含JAVA与PHP源码??? 做电商&#xff0c;就找来客推&#xff0c;涵盖多种商业模式&#xff0c;注重界面美感与用户体验&#xff0c;打造独特电商…

21.1、网络设备安全概述

目录 网络设备安全概况——交换机、路由器安全威胁 网络设备安全概况——交换机、路由器安全威胁 第一个是MAC地址泛洪&#xff0c;MAC地址表记录着交换机拥有的MAC地址跟端口的对应关系 MAC地址表主要是三个字段&#xff0c;MAC地址对应的端口号&#xff0c;也就表示主机是连…

财务RPA就是财务机器人吗?有什么作用

近年来&#xff0c;财务RPA&#xff08;机器人流程自动化&#xff09;逐渐成为财务领域的热门话题。很多人初次听到“财务RPA”时&#xff0c;可能会疑惑&#xff1a;财务RPA是不是财务机器人&#xff1f;它到底能做什么&#xff1f;带着这些问题&#xff0c;我们一起来探讨财务…

头歌答案--爬虫实战

目录 urllib 爬虫? 第1关&#xff1a;urllib基础 任务描述 第2关&#xff1a;urllib进阶? 任务描述 requests 爬虫 第1关&#xff1a;requests 基础 任务描述 第2关&#xff1a;requests 进阶 任务描述 网页数据解析 第1关&#xff1a;XPath解析网页? 任务描述…

Java 中求两个 List集合的交集元素

在 Java 中&#xff0c;求两个 List 的交集元素可以通过多种方式实现。常见的做法包括使用 retainAll 方法、Stream API 或手动遍历。以下是这些方法的原理和实现&#xff1a; 1. 使用 retainAll 方法 retainAll 是 Collection 接口中的一个方法&#xff0c;用于保留集合中与…