From be727c58905b81eb4792a4688927a0b1d6563065 Mon Sep 17 00:00:00 2001 From: Uwe Kindler Date: Wed, 12 Jul 2023 10:42:24 +0200 Subject: [PATCH] Added initial support for inserting dropped dock widgets at a certain sidebar position --- src/AutoHideDockContainer.cpp | 5 +-- src/AutoHideDockContainer.h | 2 +- src/AutoHideSideBar.cpp | 64 +++++++++++++++++++++++++++-------- src/AutoHideSideBar.h | 19 +++++++++-- src/DockAreaWidget.cpp | 6 ++-- src/DockAreaWidget.h | 2 +- src/DockContainerWidget.cpp | 21 ++++++------ src/DockContainerWidget.h | 4 +-- src/DockOverlay.cpp | 23 +++++++++---- src/DockWidget.cpp | 4 +-- src/DockWidget.h | 2 +- src/FloatingDragPreview.cpp | 3 +- 12 files changed, 107 insertions(+), 48 deletions(-) diff --git a/src/AutoHideDockContainer.cpp b/src/AutoHideDockContainer.cpp index 0ab151a..c17b195 100644 --- a/src/AutoHideDockContainer.cpp +++ b/src/AutoHideDockContainer.cpp @@ -689,7 +689,8 @@ void CAutoHideDockContainer::resetToInitialDockWidgetSize() //============================================================================ -void CAutoHideDockContainer::moveToNewSideBarLocation(SideBarLocation NewSideBarLocation) +void CAutoHideDockContainer::moveToNewSideBarLocation(SideBarLocation NewSideBarLocation, + int TabIndex) { if (NewSideBarLocation == sideBarLocation()) { @@ -698,7 +699,7 @@ void CAutoHideDockContainer::moveToNewSideBarLocation(SideBarLocation NewSideBar auto OldOrientation = orientation(); auto SideBar = dockContainer()->autoHideSideBar(NewSideBarLocation); - SideBar->addAutoHideWidget(this); + SideBar->addAutoHideWidget(this, TabIndex); // If we move a horizontal auto hide container to a vertical position // then we resize it to the orginal dock widget size, to avoid // an extremely streched dock widget after insertion diff --git a/src/AutoHideDockContainer.h b/src/AutoHideDockContainer.h index 3183682..0eafc42 100644 --- a/src/AutoHideDockContainer.h +++ b/src/AutoHideDockContainer.h @@ -195,7 +195,7 @@ public: * Removes the AutoHide container from the current side bar and adds * it to the new side bar given in SideBarLocation */ - void moveToNewSideBarLocation(SideBarLocation SideBarLocation); + void moveToNewSideBarLocation(SideBarLocation SideBarLocation, int TabIndex = -1); }; } // namespace ads diff --git a/src/AutoHideSideBar.cpp b/src/AutoHideSideBar.cpp index f0aa03d..ae79f54 100644 --- a/src/AutoHideSideBar.cpp +++ b/src/AutoHideSideBar.cpp @@ -233,7 +233,8 @@ void CAutoHideSideBar::removeAutoHideWidget(CAutoHideDockContainer* AutoHideWidg } //============================================================================ -void CAutoHideSideBar::addAutoHideWidget(CAutoHideDockContainer* AutoHideWidget) +void CAutoHideSideBar::addAutoHideWidget(CAutoHideDockContainer* AutoHideWidget, + int Index) { auto SideBar = AutoHideWidget->autoHideTab()->sideBar(); if (SideBar == this) @@ -248,7 +249,7 @@ void CAutoHideSideBar::addAutoHideWidget(CAutoHideDockContainer* AutoHideWidget) AutoHideWidget->setParent(d->ContainerWidget); AutoHideWidget->setSideBarLocation(d->SideTabArea); d->ContainerWidget->registerAutoHideWidget(AutoHideWidget); - insertTab(-1, AutoHideWidget->autoHideTab()); + insertTab(Index, AutoHideWidget->autoHideTab()); } @@ -302,14 +303,14 @@ Qt::Orientation CAutoHideSideBar::orientation() const //============================================================================ -CAutoHideTab* CAutoHideSideBar::tabAt(int index) const +CAutoHideTab* CAutoHideSideBar::tab(int index) const { return qobject_cast(d->TabsLayout->itemAt(index)->widget()); } //============================================================================ -int CAutoHideSideBar::tabCount() const +int CAutoHideSideBar::count() const { return d->TabsLayout->count() - 1; } @@ -318,17 +319,17 @@ int CAutoHideSideBar::tabCount() const //============================================================================ int CAutoHideSideBar::visibleTabCount() const { - int count = 0; + int VisibleTabCount = 0; auto ParentWidget = parentWidget(); - for (auto i = 0; i < tabCount(); i++) + for (auto i = 0; i < count(); i++) { - if (tabAt(i)->isVisibleTo(ParentWidget)) + if (tab(i)->isVisibleTo(ParentWidget)) { - count++; + VisibleTabCount++; } } - return count; + return VisibleTabCount; } @@ -336,9 +337,9 @@ int CAutoHideSideBar::visibleTabCount() const bool CAutoHideSideBar::hasVisibleTabs() const { auto ParentWidget = parentWidget(); - for (auto i = 0; i < tabCount(); i++) + for (auto i = 0; i < count(); i++) { - if (tabAt(i)->isVisibleTo(ParentWidget)) + if (tab(i)->isVisibleTo(ParentWidget)) { return true; } @@ -358,18 +359,18 @@ SideBarLocation CAutoHideSideBar::sideBarLocation() const //============================================================================ void CAutoHideSideBar::saveState(QXmlStreamWriter& s) const { - if (!tabCount()) + if (!count()) { return; } s.writeStartElement("SideBar"); s.writeAttribute("Area", QString::number(sideBarLocation())); - s.writeAttribute("Tabs", QString::number(tabCount())); + s.writeAttribute("Tabs", QString::number(count())); - for (auto i = 0; i < tabCount(); ++i) + for (auto i = 0; i < count(); ++i) { - auto Tab = tabAt(i); + auto Tab = tab(i); if (!Tab) { continue; @@ -417,5 +418,38 @@ CDockContainerWidget* CAutoHideSideBar::dockContainer() const return d->ContainerWidget; } + +//=========================================================================== +int CAutoHideSideBar::tabAt(const QPoint& Pos) const +{ + if (!isVisible()) + { + return -2; + } + + if (Pos.x() < tab(0)->geometry().x()) + { + return -1; + } + + for (int i = 0; i < count(); ++i) + { + if (tab(i)->geometry().contains(Pos)) + { + return i; + } + } + + return count(); +} + + +//=========================================================================== +int CAutoHideSideBar::tabInsertIndexAt(const QPoint& Pos) const +{ + int Index = tabAt(Pos); + return (Index < 0) ? -1 : Index; +} + } // namespace ads diff --git a/src/AutoHideSideBar.h b/src/AutoHideSideBar.h index 1b0cab5..c0cdddc 100644 --- a/src/AutoHideSideBar.h +++ b/src/AutoHideSideBar.h @@ -117,7 +117,7 @@ public: * If the AutoHideWidget is in another sidebar, then it will be removed * from this sidebar. */ - void addAutoHideWidget(CAutoHideDockContainer* AutoHideWidget); + void addAutoHideWidget(CAutoHideDockContainer* AutoHideWidget, int Index = -1); /** * Returns orientation of side tab. @@ -127,12 +127,25 @@ public: /* * get the side tab widget at position, returns nullptr if it's out of bounds */ - CAutoHideTab* tabAt(int index) const; + CAutoHideTab* tab(int index) const; + + /** + * Returns the tab at the given position. + * Returns -1 if the position is left of the first tab and count() if the + * position is right of the last tab. Returns -2 to indicate an invalid + * value. + */ + int tabAt(const QPoint& Pos) const; + + /** + * Returns the tab insertion index for the given mouse cursor position + */ + int tabInsertIndexAt(const QPoint& Pos) const; /* * Gets the count of the tab widgets */ - int tabCount() const; + int count() const; /** * Returns the number of visible tabs to its parent widget. diff --git a/src/DockAreaWidget.cpp b/src/DockAreaWidget.cpp index 29186a2..6146c66 100644 --- a/src/DockAreaWidget.cpp +++ b/src/DockAreaWidget.cpp @@ -1305,7 +1305,7 @@ SideBarLocation CDockAreaWidget::calculateSideTabBarArea() const //============================================================================ -void CDockAreaWidget::setAutoHide(bool Enable, SideBarLocation Location) +void CDockAreaWidget::setAutoHide(bool Enable, SideBarLocation Location, int TabIndex) { if (!isAutoHideFeatureEnabled()) { @@ -1324,7 +1324,7 @@ void CDockAreaWidget::setAutoHide(bool Enable, SideBarLocation Location) // If this is already an auto hide container, then move it to new location if (isAutoHide()) { - d->AutoHideDockContainer->moveToNewSideBarLocation(Location); + d->AutoHideDockContainer->moveToNewSideBarLocation(Location, TabIndex); return; } @@ -1341,7 +1341,7 @@ void CDockAreaWidget::setAutoHide(bool Enable, SideBarLocation Location) continue; } - dockContainer()->createAndSetupAutoHideContainer(area, DockWidget); + dockContainer()->createAndSetupAutoHideContainer(area, DockWidget, TabIndex++); } } diff --git a/src/DockAreaWidget.h b/src/DockAreaWidget.h index f1412e8..e88153e 100644 --- a/src/DockAreaWidget.h +++ b/src/DockAreaWidget.h @@ -400,7 +400,7 @@ public Q_SLOTS: * If the dock area is switched to auto hide mode, then all dock widgets * that are pinable will be added to the sidebar */ - void setAutoHide(bool Enable, SideBarLocation Location = SideBarNone); + void setAutoHide(bool Enable, SideBarLocation Location = SideBarNone, int TabIndex = -1); /** * Switches the dock area to auto hide mode or vice versa depending on its diff --git a/src/DockContainerWidget.cpp b/src/DockContainerWidget.cpp index 8156d3b..e0e5144 100644 --- a/src/DockContainerWidget.cpp +++ b/src/DockContainerWidget.cpp @@ -220,7 +220,7 @@ public: * Moves the dock widget or dock area given in Widget parameter to * a auto hide sidebar area */ - void moveToAutoHideSideBar(QWidget* Widget, DockWidgetArea area); + void moveToAutoHideSideBar(QWidget* Widget, DockWidgetArea area, int TabIndex = -2); /** @@ -777,7 +777,7 @@ void DockContainerWidgetPrivate::moveToNewSection(QWidget* Widget, CDockAreaWidg //============================================================================ -void DockContainerWidgetPrivate::moveToAutoHideSideBar(QWidget* Widget, DockWidgetArea area) +void DockContainerWidgetPrivate::moveToAutoHideSideBar(QWidget* Widget, DockWidgetArea area, int TabIndex) { CDockWidget* DroppedDockWidget = qobject_cast(Widget); CDockAreaWidget* DroppedDockArea = qobject_cast(Widget); @@ -787,18 +787,18 @@ void DockContainerWidgetPrivate::moveToAutoHideSideBar(QWidget* Widget, DockWidg { if (_this == DroppedDockWidget->dockContainer()) { - DroppedDockWidget->setAutoHide(true, SideBarLocation); + DroppedDockWidget->setAutoHide(true, SideBarLocation, TabIndex); } else { - _this->createAndSetupAutoHideContainer(SideBarLocation, DroppedDockWidget); + _this->createAndSetupAutoHideContainer(SideBarLocation, DroppedDockWidget, TabIndex); } } else { if (_this == DroppedDockArea->dockContainer()) { - DroppedDockArea->setAutoHide(true, SideBarLocation); + DroppedDockArea->setAutoHide(true, SideBarLocation, TabIndex); } else { @@ -811,7 +811,7 @@ void DockContainerWidgetPrivate::moveToAutoHideSideBar(QWidget* Widget, DockWidg } _this->createAndSetupAutoHideContainer(SideBarLocation, - DockWidget); + DockWidget, TabIndex++); } } } @@ -988,7 +988,7 @@ void DockContainerWidgetPrivate::saveAutoHideWidgetsState(QXmlStreamWriter& s) { for (const auto sideTabBar : SideTabBarWidgets.values()) { - if (!sideTabBar->tabCount()) + if (!sideTabBar->count()) { continue; } @@ -1484,7 +1484,7 @@ CDockAreaWidget* CDockContainerWidget::addDockWidget(DockWidgetArea area, CDockW //============================================================================ CAutoHideDockContainer* CDockContainerWidget::createAndSetupAutoHideContainer( - SideBarLocation area, CDockWidget* DockWidget) + SideBarLocation area, CDockWidget* DockWidget, int TabIndex) { if (!CDockManager::testAutoHideConfigFlag(CDockManager::AutoHideFeatureEnabled)) { @@ -1497,7 +1497,8 @@ CAutoHideDockContainer* CDockContainerWidget::createAndSetupAutoHideContainer( DockWidget->setDockManager(d->DockManager); // Auto hide Dock Container needs a valid dock manager } - return autoHideSideBar(area)->insertDockWidget(-1, DockWidget); + qDebug() << "CDockContainerWidget::createAndSetupAutoHideContainer TabIndex: " << TabIndex; + return autoHideSideBar(area)->insertDockWidget(TabIndex, DockWidget); } @@ -1794,7 +1795,7 @@ void CDockContainerWidget::dropWidget(QWidget* Widget, DockWidgetArea DropArea, } else if (internal::isSideBarArea(DropArea)) { - d->moveToAutoHideSideBar(Widget, DropArea); + d->moveToAutoHideSideBar(Widget, DropArea, TabIndex); } else { diff --git a/src/DockContainerWidget.h b/src/DockContainerWidget.h index 700a8cb..11fc339 100644 --- a/src/DockContainerWidget.h +++ b/src/DockContainerWidget.h @@ -101,7 +101,7 @@ protected: * Initializing inserts the tabs into the side tab widget and hides it * Returns nullptr if you try and insert into an area where the configuration is not enabled */ - CAutoHideDockContainer* createAndSetupAutoHideContainer(SideBarLocation area, CDockWidget* DockWidget); + CAutoHideDockContainer* createAndSetupAutoHideContainer(SideBarLocation area, CDockWidget* DockWidget, int TabIndex = -1); /** * The funtion does the same like createAndSetupAutoHideContainer() but checks @@ -133,7 +133,7 @@ protected: * TargetAreaWidget */ void dropWidget(QWidget* Widget, DockWidgetArea DropArea, CDockAreaWidget* TargetAreaWidget, - int TabIndex = -2); + int TabIndex = -1); /** * Adds the given dock area to this container widget diff --git a/src/DockOverlay.cpp b/src/DockOverlay.cpp index e54a14c..40d84c1 100644 --- a/src/DockOverlay.cpp +++ b/src/DockOverlay.cpp @@ -471,6 +471,7 @@ DockWidgetArea CDockOverlay::dropAreaUnderCursor() const return Result; } + auto CursorPos = QCursor::pos(); auto DockArea = qobject_cast(d->TargetWidget.data()); if (!DockArea && CDockManager::autoHideConfigFlags().testFlag(CDockManager::AutoHideFeatureEnabled)) { @@ -479,26 +480,34 @@ DockWidgetArea CDockOverlay::dropAreaUnderCursor() const if ((pos.x() < d->sideBarMouseZone(SideBarLeft)) && d->AllowedAreas.testFlag(LeftAutoHideArea)) { - return LeftAutoHideArea; + Result = LeftAutoHideArea; } else if (pos.x() > (Rect.width() - d->sideBarMouseZone(SideBarRight)) && d->AllowedAreas.testFlag(RightAutoHideArea)) { - return RightAutoHideArea; + Result = RightAutoHideArea; } else if (pos.y() < d->sideBarMouseZone(SideBarTop) && d->AllowedAreas.testFlag(TopAutoHideArea)) { - return TopAutoHideArea; + Result = TopAutoHideArea; } else if (pos.y() > (Rect.height() - d->sideBarMouseZone(SideBarBottom)) && d->AllowedAreas.testFlag(BottomAutoHideArea)) { - return BottomAutoHideArea; + Result = BottomAutoHideArea; } - else + + auto SideBarLocation = ads::internal::toSideBarLocation(Result); + if (SideBarLocation != SideBarNone) { - return Result; + auto Container = qobject_cast(d->TargetWidget.data()); + auto SideBar = Container->autoHideSideBar(SideBarLocation); + if (SideBar->isVisible()) + { + d->TabIndex = SideBar->tabInsertIndexAt(SideBar->mapFromGlobal(CursorPos)); + qDebug() << "TabIndex " << d->TabIndex; + } } return Result; } @@ -507,13 +516,13 @@ DockWidgetArea CDockOverlay::dropAreaUnderCursor() const return Result; } - auto CursorPos = QCursor::pos(); if (DockArea->allowedAreas().testFlag(CenterDockWidgetArea) && !DockArea->titleBar()->isHidden() && DockArea->titleBarGeometry().contains(DockArea->mapFromGlobal(CursorPos))) { auto TabBar = DockArea->titleBar()->tabBar(); d->TabIndex = TabBar->tabAt(TabBar->mapFromGlobal(CursorPos)); + qDebug() << "TabIndex " << d->TabIndex; return CenterDockWidgetArea; } diff --git a/src/DockWidget.cpp b/src/DockWidget.cpp index a180cf6..60cbff0 100644 --- a/src/DockWidget.cpp +++ b/src/DockWidget.cpp @@ -1221,7 +1221,7 @@ void CDockWidget::raise() //============================================================================ -void CDockWidget::setAutoHide(bool Enable, SideBarLocation Location) +void CDockWidget::setAutoHide(bool Enable, SideBarLocation Location, int TabIndex) { if (!CDockManager::testAutoHideConfigFlag(CDockManager::AutoHideFeatureEnabled)) { @@ -1247,7 +1247,7 @@ void CDockWidget::setAutoHide(bool Enable, SideBarLocation Location) else { auto area = (SideBarNone == Location) ? DockArea->calculateSideTabBarArea() : Location; - dockContainer()->createAndSetupAutoHideContainer(area, this); + dockContainer()->createAndSetupAutoHideContainer(area, this, TabIndex); } } diff --git a/src/DockWidget.h b/src/DockWidget.h index 188c14b..c181932 100644 --- a/src/DockWidget.h +++ b/src/DockWidget.h @@ -621,7 +621,7 @@ public Q_SLOTS: * Sets the dock widget into auto hide mode if this feature is enabled * via CDockManager::setAutoHideFlags(CDockManager::AutoHideFeatureEnabled) */ - void setAutoHide(bool Enable, SideBarLocation Location = SideBarNone); + void setAutoHide(bool Enable, SideBarLocation Location = SideBarNone, int TabIndex = -1); /** * Switches the dock widget to auto hide mode or vice versa depending on its diff --git a/src/FloatingDragPreview.cpp b/src/FloatingDragPreview.cpp index b1c18e1..f7a45a2 100644 --- a/src/FloatingDragPreview.cpp +++ b/src/FloatingDragPreview.cpp @@ -409,7 +409,8 @@ void CFloatingDragPreview::finishDragging() DockArea = d->DropContainer->dockAreaAt(QCursor::pos()); } - d->DropContainer->dropWidget(d->Content, ContainerDropArea, DockArea); + d->DropContainer->dropWidget(d->Content, ContainerDropArea, DockArea, + d->DockManager->containerOverlay()->tabIndexUnderCursor()); } else {