web-dev-qa-db-ja.com

Qt 5では、マルチモニターのフルスクリーンQWidgetウィンドウを表示する正しい方法は何ですか?

マルチモニターでフルスクリーンモードに切り替えるWindowsおよびMacプログラムがあります。 Qt 4では、これを行う「正しい」方法のように(これを行う方法に関する明確なドキュメントを見つけることができません)、マシンのNモニターにN QMainWindowを作成し、QWidget::move()をNモニターの左上のX、Y座標に変換し、QWidget::setWindowState(Qt::WindowFullScreen)を呼び出します。これが正しいことかどうかはわかりません-繰り返しますが、Qtでこれを行うドキュメントや例はどこにもありません。

これはQt 5.4.1で、特にWindows 7で「壊れた」ように見えます(これが最初から正しいことだった場合)。問題を特定しようとしていますが、QMainWindowsは全画面モードを終了しています。

これがはっきりしているので、これを行う正しい方法は何ですか?私は this フォーラムの投稿を見つけました。これは、QScreensが保持する基礎となるQWindowオブジェクトにQMainWindowを設定する必要があることを示唆しているようです。しかし、これは私のテストでは機能しないようです。これが私が書いたプログラムの例です:

app.h:

#include <vector>
#include <QObject>

class QMainWindow;

class app : public QObject
{
    Q_OBJECT
public:
    int run(int argc, char** argv);

public slots:
    void add_window();
    void remove_window();
    void windows_go_to_screens();
    void windows_go_to_screens_old();
    void windows_go_to_primary_screen();
    void windows_fullscreen();
    void windows_nonfullscreen();

private:
    QMainWindow * create_window(const char * id);
    void init_menus( QMainWindow * w );

    std::vector<QMainWindow *> m_windows;
};

app.cpp:

#include <assert.h>
#include <algorithm>
#include <iostream>
#include <vector>
#include <QObject>
#include <QMainWindow>
#include <QApplication>
#include <QMenubar>
#include <QAction>
#include <QScreen>
#include <QWindow>
#include <QLayout>
#include <QLabel>
#include <QStyle>

#include "app.h"

using namespace std;

int app::run(int argc, char** argv)
{
    QApplication a(argc, argv);
    QMainWindow * w = create_window("0");
    m_windows.Push_back(w);
    w->show();
    return a.exec();
}

void app::add_window()
{
    static const char * nums[] = {"0", "1", "2", "3", "4", "5", "6", "7", "8", "9"};
    m_windows.Push_back(create_window(nums[m_windows.size()]));
    m_windows.back()->show();
}

void app::remove_window()
{
    if (m_windows.size() > 1)
    {
        QMainWindow * w = m_windows.back();
        m_windows.pop_back();
        w->close();
        w->deleteLater();
    }
}

void app::windows_go_to_screens()
{
    QList<QScreen*> screens = qApp->screens();

    for (unsigned i = 0; i < std::min((unsigned)m_windows.size(), (unsigned)screens.size()); ++i)
    {
        QMainWindow * mw = m_windows[i];
        QScreen * screen = screens[i];
        QWindow * wh = mw->windowHandle();
        wh->setScreen(screen);
    }
}

void app::windows_go_to_screens_old()
{
    QList<QScreen*> screens = qApp->screens();

    for (unsigned i = 0; i < std::min((unsigned)m_windows.size(), (unsigned)screens.size()); ++i)
    {
        QMainWindow * mw = m_windows[i];
        QScreen * screen = screens[i];
        mw->move(screen->geometry().left(), screen->geometry().top());
    }
}

void app::windows_go_to_primary_screen()
{
    QList<QScreen*> screens = qApp->screens();

    for (unsigned i = 0; i < std::min((unsigned)m_windows.size(), (unsigned)screens.size()); ++i)
    {
        QMainWindow * mw = m_windows[i];
        QScreen * screen = screens[0];
        QWindow * wh = mw->windowHandle();
        wh->setScreen(screen);
    }
}

void app::windows_fullscreen()
{
    for (unsigned i = 0; i < m_windows.size(); ++i)
    {
        QMainWindow * mw = m_windows[i];
        mw->showFullScreen();
    }
}

void app::windows_nonfullscreen()
{
    for (unsigned i = 0; i < m_windows.size(); ++i)
    {
        QMainWindow * mw = m_windows[i];
        mw->showNormal();
    }
}



QMainWindow * app::create_window(const char * id)
{
    QMainWindow * w = new QMainWindow(NULL);
    init_menus(w);
    QWidget * cw = new QWidget(w);
    w->setCentralWidget(cw);
    QHBoxLayout * l = new QHBoxLayout(cw);
    cw->setLayout(l);
    QLabel * lab = new QLabel(id, cw);
    QPalette pal(lab->palette());
    pal.setColor(QPalette::Background, Qt::red);
    lab->setAutoFillBackground(true);
    lab->setPalette(pal);
    lab->setScaledContents(true);
    lab->setAlignment(Qt::AlignCenter);
    l->addWidget( lab );
    return w;
}

void app::init_menus( QMainWindow * w )
{
    QMenuBar * menubar = w->menuBar();
    QMenu * view_menu = new QMenu(tr("View"), w);
    view_menu->addAction("Add Window", this, SLOT(add_window()));
    view_menu->addAction("Remove Window", this, SLOT(remove_window()));
    view_menu->addAction("Windows Go To Screens", this, SLOT(windows_go_to_screens()));
    view_menu->addAction("Windows Go To Screens (old method)", this, SLOT(windows_go_to_screens_old()));
    view_menu->addAction("Windows Go To Primary Screen", this, SLOT(windows_go_to_primary_screen()));
    view_menu->addAction("Windows Fullscreen", this, SLOT(windows_fullscreen()));
    view_menu->addAction("Windows Non-Fullscreen", this, SLOT(windows_nonfullscreen()));
    menubar->addMenu(view_menu);
}

main.cpp:

#include "app.h"

int main(int argc, char** argv)
{
    app a;
    return a.run(argc, argv);
}

このプログラムをOS Xで実行すると、「Windows Go To Screens」機能は何も実行せず、どのウィンドウも移動しません。また、「Windows Go To Primary Screen」(名前がおかしい-0画面であるべき?)もありません。 NウィンドウMacでN個を超えるウィンドウを作成するのは興味深いことです。その場合、「Windowsフルスクリーン」を数回呼び出すと、QMainWindowsが実際に一度にフルスクリーンモードに切り替わります。

さらに興味深いのは、これを実行するとマルチモニターOS Xマシンで何が起こるかです。「ウィンドウの追加」は、ディスプレイと同じ数のウィンドウができるまで続きます。 「Windows Go To Screens(old method)」は、各ウィンドウを各モニターの左上に送信します。 「Windows Fullscreen」は、すべてのウィンドウをすべてのモニターでフルスクリーンにします。 「ウィンドウを削除」して、ウィンドウが1つだけ残るようにします。次に、「Windows Non-FullScreen」と入力すると、興味深い驚きが得られます。 Mission Controlに移動して、何が起こっているかを確認してください。

これを行う[〜#〜]正しい[〜#〜]方法は誰かに教えてもらえますか?私はQt5の例を調べました-完全に壊れているように見えるプレーヤーアプリケーションがあります(ビデオを一度に全画面モードで再生でき、その後の再生は別のデスクトップウィンドウで行われます)、サブゲームは最大化するだけです単一のディスプレイであり、他の例では全画面モードを利用していないようで、複数のモニターでは表示されません。

21
Ted Middleton

Qt5でこれを行う1つの方法は、_QWindow::setScreen_を使用して、ウィンドウを表示する画面を設定することです。 QWidgetには、QWindowへのポインタを返すwindowHandle()があります。そのため、ウィンドウごとにそのポインタを取得して、別の画面を設定できます。

全画面モードで最後の画面にウィジェットを表示する方法は次のとおりです。

_QWidget * widget = new QWidget();
widget->show();
widget->windowHandle()->setScreen(qApp->screens().last());
widget->showFullScreen();
_

または2番目の画面で:

_QWidget * widget = new QWidget();
widget->show();
widget->windowHandle()->setScreen(qApp->screens()[1]);
widget->showFullScreen();
_
9
Nejat