免费资源网 – https://freexyz.cn/

目录
  • 一、全屏显示效果
  • 二、全屏相关函数
  • 三,子窗口全屏显示两种实现方式
    • 1. 方式一: 直接将主窗口全屏,只显示某个子窗口
    • 2. 方式二:子窗口设置Qt::Window标志,全屏显示
  • 四、源码

    一、全屏显示效果

    Qt6子窗口全屏显示的实现示例

    二、全屏相关函数

    1,全屏显示函数

    QWidget::showFullScreen(); // 此方法只对顶级窗口有效,对子窗口无效

    2,恢复显示函数

    QWidget::showNormal(); // 此方法也只对顶级窗口有效,对子窗口无效

    3,最小化显示函数

    QWidget::showMinimized();

    4,最大化显示函数

    QWidget::showMaximized();

    5,设置窗口类型

    QWidget::setWindowFlags(Qt::WindowFlags);

    三,子窗口全屏显示两种实现方式

    ps: 本文只测试了Qt 6环境运行情况。

    Qt中的窗口QWidget成员函数showFullScreen,可以将窗口全屏显示,但是只是对窗口模式有用, 也就是具有Qt::Window属性的窗口。

        enum WindowType {
            Widget = 0x00000000,
            Window = 0x00000001,
            Dialog = 0x00000002 | Window,
            Sheet = 0x00000004 | Window,
            Drawer = Sheet | Dialog,
            Popup = 0x00000008 | Window,
            Tool = Popup | Dialog,
            ToolTip = Popup | Sheet,
            SplashScreen = ToolTip | Dialog,
            Desktop = 0x00000010 | Window,
            SubWindow = 0x00000012,
            ForeignWindow = 0x00000020 | Window,
            CoverWindow = 0x00000040 | Window,
            ...
        };
    

    Dialog也具有Qt::Window属性。

    1. 方式一: 直接将主窗口全屏,只显示某个子窗口

    这是一种实现起来可能比较繁琐的方式,因为要隐藏所有不想看到的控件,退出全屏还得恢复原样,控制粒度比较精细。

    但是这种实现方式,不会有多屏显示器的问题,会直接全屏显示到当前窗口屏幕。

    先建立一个工程如下

    Qt6子窗口全屏显示的实现示例

    由于要隐藏控件,使用QWidget做布局控件,不要使用Vertical Layout或者Horizontal Layout,它们没有hide()函数。

    点击按钮实现全屏或者退出全屏

    void MainWindow::on_pushButtonHideFullScreen_clicked() {
        if (this->isFullScreen()) {
            this->showNormal();
            ui->widgetControl->show();
            ui->statusbar->show();
        } else {
            this->showFullScreen();
            ui->widgetControl->hide();
            ui->statusbar->hide();
        }
    }
    

    在全屏的方式下,不需要的控件需要隐藏,所以最好有一个QWidget来包含这些要隐藏的控件,就只需要隐藏这个QWidget本身。

    当退出全屏时候需要恢复显示。

    ESC按键退出全屏

    在主窗口中进行键盘按键过滤可以直接实现keyPressEvent虚函数即可。

    void MainWindow::keyPressEvent(QKeyEvent *event) {
        if (this->isFullScreen() && event->key() == Qt::Key_Escape) {
            qDebug() << "ESC";
            this->showNormal();
            ui->widgetControl->show();
            ui->statusbar->show();
        }
    }
    

    上述代码会在键盘按键按下那一瞬间执行,如果匹配Qt::Key_Escape就退出全屏。

    2. 方式二:子窗口设置Qt::Window标志,全屏显示

    mainwindow.h

    需要用到成员变量,保存子窗口和它以前的WindowFlags,退出全屏时候需要恢复。

        // 子窗口全屏
        QWidget *fsWidget_ = nullptr;
        Qt::WindowFlags fsFlags_;
    
        void enableChildFullScreen();
        void disableChildFullScreen();
    

    全屏与退出

    void MainWindow::enableChildFullScreen() {
        fsWidget_ = ui->openGLWidget;
        fsFlags_ = fsWidget_->windowFlags();
    
        fsWidget_->setWindowFlags(Qt::Window | Qt::WindowStaysOnTopHint |
                                  Qt::FramelessWindowHint);
        fsWidget_->setFocus();
        fsWidget_->showFullScreen();
        fsWidget_->installEventFilter(this);
    }
    
    void MainWindow::disableChildFullScreen() {
        fsWidget_->setWindowFlags(fsFlags_);
        fsWidget_->showNormal();
        fsWidget_->removeEventFilter(this);
        fsWidget_ = nullptr;
    }
    

    注意到这里有个installEventFilter,因为子窗口全屏了,MainWindow不是激活的,他没法捕捉到键盘事件,这里只能重新指定事件过滤器。

    当全屏的时候安装子窗口事件过滤器,退出全屏时候移除。

    响应按钮事件

    void MainWindow::on_pushButtonChildFullScreen_clicked() {
        if (!fsWidget_) {
            qDebug() << "enable full screen";
            enableChildFullScreen();
        } else {
            qDebug() << "disable full screen";
            disableChildFullScreen();
        }
    }
    

    事件过滤器

    bool MainWindow::eventFilter(QObject *watched, QEvent *event) {
        if (fsWidget_ != nullptr && watched == fsWidget_ &&
            event->type() == QEvent::KeyPress) {
            qDebug() << "ESC";
            QKeyEvent *keyEvent = static_cast<QKeyEvent *>(event);
            if (keyEvent->key() == Qt::Key_Escape) {
                disableChildFullScreen();
    
                return true; // 事件已处理,不传递给其他对象
            }
        }
    
        return QMainWindow::eventFilter(watched, event); // 将事件传递给基类处理
    }
    

    多显示器问题

    这种方式如果遇到多显示器会有问题,子窗口全屏后只会显示在主显示器。同时原来的窗口框架依然在,会显示如下一个缺少那个子窗口的样子。

    Qt6子窗口全屏显示的实现示例

    如果只有一个显示器,这个问题也就不用解决了。
    另一个就是hide主窗口,子窗口依然会全屏,但是hide了之后任务栏是看不见的。
    再或者解决方法就是移动子窗口到主窗口显示器……

    四、源码

    https://gitee.com/noevilme/QtDemo/tree/master/FullScreen

    免费资源网 – https://freexyz.cn/

    声明:本站所有文章,如无特殊说明或标注,均为本站原创发布。任何个人或组织,在未征得本站同意时,禁止复制、盗用、采集、发布本站内容到任何网站、书籍等各类媒体平台。如若本站内容侵犯了原著者的合法权益,可联系我们进行处理。