Qml - ApplicationWindow fullscreen issues



  • Hi all,

    [Setup]
    Qt 5.4.1
    Windows Desktop

    I'm struggling with the fullscreen mode of ApplicationWindow in a full-qml based project.
    When using the method showFullScreen(), the expected result occurs : the window get displayed fullscreen.
    The trouble is that I get strange black screen flashes whenever I hover a Button or click items in the menu bar for instance.
    I also get those flashes on a dual screen setup, when I click somewhere on the second screen and click back inside the fullscreen Qml app (it seems to run fine when the app is shown fullscreen on the secondary screen though).
    This is making the application really hard to use. Also, tooltips are not displayed.
    I guess the issue is related to the OpenGL surface being set to fullscreen and the way Windows handles that (like it does with a fullscreen game).

    I was able to solve this problem back in Qt 4.8 by using a QMainWindow and embedding the QDeclarativeView inside a QWidget used as the central widget with a QLayout with 1px margin. This way, when making the central widget go fullscreen, the OpenGL viewport of the QDeclarativeView is not filling the screen and everything works fine.

    Since I'm now using an ApplicationWindow instanciated in Qml, this trick is outdated. I thought I had found another workaround by manually settings visibility [1] and window flags [2].

    import QtQuick 2.4
    import QtQuick.Controls 1.3
    import QtQuick.Window 2.2
    import QtQuick.Dialogs 1.2
    
    ApplicationWindow {
        id: mainWindow
    
        title: qsTr("Hello World")
        width: 640
        height: 480
        property bool fullscreen: false
    
        menuBar: MenuBar {
            Menu {
                title: qsTr("&File")
                MenuItem {
                    text: qsTr("&Open")
                    onTriggered: messageDialog.show(qsTr("Open action triggered"));
                }
                MenuItem {
                    text: qsTr("E&xit")
                    onTriggered: Qt.quit();
                }
            }
        }
    
        Item {
            states: [
                State {
                    when: mainWindow.fullscreen
                    name: "Full"
                    PropertyChanges {
                        target: mainWindow
                        // [1] using Window.FullScreen => still have black flashes.
                        //     have to use "FullScreen"
                        // visibility: Window.FullScreen
                        visibility: "FullScreen"
    
                        // [2] The unfamous workaround
                        flags: Qt.WindowFullScreen
                    }
                }
            ]
        }
    
        Button {
            anchors.centerIn: parent
            checkable: true
            tooltip: "Change mode"
            text: mainWindow.fullscreen ? "Go Windowed" : "Go Fullscreen"
    
            onClicked: mainWindow.fullscreen = !mainWindow.fullscreen
        }
    
    }
    

    Setting the WindowFullScreen flag does resolve the flashes (and the tooltips) when combined with the visibility set to "Fullscreen". But it introduces another showstopper bug : it breaks Drop events from outside when going back to windowed mode, making it impossible to use DropAreas.
    And this might only be one bug among others, so this workaround does not seem viable...

    Has anyone another solution or have insights into what is really happening with the fullscreen mode ?

    Thanks,
    Yann



  • After taking a closer at the C++ code of QWindowsWindow::setWindowFlag, I stumbled upon a call to QWindowsWindow::updateDropSite. This enables/disables the window drop capabilities according to its WindowType.
    The thing is that d->windowFlags, used to determine the type of the window is updated after the call to updateDropSite. This is why messing up with the flags when switching to fullscreen breaks the drop system when switching back flags to its initial value; Qt.WindowFullScreen is an invalid WindowType => drops are disabled.

    Knowing that, I was able to improve my previous workaround :

    StateGroup {
        state: mainWindow.fullScreen ? "FullScreen" : ""
        states: [
            State {
                name: "FullScreen"
                PropertyChanges {
                    target: mainWindow
                    // [1] using Window.FullScreen => still have black flashes.
                    //     have to use "FullScreen"
                    // visibility: Window.FullScreen
                    visibility: "FullScreen"
                    // [2] Flag this window as a Widget to prevent black flashes from happening.
                    // updateDropSite considers type Window : drops work 
                     flags: Qt.Widget
                }
            },
            State {
                name: ""
                StateChangeScript {
                    // [2.b] When switching back to default state, use a script to change the flags value a first time. 
                    // updateDropSite considers type Widget: drops don't work 
                    script: { mainWindow.flags = Qt.Window }
                   //  [2.c] Then flags will be reset to its default value because we use a script, not a direct binding.
                   //  updateDropSite considers type Window: drops work 
                }
            }
        ]
    }
    

    So, this solves my problem but if feels a bit too hacky, especially setting the Window type to Qt.Widget in a full Qml app... (or any invalid Window type, that's why it worked with Qt.WindowFullScreen).

    Before marking this thread as (kinda) solved, I would still appreciate some feedback :).

    Yann



  • Hi, I had similar issue, qml app in full screen flickers when showing dialog. This is in Win10 using Qt 5.9. Graphics NVidia GForce GT 710 (using OpenGL Version: 4.4.0 NVIDIA 378.78).
    My workaround is:

    flags: Qt.FramelessWindowHint
    x: 0
    y: - 1
    width: Screen.width
    height: Screen.height + 1
    

    This is satisfactory solution for me ;)


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.