2015-05-07 2 views
18

У меня есть Windows & Программа Mac, которая переключается в полноэкранный режим на нескольких мониторах. В Qt 4 кажется (я не могу найти явную документацию о том, как это сделать), как «правильный» способ сделать это, создав N QMainWindow для N мониторов на машине, вызвав QWidget::move() в N координаты верхнего левого монитора, а затем вызов QWidget::setWindowState(Qt::WindowFullScreen). Я не знаю, является ли это правильным делом - опять же, я не могу найти никакой документации или примеров в любом месте, где это делается в Qt.В Qt 5, каков правильный способ показать полноэкранные окна QWidget с несколькими мониторами?

Это, кажется, «сломан» (если это было когда-либо правильно, что нужно делать в первую очередь) в Qt 5.4.1, особенно в Windows 7. Я все еще пытаюсь изолировать проблему, но кажется например, QMainWindow s выходят из полноэкранного режима.

Просто так я понимаю, что это правильный способ сделать это? Я нашел this сообщение в форуме, которое, кажется, предполагает, что я должен установить QScreen на базовые объекты 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» ничего не делает - ни один из окон не перемещается. Также не отображается экран «Windows Go To Primary» (плохо названный - 0)?). Создание более чем N окон в окне N Mac интересен - в этом случае несколько раз вызовы «Windows Fullscreen» фактически переключат QMainWindows в полноэкранный режим по одному!

Еще более интересным является то, что происходит на компьютере с несколькими мониторами OS X, когда вы это делаете: «Добавить окно», пока у вас не будет столько окон, сколько отображается. «Windows Go To Screens (старый метод)» отправит каждое окно в верхнем левом углу каждого монитора. «Windows Fullscreen» сделает все окна в полноэкранном режиме на всех мониторах. «Удалить окно», пока не останется только 1 окно. Затем «Windows Non-FullScreen», и вы получите интересный сюрприз. Зайдите в Mission Control, чтобы узнать, что происходит.

Может ли кто-нибудь сказать мне, что такое RIGHT Способ сделать это? Я просмотрел примеры Qt5 - есть приложение для проигрывателя, которое, кажется, полностью сломано (он может воспроизводить видео в полноэкранном режиме один раз, а затем последующие пьесы находятся в отдельном окне рабочего стола), под игра только максимизирует один дисплей, и ни один из других примеров, похоже, не использует полноэкранный режим, и, конечно, не на нескольких мониторах.

ответ

6

Один из способов сделать это в Qt5 - использовать QWindow::setScreen для установки экрана, на котором должно отображаться окно. QWidget имеет windowHandle(), который возвращает указатель на QWindow. Таким образом, вы можете получить этот указатель для каждого окна и установить другой экран.

Вот как показать свой виджет в последнем экране в полноэкранном режиме:

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

Или на втором экране:

QWidget * widget = new QWidget(); 
widget->show(); 
widget->windowHandle()->setScreen(qApp->screens()[1]); 
widget->showFullScreen(); 
Смежные вопросы