mirror of
https://github.com/githubuser0xFFFF/Qt-Advanced-Docking-System.git
synced 2025-01-25 05:49:02 +08:00
Properly implemented DockAreaTitle bar to encapsulate title bar functionality
This commit is contained in:
parent
9bfb3fbea1
commit
11e5f9c95a
@ -467,16 +467,12 @@ bool CDockAreaTabBar::eventFilter(QObject *watched, QEvent *event)
|
||||
return Result;
|
||||
}
|
||||
|
||||
if (event->type() == QEvent::Hide)
|
||||
{
|
||||
return Result;
|
||||
}
|
||||
|
||||
int TabIndex = d->TabsLayout->indexOf(Tab);
|
||||
switch (event->type())
|
||||
{
|
||||
case QEvent::Hide: emit tabClosed(TabIndex); break;
|
||||
case QEvent::Show: emit tabOpened(TabIndex); break;
|
||||
case QEvent::Hide:
|
||||
emit tabClosed(d->TabsLayout->indexOf(Tab)); break;
|
||||
case QEvent::Show:
|
||||
emit tabOpened(d->TabsLayout->indexOf(Tab)); break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
@ -83,7 +83,7 @@ void DockAreaTitleBarPrivate::createButtons()
|
||||
_this->connect(TabsMenu, SIGNAL(aboutToShow()), SLOT(onTabsMenuAboutToShow()));
|
||||
TabsMenuButton->setMenu(TabsMenu);
|
||||
TopLayout->addWidget(TabsMenuButton, 0);
|
||||
TabsMenuButton->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
|
||||
TabsMenuButton->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed);
|
||||
_this->connect(TabsMenuButton->menu(), SIGNAL(triggered(QAction*)),
|
||||
SLOT(onTabsMenuActionTriggered(QAction*)));
|
||||
|
||||
@ -92,7 +92,7 @@ void DockAreaTitleBarPrivate::createButtons()
|
||||
CloseButton->setFlat(true);
|
||||
CloseButton->setIcon(_this->style()->standardIcon(QStyle::SP_TitleBarCloseButton));
|
||||
CloseButton->setToolTip(QObject::tr("Close"));
|
||||
CloseButton->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
|
||||
CloseButton->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed);
|
||||
TopLayout->addWidget(CloseButton, 0);
|
||||
_this->connect(CloseButton, SIGNAL(clicked()), SLOT(onCloseButtonClicked()));
|
||||
}
|
||||
@ -103,10 +103,12 @@ void DockAreaTitleBarPrivate::createTabBar()
|
||||
{
|
||||
TabBar = new CDockAreaTabBar(DockArea);
|
||||
TopLayout->addWidget(TabBar);
|
||||
_this->connect(TabBar, SIGNAL(tabClosed()), SLOT(markTabsMenuOutdated()));
|
||||
_this->connect(TabBar, SIGNAL(tabOpened()), SLOT(markTabsMenuOutdated()));
|
||||
_this->connect(TabBar, SIGNAL(tabInserted()), SLOT(markTabsMenuOutdated()));
|
||||
_this->connect(TabBar, SIGNAL(tabRemoved()), SLOT(markTabsMenuOutdated()));
|
||||
_this->connect(TabBar, SIGNAL(tabClosed(int)), SLOT(markTabsMenuOutdated()));
|
||||
_this->connect(TabBar, SIGNAL(tabOpened(int)), SLOT(markTabsMenuOutdated()));
|
||||
_this->connect(TabBar, SIGNAL(tabInserted(int)), SLOT(markTabsMenuOutdated()));
|
||||
_this->connect(TabBar, SIGNAL(removingTab(int)), SLOT(markTabsMenuOutdated()));
|
||||
_this->connect(TabBar, SIGNAL(tabMoved(int, int)), SLOT(markTabsMenuOutdated()));
|
||||
_this->connect(TabBar, SIGNAL(currentChanged(int)), SLOT(onCurrentTabChanged(int)));
|
||||
}
|
||||
|
||||
|
||||
@ -193,6 +195,14 @@ void CDockAreaTitleBar::onTabsMenuActionTriggered(QAction* Action)
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CDockAreaTitleBar::onCurrentTabChanged(int Index)
|
||||
{
|
||||
CDockWidget* DockWidget = d->TabBar->tab(Index)->dockWidget();
|
||||
d->CloseButton->setVisible(DockWidget->features().testFlag(CDockWidget::DockWidgetClosable));
|
||||
}
|
||||
|
||||
|
||||
} // namespace ads
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
|
@ -33,6 +33,7 @@ private slots:
|
||||
void onTabsMenuAboutToShow();
|
||||
void onCloseButtonClicked();
|
||||
void onTabsMenuActionTriggered(QAction* Action);
|
||||
void onCurrentTabChanged(int Index);
|
||||
|
||||
public:
|
||||
using Super = QFrame;
|
||||
|
@ -52,6 +52,7 @@
|
||||
#include "DockOverlay.h"
|
||||
#include "DockAreaTabBar.h"
|
||||
#include "DockSplitter.h"
|
||||
#include "DockAreaTitleBar.h"
|
||||
|
||||
#include <iostream>
|
||||
|
||||
@ -209,14 +210,9 @@ struct DockAreaWidgetPrivate
|
||||
{
|
||||
CDockAreaWidget* _this;
|
||||
QBoxLayout* Layout;
|
||||
QFrame* TitleBar;
|
||||
QBoxLayout* TopLayout;
|
||||
DockAreaLayout* ContentsLayout;
|
||||
CDockAreaTabBar* TabBar;
|
||||
QPushButton* TabsMenuButton;
|
||||
QPushButton* CloseButton;
|
||||
CDockAreaTitleBar* TitleBar;
|
||||
CDockManager* DockManager = nullptr;
|
||||
bool MenuOutdated = true;
|
||||
|
||||
/**
|
||||
* Private data constructor
|
||||
@ -226,7 +222,7 @@ struct DockAreaWidgetPrivate
|
||||
/**
|
||||
* Creates the layout for top area with tabs and close button
|
||||
*/
|
||||
void createTabBar();
|
||||
void createTitleBar();
|
||||
|
||||
/**
|
||||
* Returns the dock widget with the given index
|
||||
@ -244,13 +240,6 @@ struct DockAreaWidgetPrivate
|
||||
return dockWidgetAt(index)->tabWidget();
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds a tabs menu entry for the given dock widget
|
||||
* If menu is 0, a menu entry is added to the menu of the TabsMenuButton
|
||||
* member. If menu is a valid menu pointer, the entry will be added to
|
||||
* the given menu
|
||||
*/
|
||||
void addTabsMenuEntry(CDockWidget* DockWidget, int Index = -1, QMenu* menu = 0);
|
||||
|
||||
/**
|
||||
* Returns the tab action of the given dock widget
|
||||
@ -268,22 +257,19 @@ struct DockAreaWidgetPrivate
|
||||
return DockWidget->property(INDEX_PROPERTY).toInt();
|
||||
}
|
||||
|
||||
/**
|
||||
* Update the tabs menu if dock widget order changed or if dock widget has
|
||||
* been removed
|
||||
*/
|
||||
void markTabsMenuOutdated();
|
||||
|
||||
/**
|
||||
* Updates the tabs menu if it is outdated
|
||||
*/
|
||||
void updateTabsMenu();
|
||||
|
||||
/**
|
||||
* Updates the tab bar visibility depending on the number of dock widgets
|
||||
* in this area
|
||||
*/
|
||||
void updateTabBar();
|
||||
|
||||
/**
|
||||
* Convenience function for tabbar access
|
||||
*/
|
||||
CDockAreaTabBar* tabBar() const
|
||||
{
|
||||
return TitleBar->tabBar();
|
||||
}
|
||||
};
|
||||
// struct DockAreaWidgetPrivate
|
||||
|
||||
@ -297,43 +283,14 @@ DockAreaWidgetPrivate::DockAreaWidgetPrivate(CDockAreaWidget* _public) :
|
||||
|
||||
|
||||
//============================================================================
|
||||
void DockAreaWidgetPrivate::createTabBar()
|
||||
void DockAreaWidgetPrivate::createTitleBar()
|
||||
{
|
||||
TitleBar = new QFrame(_this);
|
||||
TitleBar->setObjectName("dockAreaTitleBar");
|
||||
TopLayout = new QBoxLayout(QBoxLayout::LeftToRight);
|
||||
TopLayout->setContentsMargins(0, 0, 0, 0);
|
||||
TopLayout->setSpacing(0);
|
||||
TitleBar->setLayout(TopLayout);
|
||||
TitleBar = new CDockAreaTitleBar(_this);
|
||||
Layout->addWidget(TitleBar);
|
||||
TitleBar->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Fixed);
|
||||
|
||||
TabBar = new CDockAreaTabBar(_this);
|
||||
TopLayout->addWidget(TabBar, 1);
|
||||
_this->connect(TabBar, SIGNAL(currentChanged(int)), SLOT(setCurrentIndex(int)));
|
||||
_this->connect(TabBar, SIGNAL(tabMoved(int, int)), SLOT(reorderDockWidget(int, int)));
|
||||
|
||||
TabsMenuButton = new QPushButton();
|
||||
TabsMenuButton->setObjectName("tabsMenuButton");
|
||||
TabsMenuButton->setFlat(true);
|
||||
TabsMenuButton->setIcon(_this->style()->standardIcon(QStyle::SP_TitleBarUnshadeButton));
|
||||
TabsMenuButton->setMaximumWidth(TabsMenuButton->iconSize().width());
|
||||
QMenu* TabsMenu = new QMenu(TabsMenuButton);
|
||||
_this->connect(TabsMenu, SIGNAL(aboutToShow()), SLOT(onTabsMenuAboutToShow()));
|
||||
TabsMenuButton->setMenu(TabsMenu);
|
||||
TopLayout->addWidget(TabsMenuButton, 0);
|
||||
TabsMenuButton->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
|
||||
_this->connect(TabsMenuButton->menu(), SIGNAL(triggered(QAction*)),
|
||||
SLOT(onTabsMenuActionTriggered(QAction*)));
|
||||
|
||||
CloseButton = new QPushButton();
|
||||
CloseButton->setObjectName("closeButton");
|
||||
CloseButton->setFlat(true);
|
||||
CloseButton->setIcon(_this->style()->standardIcon(QStyle::SP_TitleBarCloseButton));
|
||||
CloseButton->setToolTip(_this->tr("Close"));
|
||||
CloseButton->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
|
||||
TopLayout->addWidget(CloseButton, 0);
|
||||
_this->connect(CloseButton, SIGNAL(clicked()), SLOT(onCloseButtonClicked()));
|
||||
_this->connect(tabBar(), SIGNAL(tabCloseRequested(int)),
|
||||
SLOT(onTabCloseRequested(int)));
|
||||
_this->connect(tabBar(), SIGNAL(tabBarClicked(int)),
|
||||
SLOT(setCurrentIndex(int)));
|
||||
}
|
||||
|
||||
|
||||
@ -350,57 +307,6 @@ void DockAreaWidgetPrivate::updateTabBar()
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void DockAreaWidgetPrivate::addTabsMenuEntry(CDockWidget* DockWidget,
|
||||
int Index, QMenu* menu)
|
||||
{
|
||||
menu = menu ? menu : TabsMenuButton->menu();
|
||||
QAction* Action;
|
||||
if (Index >= 0 && Index < menu->actions().count())
|
||||
{
|
||||
Action = new QAction(DockWidget->icon(), DockWidget->windowTitle());
|
||||
menu->insertAction(menu->actions().at(Index), Action);
|
||||
}
|
||||
else
|
||||
{
|
||||
Action = menu->addAction(DockWidget->icon(), DockWidget->windowTitle());
|
||||
}
|
||||
Action->setProperty(DOCKWIDGET_PROPERTY, QVariant::fromValue(DockWidget));
|
||||
QVariant vAction = QVariant::fromValue(Action);
|
||||
DockWidget->setProperty(ACTION_PROPERTY, vAction);
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void DockAreaWidgetPrivate::markTabsMenuOutdated()
|
||||
{
|
||||
MenuOutdated = true;
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void DockAreaWidgetPrivate::updateTabsMenu()
|
||||
{
|
||||
if (!MenuOutdated)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
QMenu* menu = TabsMenuButton->menu();
|
||||
menu->clear();
|
||||
for (int i = 0; i < ContentsLayout->count(); ++i)
|
||||
{
|
||||
if (dockWidgetAt(i)->isClosed())
|
||||
{
|
||||
continue;
|
||||
}
|
||||
addTabsMenuEntry(dockWidgetAt(i), APPEND, menu);
|
||||
}
|
||||
|
||||
MenuOutdated = false;
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
CDockAreaWidget::CDockAreaWidget(CDockManager* DockManager, CDockContainerWidget* parent) :
|
||||
QFrame(parent),
|
||||
@ -412,7 +318,7 @@ CDockAreaWidget::CDockAreaWidget(CDockManager* DockManager, CDockContainerWidget
|
||||
d->Layout->setSpacing(0);
|
||||
setLayout(d->Layout);
|
||||
|
||||
d->createTabBar();
|
||||
d->createTitleBar();
|
||||
d->ContentsLayout = new DockAreaLayout(d->Layout);
|
||||
}
|
||||
|
||||
@ -453,10 +359,9 @@ void CDockAreaWidget::insertDockWidget(int index, CDockWidget* DockWidget,
|
||||
d->ContentsLayout->insertWidget(index, DockWidget);
|
||||
DockWidget->tabWidget()->setDockAreaWidget(this);
|
||||
auto TabWidget = DockWidget->tabWidget();
|
||||
d->TabBar->insertTab(index, TabWidget);
|
||||
d->tabBar()->insertTab(index, TabWidget);
|
||||
TabWidget->setVisible(!DockWidget->isClosed());
|
||||
DockWidget->setProperty(INDEX_PROPERTY, index);
|
||||
d->markTabsMenuOutdated();
|
||||
if (Activate)
|
||||
{
|
||||
setCurrentIndex(index);
|
||||
@ -474,11 +379,10 @@ void CDockAreaWidget::removeDockWidget(CDockWidget* DockWidget)
|
||||
d->ContentsLayout->removeWidget(DockWidget);
|
||||
auto TabWidget = DockWidget->tabWidget();
|
||||
TabWidget->hide();
|
||||
d->TabBar->removeTab(TabWidget);
|
||||
d->tabBar()->removeTab(TabWidget);
|
||||
if (NextOpenDockWidget)
|
||||
{
|
||||
setCurrentDockWidget(NextOpenDockWidget);
|
||||
d->markTabsMenuOutdated();
|
||||
}
|
||||
else if (d->ContentsLayout->isEmpty())
|
||||
{
|
||||
@ -541,9 +445,10 @@ void CDockAreaWidget::hideAreaIfNoVisibleContent()
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CDockAreaWidget::onCloseButtonClicked()
|
||||
void CDockAreaWidget::onTabCloseRequested(int Index)
|
||||
{
|
||||
currentDockWidget()->toggleView(false);
|
||||
qDebug() << "CDockAreaWidget::onTabCloseRequested " << Index;
|
||||
dockWidget(Index)->toggleView(false);
|
||||
}
|
||||
|
||||
|
||||
@ -576,18 +481,15 @@ void CDockAreaWidget::setCurrentDockWidget(CDockWidget* DockWidget)
|
||||
void CDockAreaWidget::setCurrentIndex(int index)
|
||||
{
|
||||
std::cout << "CDockAreaWidget::setCurrentIndex " << index << std::endl;
|
||||
if (index < 0 || index > (d->TabBar->count() - 1))
|
||||
auto TabBar = d->tabBar();
|
||||
if (index < 0 || index > (TabBar->count() - 1))
|
||||
{
|
||||
qWarning() << Q_FUNC_INFO << "Invalid index" << index;
|
||||
return;
|
||||
}
|
||||
|
||||
emit currentChanging(index);
|
||||
d->TabBar->setCurrentIndex(index);
|
||||
CDockWidgetTab* CurrentTab = d->TabBar->currentTab();
|
||||
auto Features = CurrentTab->dockWidget()->features();
|
||||
d->CloseButton->setVisible(Features.testFlag(CDockWidget::DockWidgetClosable));
|
||||
|
||||
TabBar->setCurrentIndex(index);
|
||||
d->ContentsLayout->setCurrentIndex(index);
|
||||
d->ContentsLayout->currentWidget()->show();
|
||||
emit currentChanged(index);
|
||||
@ -602,9 +504,9 @@ int CDockAreaWidget::currentIndex() const
|
||||
|
||||
|
||||
//============================================================================
|
||||
QRect CDockAreaWidget::titleAreaGeometry() const
|
||||
QRect CDockAreaWidget::titleBarGeometry() const
|
||||
{
|
||||
return d->TopLayout->geometry();
|
||||
return d->TitleBar->geometry();
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
@ -664,21 +566,6 @@ QList<CDockWidget*> CDockAreaWidget::openedDockWidgets() const
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
int CDockAreaWidget::indexOfContentByTitlePos(const QPoint& p, QWidget* exclude) const
|
||||
{
|
||||
for (int i = 0; i < d->ContentsLayout->count(); ++i)
|
||||
{
|
||||
auto TabWidget = d->tabWidgetAt(i);
|
||||
if (TabWidget->isVisible() && TabWidget->geometry().contains(p) && (!exclude || TabWidget != exclude))
|
||||
{
|
||||
return i;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
int CDockAreaWidget::dockWidgetsCount() const
|
||||
{
|
||||
@ -716,16 +603,6 @@ void CDockAreaWidget::toggleDockWidgetView(CDockWidget* DockWidget, bool Open)
|
||||
Q_UNUSED(DockWidget);
|
||||
Q_UNUSED(Open);
|
||||
updateTabBarVisibility();
|
||||
d->markTabsMenuOutdated();
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CDockAreaWidget::onTabsMenuActionTriggered(QAction* Action)
|
||||
{
|
||||
QVariant vDockWidget = Action->property(DOCKWIDGET_PROPERTY);
|
||||
CDockWidget* DockWidget = vDockWidget.value<CDockWidget*>();
|
||||
setCurrentDockWidget(DockWidget);
|
||||
}
|
||||
|
||||
|
||||
@ -777,13 +654,6 @@ CDockWidget* CDockAreaWidget::nextOpenDockWidget(CDockWidget* DockWidget) const
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//============================================================================
|
||||
void CDockAreaWidget::onTabsMenuAboutToShow()
|
||||
{
|
||||
d->updateTabsMenu();
|
||||
}
|
||||
|
||||
} // namespace ads
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
|
@ -63,9 +63,7 @@ private:
|
||||
friend class CDockWidget;
|
||||
|
||||
private slots:
|
||||
void onTabsMenuActionTriggered(QAction* Action);
|
||||
void onCloseButtonClicked();
|
||||
void onTabsMenuAboutToShow();
|
||||
void onTabCloseRequested(int Index);
|
||||
|
||||
/**
|
||||
* Reorder the index position of DockWidget at fromIndx to toIndex
|
||||
@ -94,12 +92,6 @@ protected:
|
||||
*/
|
||||
void removeDockWidget(CDockWidget* DockWidget);
|
||||
|
||||
/**
|
||||
* Returns the index of contents of the title widget that is located at
|
||||
* mouse position pos
|
||||
*/
|
||||
int indexOfContentByTitlePos(const QPoint& pos, QWidget* exclude = nullptr) const;
|
||||
|
||||
/**
|
||||
* Called from dock widget if it is opened or closed
|
||||
*/
|
||||
@ -161,7 +153,7 @@ public:
|
||||
/**
|
||||
* Returns the rectangle of the title area
|
||||
*/
|
||||
QRect titleAreaGeometry() const;
|
||||
QRect titleBarGeometry() const;
|
||||
|
||||
/**
|
||||
* Returns the rectangle of the content
|
||||
|
@ -346,7 +346,7 @@ DockWidgetArea CDockOverlay::dropAreaUnderCursor() const
|
||||
return Result;
|
||||
}
|
||||
|
||||
if (DockArea->titleAreaGeometry().contains(DockArea->mapFromGlobal(QCursor::pos())))
|
||||
if (DockArea->titleBarGeometry().contains(DockArea->mapFromGlobal(QCursor::pos())))
|
||||
{
|
||||
return CenterDockWidgetArea;
|
||||
}
|
||||
|
@ -107,7 +107,7 @@ struct DockWidgetTabPrivate
|
||||
*/
|
||||
bool titleAreaGeometryContains(const QPoint& GlobalPos) const
|
||||
{
|
||||
return DockArea->titleAreaGeometry().contains(DockArea->mapFromGlobal(GlobalPos));
|
||||
return DockArea->titleBarGeometry().contains(DockArea->mapFromGlobal(GlobalPos));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -227,7 +227,6 @@ void CDockWidgetTab::mousePressEvent(QMouseEvent* ev)
|
||||
{
|
||||
if (ev->button() == Qt::LeftButton)
|
||||
{
|
||||
qDebug() << "CDockWidgetTab::mousePressEvent";
|
||||
ev->accept();
|
||||
d->DragStartMousePosition = ev->pos();
|
||||
d->DragState = DraggingMousePressed;
|
||||
@ -242,7 +241,6 @@ void CDockWidgetTab::mousePressEvent(QMouseEvent* ev)
|
||||
//============================================================================
|
||||
void CDockWidgetTab::mouseReleaseEvent(QMouseEvent* ev)
|
||||
{
|
||||
qDebug() << "CDockWidgetTab::mouseReleaseEvent";
|
||||
// End of tab moving, emit signal
|
||||
if (d->isDraggingState(DraggingTab) && d->DockArea)
|
||||
{
|
||||
|
Loading…
Reference in New Issue
Block a user