设为首页 加入收藏

TOP

【Qt6】QWindow类可以做什么(一)
2023-07-23 13:32:42 】 浏览:79
Tags:Qt6 QWindow

原来的水文标题是“用 VS Code 搞 Qt6”,想想还是直接改为“Qt6”,反正这个用不用 VS Code 也能搞。虽然我知道大伙伴们都很讨厌 CMake,但毕竟这厮几乎成了 C++ 的玩家规范了。Qt 也算识大体,支持用 CMake 来构建程序。所以,只要你用的是能写 C++ 的工具,理论上都能搞 Qt。

创建应用程序界面的时候,我们一般会选用 QWidget 以及其子类的。不过,在 Gui 模块中,有一个 QWindow 类,干吗用的呢?写个程序试试看。

#include <QGuiApplication>
#include <QWindow>

int main(int argc, char** argv)
{
    // 一定要先创建应用程序对象
    QGuiApplication app(argc, argv);
    // 创建窗口实例
    QWindow win;
    // create方法其实可以不调用
    win.create();
    // 调整窗口的大小
    win.resize(300, 250);
    // 设置标题栏文本
    win.setTitle("番薯联盟");
    // 显示窗口
    win.show();
    // exec进入事件(消息)循环
    return QGuiApplication::exec();
}

这里说明一下,QWindow 类有个 create 方法,它的作用是创建平台相关的资源的,对应的是 destroy 方法,用来销毁这些平台相关的资源。这些平台相关的资源是为了实现跨平台的类型,如 QPlatformWindow、QPlatformSurfaceEvent 之类的。Windows 平台有单独的实现,Linux 平台也单独地实现。像 qwindowsguieventdispatcher、qunixeventdispatcher 这些也是。总之,QWindow 类可能会用到它们,于是,这些平台相关的资源,其生命周期始于 create 方法,终于 destroy 方法。

不过,create 方法这里其实可以不调用的,因为 show 方法会调用;destroy 方法也不可以不调用,它在 QWindow 类的析构函数中被调用。

咱们为上述代码写一个 CMakeLists.txt。

cmake_minimum_required(VERSION 3.0.0)
project(TestApp VERSION 0.1.0)

find_package(Qt6 REQUIRED COMPONENTS Core Gui)

add_executable(TestApp main.cpp)
target_link_libraries(TestApp PRIVATE Qt6::Core Qt6::Gui)

这里我们不到“铁三角”库,只用 core 和 gui 就够了,不需要 widgets。

好了,尝试运行,看看会出现什么。

这标题栏上的字体好像有问题。不管它,继续。

哦,直接实例化 QWindow 类会呈现一个空白窗口,而且这个窗口很诡异,你拖动一下改变它的大小后,就会变成这样。

 这是因为这个窗口是真的很空,空到连基本的绘制都没有,只是在启动的时候填充了个颜色。这个颜色是跟随系统主题的,刚才你看到的是深色主题下的背景色。现在我把系统主题调成浅色主题,它就会变成这样。

当你调整其大小后,发生重新绘制的部分变成了黑色(就是啥也没有)。

QWindow 类虽然定义了 paintEvent 方法,但是,它实现了个寂寞。

void QWindow::paintEvent(QPaintEvent *ev)
{
    ev->ignore();
}

从源代码中你会看到,默认的实现是直接把 paint 事件忽略了。

所以,我们只能从 QWindow 类派生,并重写 paintEvent 方法,绘制我们所需要的内容。

cmake_minimum_required(VERSION 3.0.0)
project(TestApp VERSION 1.2.3)

find_package(Qt6 REQUIRED COMPONENTS Core Gui)
set(CMAKE_AUTOMOC ON)
set(CMAKE_CXX_STANDARD 20)
set(CMAKE_CXX_STANDARD_REQUIRED ON)

add_executable(TestApp MyWindow.h MyWindow.cpp main.cpp)

target_link_libraries(TestApp PRIVATE Qt6::Core Qt6::Gui)

 

 1 #include <QWindow>
 2 #include <QPaintEvent>
 3 #include <QBackingStore>
 4 
 5 #ifndef __MYWINDOW_H__
 6 #define __MYWINDOW_H__
 7 class MyWindow : public QWindow
 8 {
 9     Q_OBJECT
10 public:
11     // 构造函数
12     explicit MyWindow(QWindow* parent = nullptr);
13 protected:
14     // 重写事件
15     void paintEvent(QPaintEvent *ev) override;
16 private:
17     // 绘制窗口内容需要这个类
18     QBackingStore* m_backstore;
19 };
20 #endif

要在窗口上涂鸦,需要用到 QBackingStore 类。这是由于 QPainter 类需要一个 QPaintDevice 指针才能完成绘图。QBackingStore类可以通过 paintDevice 方法返回一个 QPaintDevice 类的指针。

m_backstore 成员也可以用 QScopedPointer 封装,防止内存泄漏。

private:
    // 绘制窗口内容需要这个类
    QScopedPointer<QBackingStore> m_backstore;

当超出成员作用域时会自动删除指针。

下面是实现代码。

#include "MyWindow.h"
#include <QPaintDevice>
#include <QPainter>
#include <QColor>
#include <QRect>
#include <QtDebug>

MyWindow::MyWindow(QWindow* parent)
    : QWindow(parent), 
      m_backstore(new QBackingStore(this))
{
    // 设置当前窗口的位置和大小
    setGeometry(799, 304, 425, 385);
    // 设置绘画设备画布大小
    m_backstore -> resize(QSize(400, 300));
    // 设置窗口标题
    setTitle("红红火火");
}

void MyWindow::paintEvent(QPaintEvent* ev)
{
    // 要进行绘图的区域
    QRect rect = e
首页 上一页 1 2 3 下一页 尾页 1/3/3
】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
上一篇C++的拓扑排序实现 下一篇【Visual Leak Detector】源码文..

最新文章

热门文章

Hot 文章

Python

C 语言

C++基础

大数据基础

linux编程基础

C/C++面试题目