mirror of
https://github.com/githubuser0xFFFF/Qt-Advanced-Docking-System.git
synced 2025-01-13 00:30:25 +08:00
Improved support when moving widgets out of FloatingWidget
This commit is contained in:
parent
df85c8bee0
commit
fac5661280
@ -43,6 +43,8 @@
|
|||||||
#include "DockWidget.h"
|
#include "DockWidget.h"
|
||||||
#include "DockWidgetTitleBar.h"
|
#include "DockWidgetTitleBar.h"
|
||||||
#include "FloatingDockContainer.h"
|
#include "FloatingDockContainer.h"
|
||||||
|
#include "DockManager.h"
|
||||||
|
#include "DockOverlay.h"
|
||||||
|
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
@ -104,7 +106,8 @@ protected:
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Starts floating the complete docking area including all dock widgets
|
* Starts floating the complete docking area including all dock widgets,
|
||||||
|
* if it is not the last dock area in a floating widget
|
||||||
*/
|
*/
|
||||||
virtual void mouseMoveEvent(QMouseEvent* ev) override
|
virtual void mouseMoveEvent(QMouseEvent* ev) override
|
||||||
{
|
{
|
||||||
@ -113,11 +116,24 @@ protected:
|
|||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// If this is the last dock area in a dock container it does not make
|
||||||
|
// sense to move it to a new floating widget and leave this one
|
||||||
|
// empty
|
||||||
|
if (DockArea->dockContainer()->isFloating() && DockArea->dockContainer()->dockAreaCount() == 1)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (!this->geometry().contains(ev->pos()))
|
if (!this->geometry().contains(ev->pos()))
|
||||||
{
|
{
|
||||||
|
std::cout << "CTabsScrollArea::startFloating" << std::endl;
|
||||||
QSize Size = DockArea->size();
|
QSize Size = DockArea->size();
|
||||||
CFloatingDockContainer* FloatingWidget = new CFloatingDockContainer(DockArea);
|
CFloatingDockContainer* FloatingWidget = new CFloatingDockContainer(DockArea);
|
||||||
FloatingWidget->startFloating(m_DragStartMousePos, Size);
|
FloatingWidget->startFloating(m_DragStartMousePos, Size);
|
||||||
|
|
||||||
|
auto Overlay = DockArea->dockManager()->containerOverlay();
|
||||||
|
Overlay->setAllowedAreas(OuterDockAreas);
|
||||||
}
|
}
|
||||||
|
|
||||||
return;
|
return;
|
||||||
@ -142,6 +158,7 @@ struct DockAreaWidgetPrivate
|
|||||||
{
|
{
|
||||||
CDockAreaWidget* _this;
|
CDockAreaWidget* _this;
|
||||||
QBoxLayout* Layout;
|
QBoxLayout* Layout;
|
||||||
|
QFrame* TitleBar;
|
||||||
QBoxLayout* TopLayout;
|
QBoxLayout* TopLayout;
|
||||||
QStackedLayout* ContentsLayout;
|
QStackedLayout* ContentsLayout;
|
||||||
QScrollArea* TabsScrollArea;
|
QScrollArea* TabsScrollArea;
|
||||||
@ -207,6 +224,12 @@ struct DockAreaWidgetPrivate
|
|||||||
* been removed
|
* been removed
|
||||||
*/
|
*/
|
||||||
void updateTabsMenu();
|
void updateTabsMenu();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Updates the tab bar visibility depending on the number of dock widgets
|
||||||
|
* in this area
|
||||||
|
*/
|
||||||
|
void updateTabBar();
|
||||||
};
|
};
|
||||||
// struct DockAreaWidgetPrivate
|
// struct DockAreaWidgetPrivate
|
||||||
|
|
||||||
@ -222,10 +245,12 @@ DockAreaWidgetPrivate::DockAreaWidgetPrivate(CDockAreaWidget* _public) :
|
|||||||
//============================================================================
|
//============================================================================
|
||||||
void DockAreaWidgetPrivate::createTabBar()
|
void DockAreaWidgetPrivate::createTabBar()
|
||||||
{
|
{
|
||||||
|
TitleBar = new QFrame(_this);
|
||||||
TopLayout = new QBoxLayout(QBoxLayout::LeftToRight);
|
TopLayout = new QBoxLayout(QBoxLayout::LeftToRight);
|
||||||
TopLayout->setContentsMargins(0, 0, 0, 0);
|
TopLayout->setContentsMargins(0, 0, 0, 0);
|
||||||
TopLayout->setSpacing(0);
|
TopLayout->setSpacing(0);
|
||||||
Layout->addLayout(TopLayout);
|
TitleBar->setLayout(TopLayout);
|
||||||
|
Layout->addWidget(TitleBar);
|
||||||
|
|
||||||
TabsScrollArea = new CTabsScrollArea(_this);
|
TabsScrollArea = new CTabsScrollArea(_this);
|
||||||
TopLayout->addWidget(TabsScrollArea, 1);
|
TopLayout->addWidget(TabsScrollArea, 1);
|
||||||
@ -263,6 +288,26 @@ void DockAreaWidgetPrivate::createTabBar()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
void DockAreaWidgetPrivate::updateTabBar()
|
||||||
|
{
|
||||||
|
CDockContainerWidget* Container = _this->dockContainer();
|
||||||
|
if (!Container)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Container->isFloating() && (Container->dockAreaCount() == 1) && (_this->count() == 1))
|
||||||
|
{
|
||||||
|
TitleBar->setVisible(false);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
TitleBar->setVisible(true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
//============================================================================
|
//============================================================================
|
||||||
void DockAreaWidgetPrivate::addTabsMenuEntry(CDockWidget* DockWidget,
|
void DockAreaWidgetPrivate::addTabsMenuEntry(CDockWidget* DockWidget,
|
||||||
QMenu* menu)
|
QMenu* menu)
|
||||||
@ -376,6 +421,8 @@ void CDockAreaWidget::removeDockWidget(CDockWidget* DockWidget)
|
|||||||
dockContainer()->removeDockArea(this);
|
dockContainer()->removeDockArea(this);
|
||||||
this->deleteLater();
|
this->deleteLater();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
d->updateTabBar();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -540,6 +587,14 @@ void CDockAreaWidget::onTabsMenuActionTriggered(QAction* Action)
|
|||||||
int Index = d->TabsMenuButton->menu()->actions().indexOf(Action);
|
int Index = d->TabsMenuButton->menu()->actions().indexOf(Action);
|
||||||
setCurrentIndex(Index);
|
setCurrentIndex(Index);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
void CDockAreaWidget::updateDockArea()
|
||||||
|
{
|
||||||
|
d->updateTabBar();
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace ads
|
} // namespace ads
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
@ -134,6 +134,11 @@ public slots:
|
|||||||
* This sets the index position of the current tab page.
|
* This sets the index position of the current tab page.
|
||||||
*/
|
*/
|
||||||
void setCurrentIndex(int index);
|
void setCurrentIndex(int index);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Updates the dock area layout and components visibility
|
||||||
|
*/
|
||||||
|
void updateDockArea();
|
||||||
}; // class DockAreaWidget
|
}; // class DockAreaWidget
|
||||||
}
|
}
|
||||||
// namespace ads
|
// namespace ads
|
||||||
|
@ -39,6 +39,7 @@
|
|||||||
#include "DockManager.h"
|
#include "DockManager.h"
|
||||||
#include "DockAreaWidget.h"
|
#include "DockAreaWidget.h"
|
||||||
#include "DockWidget.h"
|
#include "DockWidget.h"
|
||||||
|
#include "FloatingDockContainer.h"
|
||||||
#include "ads_globals.h"
|
#include "ads_globals.h"
|
||||||
|
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
@ -72,6 +73,7 @@ struct DockContainerWidgetPrivate
|
|||||||
unsigned int zOrderIndex = 0;
|
unsigned int zOrderIndex = 0;
|
||||||
QList<CDockAreaWidget*> DockAreas;
|
QList<CDockAreaWidget*> DockAreas;
|
||||||
QGridLayout* Layout = nullptr;
|
QGridLayout* Layout = nullptr;
|
||||||
|
bool isFloating = false;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Private data constructor
|
* Private data constructor
|
||||||
@ -170,6 +172,7 @@ void DockContainerWidgetPrivate::addDockArea(CDockAreaWidget* NewDockArea, DockW
|
|||||||
}
|
}
|
||||||
|
|
||||||
DockAreas.append(NewDockArea);
|
DockAreas.append(NewDockArea);
|
||||||
|
NewDockArea->updateDockArea();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -212,6 +215,8 @@ CDockContainerWidget::CDockContainerWidget(CDockManager* DockManager, QWidget *p
|
|||||||
QFrame(parent),
|
QFrame(parent),
|
||||||
d(new DockContainerWidgetPrivate(this))
|
d(new DockContainerWidgetPrivate(this))
|
||||||
{
|
{
|
||||||
|
d->isFloating = dynamic_cast<CFloatingDockContainer*>(parent) != 0;
|
||||||
|
|
||||||
//setStyleSheet("background: green;");
|
//setStyleSheet("background: green;");
|
||||||
d->DockManager = DockManager;
|
d->DockManager = DockManager;
|
||||||
if (DockManager != this)
|
if (DockManager != this)
|
||||||
@ -306,6 +311,7 @@ void CDockContainerWidget::addDockArea(CDockAreaWidget* DockAreaWidget,
|
|||||||
//============================================================================
|
//============================================================================
|
||||||
void CDockContainerWidget::removeDockArea(CDockAreaWidget* area)
|
void CDockContainerWidget::removeDockArea(CDockAreaWidget* area)
|
||||||
{
|
{
|
||||||
|
std::cout << "CDockContainerWidget::removeDockArea" << std::endl;
|
||||||
d->DockAreas.removeAll(area);
|
d->DockAreas.removeAll(area);
|
||||||
QSplitter* Splitter = internal::findParent<QSplitter*>(area);
|
QSplitter* Splitter = internal::findParent<QSplitter*>(area);
|
||||||
area->setParent(0);
|
area->setParent(0);
|
||||||
@ -345,6 +351,20 @@ CDockAreaWidget* CDockContainerWidget::dockAreaAt(const QPoint& GlobalPos) const
|
|||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
bool CDockContainerWidget::isFloating() const
|
||||||
|
{
|
||||||
|
return d->isFloating;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
int CDockContainerWidget::dockAreaCount() const
|
||||||
|
{
|
||||||
|
return d->DockAreas.count();
|
||||||
|
}
|
||||||
} // namespace ads
|
} // namespace ads
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
//---------------------------------------------------------------------------
|
||||||
|
@ -104,6 +104,16 @@ public:
|
|||||||
* dock area at this position
|
* dock area at this position
|
||||||
*/
|
*/
|
||||||
CDockAreaWidget* dockAreaAt(const QPoint& GlobalPos) const;
|
CDockAreaWidget* dockAreaAt(const QPoint& GlobalPos) const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the number of dock areas in this container
|
||||||
|
*/
|
||||||
|
int dockAreaCount() const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This function returns true, if this container is in a floating widget
|
||||||
|
*/
|
||||||
|
bool isFloating() const;
|
||||||
}; // class DockContainerWidget
|
}; // class DockContainerWidget
|
||||||
} // namespace ads
|
} // namespace ads
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
|
@ -77,8 +77,8 @@ CDockManager::CDockManager(QWidget *parent) :
|
|||||||
MainWindow->setCentralWidget(this);
|
MainWindow->setCentralWidget(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
d->DockAreaOverlay = new CDockOverlay(this);
|
d->DockAreaOverlay = new CDockOverlay(this, CDockOverlay::ModeDockAreaOverlay);
|
||||||
d->ContainerOverlay = new CDockOverlay(this);
|
d->ContainerOverlay = new CDockOverlay(this, CDockOverlay::ModeContainerOverlay);
|
||||||
d->Containers.append(this);
|
d->Containers.append(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -17,61 +17,185 @@
|
|||||||
******************************************************************************/
|
******************************************************************************/
|
||||||
|
|
||||||
|
|
||||||
//============================================================================
|
|
||||||
/// \file DropOverlay.cpp
|
|
||||||
/// \author Uwe Kindler
|
|
||||||
/// \date 01.03.2017
|
|
||||||
/// \brief Implementation of CDropOverlay class
|
|
||||||
//============================================================================
|
|
||||||
|
|
||||||
|
|
||||||
//============================================================================
|
//============================================================================
|
||||||
// INCLUDES
|
// INCLUDES
|
||||||
//============================================================================
|
//============================================================================
|
||||||
#include "DockOverlay.h"
|
#include "DockOverlay.h"
|
||||||
|
|
||||||
|
#include <QPointer>
|
||||||
|
#include <QPaintEvent>
|
||||||
|
#include <QResizeEvent>
|
||||||
|
#include <QMoveEvent>
|
||||||
|
#include <QPainter>
|
||||||
|
#include <QGridLayout>
|
||||||
|
#include <QCursor>
|
||||||
|
#include <QIcon>
|
||||||
|
#include <QLabel>
|
||||||
|
#include <QtGlobal>
|
||||||
|
#include <QDebug>
|
||||||
|
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
namespace ads
|
namespace ads
|
||||||
{
|
{
|
||||||
|
//============================================================================
|
||||||
|
static QPixmap createDropIndicatorPixmap(const QPalette& pal, const QSizeF& size, DockWidgetArea DockWidgetArea)
|
||||||
|
{
|
||||||
|
const QColor borderColor = pal.color(QPalette::Active, QPalette::Highlight);
|
||||||
|
const QColor backgroundColor = pal.color(QPalette::Active, QPalette::Base);
|
||||||
|
const QColor areaBackgroundColor = pal.color(QPalette::Active, QPalette::Highlight).lighter(150);
|
||||||
|
|
||||||
|
QPixmap pm(size.width(), size.height());
|
||||||
|
pm.fill(QColor(0, 0, 0, 0));
|
||||||
|
|
||||||
|
QPainter p(&pm);
|
||||||
|
QPen pen = p.pen();
|
||||||
|
QRectF baseRect(pm.rect());
|
||||||
|
|
||||||
|
// Fill
|
||||||
|
p.fillRect(baseRect, backgroundColor);
|
||||||
|
|
||||||
|
// Drop area rect.
|
||||||
|
p.save();
|
||||||
|
QRectF areaRect;
|
||||||
|
QLineF areaLine;
|
||||||
|
QLinearGradient gradient;
|
||||||
|
switch (DockWidgetArea)
|
||||||
|
{
|
||||||
|
case TopDockWidgetArea:
|
||||||
|
areaRect = QRectF(baseRect.x(), baseRect.y(), baseRect.width(), baseRect.height() * .5f);
|
||||||
|
areaLine = QLineF(areaRect.bottomLeft(), areaRect.bottomRight());
|
||||||
|
gradient.setStart(areaRect.topLeft());
|
||||||
|
gradient.setFinalStop(areaRect.bottomLeft());
|
||||||
|
break;
|
||||||
|
case RightDockWidgetArea:
|
||||||
|
areaRect = QRectF(baseRect.width() * .5f, baseRect.y(), baseRect.width() * .5f, baseRect.height());
|
||||||
|
areaLine = QLineF(areaRect.topLeft(), areaRect.bottomLeft());
|
||||||
|
gradient.setStart(areaRect.topLeft());
|
||||||
|
gradient.setFinalStop(areaRect.topRight());
|
||||||
|
break;
|
||||||
|
case BottomDockWidgetArea:
|
||||||
|
areaRect = QRectF(baseRect.x(), baseRect.height() * .5f, baseRect.width(), baseRect.height() * .5f);
|
||||||
|
areaLine = QLineF(areaRect.topLeft(), areaRect.topRight());
|
||||||
|
gradient.setStart(areaRect.topLeft());
|
||||||
|
gradient.setFinalStop(areaRect.bottomLeft());
|
||||||
|
break;
|
||||||
|
case LeftDockWidgetArea:
|
||||||
|
areaRect = QRectF(baseRect.x(), baseRect.y(), baseRect.width() * .5f, baseRect.height());
|
||||||
|
areaLine = QLineF(areaRect.topRight(), areaRect.bottomRight());
|
||||||
|
gradient.setStart(areaRect.topLeft());
|
||||||
|
gradient.setFinalStop(areaRect.topRight());
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (areaRect.isValid())
|
||||||
|
{
|
||||||
|
gradient.setColorAt(0.f, areaBackgroundColor);
|
||||||
|
gradient.setColorAt(1.f, areaBackgroundColor.lighter(120));
|
||||||
|
p.fillRect(areaRect, gradient);
|
||||||
|
|
||||||
|
pen = p.pen();
|
||||||
|
pen.setColor(borderColor);
|
||||||
|
pen.setStyle(Qt::DashLine);
|
||||||
|
p.setPen(pen);
|
||||||
|
p.drawLine(areaLine);
|
||||||
|
}
|
||||||
|
p.restore();
|
||||||
|
|
||||||
|
p.save();
|
||||||
|
pen = p.pen();
|
||||||
|
pen.setColor(borderColor);
|
||||||
|
pen.setWidth(1);
|
||||||
|
|
||||||
|
p.setPen(pen);
|
||||||
|
p.drawRect(baseRect.adjusted(0, 0, -pen.width(), -pen.width()));
|
||||||
|
p.restore();
|
||||||
|
return pm;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
QWidget* createDropIndicatorWidget(DockWidgetArea DockWidgetArea)
|
||||||
|
{
|
||||||
|
QLabel* l = new QLabel();
|
||||||
|
l->setObjectName("DockWidgetAreaLabel");
|
||||||
|
|
||||||
|
const qreal metric = static_cast<qreal>(l->fontMetrics().height()) * 2.f;
|
||||||
|
const QSizeF size(metric, metric);
|
||||||
|
|
||||||
|
l->setPixmap(createDropIndicatorPixmap(l->palette(), size, DockWidgetArea));
|
||||||
|
l->setWindowFlags(Qt::Tool | Qt::FramelessWindowHint);
|
||||||
|
l->setAttribute(Qt::WA_TranslucentBackground);
|
||||||
|
return l;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Private data class of CDropOverlay class (pimpl)
|
* Private data class of CDockOverlay
|
||||||
*/
|
*/
|
||||||
struct DockOverlayPrivate
|
struct DockOverlayPrivate
|
||||||
{
|
{
|
||||||
CDockOverlay* _this;
|
CDockOverlay* _this;
|
||||||
|
DockWidgetAreas AllowedAreas = InvalidDockWidgetArea;
|
||||||
|
CDockOverlayCross* Cross;
|
||||||
|
QPointer<QWidget> TargetWidget;
|
||||||
|
QRect TargetRect;
|
||||||
|
DockWidgetArea LastLocation = InvalidDockWidgetArea;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Private data constructor
|
* Private data constructor
|
||||||
*/
|
*/
|
||||||
DockOverlayPrivate(CDockOverlay* _public);
|
DockOverlayPrivate(CDockOverlay* _public) : _this(_public) {}
|
||||||
};
|
};
|
||||||
// struct DropOverlayPrivate
|
|
||||||
|
|
||||||
//============================================================================
|
/**
|
||||||
DockOverlayPrivate::DockOverlayPrivate(CDockOverlay* _public) :
|
* Private data of CDockOverlayCross class
|
||||||
_this(_public)
|
*/
|
||||||
|
struct DockOverlayCrossPrivate
|
||||||
{
|
{
|
||||||
|
CDockOverlayCross* _this;
|
||||||
|
CDockOverlay::eMode Mode = CDockOverlay::ModeDockAreaOverlay;
|
||||||
|
CDockOverlay* DockOverlay;
|
||||||
|
QHash<DockWidgetArea, QWidget*> DropIndicatorWidgets;
|
||||||
|
QGridLayout* GridLayout;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Private data constructor
|
||||||
|
*/
|
||||||
|
DockOverlayCrossPrivate(CDockOverlayCross* _public) : _this(_public) {}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param area
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
QPoint areaGridPosition(const DockWidgetArea area);
|
||||||
|
};
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
//============================================================================
|
//============================================================================
|
||||||
CDockOverlay::CDockOverlay(QWidget *parent) :
|
CDockOverlay::CDockOverlay(QWidget* parent, eMode Mode) :
|
||||||
QFrame(parent),
|
QFrame(parent),
|
||||||
d(new DockOverlayPrivate(this))
|
d(new DockOverlayPrivate(this))
|
||||||
{
|
{
|
||||||
setStyleSheet("ads--CDockOverlay {background: palette(highlight);}");
|
d->Cross = new CDockOverlayCross(this);
|
||||||
setWindowFlags(Qt::Tool | Qt::FramelessWindowHint);
|
setWindowFlags(Qt::Tool | Qt::FramelessWindowHint);
|
||||||
setWindowOpacity(0.2);
|
setWindowOpacity(0.2);
|
||||||
setWindowTitle("DockOverlay");
|
setWindowTitle("DockOverlay");
|
||||||
//setAttribute(Qt::WA_NoSystemBackground);
|
setAttribute(Qt::WA_NoSystemBackground);
|
||||||
//setAttribute(Qt::WA_TranslucentBackground);
|
setAttribute(Qt::WA_TranslucentBackground);
|
||||||
|
|
||||||
setAttribute(Qt::WA_TransparentForMouseEvents);
|
QBoxLayout* l = new QBoxLayout(QBoxLayout::TopToBottom);
|
||||||
setWindowFlags(windowFlags() | Qt::WindowTransparentForInput);
|
l->setSpacing(0);
|
||||||
|
setLayout(l);
|
||||||
|
|
||||||
|
d->Cross->setupOverlayCross(Mode);
|
||||||
|
d->Cross->setVisible(false);
|
||||||
setVisible(false);
|
setVisible(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
//============================================================================
|
//============================================================================
|
||||||
CDockOverlay::~CDockOverlay()
|
CDockOverlay::~CDockOverlay()
|
||||||
{
|
{
|
||||||
@ -79,22 +203,344 @@ CDockOverlay::~CDockOverlay()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
void CDockOverlay::setAllowedAreas(DockWidgetAreas areas)
|
||||||
|
{
|
||||||
|
if (areas == d->AllowedAreas)
|
||||||
|
return;
|
||||||
|
d->AllowedAreas = areas;
|
||||||
|
d->Cross->reset();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
DockWidgetAreas CDockOverlay::allowedAreas() const
|
||||||
|
{
|
||||||
|
return d->AllowedAreas;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
DockWidgetArea CDockOverlay::dropAreaUnderCursor() const
|
||||||
|
{
|
||||||
|
return d->Cross->cursorLocation();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
//============================================================================
|
//============================================================================
|
||||||
DockWidgetArea CDockOverlay::showOverlay(QWidget* target)
|
DockWidgetArea CDockOverlay::showOverlay(QWidget* target)
|
||||||
{
|
{
|
||||||
std::cout << "CDockOverlay::showOverlay" << std::endl;
|
//std::cout << "CDockOverlay::showDockOverlay(QWidget* target)" << std::endl;
|
||||||
|
if (d->TargetWidget == target)
|
||||||
|
{
|
||||||
|
qInfo() << "_target == target";
|
||||||
|
// Hint: We could update geometry of overlay here.
|
||||||
|
DockWidgetArea da = dropAreaUnderCursor();
|
||||||
|
if (da != d->LastLocation)
|
||||||
|
{
|
||||||
|
qInfo() << "repaint()";
|
||||||
|
repaint();
|
||||||
|
d->LastLocation = da;
|
||||||
|
}
|
||||||
|
return da;
|
||||||
|
}
|
||||||
|
|
||||||
|
d->TargetWidget = target;
|
||||||
|
d->TargetRect = QRect();
|
||||||
|
d->LastLocation = InvalidDockWidgetArea;
|
||||||
|
|
||||||
|
// Move it over the target.
|
||||||
resize(target->size());
|
resize(target->size());
|
||||||
move(target->mapToGlobal(target->rect().topLeft()));
|
move(target->mapToGlobal(target->rect().topLeft()));
|
||||||
this->show();
|
show();
|
||||||
return NoDockWidgetArea;
|
return dropAreaUnderCursor();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
void CDockOverlay::showOverlay(QWidget* target, const QRect& targetAreaRect)
|
||||||
|
{
|
||||||
|
qInfo() << "CDockOverlay::showDockOverlay(QWidget* target, const QRect& targetAreaRect)";
|
||||||
|
if (d->TargetWidget == target && d->TargetRect == targetAreaRect)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
//hideDockOverlay();
|
||||||
|
d->TargetWidget = target;
|
||||||
|
d->TargetRect = targetAreaRect;
|
||||||
|
d->LastLocation = InvalidDockWidgetArea;
|
||||||
|
|
||||||
|
// Move it over the target's area.
|
||||||
|
resize(targetAreaRect.size());
|
||||||
|
move(target->mapToGlobal(QPoint(targetAreaRect.x(), targetAreaRect.y())));
|
||||||
|
show();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
//============================================================================
|
//============================================================================
|
||||||
void CDockOverlay::hideOverlay()
|
void CDockOverlay::hideOverlay()
|
||||||
{
|
{
|
||||||
this->hide();
|
qInfo() << "hideDockOverlay() _fullAreaDrop = false";
|
||||||
|
hide();
|
||||||
|
d->TargetWidget.clear();
|
||||||
|
d->TargetRect = QRect();
|
||||||
|
d->LastLocation = InvalidDockWidgetArea;
|
||||||
}
|
}
|
||||||
} // namespace ads
|
|
||||||
|
|
||||||
//---------------------------------------------------------------------------
|
|
||||||
// EOF DropOverlay.cpp
|
//============================================================================
|
||||||
|
void CDockOverlay::paintEvent(QPaintEvent*)
|
||||||
|
{
|
||||||
|
// Draw rect based on location
|
||||||
|
QRect r = rect();
|
||||||
|
const DockWidgetArea da = dropAreaUnderCursor();
|
||||||
|
std::cout << "CursorLocation: " << dropAreaUnderCursor() << std::endl;
|
||||||
|
switch (da)
|
||||||
|
{
|
||||||
|
case TopDockWidgetArea: r.setHeight(r.height() / 2); break;
|
||||||
|
case RightDockWidgetArea: r.setX(r.width() / 2); break;
|
||||||
|
case BottomDockWidgetArea: r.setY(r.height() / 2); break;
|
||||||
|
case LeftDockWidgetArea: r.setWidth(r.width() / 2); break;
|
||||||
|
case CenterDockWidgetArea: r = rect();break;
|
||||||
|
default: return;
|
||||||
|
}
|
||||||
|
QPainter painter(this);
|
||||||
|
QColor Color = palette().color(QPalette::Active, QPalette::Highlight);
|
||||||
|
painter.fillRect(r, QBrush(Color, Qt::Dense4Pattern));
|
||||||
|
painter.setBrush(QBrush(Color));
|
||||||
|
painter.drawRect(r);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
void CDockOverlay::showEvent(QShowEvent*)
|
||||||
|
{
|
||||||
|
d->Cross->show();
|
||||||
|
QWidget* w = parentWidget() ? parentWidget() : d->TargetWidget.data();
|
||||||
|
QRect WidgetRect = w->rect();
|
||||||
|
QPoint Pos(WidgetRect.left(), WidgetRect.center().y());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
void CDockOverlay::hideEvent(QHideEvent*)
|
||||||
|
{
|
||||||
|
d->Cross->hide();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
void CDockOverlay::resizeEvent(QResizeEvent* e)
|
||||||
|
{
|
||||||
|
qInfo() << "CDockOverlay::resizeEvent" << e->size();
|
||||||
|
d->Cross->resize(e->size());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
void CDockOverlay::moveEvent(QMoveEvent* e)
|
||||||
|
{
|
||||||
|
qInfo() << "CDockOverlay::moveEvent" << e->pos();
|
||||||
|
d->Cross->move(e->pos());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
static int areaAlignment(const DockWidgetArea area)
|
||||||
|
{
|
||||||
|
switch (area)
|
||||||
|
{
|
||||||
|
case TopDockWidgetArea: return (int) Qt::AlignHCenter | Qt::AlignBottom;
|
||||||
|
case RightDockWidgetArea: return (int) Qt::AlignLeft | Qt::AlignVCenter;
|
||||||
|
case BottomDockWidgetArea: return (int) Qt::AlignHCenter | Qt::AlignTop;
|
||||||
|
case LeftDockWidgetArea: return (int) Qt::AlignRight | Qt::AlignVCenter;
|
||||||
|
case CenterDockWidgetArea: return (int) Qt::AlignCenter;
|
||||||
|
default: return Qt::AlignCenter;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
// DockOverlayCrossPrivate
|
||||||
|
//============================================================================
|
||||||
|
QPoint DockOverlayCrossPrivate::areaGridPosition(const DockWidgetArea area)
|
||||||
|
{
|
||||||
|
if (CDockOverlay::ModeDockAreaOverlay == Mode)
|
||||||
|
{
|
||||||
|
switch (area)
|
||||||
|
{
|
||||||
|
case TopDockWidgetArea: return QPoint(1, 2);
|
||||||
|
case RightDockWidgetArea: return QPoint(2, 3);
|
||||||
|
case BottomDockWidgetArea: return QPoint(3, 2);
|
||||||
|
case LeftDockWidgetArea: return QPoint(2, 1);
|
||||||
|
case CenterDockWidgetArea: return QPoint(2, 2);
|
||||||
|
default: return QPoint();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
switch (area)
|
||||||
|
{
|
||||||
|
case TopDockWidgetArea: return QPoint(0, 2);
|
||||||
|
case RightDockWidgetArea: return QPoint(2, 4);
|
||||||
|
case BottomDockWidgetArea: return QPoint(4, 2);
|
||||||
|
case LeftDockWidgetArea: return QPoint(2, 0);
|
||||||
|
case CenterDockWidgetArea: return QPoint(2, 2);
|
||||||
|
default: return QPoint();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
CDockOverlayCross::CDockOverlayCross(CDockOverlay* overlay) :
|
||||||
|
QWidget(overlay->parentWidget()),
|
||||||
|
d(new DockOverlayCrossPrivate(this))
|
||||||
|
{
|
||||||
|
d->DockOverlay = overlay;
|
||||||
|
setWindowFlags(Qt::Tool | Qt::FramelessWindowHint);
|
||||||
|
setWindowTitle("DockOverlayCross");
|
||||||
|
setAttribute(Qt::WA_TranslucentBackground);
|
||||||
|
|
||||||
|
d->GridLayout = new QGridLayout();
|
||||||
|
d->GridLayout->setSpacing(6);
|
||||||
|
setLayout(d->GridLayout);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
CDockOverlayCross::~CDockOverlayCross()
|
||||||
|
{
|
||||||
|
delete d;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
void CDockOverlayCross::setupOverlayCross(CDockOverlay::eMode Mode)
|
||||||
|
{
|
||||||
|
d->Mode = Mode;
|
||||||
|
|
||||||
|
QHash<DockWidgetArea, QWidget*> areaWidgets;
|
||||||
|
areaWidgets.insert(TopDockWidgetArea, createDropIndicatorWidget(TopDockWidgetArea));
|
||||||
|
areaWidgets.insert(RightDockWidgetArea, createDropIndicatorWidget(RightDockWidgetArea));
|
||||||
|
areaWidgets.insert(BottomDockWidgetArea, createDropIndicatorWidget(BottomDockWidgetArea));
|
||||||
|
areaWidgets.insert(LeftDockWidgetArea, createDropIndicatorWidget(LeftDockWidgetArea));
|
||||||
|
areaWidgets.insert(CenterDockWidgetArea, createDropIndicatorWidget(CenterDockWidgetArea));
|
||||||
|
|
||||||
|
setAreaWidgets(areaWidgets);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
void CDockOverlayCross::setAreaWidgets(const QHash<DockWidgetArea, QWidget*>& widgets)
|
||||||
|
{
|
||||||
|
// Delete old widgets.
|
||||||
|
QMutableHashIterator<DockWidgetArea, QWidget*> i(d->DropIndicatorWidgets);
|
||||||
|
while (i.hasNext())
|
||||||
|
{
|
||||||
|
i.next();
|
||||||
|
QWidget* widget = i.value();
|
||||||
|
d->GridLayout->removeWidget(widget);
|
||||||
|
delete widget;
|
||||||
|
i.remove();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Insert new widgets into grid.
|
||||||
|
d->DropIndicatorWidgets = widgets;
|
||||||
|
QHashIterator<DockWidgetArea, QWidget*> i2(d->DropIndicatorWidgets);
|
||||||
|
while (i2.hasNext())
|
||||||
|
{
|
||||||
|
i2.next();
|
||||||
|
const DockWidgetArea area = i2.key();
|
||||||
|
QWidget* widget = i2.value();
|
||||||
|
QPoint p = d->areaGridPosition(area);
|
||||||
|
d->GridLayout->addWidget(widget, p.x(), p.y(), (Qt::Alignment) areaAlignment(area));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (CDockOverlay::ModeDockAreaOverlay == d->Mode)
|
||||||
|
{
|
||||||
|
d->GridLayout->setContentsMargins(0, 0, 0, 0);
|
||||||
|
d->GridLayout->setRowStretch(0, 1);
|
||||||
|
d->GridLayout->setRowStretch(1, 0);
|
||||||
|
d->GridLayout->setRowStretch(2, 0);
|
||||||
|
d->GridLayout->setRowStretch(3, 0);
|
||||||
|
d->GridLayout->setRowStretch(4, 1);
|
||||||
|
|
||||||
|
d->GridLayout->setColumnStretch(0, 1);
|
||||||
|
d->GridLayout->setColumnStretch(1, 0);
|
||||||
|
d->GridLayout->setColumnStretch(2, 0);
|
||||||
|
d->GridLayout->setColumnStretch(3, 0);
|
||||||
|
d->GridLayout->setColumnStretch(4, 1);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
d->GridLayout->setContentsMargins(4, 4, 4, 4);
|
||||||
|
d->GridLayout->setRowStretch(0, 0);
|
||||||
|
d->GridLayout->setRowStretch(1, 1);
|
||||||
|
d->GridLayout->setRowStretch(2, 1);
|
||||||
|
d->GridLayout->setRowStretch(3, 1);
|
||||||
|
d->GridLayout->setRowStretch(4, 0);
|
||||||
|
|
||||||
|
d->GridLayout->setColumnStretch(0, 0);
|
||||||
|
d->GridLayout->setColumnStretch(1, 1);
|
||||||
|
d->GridLayout->setColumnStretch(2, 1);
|
||||||
|
d->GridLayout->setColumnStretch(3, 1);
|
||||||
|
d->GridLayout->setColumnStretch(4, 0);
|
||||||
|
}
|
||||||
|
reset();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
DockWidgetArea CDockOverlayCross::cursorLocation() const
|
||||||
|
{
|
||||||
|
const QPoint pos = mapFromGlobal(QCursor::pos());
|
||||||
|
QHashIterator<DockWidgetArea, QWidget*> i(d->DropIndicatorWidgets);
|
||||||
|
while (i.hasNext())
|
||||||
|
{
|
||||||
|
i.next();
|
||||||
|
if (d->DockOverlay->allowedAreas().testFlag(i.key())
|
||||||
|
&& i.value()
|
||||||
|
&& i.value()->isVisible()
|
||||||
|
&& i.value()->geometry().contains(pos))
|
||||||
|
{
|
||||||
|
return i.key();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return InvalidDockWidgetArea;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
void CDockOverlayCross::showEvent(QShowEvent*)
|
||||||
|
{
|
||||||
|
resize(d->DockOverlay->size());
|
||||||
|
move(d->DockOverlay->pos());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
void CDockOverlayCross::reset()
|
||||||
|
{
|
||||||
|
QList<DockWidgetArea> allAreas;
|
||||||
|
allAreas << TopDockWidgetArea << RightDockWidgetArea
|
||||||
|
<< BottomDockWidgetArea << LeftDockWidgetArea << CenterDockWidgetArea;
|
||||||
|
const DockWidgetAreas allowedAreas = d->DockOverlay->allowedAreas();
|
||||||
|
|
||||||
|
// Update visibility of area widgets based on allowedAreas.
|
||||||
|
for (int i = 0; i < allAreas.count(); ++i)
|
||||||
|
{
|
||||||
|
QPoint p = d->areaGridPosition(allAreas.at(i));
|
||||||
|
QLayoutItem* item = d->GridLayout->itemAtPosition(p.x(), p.y());
|
||||||
|
QWidget* w = nullptr;
|
||||||
|
if (item && (w = item->widget()) != nullptr)
|
||||||
|
{
|
||||||
|
w->setVisible(allowedAreas.testFlag(allAreas.at(i)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace ads
|
||||||
|
//----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
@ -19,58 +19,139 @@
|
|||||||
******************************************************************************/
|
******************************************************************************/
|
||||||
|
|
||||||
|
|
||||||
//============================================================================
|
|
||||||
/// \file DockOverlay.h
|
|
||||||
/// \author Uwe Kindler
|
|
||||||
/// \date 01.03.2017
|
|
||||||
/// \brief Declaration of CDockOverlay class
|
|
||||||
//============================================================================
|
|
||||||
|
|
||||||
|
|
||||||
//============================================================================
|
//============================================================================
|
||||||
// INCLUDES
|
// INCLUDES
|
||||||
//============================================================================
|
//============================================================================
|
||||||
|
#include <QPointer>
|
||||||
|
#include <QHash>
|
||||||
|
#include <QRect>
|
||||||
#include <QFrame>
|
#include <QFrame>
|
||||||
|
class QGridLayout;
|
||||||
|
|
||||||
#include "ads_globals.h"
|
#include "ads_globals.h"
|
||||||
|
|
||||||
namespace ads
|
namespace ads
|
||||||
{
|
{
|
||||||
struct DockOverlayPrivate;
|
struct DockOverlayPrivate;
|
||||||
|
class CDockOverlayCross;
|
||||||
|
|
||||||
/**
|
/*!
|
||||||
* DockOverlay paints a translucent rectangle over another widget. The geometry
|
* DockOverlay paints a translucent rectangle over another widget. The geometry
|
||||||
* of the rectangle is based on drop area at the mouse location.
|
* of the rectangle is based on the mouse location.
|
||||||
*/
|
*/
|
||||||
class CDockOverlay : public QFrame
|
class CDockOverlay : public QFrame
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
private:
|
private:
|
||||||
DockOverlayPrivate* d; ///< private data (pimpl)
|
DockOverlayPrivate* d; //< private data class
|
||||||
friend class DockOverlayPrivate;
|
friend class DockOverlayPrivate;
|
||||||
protected:
|
friend class DockOverlayCross;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
/**
|
enum eMode
|
||||||
* Default Constructor
|
{
|
||||||
*/
|
ModeDockAreaOverlay,
|
||||||
CDockOverlay(QWidget* parent = 0);
|
ModeContainerOverlay
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Virtual Destructor
|
* Creates a dock overlay
|
||||||
|
*/
|
||||||
|
CDockOverlay(QWidget* parent, eMode Mode = ModeDockAreaOverlay);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Virtual destructor
|
||||||
*/
|
*/
|
||||||
virtual ~CDockOverlay();
|
virtual ~CDockOverlay();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Shows the dock overlay for the given target widget
|
* Configures the areas that are allowed for docking
|
||||||
|
*/
|
||||||
|
void setAllowedAreas(DockWidgetAreas areas);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns flags with all allowed drop areas
|
||||||
|
*/
|
||||||
|
DockWidgetAreas allowedAreas() const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the drop area under the current cursor location
|
||||||
|
*/
|
||||||
|
DockWidgetArea dropAreaUnderCursor() const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Show the drop overly for the given target widget
|
||||||
*/
|
*/
|
||||||
DockWidgetArea showOverlay(QWidget* target);
|
DockWidgetArea showOverlay(QWidget* target);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Hides this verlay
|
* Show drop overlay for the given target widget and the given rectangle
|
||||||
|
*/
|
||||||
|
void showOverlay(QWidget* target, const QRect& targetAreaRect);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Hides the overlay
|
||||||
*/
|
*/
|
||||||
void hideOverlay();
|
void hideOverlay();
|
||||||
}; // class DockOverlay
|
|
||||||
}
|
protected:
|
||||||
// namespace ads
|
virtual void paintEvent(QPaintEvent *e) override;
|
||||||
//-----------------------------------------------------------------------------
|
virtual void showEvent(QShowEvent* e) override;
|
||||||
|
virtual void hideEvent(QHideEvent* e) override;
|
||||||
|
virtual void resizeEvent(QResizeEvent* e) override;
|
||||||
|
virtual void moveEvent(QMoveEvent* e) override;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
struct DockOverlayCrossPrivate;
|
||||||
|
/*!
|
||||||
|
* DockOverlayCross shows a cross with 5 different drop area possibilities.
|
||||||
|
* I could have handled everything inside DockOverlay, but because of some
|
||||||
|
* styling issues it's better to have a separate class for the cross.
|
||||||
|
*/
|
||||||
|
class CDockOverlayCross : public QWidget
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
private:
|
||||||
|
DockOverlayCrossPrivate* d;
|
||||||
|
friend class DockOverlayCrossPrivate;
|
||||||
|
friend class CDockOverlay;
|
||||||
|
|
||||||
|
public:
|
||||||
|
/**
|
||||||
|
* Creates an overlay corss for the given overlay
|
||||||
|
*/
|
||||||
|
CDockOverlayCross(CDockOverlay* overlay);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Virtual destructor
|
||||||
|
*/
|
||||||
|
virtual ~CDockOverlayCross();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the dock widget area depending on the current cursor location.
|
||||||
|
* The function checks, if the mouse cursor is inside of any drop indicator
|
||||||
|
* widget and returns the corresponding DockWidgetArea.
|
||||||
|
*/
|
||||||
|
DockWidgetArea cursorLocation() const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Sets up the overlay cross for the given overlay mode
|
||||||
|
*/
|
||||||
|
void setupOverlayCross(CDockOverlay::eMode Mode);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Resets and updates the
|
||||||
|
*/
|
||||||
|
void reset();
|
||||||
|
|
||||||
|
protected:
|
||||||
|
virtual void showEvent(QShowEvent* e) override;
|
||||||
|
void setAreaWidgets(const QHash<DockWidgetArea, QWidget*>& widgets);
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
}; // CDockOverlayCross
|
||||||
|
|
||||||
|
} // namespace ads
|
||||||
#endif // DockOverlayH
|
#endif // DockOverlayH
|
||||||
|
@ -43,6 +43,8 @@
|
|||||||
#include "DockWidget.h"
|
#include "DockWidget.h"
|
||||||
#include "DockAreaWidget.h"
|
#include "DockAreaWidget.h"
|
||||||
#include "FloatingDockContainer.h"
|
#include "FloatingDockContainer.h"
|
||||||
|
#include "DockOverlay.h"
|
||||||
|
#include "DockManager.h"
|
||||||
|
|
||||||
namespace ads
|
namespace ads
|
||||||
{
|
{
|
||||||
@ -107,8 +109,10 @@ struct DockWidgetTitleBarPrivate
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Starts floating of the dock widget that belongs to this title bar
|
* Starts floating of the dock widget that belongs to this title bar
|
||||||
|
* Returns true, if floating has been started and false if floating
|
||||||
|
* is not possible for any reason
|
||||||
*/
|
*/
|
||||||
void startFloating(const QPoint& GlobalPos);
|
bool startFloating(const QPoint& GlobalPos);
|
||||||
};
|
};
|
||||||
// struct DockWidgetTitleBarPrivate
|
// struct DockWidgetTitleBarPrivate
|
||||||
|
|
||||||
@ -153,8 +157,21 @@ void DockWidgetTitleBarPrivate::moveTab(QMouseEvent* ev)
|
|||||||
|
|
||||||
|
|
||||||
//============================================================================
|
//============================================================================
|
||||||
void DockWidgetTitleBarPrivate::startFloating(const QPoint& GlobalPos)
|
bool DockWidgetTitleBarPrivate::startFloating(const QPoint& GlobalPos)
|
||||||
{
|
{
|
||||||
|
std::cout << "isFloating " << DockWidget->dockContainer()->isFloating() << std::endl;
|
||||||
|
std::cout << "areaCount " << DockWidget->dockContainer()->dockAreaCount() << std::endl;
|
||||||
|
std::cout << "widgetCount " << DockWidget->dockAreaWidget()->count() << std::endl;
|
||||||
|
// if this is the last dock widget inside of this floating widget,
|
||||||
|
// then it does not make any sense, to make if floating because
|
||||||
|
// it is already floating
|
||||||
|
if (DockWidget->dockContainer()->isFloating()
|
||||||
|
&& (DockWidget->dockContainer()->dockAreaCount() == 1)
|
||||||
|
&& (DockWidget->dockAreaWidget()->count() == 1))
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
std::cout << "startFloating" << std::endl;
|
std::cout << "startFloating" << std::endl;
|
||||||
DragState = DraggingFloatingWidget;
|
DragState = DraggingFloatingWidget;
|
||||||
QSize Size = DockArea->size();
|
QSize Size = DockArea->size();
|
||||||
@ -166,6 +183,7 @@ void DockWidgetTitleBarPrivate::startFloating(const QPoint& GlobalPos)
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
std::cout << "DockWidgetTitleBarPrivate::startFloating DockArea" << std::endl;
|
||||||
// If section widget has only one content widget, we can move the complete
|
// If section widget has only one content widget, we can move the complete
|
||||||
// section widget into floating widget
|
// section widget into floating widget
|
||||||
auto splitter = internal::findParent<QSplitter*>(DockArea);
|
auto splitter = internal::findParent<QSplitter*>(DockArea);
|
||||||
@ -173,13 +191,9 @@ void DockWidgetTitleBarPrivate::startFloating(const QPoint& GlobalPos)
|
|||||||
}
|
}
|
||||||
|
|
||||||
FloatingWidget->startFloating(DragStartMousePosition, Size);
|
FloatingWidget->startFloating(DragStartMousePosition, Size);
|
||||||
|
auto Overlay = DockWidget->dockManager()->containerOverlay();
|
||||||
/*
|
Overlay->setAllowedAreas(OuterDockAreas);
|
||||||
* DropOverlay* ContainerDropOverlay = cw->dropOverlay();
|
return true;
|
||||||
ContainerDropOverlay->setAllowedAreas(OuterAreas);
|
|
||||||
ContainerDropOverlay->showDropOverlay(this);
|
|
||||||
ContainerDropOverlay->raise();
|
|
||||||
*/
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -188,6 +202,7 @@ CDockWidgetTitleBar::CDockWidgetTitleBar(CDockWidget* DockWidget, QWidget *paren
|
|||||||
QFrame(parent),
|
QFrame(parent),
|
||||||
d(new DockWidgetTitleBarPrivate(this))
|
d(new DockWidgetTitleBarPrivate(this))
|
||||||
{
|
{
|
||||||
|
setAttribute(Qt::WA_NoMousePropagation, true);
|
||||||
d->DockWidget = DockWidget;
|
d->DockWidget = DockWidget;
|
||||||
d->createLayout();
|
d->createLayout();
|
||||||
}
|
}
|
||||||
@ -271,9 +286,12 @@ void CDockWidgetTitleBar::mouseMoveEvent(QMouseEvent* ev)
|
|||||||
if (!MouseInsideTitleArea)
|
if (!MouseInsideTitleArea)
|
||||||
{
|
{
|
||||||
d->startFloating(ev->globalPos());
|
d->startFloating(ev->globalPos());
|
||||||
return;
|
// do not delegate handling of mouse move event base class to prevent
|
||||||
|
// move events for the title area
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
else if ((ev->pos() - d->DragStartMousePosition).manhattanLength() >= QApplication::startDragDistance()) // Wait a few pixels before start moving
|
else if (d->DockArea->count() > 1
|
||||||
|
&& (ev->pos() - d->DragStartMousePosition).manhattanLength() >= QApplication::startDragDistance()) // Wait a few pixels before start moving
|
||||||
{
|
{
|
||||||
d->DragState = DraggingTab;
|
d->DragState = DraggingTab;
|
||||||
return;
|
return;
|
||||||
|
@ -84,16 +84,16 @@ FloatingDockContainerPrivate::FloatingDockContainerPrivate(CFloatingDockContaine
|
|||||||
void FloatingDockContainerPrivate::titleMouseReleaseEvent()
|
void FloatingDockContainerPrivate::titleMouseReleaseEvent()
|
||||||
{
|
{
|
||||||
setDraggingActive(false);
|
setDraggingActive(false);
|
||||||
/*if (!m_DropContainer)
|
if (!DropContainer)
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::cout << "Dropped" << std::endl;
|
std::cout << "Dropped" << std::endl;
|
||||||
CMainContainerWidget* MainContainerWidget = mainContainerWidget();
|
/*CMainContainerWidget* MainContainerWidget = mainContainerWidget();
|
||||||
m_DropContainer->dropFloatingWidget(this, QCursor::pos());
|
m_DropContainer->dropFloatingWidget(this, QCursor::pos());*/
|
||||||
MainContainerWidget->dropOverlay()->hideDropOverlay();
|
DockManager->containerOverlay()->hideOverlay();
|
||||||
MainContainerWidget->sectionDropOverlay()->hideDropOverlay();*/
|
DockManager->dockAreaOverlay()->hideOverlay();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -123,7 +123,6 @@ void FloatingDockContainerPrivate::updateDropOverlays(const QPoint& GlobalPos)
|
|||||||
QPoint MappedPos = ContainerWidget->mapFromGlobal(GlobalPos);
|
QPoint MappedPos = ContainerWidget->mapFromGlobal(GlobalPos);
|
||||||
if (ContainerWidget->rect().contains(MappedPos))
|
if (ContainerWidget->rect().contains(MappedPos))
|
||||||
{
|
{
|
||||||
std::cout << "Container " << ContainerWidget << " contains mousepos" << std::endl;
|
|
||||||
if (!TopContainer || ContainerWidget->isInFrontOf(TopContainer))
|
if (!TopContainer || ContainerWidget->isInFrontOf(TopContainer))
|
||||||
{
|
{
|
||||||
TopContainer = ContainerWidget;
|
TopContainer = ContainerWidget;
|
||||||
@ -148,7 +147,7 @@ void FloatingDockContainerPrivate::updateDropOverlays(const QPoint& GlobalPos)
|
|||||||
auto DockArea = TopContainer->dockAreaAt(GlobalPos);
|
auto DockArea = TopContainer->dockAreaAt(GlobalPos);
|
||||||
if (DockArea)
|
if (DockArea)
|
||||||
{
|
{
|
||||||
//SectionOverlay->setAllowedAreas(AllAreas);
|
DockAreaOverlay->setAllowedAreas(AllDockAreas);
|
||||||
DockAreaOverlay->showOverlay(DockArea);
|
DockAreaOverlay->showOverlay(DockArea);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -172,22 +171,7 @@ void FloatingDockContainerPrivate::updateDropOverlays(const QPoint& GlobalPos)
|
|||||||
//============================================================================
|
//============================================================================
|
||||||
void FloatingDockContainerPrivate::setDraggingActive(bool Active)
|
void FloatingDockContainerPrivate::setDraggingActive(bool Active)
|
||||||
{
|
{
|
||||||
if (DraggingActive == Active)
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
DraggingActive = Active;
|
DraggingActive = Active;
|
||||||
if (Active)
|
|
||||||
{
|
|
||||||
std::cout << "FloatingWidget:: InstallEventFilter" << std::endl;
|
|
||||||
qApp->installEventFilter(_this);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
std::cout << "FloatingWidget:: RemoveEventFilter" << std::endl;
|
|
||||||
qApp->removeEventFilter(_this);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -205,6 +189,8 @@ CFloatingDockContainer::CFloatingDockContainer(CDockManager* DockManager) :
|
|||||||
d->DockContainer = new CDockContainerWidget(DockManager, this);
|
d->DockContainer = new CDockContainerWidget(DockManager, this);
|
||||||
l->addWidget(d->DockContainer);
|
l->addWidget(d->DockContainer);
|
||||||
DockManager->registerFloatingWidget(this);
|
DockManager->registerFloatingWidget(this);
|
||||||
|
|
||||||
|
qApp->installEventFilter(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -45,6 +45,7 @@ enum DockWidgetArea
|
|||||||
BottomDockWidgetArea = 0x08,
|
BottomDockWidgetArea = 0x08,
|
||||||
CenterDockWidgetArea = 0x10,
|
CenterDockWidgetArea = 0x10,
|
||||||
|
|
||||||
|
InvalidDockWidgetArea = NoDockWidgetArea,
|
||||||
OuterDockAreas = TopDockWidgetArea | LeftDockWidgetArea | RightDockWidgetArea | BottomDockWidgetArea,
|
OuterDockAreas = TopDockWidgetArea | LeftDockWidgetArea | RightDockWidgetArea | BottomDockWidgetArea,
|
||||||
AllDockAreas = OuterDockAreas | CenterDockWidgetArea
|
AllDockAreas = OuterDockAreas | CenterDockWidgetArea
|
||||||
};
|
};
|
||||||
|
Loading…
Reference in New Issue
Block a user