26#include "private/multisplitter/Item_p.h" 
   27#include "private/LayoutSaver_p.h" 
   28#include "private/DockRegistry_p.h" 
   29#include "private/DockWidgetBase_p.h" 
   30#include "private/FloatingWindow_p.h" 
   31#include "private/Frame_p.h" 
   32#include "private/LayoutWidget_p.h" 
   33#include "private/Logging_p.h" 
   34#include "private/Position_p.h" 
   35#include "private/Utils_p.h" 
   64LayoutSaver::Layout *LayoutSaver::Layout::s_currentLayoutBeingRestored = 
nullptr;
 
   69    InternalRestoreOptions ret = {};
 
   71        ret.setFlag(InternalRestoreOption::SkipMainWindowGeometry);
 
   72        ret.setFlag(InternalRestoreOption::RelativeFloatingWindowGeometry);
 
   76        ret.setFlag(InternalRestoreOption::RelativeFloatingWindowGeometry, 
false);
 
   81        qWarning() << Q_FUNC_INFO << 
"Unknown options" << options;
 
 
   87bool LayoutSaver::Private::s_restoreInProgress = 
false;
 
   91    QVariantList variantList;
 
   94        variantList.push_back(str);
 
 
  102    stringList.
reserve(variantList.size());
 
  103    for (
const QVariant &variant : variantList)
 
  104        stringList.
push_back(variant.toString());
 
 
  110    : d(new Private(options))
 
 
  123    QFile f(jsonFilename);
 
  125        qWarning() << Q_FUNC_INFO << 
"Failed to open" << jsonFilename << f.
errorString();
 
 
  135    QFile f(jsonFilename);
 
  137        qWarning() << Q_FUNC_INFO << 
"Failed to open" << jsonFilename << f.
errorString();
 
 
  149    if (!d->m_dockRegistry->isSane()) {
 
  150        qWarning() << Q_FUNC_INFO << 
"Refusing to serialize this layout. Check previous warnings.";
 
  154    LayoutSaver::Layout layout;
 
  157    d->m_dockRegistry->ensureAllFloatingWidgetsAreMorphed();
 
  160    layout.mainWindows.reserve(mainWindows.
size());
 
  162        if (d->matchesAffinity(mainWindow->affinities()))
 
  163            layout.mainWindows.push_back(mainWindow->serialize());
 
  167    layout.floatingWindows.reserve(floatingWindows.
size());
 
  168    for (KDDockWidgets::FloatingWindow *floatingWindow : floatingWindows) {
 
  169        if (d->matchesAffinity(floatingWindow->affinities()))
 
  170            layout.floatingWindows.push_back(floatingWindow->serialize());
 
  175    layout.closedDockWidgets.reserve(closedDockWidgets.
size());
 
  177        if (d->matchesAffinity(dockWidget->affinities()))
 
  178            layout.closedDockWidgets.push_back(dockWidget->d->serialize());
 
  185    layout.allDockWidgets.reserve(dockWidgets.
size());
 
  188        if (!skipsRestore && d->matchesAffinity(dockWidget->affinities())) {
 
  189            auto dw = dockWidget->d->serialize();
 
  190            dw->lastPosition = dockWidget->d->lastPosition()->serialize();
 
  191            layout.allDockWidgets.push_back(dw);
 
  195    return layout.toJson();
 
 
  200    d->clearRestoredProperty();
 
  213            m_saver->d->deleteEmptyFrames();
 
  219    FrameCleanup cleanup(
this);
 
  220    LayoutSaver::Layout layout;
 
  221    if (!layout.fromJson(data)) {
 
  222        qWarning() << Q_FUNC_INFO << 
"Failed to parse json data";
 
  226    if (!layout.isValid()) {
 
  230    layout.scaleSizes(d->m_restoreOptions);
 
  232    d->floatWidgetsWhichSkipRestore(layout.mainWindowNames());
 
  233    d->floatUnknownWidgets(layout);
 
  235    Private::RAIIIsRestoring isRestoring;
 
  240    d->m_dockRegistry->clear(d->m_dockRegistry->dockWidgets(layout.dockWidgetsToClose()),
 
  241                             d->m_dockRegistry->mainWindows(layout.mainWindowNames()),
 
  245    for (
const LayoutSaver::MainWindow &mw : qAsConst(layout.mainWindows)) {
 
  246        MainWindowBase *mainWindow = d->m_dockRegistry->mainWindowByName(mw.uniqueName);
 
  249                mainWindow = mwFunc(mw.uniqueName);
 
  251                qWarning() << 
"Failed to restore layout create MainWindow with name" << mw.uniqueName << 
"first";
 
  256        if (!d->matchesAffinity(mainWindow->
affinities()))
 
  259        if (!(d->m_restoreOptions & InternalRestoreOption::SkipMainWindowGeometry)) {
 
  260            d->deserializeWindowGeometry(mw, mainWindow->
window()); 
 
  263                    w->setWindowState(mw.windowState);
 
  268        if (!mainWindow->deserialize(mw))
 
  273    for (LayoutSaver::FloatingWindow &fw : layout.floatingWindows) {
 
  274        if (!d->matchesAffinity(fw.affinities) || fw.skipsRestore())
 
  278                                                      : DockRegistry::self()->mainwindows().at(fw.parentIndex);
 
  281        fw.floatingWindowInstance = floatingWindow;
 
  282        d->deserializeWindowGeometry(fw, floatingWindow);
 
  283        if (!floatingWindow->deserialize(fw)) {
 
  284            qWarning() << Q_FUNC_INFO << 
"Failed to deserialize floating window";
 
  290    for (
const auto &dw : qAsConst(layout.closedDockWidgets)) {
 
  291        if (d->matchesAffinity(dw->affinities)) {
 
  292            DockWidgetBase::deserialize(dw);
 
  297    for (
const auto &dw : qAsConst(layout.allDockWidgets)) {
 
  298        if (!d->matchesAffinity(dw->affinities))
 
  302                d->m_dockRegistry->dockByName(dw->uniqueName, DockRegistry::DockByNameFlag::ConsultRemapping)) {
 
  303            dockWidget->d->lastPosition()->deserialize(dw->lastPosition);
 
  305            qWarning() << Q_FUNC_INFO << 
"Couldn't find dock widget" << dw->uniqueName;
 
 
  314    d->m_affinityNames = affinityNames;
 
  317        d->m_affinityNames << 
QString();
 
 
  332        if (dw->property(
"kddockwidget_was_restored").toBool())
 
 
  339void LayoutSaver::Private::clearRestoredProperty()
 
  343        dw->setProperty(
"kddockwidget_was_restored", 
QVariant());
 
  348void LayoutSaver::Private::deserializeWindowGeometry(
const T &saved, 
QWidgetOrQuick *topLevel)
 
  353    QRect geometry = saved.geometry;
 
  354    if (!isNormalWindowState(saved.windowState)) {
 
  357        geometry = saved.normalGeometry;
 
  360    ::FloatingWindow::ensureRectIsOnScreen(geometry);
 
  365        KDDockWidgets::Private::setTopLevelGeometry(geometry, topLevel);
 
  371LayoutSaver::Private::Private(RestoreOptions options)
 
  372    : m_dockRegistry(DockRegistry::self())
 
  377bool LayoutSaver::Private::matchesAffinity(
const QStringList &affinities)
 const 
  379    return m_affinityNames.isEmpty() || affinities.
isEmpty()
 
  380        || DockRegistry::self()->affinitiesMatch(m_affinityNames, affinities);
 
  383void LayoutSaver::Private::floatWidgetsWhichSkipRestore(
const QStringList &mainWindowNames)
 
  390    for (
MainWindowBase *mw : DockRegistry::self()->mainWindows(mainWindowNames)) {
 
  392        for (
auto dw : docks) {
 
  393            if (dw->skipsRestore()) {
 
  394                dw->setFloating(
true);
 
  400void LayoutSaver::Private::floatUnknownWidgets(
const LayoutSaver::Layout &layout)
 
  406    for (
MainWindowBase *mw : DockRegistry::self()->mainWindows(layout.mainWindowNames())) {
 
  409            if (!layout.containsDockWidget(dw->uniqueName())) {
 
  410                dw->setFloating(
true);
 
  416void LayoutSaver::Private::deleteEmptyFrames()
 
  421    for (
auto frame : m_dockRegistry->frames()) {
 
  422        if (!frame->beingDeletedLater() && frame->isEmpty() && !frame->isCentralFrame()) {
 
  423            if (
auto item = frame->layoutItem()) {
 
  424                item->turnIntoPlaceholder();
 
  427                qWarning() << Q_FUNC_INFO << 
"Expected item for frame";
 
  435std::unique_ptr<QSettings> LayoutSaver::Private::settings()
 const 
  437    auto settings = std::unique_ptr<QSettings>(
new QSettings(qApp->organizationName(),
 
  438                                                             qApp->applicationName()));
 
  439    settings->beginGroup(QStringLiteral(
"KDDockWidgets::LayoutSaver"));
 
  446    return Private::s_restoreInProgress;
 
 
  449bool LayoutSaver::Layout::isValid()
 const 
  451    if (serializationVersion != KDDOCKWIDGETS_SERIALIZATION_VERSION) {
 
  452        qWarning() << Q_FUNC_INFO << 
"Serialization format is too old" 
  453                   << serializationVersion << 
"current=" << KDDOCKWIDGETS_SERIALIZATION_VERSION;
 
  457    for (
auto &m : mainWindows) {
 
  462    for (
auto &m : floatingWindows) {
 
  467    for (
auto &m : allDockWidgets) {
 
  481bool LayoutSaver::Layout::fromJson(
const QByteArray &jsonData)
 
  493QVariantMap LayoutSaver::Layout::toVariantMap()
 const 
  496    map.insert(QStringLiteral(
"serializationVersion"), serializationVersion);
 
  497    map.insert(QStringLiteral(
"mainWindows"), toVariantList<LayoutSaver::MainWindow>(mainWindows));
 
  498    map.insert(QStringLiteral(
"floatingWindows"), toVariantList<LayoutSaver::FloatingWindow>(floatingWindows));
 
  499    map.insert(QStringLiteral(
"closedDockWidgets"), ::dockWidgetNames(closedDockWidgets));
 
  500    map.insert(QStringLiteral(
"allDockWidgets"), toVariantList(allDockWidgets));
 
  501    map.insert(QStringLiteral(
"screenInfo"), toVariantList<LayoutSaver::ScreenInfo>(screenInfo));
 
  506void LayoutSaver::Layout::fromVariantMap(
const QVariantMap &map)
 
  508    allDockWidgets.
clear();
 
  509    const QVariantList dockWidgetsV = map.value(QStringLiteral(
"allDockWidgets")).toList();
 
  510    for (
const QVariant &v : dockWidgetsV) {
 
  511        const QVariantMap dwV = v.toMap();
 
  512        const QString name = dwV.value(QStringLiteral(
"uniqueName")).toString();
 
  513        auto dw = LayoutSaver::DockWidget::dockWidgetForName(name);
 
  514        dw->fromVariantMap(dwV);
 
  518    closedDockWidgets.clear();
 
  519    const QVariantList closedDockWidgetsV = map.value(QStringLiteral(
"closedDockWidgets")).toList();
 
  520    closedDockWidgets.reserve(closedDockWidgetsV.size());
 
  521    for (
const QVariant &v : closedDockWidgetsV) {
 
  522        closedDockWidgets.push_back(LayoutSaver::DockWidget::dockWidgetForName(v.toString()));
 
  525    serializationVersion = map.value(QStringLiteral(
"serializationVersion")).toInt();
 
  526    mainWindows = fromVariantList<LayoutSaver::MainWindow>(map.value(QStringLiteral(
"mainWindows")).toList());
 
  527    floatingWindows = fromVariantList<LayoutSaver::FloatingWindow>(map.value(QStringLiteral(
"floatingWindows")).toList());
 
  528    screenInfo = fromVariantList<LayoutSaver::ScreenInfo>(map.value(QStringLiteral(
"screenInfo")).toList());
 
  531void LayoutSaver::Layout::scaleSizes(InternalRestoreOptions options)
 
  533    if (mainWindows.isEmpty())
 
  536    const bool skipsMainWindowGeometry = options & InternalRestoreOption::SkipMainWindowGeometry;
 
  537    if (!skipsMainWindowGeometry) {
 
  546    for (
auto &mw : mainWindows)
 
  552    const bool useRelativeSizesForFloatingWidgets =
 
  553        options & InternalRestoreOption::RelativeFloatingWindowGeometry;
 
  555    if (useRelativeSizesForFloatingWidgets) {
 
  556        for (
auto &fw : floatingWindows) {
 
  557            LayoutSaver::MainWindow mw = mainWindowForIndex(fw.parentIndex);
 
  558            if (mw.scalingInfo.isValid())
 
  559                fw.scaleSizes(mw.scalingInfo);
 
  563    const ScalingInfo firstScalingInfo = mainWindows.constFirst().scalingInfo;
 
  564    if (firstScalingInfo.isValid()) {
 
  565        for (
auto &dw : allDockWidgets) {
 
  569            dw->scaleSizes(firstScalingInfo);
 
  574LayoutSaver::MainWindow LayoutSaver::Layout::mainWindowForIndex(
int index)
 const 
  576    if (index < 0 || index >= mainWindows.size())
 
  579    return mainWindows.at(index);
 
  582LayoutSaver::FloatingWindow LayoutSaver::Layout::floatingWindowForIndex(
int index)
 const 
  584    if (index < 0 || index >= floatingWindows.size())
 
  587    return floatingWindows.at(index);
 
  590QStringList LayoutSaver::Layout::mainWindowNames()
 const 
  593    names.
reserve(mainWindows.size());
 
  594    for (
const auto &mw : mainWindows) {
 
  595        names << mw.uniqueName;
 
  601QStringList LayoutSaver::Layout::dockWidgetNames()
 const 
  605    for (
const auto &dw : allDockWidgets) {
 
  606        names << dw->uniqueName;
 
  612QStringList LayoutSaver::Layout::dockWidgetsToClose()
 const 
  618    auto registry = DockRegistry::self();
 
  619    for (
const auto &dw : allDockWidgets) {
 
  620        if (
DockWidgetBase *dockWidget = registry->dockByName(dw->uniqueName)) {
 
  624            if (dockWidget->skipsRestore()) {
 
  625                if (
auto fw = dockWidget->floatingWindow()) {
 
  634                names << dw->uniqueName;
 
  641bool LayoutSaver::Layout::containsDockWidget(
const QString &uniqueName)
 const 
  643    return std::find_if(allDockWidgets.
cbegin(), allDockWidgets.
cend(), [uniqueName](
const std::shared_ptr<LayoutSaver::DockWidget> &dock) {
 
  644               return dock->uniqueName == uniqueName;
 
  646        != allDockWidgets.
cend();
 
  649bool LayoutSaver::Frame::isValid()
 const 
  655        qWarning() << Q_FUNC_INFO << 
"Invalid geometry";
 
  660        qWarning() << Q_FUNC_INFO << 
"Invalid id";
 
  664    if (!dockWidgets.isEmpty()) {
 
  665        if (currentTabIndex >= dockWidgets.size() || currentTabIndex < 0) {
 
  666            qWarning() << Q_FUNC_INFO << 
"Invalid tab index" << currentTabIndex << dockWidgets.size();
 
  671    for (
auto &dw : dockWidgets) {
 
  679bool LayoutSaver::Frame::hasSingleDockWidget()
 const 
  681    return dockWidgets.size() == 1;
 
  684bool LayoutSaver::Frame::skipsRestore()
 const 
  686    return std::all_of(dockWidgets.cbegin(), dockWidgets.cend(), [](LayoutSaver::DockWidget::Ptr dw) {
 
  687        return dw->skipsRestore();
 
  691LayoutSaver::DockWidget::Ptr LayoutSaver::Frame::singleDockWidget()
 const 
  693    if (!hasSingleDockWidget())
 
  696    return dockWidgets.first();
 
  699QVariantMap LayoutSaver::Frame::toVariantMap()
 const 
  702    map.insert(QStringLiteral(
"id"), 
id);
 
  703    map.insert(QStringLiteral(
"isNull"), isNull);
 
  704    map.insert(QStringLiteral(
"objectName"), objectName);
 
  705    map.insert(QStringLiteral(
"geometry"), Layouting::rectToMap(geometry));
 
  706    map.insert(QStringLiteral(
"options"), options);
 
  707    map.insert(QStringLiteral(
"currentTabIndex"), currentTabIndex);
 
  708    map.insert(QStringLiteral(
"mainWindowUniqueName"), mainWindowUniqueName);
 
  709    map.insert(QStringLiteral(
"dockWidgets"), dockWidgetNames(dockWidgets));
 
  714void LayoutSaver::Frame::fromVariantMap(
const QVariantMap &map)
 
  722    id = map.value(QStringLiteral(
"id")).toString();
 
  723    isNull = map.value(QStringLiteral(
"isNull")).toBool();
 
  724    objectName = map.value(QStringLiteral(
"objectName")).toString();
 
  725    mainWindowUniqueName = map.value(QStringLiteral(
"mainWindowUniqueName")).toString();
 
  726    geometry = Layouting::mapToRect(map.value(QStringLiteral(
"geometry")).toMap());
 
  728    currentTabIndex = map.value(QStringLiteral(
"currentTabIndex")).toInt();
 
  730    const QVariantList dockWidgetsV = map.value(QStringLiteral(
"dockWidgets")).toList();
 
  733    dockWidgets.reserve(dockWidgetsV.size());
 
  734    for (
const auto &variant : dockWidgetsV) {
 
  735        DockWidget::Ptr dw = DockWidget::dockWidgetForName(variant.toString());
 
  736        dockWidgets.push_back(dw);
 
  740bool LayoutSaver::DockWidget::isValid()
 const 
  745void LayoutSaver::DockWidget::scaleSizes(
const ScalingInfo &scalingInfo)
 
  747    lastPosition.scaleSizes(scalingInfo);
 
  750bool LayoutSaver::DockWidget::skipsRestore()
 const 
  752    if (
DockWidgetBase *dw = DockRegistry::self()->dockByName(uniqueName))
 
  753        return dw->skipsRestore();
 
  758QVariantMap LayoutSaver::DockWidget::toVariantMap()
 const 
  763    map.insert(QStringLiteral(
"uniqueName"), uniqueName);
 
  764    map.insert(QStringLiteral(
"lastPosition"), lastPosition.toVariantMap());
 
  769void LayoutSaver::DockWidget::fromVariantMap(
const QVariantMap &map)
 
  774    const QString affinityName = map.value(QStringLiteral(
"affinityName")).toString();
 
  779    uniqueName = map.value(QStringLiteral(
"uniqueName")).toString();
 
  780    lastPosition.fromVariantMap(map.value(QStringLiteral(
"lastPosition")).toMap());
 
  783bool LayoutSaver::FloatingWindow::isValid()
 const 
  785    if (!multiSplitterLayout.isValid())
 
  789        qWarning() << Q_FUNC_INFO << 
"Invalid geometry";
 
  796bool LayoutSaver::FloatingWindow::hasSingleDockWidget()
 const 
  798    return multiSplitterLayout.hasSingleDockWidget();
 
  801LayoutSaver::DockWidget::Ptr LayoutSaver::FloatingWindow::singleDockWidget()
 const 
  803    return multiSplitterLayout.singleDockWidget();
 
  806bool LayoutSaver::FloatingWindow::skipsRestore()
 const 
  808    return multiSplitterLayout.skipsRestore();
 
  811void LayoutSaver::FloatingWindow::scaleSizes(
const ScalingInfo &scalingInfo)
 
  813    scalingInfo.applyFactorsTo( geometry);
 
  816QVariantMap LayoutSaver::FloatingWindow::toVariantMap()
 const 
  819    map.
insert(QStringLiteral(
"multiSplitterLayout"), multiSplitterLayout.toVariantMap());
 
  820    map.
insert(QStringLiteral(
"parentIndex"), parentIndex);
 
  821    map.
insert(QStringLiteral(
"geometry"), Layouting::rectToMap(geometry));
 
  822    map.
insert(QStringLiteral(
"normalGeometry"), Layouting::rectToMap(normalGeometry));
 
  823    map.
insert(QStringLiteral(
"screenIndex"), screenIndex);
 
  824    map.
insert(QStringLiteral(
"screenSize"), Layouting::sizeToMap(screenSize));
 
  825    map.
insert(QStringLiteral(
"isVisible"), isVisible);
 
  826    map.
insert(QStringLiteral(
"windowState"), windowState);
 
  827    map.
insert(QStringLiteral(
"flags"), flags);
 
  835void LayoutSaver::FloatingWindow::fromVariantMap(
const QVariantMap &map)
 
  837    multiSplitterLayout.fromVariantMap(map.value(QStringLiteral(
"multiSplitterLayout")).toMap());
 
  838    parentIndex = map.value(QStringLiteral(
"parentIndex")).
toInt();
 
  839    geometry = Layouting::mapToRect(map.value(QStringLiteral(
"geometry")).toMap());
 
  840    normalGeometry = Layouting::mapToRect(map.value(QStringLiteral(
"normalGeometry")).toMap());
 
  841    screenIndex = map.value(QStringLiteral(
"screenIndex")).toInt();
 
  843    screenSize = Layouting::mapToSize(map.value(QStringLiteral(
"screenSize")).toMap());
 
  844    isVisible = map.value(QStringLiteral(
"isVisible")).toBool();
 
  849    const QString affinityName = map.value(QStringLiteral(
"affinityName")).toString();
 
  855bool LayoutSaver::MainWindow::isValid()
 const 
  857    if (!multiSplitterLayout.isValid())
 
  863void LayoutSaver::MainWindow::scaleSizes()
 
  865    if (scalingInfo.isValid()) {
 
  871    scalingInfo = ScalingInfo(uniqueName, geometry, screenIndex);
 
  874QVariantMap LayoutSaver::MainWindow::toVariantMap()
 const 
  877    map.insert(QStringLiteral(
"options"), 
int(options));
 
  878    map.insert(QStringLiteral(
"multiSplitterLayout"), multiSplitterLayout.toVariantMap());
 
  879    map.insert(QStringLiteral(
"uniqueName"), uniqueName);
 
  880    map.insert(QStringLiteral(
"geometry"), Layouting::rectToMap(geometry));
 
  881    map.insert(QStringLiteral(
"normalGeometry"), Layouting::rectToMap(normalGeometry));
 
  882    map.insert(QStringLiteral(
"screenIndex"), screenIndex);
 
  883    map.insert(QStringLiteral(
"screenSize"), Layouting::sizeToMap(screenSize));
 
  884    map.insert(QStringLiteral(
"isVisible"), isVisible);
 
  886    map.insert(QStringLiteral(
"windowState"), windowState);
 
  897void LayoutSaver::MainWindow::fromVariantMap(
const QVariantMap &map)
 
  899    options = KDDockWidgets::MainWindowOptions(map.value(QStringLiteral(
"options")).toInt());
 
  900    multiSplitterLayout.fromVariantMap(map.value(QStringLiteral(
"multiSplitterLayout")).toMap());
 
  901    uniqueName = map.value(QStringLiteral(
"uniqueName")).toString();
 
  902    geometry = Layouting::mapToRect(map.value(QStringLiteral(
"geometry")).toMap());
 
  903    normalGeometry = Layouting::mapToRect(map.value(QStringLiteral(
"normalGeometry")).toMap());
 
  904    screenIndex = map.value(QStringLiteral(
"screenIndex")).toInt();
 
  905    screenSize = Layouting::mapToSize(map.value(QStringLiteral(
"screenSize")).toMap());
 
  906    isVisible = map.value(QStringLiteral(
"isVisible")).toBool();
 
  911    const QString affinityName = map.value(QStringLiteral(
"affinityName")).toString();
 
  917    dockWidgetsPerSideBar.clear();
 
  919        const QVariantList dockWidgets = map.
value(QStringLiteral(
"sidebar-%1").arg(
int(loc))).toList();
 
  920        if (!dockWidgets.isEmpty())
 
  925bool LayoutSaver::MultiSplitter::isValid()
 const 
  927    if (layout.isEmpty())
 
  938bool LayoutSaver::MultiSplitter::hasSingleDockWidget()
 const 
  940    return frames.size() == 1 && frames.cbegin()->hasSingleDockWidget();
 
  943LayoutSaver::DockWidget::Ptr LayoutSaver::MultiSplitter::singleDockWidget()
 const 
  945    if (!hasSingleDockWidget())
 
  948    return frames.cbegin()->singleDockWidget();
 
  951bool LayoutSaver::MultiSplitter::skipsRestore()
 const 
  953    return std::all_of(frames.cbegin(), frames.cend(), [](
const LayoutSaver::Frame &frame) {
 
  954        return frame.skipsRestore();
 
  958QVariantMap LayoutSaver::MultiSplitter::toVariantMap()
 const 
  961    result.insert(QStringLiteral(
"layout"), layout);
 
  964    for (
auto &frame : frames)
 
  965        framesV.insert(frame.id, frame.toVariantMap());
 
  967    result.insert(QStringLiteral(
"frames"), framesV);
 
  971void LayoutSaver::MultiSplitter::fromVariantMap(
const QVariantMap &map)
 
  973    layout = map.value(QStringLiteral(
"layout")).toMap();
 
  974    const QVariantMap framesV = map.value(QStringLiteral(
"frames")).toMap();
 
  976    for (
const QVariant &frameV : framesV) {
 
  977        LayoutSaver::Frame frame;
 
  978        frame.fromVariantMap(frameV.toMap());
 
  979        frames.insert(frame.id, frame);
 
  983void LayoutSaver::Position::scaleSizes(
const ScalingInfo &scalingInfo)
 
  985    scalingInfo.applyFactorsTo( lastFloatingGeometry);
 
  991    result.reserve(geometries.
size());
 
  992    for (
auto it = geometries.
cbegin(), end = geometries.
cend(); it != end; ++it) {
 
  994        map.insert(QStringLiteral(
"location"), 
static_cast<int>(it.key()));
 
  995        map.insert(QStringLiteral(
"rect"), Layouting::rectToMap(it.value()));
 
  996        result.push_back(map);
 
 
 1001QVariantMap LayoutSaver::Position::toVariantMap()
 const 
 1004    map.insert(QStringLiteral(
"lastFloatingGeometry"), Layouting::rectToMap(lastFloatingGeometry));
 
 1006    map.insert(QStringLiteral(
"tabIndex"), tabIndex);
 
 1007    map.insert(QStringLiteral(
"wasFloating"), wasFloating);
 
 1008    map.insert(QStringLiteral(
"placeholders"), toVariantList<LayoutSaver::Placeholder>(placeholders));
 
 1017        const auto map = v.toMap();
 
 1019        const auto rect = Layouting::mapToRect(map.value(QStringLiteral(
"rect")).toMap());
 
 1020        result.
insert(location, rect);
 
 
 1025void LayoutSaver::Position::fromVariantMap(
const QVariantMap &map)
 
 1027    lastFloatingGeometry = Layouting::mapToRect(map.value(QStringLiteral(
"lastFloatingGeometry")).toMap());
 
 1029    tabIndex = map.value(QStringLiteral(
"tabIndex")).toInt();
 
 1030    wasFloating = map.value(QStringLiteral(
"wasFloating")).toBool();
 
 1031    placeholders = fromVariantList<LayoutSaver::Placeholder>(map.value(QStringLiteral(
"placeholders")).toList());
 
 1034QVariantMap LayoutSaver::ScreenInfo::toVariantMap()
 const 
 1037    map.insert(QStringLiteral(
"index"), index);
 
 1038    map.insert(QStringLiteral(
"geometry"), Layouting::rectToMap(geometry));
 
 1039    map.insert(QStringLiteral(
"name"), name);
 
 1040    map.insert(QStringLiteral(
"devicePixelRatio"), devicePixelRatio);
 
 1045void LayoutSaver::ScreenInfo::fromVariantMap(
const QVariantMap &map)
 
 1047    index = map.value(QStringLiteral(
"index")).toInt();
 
 1048    geometry = Layouting::mapToRect(map.value(QStringLiteral(
"geometry")).toMap());
 
 1049    name = map.value(QStringLiteral(
"name")).toString();
 
 1050    devicePixelRatio = map.value(QStringLiteral(
"devicePixelRatio")).
toDouble();
 
 1053QVariantMap LayoutSaver::Placeholder::toVariantMap()
 const 
 1056    map.insert(QStringLiteral(
"isFloatingWindow"), isFloatingWindow);
 
 1057    map.insert(QStringLiteral(
"itemIndex"), itemIndex);
 
 1059    if (isFloatingWindow)
 
 1060        map.insert(QStringLiteral(
"indexOfFloatingWindow"), indexOfFloatingWindow);
 
 1062        map.insert(QStringLiteral(
"mainWindowUniqueName"), mainWindowUniqueName);
 
 1067void LayoutSaver::Placeholder::fromVariantMap(
const QVariantMap &map)
 
 1069    isFloatingWindow = map.value(QStringLiteral(
"isFloatingWindow")).toBool();
 
 1070    indexOfFloatingWindow = map.value(QStringLiteral(
"indexOfFloatingWindow"), -1).toInt();
 
 1071    itemIndex = map.value(QStringLiteral(
"itemIndex")).toInt();
 
 1072    mainWindowUniqueName = map.value(QStringLiteral(
"mainWindowUniqueName")).toString();
 
 1079#ifdef KDDOCKWIDGETS_QTQUICK 
 1083#if QT_VERSION < QT_VERSION_CHECK(5, 14, 0) 
 1085        return window->screen();
 
 
 1092LayoutSaver::ScalingInfo::ScalingInfo(
const QString &mainWindowId, 
QRect savedMainWindowGeo, 
int screenIndex)
 
 1094    auto mainWindow = DockRegistry::self()->mainWindowByName(mainWindowId);
 
 1096        qWarning() << Q_FUNC_INFO << 
"Failed to find main window with name" << mainWindowName;
 
 1100    if (!savedMainWindowGeo.
isValid() || savedMainWindowGeo.
isNull()) {
 
 1101        qWarning() << Q_FUNC_INFO << 
"Invalid saved main window geometry" << savedMainWindowGeo;
 
 1105    if (!mainWindow->geometry().isValid() || mainWindow->geometry().isNull()) {
 
 1106        qWarning() << Q_FUNC_INFO << 
"Invalid main window geometry" << mainWindow->geometry();
 
 1112    this->mainWindowName = mainWindowId;
 
 1113    this->savedMainWindowGeometry = savedMainWindowGeo;
 
 1114    realMainWindowGeometry = mainWindow->windowGeometry();
 
 1115    widthFactor = double(realMainWindowGeometry.width()) / savedMainWindowGeo.
width();
 
 1116    heightFactor = double(realMainWindowGeometry.height()) / savedMainWindowGeo.
height();
 
 1117    mainWindowChangedScreen = currentScreenIndex != screenIndex;
 
 1120void LayoutSaver::ScalingInfo::translatePos(
QPoint &pt)
 const 
 1122    const int deltaX = pt.
x() - savedMainWindowGeometry.x();
 
 1123    const int deltaY = pt.
y() - savedMainWindowGeometry.y();
 
 1125    const double newDeltaX = deltaX * widthFactor;
 
 1126    const double newDeltaY = deltaY * heightFactor;
 
 1128    pt.
setX(qCeil(savedMainWindowGeometry.x() + newDeltaX));
 
 1129    pt.
setY(qCeil(savedMainWindowGeometry.y() + newDeltaY));
 
 1132void LayoutSaver::ScalingInfo::applyFactorsTo(
QPoint &pt)
 const 
 1137void LayoutSaver::ScalingInfo::applyFactorsTo(
QSize &sz)
 const 
 1143void LayoutSaver::ScalingInfo::applyFactorsTo(
QRect &rect)
 const 
 1151    applyFactorsTo( size);
 
 1154    if (!mainWindowChangedScreen) {
 
 1159        applyFactorsTo( pos);
 
 1166LayoutSaver::Private::RAIIIsRestoring::RAIIIsRestoring()
 
 1168    LayoutSaver::Private::s_restoreInProgress = 
true;
 
 1171LayoutSaver::Private::RAIIIsRestoring::~RAIIIsRestoring()
 
 1173    LayoutSaver::Private::s_restoreInProgress = 
false;
 
Application-wide config to tune certain behaviours of the framework.
static QStringList variantToStringList(const QVariantList &variantList)
InternalRestoreOptions internalRestoreOptions(RestoreOptions options)
static QHash< KDDockWidgets::SideBarLocation, QRect > listToOverlayedGeometries(const QVariantList &list)
static QScreen * screenForMainWindow(MainWindowBase *mw)
static QVariantList stringListToVariant(const QStringList &strs)
static QVariantList overlayedGeometriesToList(const QHash< KDDockWidgets::SideBarLocation, QRect > &geometries)
Class to save and restore dockwidget layouts.
The MainWindow base-class that's shared between QtWidgets and QtQuick stack.
The MainWindow base-class. MainWindow and MainWindowBase are only split in two so we can share some c...
bool isEmpty() const const
virtual bool open(QIODevice::OpenMode mode) override
QHash::const_iterator cbegin() const const
QHash::const_iterator cend() const const
QHash::iterator insert(const Key &key, const T &value)
QString errorString() const const
qint64 write(const char *data, qint64 maxSize)
QJsonDocument fromJson(const QByteArray &json, QJsonParseError *error)
QJsonDocument fromVariant(const QVariant &variant)
QByteArray toJson() const const
QVariant toVariant() const const
bool isEmpty() const const
void push_back(const T &value)
T value(int i) const const
bool isEmpty() const const
bool isNull() const const
bool isValid() const const
void moveTopLeft(const QPoint &position)
void setSize(const QSize &size)
QPoint topLeft() const const
void setHeight(int height)
QString & insert(int position, QChar ch)
bool isEmpty() const const
double toDouble(bool *ok) const const
int toInt(bool *ok, int base) const const
bool contains(const QString &str, Qt::CaseSensitivity cs) const const
QMap< QString, QVariant > toMap() const const
QVector::const_iterator cbegin() const const
QVector::const_iterator cend() const const
void push_back(const T &value)