diff options
Diffstat (limited to 'src/widgets/widgets/qdockarealayout.cpp')
-rw-r--r-- | src/widgets/widgets/qdockarealayout.cpp | 183 |
1 files changed, 134 insertions, 49 deletions
diff --git a/src/widgets/widgets/qdockarealayout.cpp b/src/widgets/widgets/qdockarealayout.cpp index cec1d1bc14..da0e987171 100644 --- a/src/widgets/widgets/qdockarealayout.cpp +++ b/src/widgets/widgets/qdockarealayout.cpp @@ -91,7 +91,7 @@ bool QDockAreaLayoutItem::skip() const return widgetItem->isEmpty(); if (subinfo != nullptr) { - for (int i = 0; i < subinfo->item_list.count(); ++i) { + for (int i = 0; i < subinfo->item_list.size(); ++i) { if (!subinfo->item_list.at(i).skip()) return false; } @@ -171,6 +171,38 @@ QDockAreaLayoutItem return *this; } +#ifndef QT_NO_DEBUG_STREAM +QDebug operator<<(QDebug dbg, const QDockAreaLayoutItem *item) +{ + QDebugStateSaver saver(dbg); + dbg.nospace(); + return item ? dbg << *item : dbg << "QDockAreaLayoutItem(0x0)"; +} + +QDebug operator<<(QDebug dbg, const QDockAreaLayoutItem &item) +{ + QDebugStateSaver saver(dbg); + dbg.nospace(); + dbg << "QDockAreaLayoutItem(" << static_cast<const void *>(&item) << "->"; + if (item.widgetItem) { + QWidget *widget = item.widgetItem->widget(); + if (auto *dockWidget = qobject_cast<QDockWidget *>(widget)) { + dbg << "widgetItem(" << dockWidget << ")"; + } else if (auto *groupWindow = qobject_cast<QDockWidgetGroupWindow *>(widget)) { + dbg << "widgetItem(" << groupWindow << "->(" << groupWindow->dockWidgets() << "))"; + } else { + dbg << "widgetItem(" << widget << ")"; + } + } else if (item.subinfo) { + dbg << "subInfo(" << item.subinfo << "->(" << item.subinfo->item_list << ")"; + } else if (item.placeHolderItem) { + dbg << "placeHolderItem(" << item.placeHolderItem << ")"; + } + dbg << ")"; + return dbg; +} +#endif // QT_NO_DEBUG_STREAM + /****************************************************************************** ** QDockAreaLayoutInfo */ @@ -852,7 +884,7 @@ static int separatorMoveHelper(QList<QLayoutStruct> &list, int index, int delta, delta = growlimit; int d = 0; - for (int i = index + 1; d < delta && i < list.count(); ++i) + for (int i = index + 1; d < delta && i < list.size(); ++i) d += shrink(list[i], delta - d); delta = d; d = 0; @@ -860,7 +892,7 @@ static int separatorMoveHelper(QList<QLayoutStruct> &list, int index, int delta, d += grow(list[i], delta - d); } else if (delta < 0) { int growlimit = 0; - for (int i = index + 1; i < list.count(); ++i) { + for (int i = index + 1; i < list.size(); ++i) { const QLayoutStruct &ls = list.at(i); if (ls.empty) continue; @@ -878,7 +910,7 @@ static int separatorMoveHelper(QList<QLayoutStruct> &list, int index, int delta, d += shrink(list[i], -delta - d); delta = -d; d = 0; - for (int i = index + 1; d < -delta && i < list.count(); ++i) + for (int i = index + 1; d < -delta && i < list.size(); ++i) d += grow(list[i], -delta - d); } @@ -949,12 +981,12 @@ void QDockAreaLayoutInfo::unnest(int index) QDockAreaLayoutItem &item = item_list[index]; if (item.subinfo == nullptr) return; - if (item.subinfo->item_list.count() > 1) + if (item.subinfo->item_list.size() > 1) return; - if (item.subinfo->item_list.count() == 0) { + if (item.subinfo->item_list.size() == 0) { item_list.removeAt(index); - } else if (item.subinfo->item_list.count() == 1) { + } else if (item.subinfo->item_list.size() == 1) { QDockAreaLayoutItem &child = item.subinfo->item_list.first(); if (child.widgetItem != nullptr) { item.widgetItem = child.widgetItem; @@ -974,7 +1006,7 @@ void QDockAreaLayoutInfo::remove(const QList<int> &path) { Q_ASSERT(!path.isEmpty()); - if (path.count() > 1) { + if (path.size() > 1) { const int index = path.first(); QDockAreaLayoutItem &item = item_list[index]; Q_ASSERT(item.subinfo != nullptr); @@ -986,6 +1018,14 @@ void QDockAreaLayoutInfo::remove(const QList<int> &path) } } +void QDockAreaLayoutInfo::remove(QWidget *widget) +{ + const QList<int> path = indexOf(widget); + if (path.isEmpty()) + return; + remove(path); +} + QLayoutItem *QDockAreaLayoutInfo::plug(const QList<int> &path) { Q_ASSERT(!path.isEmpty()); @@ -994,7 +1034,7 @@ QLayoutItem *QDockAreaLayoutInfo::plug(const QList<int> &path) if (index < 0) index = -index - 1; - if (path.count() > 1) { + if (path.size() > 1) { QDockAreaLayoutItem &item = item_list[index]; Q_ASSERT(item.subinfo != nullptr); return item.subinfo->plug(path.mid(1)); @@ -1013,7 +1053,7 @@ QLayoutItem *QDockAreaLayoutInfo::unplug(const QList<int> &path) Q_ASSERT(!path.isEmpty()); const int index = path.first(); - if (path.count() > 1) { + if (path.size() > 1) { QDockAreaLayoutItem &item = item_list[index]; Q_ASSERT(item.subinfo != nullptr); return item.subinfo->unplug(path.mid(1)); @@ -1090,6 +1130,21 @@ static QRect dockedGeometry(QWidget *widget) return result; } +bool QDockAreaLayoutInfo::hasGapItem(const QList<int> &path) const +{ + // empty path has no gap item + if (path.isEmpty()) + return false; + + // Index -1 isn't a gap + // Index out of range points at a position to be created. That isn't a gap either. + const int index = path.constFirst(); + if (index < 0 || index >= item_list.count()) + return false; + + return item_list[index].flags & QDockAreaLayoutItem::GapItem; +} + bool QDockAreaLayoutInfo::insertGap(const QList<int> &path, QLayoutItem *dockWidgetItem) { Q_ASSERT(!path.isEmpty()); @@ -1101,9 +1156,7 @@ bool QDockAreaLayoutInfo::insertGap(const QList<int> &path, QLayoutItem *dockWid index = -index - 1; } -// dump(qDebug() << "insertGap() before:" << index << tabIndex, *this, QString()); - - if (path.count() > 1) { + if (path.size() > 1) { QDockAreaLayoutItem &item = item_list[index]; if (item.subinfo == nullptr @@ -1185,7 +1238,7 @@ bool QDockAreaLayoutInfo::insertGap(const QList<int> &path, QLayoutItem *dockWid break; } } else { - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { const QDockAreaLayoutItem &item = item_list.at(i); if (item.skip()) continue; @@ -1224,7 +1277,7 @@ bool QDockAreaLayoutInfo::insertGap(const QList<int> &path, QLayoutItem *dockWid QDockAreaLayoutInfo *QDockAreaLayoutInfo::info(QWidget *widget) { - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { const QDockAreaLayoutItem &item = item_list.at(i); if (item.skip()) continue; @@ -1251,9 +1304,9 @@ QDockAreaLayoutInfo *QDockAreaLayoutInfo::info(const QList<int> &path) int index = path.first(); if (index < 0) index = -index - 1; - if (index >= item_list.count()) + if (index >= item_list.size()) return this; - if (path.count() == 1 || item_list[index].subinfo == nullptr) + if (path.size() == 1 || item_list[index].subinfo == nullptr) return this; return item_list[index].subinfo->info(path.mid(1)); } @@ -1308,7 +1361,7 @@ QRect QDockAreaLayoutInfo::itemRect(const QList<int> &path) const Q_ASSERT(!path.isEmpty()); const int index = path.first(); - if (path.count() > 1) { + if (path.size() > 1) { const QDockAreaLayoutItem &item = item_list.at(index); Q_ASSERT(item.subinfo != nullptr); return item.subinfo->itemRect(path.mid(1)); @@ -1341,7 +1394,7 @@ QRect QDockAreaLayoutInfo::separatorRect(const QList<int> &path) const Q_ASSERT(!path.isEmpty()); const int index = path.first(); - if (path.count() > 1) { + if (path.size() > 1) { const QDockAreaLayoutItem &item = item_list.at(index); Q_ASSERT(item.subinfo != nullptr); return item.subinfo->separatorRect(path.mid(1)); @@ -1566,7 +1619,7 @@ QRegion QDockAreaLayoutInfo::separatorRegion() const return result; #endif - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { const QDockAreaLayoutItem &item = item_list.at(i); if (item.skip()) @@ -1596,7 +1649,7 @@ void QDockAreaLayoutInfo::paintSeparators(QPainter *p, QWidget *widget, return; #endif - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { const QDockAreaLayoutItem &item = item_list.at(i); if (item.skip()) @@ -1681,7 +1734,7 @@ QDockAreaLayoutItem &QDockAreaLayoutInfo::item(const QList<int> &path) { Q_ASSERT(!path.isEmpty()); const int index = path.first(); - if (path.count() > 1) { + if (path.size() > 1) { const QDockAreaLayoutItem &item = item_list[index]; Q_ASSERT(item.subinfo != nullptr); return item.subinfo->item(path.mid(1)); @@ -1691,7 +1744,7 @@ QDockAreaLayoutItem &QDockAreaLayoutInfo::item(const QList<int> &path) QLayoutItem *QDockAreaLayoutInfo::itemAt(int *x, int index) const { - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { const QDockAreaLayoutItem &item = item_list.at(i); if (item.placeHolderItem != nullptr) continue; @@ -1708,7 +1761,7 @@ QLayoutItem *QDockAreaLayoutInfo::itemAt(int *x, int index) const QLayoutItem *QDockAreaLayoutInfo::takeAt(int *x, int index) { - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { QDockAreaLayoutItem &item = item_list[i]; if (item.placeHolderItem != nullptr) continue; @@ -1731,9 +1784,29 @@ QLayoutItem *QDockAreaLayoutInfo::takeAt(int *x, int index) return nullptr; } +// Add a dock widget or dock widget group window to the item list +void QDockAreaLayoutInfo::add(QWidget *widget) +{ + // Do not add twice + if (!indexOf(widget).isEmpty()) + return; + + if (auto *dockWidget = qobject_cast<QDockWidget *>(widget)) { + item_list.append(QDockAreaLayoutItem(new QDockWidgetItem(dockWidget))); + return; + } + + if (auto *groupWindow = qobject_cast<QDockWidgetGroupWindow *>(widget)) { + item_list.append(QDockAreaLayoutItem(new QDockWidgetGroupWindowItem(groupWindow))); + return; + } + + qFatal("Coding error. Add supports only QDockWidget and QDockWidgetGroupWindow"); +} + void QDockAreaLayoutInfo::deleteAllLayoutItems() { - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { QDockAreaLayoutItem &item= item_list[i]; if (item.subinfo) { item.subinfo->deleteAllLayoutItems(); @@ -1753,7 +1826,7 @@ void QDockAreaLayoutInfo::saveState(QDataStream &stream) const // write the index in item_list of the widget that's currently on top. quintptr id = currentTabId(); int index = -1; - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { if (tabId(item_list.at(i)) == id) { index = i; break; @@ -1766,9 +1839,9 @@ void QDockAreaLayoutInfo::saveState(QDataStream &stream) const stream << (uchar) SequenceMarker; } - stream << (uchar) o << int(item_list.count()); + stream << (uchar) o << int(item_list.size()); - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { const QDockAreaLayoutItem &item = item_list.at(i); if (item.widgetItem != nullptr) { stream << (uchar) WidgetMarker; @@ -1864,7 +1937,7 @@ bool QDockAreaLayoutInfo::restoreState(QDataStream &stream, QList<QDockWidget*> } QDockWidget *widget = nullptr; - for (int j = 0; j < widgets.count(); ++j) { + for (int j = 0; j < widgets.size(); ++j) { if (widgets.at(j)->objectName() == name) { widget = widgets.takeAt(j); break; @@ -1924,6 +1997,7 @@ bool QDockAreaLayoutInfo::restoreState(QDataStream &stream, QList<QDockWidget*> if (testing) { //was it is not really added to the layout, we need to delete the object here delete item.widgetItem; + item.widgetItem = nullptr; } } } else if (nextMarker == SequenceMarker) { @@ -1950,7 +2024,7 @@ bool QDockAreaLayoutInfo::restoreState(QDataStream &stream, QList<QDockWidget*> } #if QT_CONFIG(tabbar) - if (!testing && tabbed && index >= 0 && index < item_list.count()) { + if (!testing && tabbed && index >= 0 && index < item_list.size()) { updateTabBar(); setCurrentTabId(tabId(item_list.at(index))); } @@ -1970,7 +2044,7 @@ void QDockAreaLayoutInfo::updateSeparatorWidgets() const } int j = 0; - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { const QDockAreaLayoutItem &item = item_list.at(i); if (item.skip()) @@ -1989,14 +2063,20 @@ void QDockAreaLayoutInfo::updateSeparatorWidgets() const break; QWidget *sepWidget; - if (j < separatorWidgets.size() && separatorWidgets.at(j)) { + if (j < separatorWidgets.size()) { sepWidget = separatorWidgets.at(j); + if (!sepWidget) { + qWarning("QDockAreaLayoutInfo::updateSeparatorWidgets: null separator widget"); + sepWidget = mainWindowLayout()->getSeparatorWidget(); + separatorWidgets[j] = sepWidget; + } } else { sepWidget = mainWindowLayout()->getSeparatorWidget(); separatorWidgets.append(sepWidget); } j++; + Q_ASSERT(sepWidget); sepWidget->raise(); QRect sepRect = separatorRect(i).adjusted(-2, -2, 2, 2); @@ -2009,7 +2089,6 @@ void QDockAreaLayoutInfo::updateSeparatorWidgets() const separatorWidgets[k]->hide(); } separatorWidgets.resize(j); - Q_ASSERT(separatorWidgets.size() == j); } /*! \internal @@ -2022,7 +2101,7 @@ void QDockAreaLayoutInfo::reparentWidgets(QWidget *parent) if (tabBar) tabBar->setParent(parent); - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { const QDockAreaLayoutItem &item = item_list.at(i); if (item.flags & QDockAreaLayoutItem::GapItem) continue; @@ -2062,7 +2141,7 @@ bool QDockAreaLayoutInfo::updateTabBar() const const quintptr oldCurrentId = currentTabId(); int tab_idx = 0; - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { const QDockAreaLayoutItem &item = item_list.at(i); if (item.skip()) continue; @@ -2127,7 +2206,7 @@ void QDockAreaLayoutInfo::setTabBarShape(int shape) if (tabBar != nullptr) tabBar->setShape(static_cast<QTabBar::Shape>(shape)); - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { QDockAreaLayoutItem &item = item_list[i]; if (item.subinfo != nullptr) item.subinfo->setTabBarShape(shape); @@ -2159,7 +2238,7 @@ QSet<QTabBar*> QDockAreaLayoutInfo::usedTabBars() const result.insert(tabBar); } - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { const QDockAreaLayoutItem &item = item_list.at(i); if (item.subinfo != nullptr) result += item.subinfo->usedTabBars(); @@ -2173,13 +2252,13 @@ QSet<QTabBar*> QDockAreaLayoutInfo::usedTabBars() const QSet<QWidget*> QDockAreaLayoutInfo::usedSeparatorWidgets() const { QSet<QWidget*> result; - const int numSeparatorWidgets = separatorWidgets.count(); + const int numSeparatorWidgets = separatorWidgets.size(); result.reserve(numSeparatorWidgets); for (int i = 0; i < numSeparatorWidgets; ++i) result << separatorWidgets.at(i); - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { const QDockAreaLayoutItem &item = item_list.at(i); if (item.subinfo != nullptr) result += item.subinfo->usedSeparatorWidgets(); @@ -2226,7 +2305,7 @@ int QDockAreaLayoutInfo::tabIndexToListIndex(int tabIndex) const { Q_ASSERT(tabbed && tabBar); quintptr data = qvariant_cast<quintptr>(tabBar->tabData(tabIndex)); - for (int i = 0; i < item_list.count(); ++i) { + for (int i = 0; i < item_list.size(); ++i) { if (tabId(item_list.at(i)) == data) return i; } @@ -2490,7 +2569,7 @@ QDockAreaLayoutInfo *QDockAreaLayout::info(const QList<int> &path) const int index = path.first(); Q_ASSERT(index >= 0 && index < QInternal::DockCount); - if (path.count() == 1) + if (path.size() == 1) return &docks[index]; return docks[index].info(path.mid(1)); @@ -2545,7 +2624,7 @@ QRect QDockAreaLayout::separatorRect(const QList<int> &path) const const int index = path.first(); Q_ASSERT(index >= 0 && index < QInternal::DockCount); - if (path.count() == 1) + if (path.size() == 1) return separatorRect(index); else return docks[index].separatorRect(path.mid(1)); @@ -3043,7 +3122,7 @@ void QDockAreaLayout::addDockWidget(QInternal::DockPosition pos, QDockWidget *do { QLayoutItem *dockWidgetItem = new QDockWidgetItem(dockWidget); QDockAreaLayoutInfo &info = docks[pos]; - if (orientation == info.o || info.item_list.count() <= 1) { + if (orientation == info.o || info.item_list.size() <= 1) { // empty dock areas, or dock areas containing exactly one widget can have their orientation // switched. info.o = orientation; @@ -3089,11 +3168,11 @@ void QDockAreaLayout::tabifyDockWidget(QDockWidget *first, QDockWidget *second) void QDockAreaLayout::resizeDocks(const QList<QDockWidget *> &docks, const QList<int> &sizes, Qt::Orientation o) { - if (Q_UNLIKELY(docks.count() != sizes.count())) { + if (Q_UNLIKELY(docks.size() != sizes.size())) { qWarning("QMainWidget::resizeDocks: size of the lists are not the same"); return; } - int count = docks.count(); + int count = docks.size(); fallbackToSizeHints = false; for (int i = 0; i < count; ++i) { QList<int> path = indexOf(docks[i]); @@ -3113,7 +3192,7 @@ void QDockAreaLayout::resizeDocks(const QList<QDockWidget *> &docks, if (!info->tabbed && info->o == o) { info->item_list[path.constLast()].size = size; int totalSize = 0; - for (const QDockAreaLayoutItem &item : qAsConst(info->item_list)) { + for (const QDockAreaLayoutItem &item : std::as_const(info->item_list)) { if (!item.skip()) { if (totalSize != 0) totalSize += sep; @@ -3206,7 +3285,7 @@ int QDockAreaLayout::separatorMove(const QList<int> &separator, const QPoint &or int delta = 0; int index = separator.last(); - if (separator.count() > 1) { + if (separator.size() > 1) { QDockAreaLayoutInfo *info = this->info(separator); delta = pick(info->o, dest - origin); if (delta != 0) @@ -3271,12 +3350,18 @@ void QDockAreaLayout::updateSeparatorWidgets() const QWidget *sepWidget; if (j < separatorWidgets.size()) { sepWidget = separatorWidgets.at(j); + if (!sepWidget) { + qWarning("QDockAreaLayout::updateSeparatorWidgets: null separator widget"); + sepWidget = qt_mainwindow_layout(mainWindow)->getSeparatorWidget(); + separatorWidgets[j] = sepWidget; + } } else { sepWidget = qt_mainwindow_layout(mainWindow)->getSeparatorWidget(); separatorWidgets.append(sepWidget); } j++; + Q_ASSERT(sepWidget); sepWidget->raise(); QRect sepRect = separatorRect(i).adjusted(-2, -2, 2, 2); @@ -3347,7 +3432,7 @@ QSet<QTabBar*> QDockAreaLayout::usedTabBars() const QSet<QWidget*> QDockAreaLayout::usedSeparatorWidgets() const { QSet<QWidget*> result; - const int numSeparators = separatorWidgets.count(); + const int numSeparators = separatorWidgets.size(); result.reserve(numSeparators); for (int i = 0; i < numSeparators; ++i) result << separatorWidgets.at(i); @@ -3365,7 +3450,7 @@ QRect QDockAreaLayout::gapRect(const QList<int> &path) const if (info == nullptr) return QRect(); int index = path.last(); - if (index < 0 || index >= info->item_list.count()) + if (index < 0 || index >= info->item_list.size()) return QRect(); return info->itemRect(index, true); } |