Commit 348d5576 authored by Boudewijn Rempt's avatar Boudewijn Rempt

Merge branch 'rempt/intel-3'

parents 80bd1dc9 cf145b39
...@@ -74,6 +74,7 @@ xsi:schemaLocation="http://www.kde.org/standards/kxmlgui/1.0 http://www.kde.org ...@@ -74,6 +74,7 @@ xsi:schemaLocation="http://www.kde.org/standards/kxmlgui/1.0 http://www.kde.org
<text>&amp;View</text> <text>&amp;View</text>
<Action name="view_show_canvas_only"/> <Action name="view_show_canvas_only"/>
<Action name="fullscreen"/> <Action name="fullscreen"/>
<Action name="view_detached_canvas"/>
<Action name="wrap_around_mode"/> <Action name="wrap_around_mode"/>
<Action name="level_of_detail_mode"/> <Action name="level_of_detail_mode"/>
<Action name="softProof"/> <Action name="softProof"/>
......
...@@ -597,6 +597,18 @@ ...@@ -597,6 +597,18 @@
<isCheckable>true</isCheckable> <isCheckable>true</isCheckable>
<statusTip></statusTip> <statusTip></statusTip>
</Action> </Action>
<Action name="view_detached_canvas">
<icon></icon>
<text>Detach canvas</text>
<whatsThis></whatsThis>
<toolTip>Show the canvas on a separate window</toolTip>
<iconText>Detach canvas</iconText>
<activationFlags>0</activationFlags>
<activationConditions>0</activationConditions>
<shortcut></shortcut>
<isCheckable>true</isCheckable>
<statusTip></statusTip>
</Action>
<Action name="wrap_around_mode"> <Action name="wrap_around_mode">
<icon></icon> <icon></icon>
<text>&amp;Wrap Around Mode</text> <text>&amp;Wrap Around Mode</text>
......
...@@ -132,15 +132,9 @@ void KoCanvasControllerWidget::Private::emitPointerPositionChangedSignals(QEvent ...@@ -132,15 +132,9 @@ void KoCanvasControllerWidget::Private::emitPointerPositionChangedSignals(QEvent
void KoCanvasControllerWidget::Private::activate() void KoCanvasControllerWidget::Private::activate()
{ {
QWidget *parent = q;
while (parent->parentWidget()) {
parent = parent->parentWidget();
}
KoCanvasSupervisor *observerProvider = dynamic_cast<KoCanvasSupervisor*>(parent);
if (!observerProvider) { if (!observerProvider) {
return; return;
} }
KoCanvasBase *canvas = q->canvas(); KoCanvasBase *canvas = q->canvas();
Q_FOREACH (KoCanvasObserverBase *docker, observerProvider->canvasObservers()) { Q_FOREACH (KoCanvasObserverBase *docker, observerProvider->canvasObservers()) {
KoCanvasObserverBase *observer = dynamic_cast<KoCanvasObserverBase*>(docker); KoCanvasObserverBase *observer = dynamic_cast<KoCanvasObserverBase*>(docker);
...@@ -153,11 +147,6 @@ void KoCanvasControllerWidget::Private::activate() ...@@ -153,11 +147,6 @@ void KoCanvasControllerWidget::Private::activate()
void KoCanvasControllerWidget::Private::unsetCanvas() void KoCanvasControllerWidget::Private::unsetCanvas()
{ {
QWidget *parent = q;
while (parent->parentWidget()) {
parent = parent->parentWidget();
}
KoCanvasSupervisor *observerProvider = dynamic_cast<KoCanvasSupervisor*>(parent);
if (!observerProvider) { if (!observerProvider) {
return; return;
} }
...@@ -172,10 +161,10 @@ void KoCanvasControllerWidget::Private::unsetCanvas() ...@@ -172,10 +161,10 @@ void KoCanvasControllerWidget::Private::unsetCanvas()
} }
//////////// ////////////
KoCanvasControllerWidget::KoCanvasControllerWidget(KActionCollection * actionCollection, QWidget *parent) KoCanvasControllerWidget::KoCanvasControllerWidget(KActionCollection * actionCollection, KoCanvasSupervisor *observerProvider, QWidget *parent)
: QAbstractScrollArea(parent) : QAbstractScrollArea(parent)
, KoCanvasController(actionCollection) , KoCanvasController(actionCollection)
, d(new Private(this)) , d(new Private(this, observerProvider))
{ {
// We need to set this as QDeclarativeView sets them a bit different from QAbstractScrollArea // We need to set this as QDeclarativeView sets them a bit different from QAbstractScrollArea
setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding); setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
......
...@@ -32,7 +32,7 @@ ...@@ -32,7 +32,7 @@
class KoShape; class KoShape;
class KoCanvasBase; class KoCanvasBase;
class KoCanvasSupervisor;
/** /**
* KoCanvasController implementation for QWidget based canvases * KoCanvasController implementation for QWidget based canvases
*/ */
...@@ -46,7 +46,7 @@ public: ...@@ -46,7 +46,7 @@ public:
* @param actionCollection the action collection for this widget * @param actionCollection the action collection for this widget
* @param parent the parent this widget will belong to * @param parent the parent this widget will belong to
*/ */
explicit KoCanvasControllerWidget(KActionCollection * actionCollection, QWidget *parent = 0); explicit KoCanvasControllerWidget(KActionCollection * actionCollection, KoCanvasSupervisor *observerProvider, QWidget *parent = 0);
~KoCanvasControllerWidget() override; ~KoCanvasControllerWidget() override;
/** /**
......
...@@ -28,6 +28,7 @@ ...@@ -28,6 +28,7 @@
#include <FlakeDebug.h> #include <FlakeDebug.h>
#include <KoConfig.h> #include <KoConfig.h>
#include "KoCanvasSupervisor.h"
class KoCanvasControllerWidget; class KoCanvasControllerWidget;
class Viewport; class Viewport;
...@@ -37,8 +38,9 @@ class Q_DECL_HIDDEN KoCanvasControllerWidget::Private ...@@ -37,8 +38,9 @@ class Q_DECL_HIDDEN KoCanvasControllerWidget::Private
{ {
public: public:
Private(KoCanvasControllerWidget *qq) Private(KoCanvasControllerWidget *qq, KoCanvasSupervisor *observerProvider)
: q(qq) : q(qq)
, observerProvider(observerProvider)
, canvas(0) , canvas(0)
, ignoreScrollSignals(false) , ignoreScrollSignals(false)
, zoomWithWheel(false) , zoomWithWheel(false)
...@@ -58,6 +60,7 @@ public: ...@@ -58,6 +60,7 @@ public:
void unsetCanvas(); void unsetCanvas();
KoCanvasControllerWidget *q; KoCanvasControllerWidget *q;
KoCanvasSupervisor *observerProvider;
QPointer<KoCanvasBase> canvas; QPointer<KoCanvasBase> canvas;
Viewport *viewportWidget; Viewport *viewportWidget;
bool ignoreScrollSignals; bool ignoreScrollSignals;
......
...@@ -301,10 +301,7 @@ void KisSketchView::documentChanged() ...@@ -301,10 +301,7 @@ void KisSketchView::documentChanged()
connect(d->doc, SIGNAL(modified(bool)), SIGNAL(modifiedChanged())); connect(d->doc, SIGNAL(modified(bool)), SIGNAL(modifiedChanged()));
QPointer<KisView> view = qobject_cast<KisView*>(KisPart::instance()->createView(d->doc, QPointer<KisView> view = KisPart::instance()->createView(d->doc, d->viewManager, QApplication::activeWindow());
d->viewManager->canvasResourceProvider()->resourceManager(),
d->viewManager->actionCollection(),
QApplication::activeWindow()));
view->setViewManager(d->viewManager); view->setViewManager(d->viewManager);
view->canvasBase()->setFavoriteResourceManager(d->viewManager->paintOpBox()->favoriteResourcesManager()); view->canvasBase()->setFavoriteResourceManager(d->viewManager->paintOpBox()->favoriteResourcesManager());
view->slotLoadingFinished(); view->slotLoadingFinished();
......
...@@ -363,6 +363,7 @@ set(kritaui_LIB_SRCS ...@@ -363,6 +363,7 @@ set(kritaui_LIB_SRCS
KisTemplateTree.cpp KisTemplateTree.cpp
KisUndoActionsUpdateManager.cpp KisUndoActionsUpdateManager.cpp
KisView.cpp KisView.cpp
KisCanvasWindow.cpp
KisImportExportErrorCode.cpp KisImportExportErrorCode.cpp
KisImportExportAdditionalChecks.cpp KisImportExportAdditionalChecks.cpp
......
/*
* Copyright (c) 2018 Jouni Pentikäinen <joupent@gmail.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#include <QHBoxLayout>
#include "KisCanvasWindow.h"
#include "KisMainWindow.h"
struct KisCanvasWindow::Private {
KisMainWindow *mainWindow;
Private(KisMainWindow *mainWindow)
: mainWindow(mainWindow)
{}
};
KisCanvasWindow::KisCanvasWindow(KisMainWindow *mainWindow)
: QWidget(mainWindow)
, d(new Private(mainWindow))
{
setWindowFlags(Qt::Window);
QLayout *layout = new QHBoxLayout(this);
setLayout(layout);
}
KisCanvasWindow::~KisCanvasWindow() = default;
void KisCanvasWindow::closeEvent(QCloseEvent *event)
{
d->mainWindow->setCanvasDetached(false);
QWidget::closeEvent(event);
}
QWidget * KisCanvasWindow::swapMainWidget(QWidget *newWidget)
{
QWidget *oldWidget = (layout()->count() > 0) ? (layout()->takeAt(0)->widget()) : nullptr;
if (newWidget) {
layout()->addWidget(newWidget);
}
return oldWidget;
}
/*
* Copyright (c) 2018 Jouni Pentikäinen <joupent@gmail.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#ifndef KISCANVASWINDOW_H
#define KISCANVASWINDOW_H
#include <QWidget>
class KisMainWindow;
/**
* Window for the canvas (mdi) area. Used when detached canvas mode is enabled.
*/
class KisCanvasWindow : public QWidget
{
public:
explicit KisCanvasWindow(KisMainWindow *mainWindow);
~KisCanvasWindow() override;
QWidget * swapMainWidget(QWidget *widget);
void closeEvent(QCloseEvent *event) override;
private:
struct Private;
QScopedPointer<Private> d;
};
#endif
...@@ -110,7 +110,6 @@ ...@@ -110,7 +110,6 @@
#include "dialogs/kis_about_application.h" #include "dialogs/kis_about_application.h"
#include "dialogs/kis_delayed_save_dialog.h" #include "dialogs/kis_delayed_save_dialog.h"
#include "dialogs/kis_dlg_preferences.h" #include "dialogs/kis_dlg_preferences.h"
#include "kis_action.h"
#include "kis_action_manager.h" #include "kis_action_manager.h"
#include "KisApplication.h" #include "KisApplication.h"
#include "kis_canvas2.h" #include "kis_canvas2.h"
...@@ -147,6 +146,9 @@ ...@@ -147,6 +146,9 @@
#include "KisWelcomePageWidget.h" #include "KisWelcomePageWidget.h"
#include <KritaVersionWrapper.h> #include <KritaVersionWrapper.h>
#include <kritaversion.h> #include <kritaversion.h>
#include "KisCanvasWindow.h"
#include "kis_action.h"
#include <mutex> #include <mutex>
class ToolDockerFactory : public KoDockFactoryBase class ToolDockerFactory : public KoDockFactoryBase
...@@ -236,6 +238,7 @@ public: ...@@ -236,6 +238,7 @@ public:
KisAction *mdiPreviousWindow {0}; KisAction *mdiPreviousWindow {0};
KisAction *toggleDockers {0}; KisAction *toggleDockers {0};
KisAction *toggleDockerTitleBars {0}; KisAction *toggleDockerTitleBars {0};
KisAction *toggleDetachCanvas {0};
KisAction *fullScreenMode {0}; KisAction *fullScreenMode {0};
KisAction *showSessionManager {0}; KisAction *showSessionManager {0};
...@@ -273,6 +276,7 @@ public: ...@@ -273,6 +276,7 @@ public:
QMdiSubWindow *activeSubWindow {0}; QMdiSubWindow *activeSubWindow {0};
QSignalMapper *windowMapper; QSignalMapper *windowMapper;
QSignalMapper *documentMapper; QSignalMapper *documentMapper;
KisCanvasWindow *canvasWindow {0};
QByteArray lastExportedFormat; QByteArray lastExportedFormat;
QScopedPointer<KisSignalCompressorWithParam<int> > tabSwitchCompressor; QScopedPointer<KisSignalCompressorWithParam<int> > tabSwitchCompressor;
...@@ -401,6 +405,9 @@ KisMainWindow::KisMainWindow(QUuid uuid) ...@@ -401,6 +405,9 @@ KisMainWindow::KisMainWindow(QUuid uuid)
connect(d->windowMapper, SIGNAL(mapped(QWidget*)), this, SLOT(setActiveSubWindow(QWidget*))); connect(d->windowMapper, SIGNAL(mapped(QWidget*)), this, SLOT(setActiveSubWindow(QWidget*)));
connect(d->documentMapper, SIGNAL(mapped(QObject*)), this, SLOT(newView(QObject*))); connect(d->documentMapper, SIGNAL(mapped(QObject*)), this, SLOT(newView(QObject*)));
d->canvasWindow = new KisCanvasWindow(this);
actionCollection()->addAssociatedWidget(d->canvasWindow);
createActions(); createActions();
// the welcome screen needs to grab actions...so make sure this line goes after the createAction() so they exist // the welcome screen needs to grab actions...so make sure this line goes after the createAction() so they exist
...@@ -724,6 +731,34 @@ void KisMainWindow::slotThemeChanged() ...@@ -724,6 +731,34 @@ void KisMainWindow::slotThemeChanged()
emit themeChanged(); emit themeChanged();
} }
bool KisMainWindow::canvasDetached() const
{
return centralWidget() != d->widgetStack;
}
void KisMainWindow::setCanvasDetached(bool detach)
{
if (detach == canvasDetached()) return;
QWidget *outgoingWidget = centralWidget() ? takeCentralWidget() : nullptr;
QWidget *incomingWidget = d->canvasWindow->swapMainWidget(outgoingWidget);
if (incomingWidget) {
setCentralWidget(incomingWidget);
}
if (detach) {
d->canvasWindow->show();
} else {
d->canvasWindow->hide();
}
}
QWidget * KisMainWindow::canvasWindow() const
{
return d->canvasWindow;
}
void KisMainWindow::updateReloadFileAction(KisDocument *doc) void KisMainWindow::updateReloadFileAction(KisDocument *doc)
{ {
Q_UNUSED(doc); Q_UNUSED(doc);
...@@ -951,7 +986,7 @@ KisView* KisMainWindow::addViewAndNotifyLoadingCompleted(KisDocument *document) ...@@ -951,7 +986,7 @@ KisView* KisMainWindow::addViewAndNotifyLoadingCompleted(KisDocument *document)
{ {
showWelcomeScreen(false); // see workaround in function header showWelcomeScreen(false); // see workaround in function header
KisView *view = KisPart::instance()->createView(document, resourceManager(), actionCollection(), this); KisView *view = KisPart::instance()->createView(document, d->viewManager, this);
addView(view); addView(view);
emit guiLoadingFinished(); emit guiLoadingFinished();
...@@ -1300,6 +1335,7 @@ void KisMainWindow::closeEvent(QCloseEvent *e) ...@@ -1300,6 +1335,7 @@ void KisMainWindow::closeEvent(QCloseEvent *e)
if (childrenList.isEmpty()) { if (childrenList.isEmpty()) {
d->deferredClosingEvent = e; d->deferredClosingEvent = e;
saveWindowState(true); saveWindowState(true);
d->canvasWindow->close();
} else { } else {
e->setAccepted(false); e->setAccepted(false);
} }
...@@ -2559,6 +2595,11 @@ void KisMainWindow::createActions() ...@@ -2559,6 +2595,11 @@ void KisMainWindow::createActions()
d->toggleDockers->setChecked(true); d->toggleDockers->setChecked(true);
connect(d->toggleDockers, SIGNAL(toggled(bool)), SLOT(toggleDockersVisibility(bool))); connect(d->toggleDockers, SIGNAL(toggled(bool)), SLOT(toggleDockersVisibility(bool)));
d->toggleDetachCanvas = actionManager->createAction("view_detached_canvas");
d->toggleDetachCanvas->setChecked(false);
connect(d->toggleDetachCanvas, SIGNAL(toggled(bool)), SLOT(setCanvasDetached(bool)));
setCanvasDetached(false);
actionCollection()->addAction("settings_dockers_menu", d->dockWidgetMenu); actionCollection()->addAction("settings_dockers_menu", d->dockWidgetMenu);
actionCollection()->addAction("window", d->windowMenu); actionCollection()->addAction("window", d->windowMenu);
......
...@@ -187,6 +187,12 @@ public: ...@@ -187,6 +187,12 @@ public:
QStringList showOpenFileDialog(bool isImporting); QStringList showOpenFileDialog(bool isImporting);
/**
* The top-level window used for a detached canvas.
*/
QWidget *canvasWindow() const;
bool canvasDetached() const;
/** /**
* Shows if the main window is saving anything right now. If the * Shows if the main window is saving anything right now. If the
* user presses Ctrl+W too fast, then the document can be close * user presses Ctrl+W too fast, then the document can be close
...@@ -297,7 +303,10 @@ public Q_SLOTS: ...@@ -297,7 +303,10 @@ public Q_SLOTS:
*/ */
void reloadRecentFileList(); void reloadRecentFileList();
/**
* Detach canvas onto a separate window, or restore it back to to main window.
*/
void setCanvasDetached(bool detached);
private Q_SLOTS: private Q_SLOTS:
/** /**
......
...@@ -222,8 +222,7 @@ KisMainWindow *KisPart::createMainWindow(QUuid id) ...@@ -222,8 +222,7 @@ KisMainWindow *KisPart::createMainWindow(QUuid id)
} }
KisView *KisPart::createView(KisDocument *document, KisView *KisPart::createView(KisDocument *document,
KoCanvasResourceProvider *resourceManager, KisViewManager *viewManager,
KActionCollection *actionCollection,
QWidget *parent) QWidget *parent)
{ {
// If creating the canvas fails, record this and disable OpenGL next time // If creating the canvas fails, record this and disable OpenGL next time
...@@ -239,7 +238,7 @@ KisView *KisPart::createView(KisDocument *document, ...@@ -239,7 +238,7 @@ KisView *KisPart::createView(KisDocument *document,
grp.sync(); grp.sync();
QApplication::setOverrideCursor(Qt::WaitCursor); QApplication::setOverrideCursor(Qt::WaitCursor);
KisView *view = new KisView(document, resourceManager, actionCollection, parent); KisView *view = new KisView(document, viewManager, parent);
QApplication::restoreOverrideCursor(); QApplication::restoreOverrideCursor();
// Record successful canvas creation // Record successful canvas creation
......
...@@ -205,8 +205,7 @@ public: ...@@ -205,8 +205,7 @@ public:
* views, and if the document wasn't known yet, it's registered as well. * views, and if the document wasn't known yet, it's registered as well.
*/ */
KisView *createView(KisDocument *document, KisView *createView(KisDocument *document,
KoCanvasResourceProvider *resourceManager, KisViewManager *viewManager,
KActionCollection *actionCollection,
QWidget *parent); QWidget *parent);
/** /**
......
...@@ -104,13 +104,13 @@ class Q_DECL_HIDDEN KisView::Private ...@@ -104,13 +104,13 @@ class Q_DECL_HIDDEN KisView::Private
public: public:
Private(KisView *_q, Private(KisView *_q,
KisDocument *document, KisDocument *document,
KoCanvasResourceProvider *resourceManager, KisViewManager *viewManager)
KActionCollection *actionCollection) : actionCollection(viewManager->actionCollection())
: actionCollection(actionCollection)
, viewConverter() , viewConverter()
, canvasController(_q, actionCollection) , canvasController(_q, viewManager->mainWindow(), viewManager->actionCollection())
, canvas(&viewConverter, resourceManager, _q, document->shapeController()) , canvas(&viewConverter, viewManager->canvasResourceProvider()->resourceManager(), viewManager->mainWindow(), _q, document->shapeController())
, zoomManager(_q, &this->viewConverter, &this->canvasController) , zoomManager(_q, &this->viewConverter, &this->canvasController)
, viewManager(viewManager)
, paintingAssistantsDecoration(new KisPaintingAssistantsDecoration(_q)) , paintingAssistantsDecoration(new KisPaintingAssistantsDecoration(_q))
, referenceImagesDecoration(new KisReferenceImagesDecoration(_q, document)) , referenceImagesDecoration(new KisReferenceImagesDecoration(_q, document))
, floatingMessageCompressor(100, KisSignalCompressor::POSTPONE) , floatingMessageCompressor(100, KisSignalCompressor::POSTPONE)
...@@ -206,9 +206,9 @@ public: ...@@ -206,9 +206,9 @@ public:
}; };
KisView::KisView(KisDocument *document, KoCanvasResourceProvider *resourceManager, KActionCollection *actionCollection, QWidget *parent) KisView::KisView(KisDocument *document, KisViewManager *viewManager, QWidget *parent)
: QWidget(parent) : QWidget(parent)
, d(new Private(this, document, resourceManager, actionCollection)) , d(new Private(this, document, viewManager))
{ {
Q_ASSERT(document); Q_ASSERT(document);
connect(document, SIGNAL(titleModified(QString,bool)), this, SIGNAL(titleModified(QString,bool))); connect(document, SIGNAL(titleModified(QString,bool)), this, SIGNAL(titleModified(QString,bool)));
...@@ -661,7 +661,7 @@ QPrintDialog *KisView::createPrintDialog(KisPrintJob *printJob, QWidget *parent) ...@@ -661,7 +661,7 @@ QPrintDialog *KisView::createPrintDialog(KisPrintJob *printJob, QWidget *parent)
KisMainWindow * KisView::mainWindow() const KisMainWindow * KisView::mainWindow() const
{ {
return dynamic_cast<KisMainWindow *>(window()); return d->viewManager->mainWindow();
} }
void KisView::setSubWindow(QMdiSubWindow *subWindow) void KisView::setSubWindow(QMdiSubWindow *subWindow)
......
...@@ -75,7 +75,7 @@ public: ...@@ -75,7 +75,7 @@ public:
/** /**
* Creates a new view for the document. * Creates a new view for the document.
*/ */
KisView(KisDocument *document, KoCanvasResourceProvider *resourceManager, KActionCollection *actionCollection, QWidget *parent = 0); KisView(KisDocument *document, KisViewManager *viewManager, QWidget *parent = 0);
~KisView() override; ~KisView() override;
// Temporary while teasing apart view and mainwindow // Temporary while teasing apart view and mainwindow
......
...@@ -35,12 +35,80 @@ static const int WINDOW_LAYOUT_VERSION = 1; ...@@ -35,12 +35,80 @@ static const int WINDOW_LAYOUT_VERSION = 1;
struct KisWindowLayoutResource::Private struct KisWindowLayoutResource::Private
{ {
struct WindowGeometry{
int screen = -1;
Qt::WindowStates stateFlags = Qt::WindowNoState;
QByteArray data;
static WindowGeometry fromWindow(const QWidget *window, QList<QScreen*> screens)
{
WindowGeometry geometry;
QWindow *windowHandle = window->windowHandle();
geometry.data = window->saveGeometry();
geometry.stateFlags = windowHandle->windowState();
int index = screens.indexOf(windowHandle->screen());
if (index >= 0) {
geometry.screen = index;
}
return geometry;
}
void forceOntoCorrectScreen(QWidget *window, QList<QScreen*> screens)
{
QWindow *windowHandle = window->windowHandle();
if (screens.indexOf(windowHandle->screen()) != screen) {
QScreen *qScreen = screens[screen];
windowHandle->setScreen(qScreen);
windowHandle->setPosition(qScreen->availableGeometry().topLeft());
}
if (stateFlags) {
window->setWindowState(stateFlags);
}
}
void save(QDomDocument &doc, QDomElement &elem) const
{
if (screen >= 0) {
elem.setAttribute("screen", screen);
}
if (stateFlags & Qt::WindowMaximized) {
elem.setAttribute("maximized", "1");
}
QDomElement geometry = doc.createElement("geometry");
geometry.appendChild(doc.createCDATASection(data.toBase64()));
elem.appendChild(geometry);
}
static WindowGeometry load(const QDomElement &element)
{
WindowGeometry geometry;
geometry.screen = element.attribute("screen", "-1").toInt();
if (element.attribute("maximized", "0") != "0") {
geometry.stateFlags |= Qt::WindowMaximized;
}
QDomElement dataElement = element.firstChildElement("geometry");
geometry.data = QByteArray::fromBase64(dataElement.text().toLatin1());
return geometry;
}
};
struct Window { struct Window {
QUuid windowId; QUuid windowId;
QByteArray geometry;
QByteArray windowState; QByteArray windowState;
int screen = -1; WindowGeometry geometry;
Qt::WindowStates stateFlags = Qt::WindowNoState;
bool canvasDetached = false;
WindowGeometry canvasWindowGeometry;
}; };
QVector<Window> windows; QVector<Window> windows;
...@@ -196,27 +264,31 @@ void KisWindowLayoutResource::applyLayout() ...@@ -196,27 +264,31 @@ void KisWindowLayoutResource::applyLayout()
QPointer<KisMainWindow> mainWindow = kisPart->windowById(window.windowId); QPointer<KisMainWindow> mainWindow = kisPart->windowById(window.windowId);
KIS_SAFE_ASSERT_RECOVER_BREAK(mainWindow); KIS_SAFE_ASSERT_RECOVER_BREAK(mainWindow);
mainWindow->restoreGeometry(window.geometry); mainWindow->restoreGeometry(window.geometry.data);
mainWindow->restoreWorkspaceState(window.windowState); mainWindow->restoreWorkspaceState(window.windowState);
mainWindow->setCanvasDetached(window.canvasDetached);
if (window.canvasDetached) {
QWidget *canvasWindow = mainWindow->canvasWindow();
canvasWindow->restoreGeometry(window.canvasWindowGeometry.data);
}
} }
QApplication::processEvents(QEventLoop::ExcludeUserInputEvents); QApplication::processEvents(QEventLoop::ExcludeUserInputEvents);
QList<QScreen*> screens = d->getScreensInConsistentOrder(); QList<QScreen*> screens = d->getScreensInConsistentOrder();
Q_FOREACH(const auto &window, d->windows) { Q_FOREACH(const auto &window, d->windows) {
if (window.screen >= 0 && window.screen < screens.size()) { Private::WindowGeometry geometry = window.geometry;
QPointer<KisMainWindow> mainWindow = kisPart->windowById(window.windowId); QPointer<KisMainWindow> mainWindow = kisPart->windowById(window.windowId);
KIS_SAFE_ASSERT_RECOVER_BREAK(mainWindow); KIS_SAFE_ASSERT_RECOVER_BREAK(mainWindow);
QWindow *windowHandle = mainWindow->windowHandle();
if (screens.indexOf(windowHandle->screen()) != window.screen) {
QScreen *screen = screens[window.screen];
windowHandle->setScreen(screen);
windowHandle->setPosition(screen->availableGeometry().topLeft());
}
if (window.stateFlags) { if (geometry.screen >= 0 && geometry.screen < screens.size()) {