mirror of
https://github.com/githubuser0xFFFF/Qt-Advanced-Docking-System.git
synced 2024-11-15 13:15:43 +08:00
Adds drop functionality for outer areas
This commit is contained in:
parent
acd549d6a6
commit
863d3233ad
@ -57,4 +57,21 @@ QSplitter* findParentSplitter(class QWidget* w)
|
|||||||
return cw;
|
return cw;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QSplitter* findImmediateSplitter(class QWidget* w)
|
||||||
|
{
|
||||||
|
QSplitter* sp = NULL;
|
||||||
|
QLayout* l = w->layout();
|
||||||
|
if (!l || l->count() <= 0)
|
||||||
|
return sp;
|
||||||
|
for (int i = 0; i < l->count(); ++i)
|
||||||
|
{
|
||||||
|
QLayoutItem* li = l->itemAt(0);
|
||||||
|
if (!li->widget())
|
||||||
|
continue;
|
||||||
|
if ((sp = dynamic_cast<QSplitter*>(li->widget())) != NULL)
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
return sp;
|
||||||
|
}
|
||||||
|
|
||||||
ADS_NAMESPACE_END
|
ADS_NAMESPACE_END
|
@ -79,6 +79,7 @@ public:
|
|||||||
class ContainerWidget* findParentContainerWidget(class QWidget* w);
|
class ContainerWidget* findParentContainerWidget(class QWidget* w);
|
||||||
class SectionWidget* findParentSectionWidget(class QWidget* w);
|
class SectionWidget* findParentSectionWidget(class QWidget* w);
|
||||||
QSplitter* findParentSplitter(class QWidget* w);
|
QSplitter* findParentSplitter(class QWidget* w);
|
||||||
|
QSplitter* findImmediateSplitter(class QWidget* w);
|
||||||
|
|
||||||
ADS_NAMESPACE_END
|
ADS_NAMESPACE_END
|
||||||
|
|
||||||
|
@ -19,6 +19,41 @@ static QSplitter* newSplitter(Qt::Orientation orientation = Qt::Horizontal)
|
|||||||
return s;
|
return s;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void dropContentOuterHelper(ContainerWidget* cw, QLayout* l, const InternalContentData& data, Qt::Orientation orientation, bool append)
|
||||||
|
{
|
||||||
|
auto sw = new SectionWidget(cw);
|
||||||
|
sw->addContent(data, true);
|
||||||
|
|
||||||
|
QSplitter* oldsp = findImmediateSplitter(cw);
|
||||||
|
if (oldsp->orientation() == orientation
|
||||||
|
|| oldsp->count() == 1)
|
||||||
|
{
|
||||||
|
oldsp->setOrientation(orientation);
|
||||||
|
if (append)
|
||||||
|
oldsp->addWidget(sw);
|
||||||
|
else
|
||||||
|
oldsp->insertWidget(0, sw);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
auto sp = newSplitter(orientation);
|
||||||
|
if (append)
|
||||||
|
{
|
||||||
|
auto li = l->replaceWidget(oldsp, sp);
|
||||||
|
sp->addWidget(oldsp);
|
||||||
|
sp->addWidget(sw);
|
||||||
|
delete li;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
sp->addWidget(sw);
|
||||||
|
auto li = l->replaceWidget(oldsp, sp);
|
||||||
|
sp->addWidget(oldsp);
|
||||||
|
delete li;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
///////////////////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
ContainerWidget::ContainerWidget(QWidget *parent) :
|
ContainerWidget::ContainerWidget(QWidget *parent) :
|
||||||
@ -49,9 +84,24 @@ void ContainerWidget::setOrientation(Qt::Orientation orientation)
|
|||||||
|
|
||||||
void ContainerWidget::dropContent(const InternalContentData& data, SectionWidget* targetSection, DropArea area)
|
void ContainerWidget::dropContent(const InternalContentData& data, SectionWidget* targetSection, DropArea area)
|
||||||
{
|
{
|
||||||
|
// Drop on outer area
|
||||||
if (!targetSection)
|
if (!targetSection)
|
||||||
{
|
{
|
||||||
qWarning() << "Drop on invalid targetSection";
|
switch (area)
|
||||||
|
{
|
||||||
|
case TopDropArea:
|
||||||
|
dropContentOuterHelper(this, _mainLayout, data, Qt::Vertical, false);
|
||||||
|
break;
|
||||||
|
case RightDropArea:
|
||||||
|
dropContentOuterHelper(this, _mainLayout, data, Qt::Horizontal, true);
|
||||||
|
break;
|
||||||
|
case BottomDropArea:
|
||||||
|
dropContentOuterHelper(this, _mainLayout, data, Qt::Vertical, true);
|
||||||
|
break;
|
||||||
|
case LeftDropArea:
|
||||||
|
dropContentOuterHelper(this, _mainLayout, data, Qt::Horizontal, false);
|
||||||
|
break;
|
||||||
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -226,6 +276,27 @@ QRect ContainerWidget::outerLeftDropRect() const
|
|||||||
return QRect(r.left(), r.top(), w, r.height());
|
return QRect(r.left(), r.top(), w, r.height());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QByteArray ContainerWidget::saveGeometry() const
|
||||||
|
{
|
||||||
|
QByteArray ba;
|
||||||
|
QDataStream out(&ba, QIODevice::WriteOnly);
|
||||||
|
out.setVersion(QDataStream::Qt_4_5);
|
||||||
|
out << (int) 0x00001337;
|
||||||
|
out << _sections.size();
|
||||||
|
return ba;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool ContainerWidget::restoreGeometry(const QByteArray& data)
|
||||||
|
{
|
||||||
|
QDataStream in(data);
|
||||||
|
in.setVersion(QDataStream::Qt_4_5);
|
||||||
|
|
||||||
|
int magic = 0;
|
||||||
|
in >> magic;
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
void ContainerWidget::paintEvent(QPaintEvent* e)
|
void ContainerWidget::paintEvent(QPaintEvent* e)
|
||||||
{
|
{
|
||||||
QFrame::paintEvent(e);
|
QFrame::paintEvent(e);
|
||||||
|
@ -41,6 +41,10 @@ public:
|
|||||||
QRect outerBottomDropRect() const;
|
QRect outerBottomDropRect() const;
|
||||||
QRect outerLeftDropRect() const;
|
QRect outerLeftDropRect() const;
|
||||||
|
|
||||||
|
// Geometry and state serialization
|
||||||
|
QByteArray saveGeometry() const;
|
||||||
|
bool restoreGeometry(const QByteArray& data);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
virtual void paintEvent(QPaintEvent*);
|
virtual void paintEvent(QPaintEvent*);
|
||||||
virtual void contextMenuEvent(QContextMenuEvent*);
|
virtual void contextMenuEvent(QContextMenuEvent*);
|
||||||
|
@ -168,6 +168,7 @@ DropArea DropSplitAreas::cursorLocation() const
|
|||||||
|
|
||||||
static QPointer<DropOverlay> MyOverlay;
|
static QPointer<DropOverlay> MyOverlay;
|
||||||
static QPointer<QWidget> MyOverlayParent;
|
static QPointer<QWidget> MyOverlayParent;
|
||||||
|
static QRect MyOverlayParentRect;
|
||||||
|
|
||||||
DropArea showDropOverlay(QWidget* parent)
|
DropArea showDropOverlay(QWidget* parent)
|
||||||
{
|
{
|
||||||
@ -190,6 +191,27 @@ DropArea showDropOverlay(QWidget* parent)
|
|||||||
return MyOverlay->cursorLocation();
|
return MyOverlay->cursorLocation();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void showDropOverlay(QWidget* parent, const QRect& areaRect)
|
||||||
|
{
|
||||||
|
if (MyOverlay)
|
||||||
|
{
|
||||||
|
if (MyOverlayParent == parent && MyOverlayParentRect == areaRect)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
hideDropOverlay();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Create overlay and move it to the parent's areaRect
|
||||||
|
MyOverlay = new DropOverlay(parent);
|
||||||
|
MyOverlay->resize(areaRect.size());
|
||||||
|
MyOverlay->move(parent->mapToGlobal(QPoint(areaRect.x(), areaRect.y())));
|
||||||
|
MyOverlay->show();
|
||||||
|
MyOverlayParent = parent;
|
||||||
|
MyOverlayParentRect = areaRect;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
void hideDropOverlay()
|
void hideDropOverlay()
|
||||||
{
|
{
|
||||||
if (MyOverlay)
|
if (MyOverlay)
|
||||||
@ -197,6 +219,7 @@ void hideDropOverlay()
|
|||||||
MyOverlay->hide();
|
MyOverlay->hide();
|
||||||
delete MyOverlay;
|
delete MyOverlay;
|
||||||
MyOverlayParent.clear();
|
MyOverlayParent.clear();
|
||||||
|
MyOverlayParentRect = QRect();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2,6 +2,7 @@
|
|||||||
#define DROP_OVERLAY_H
|
#define DROP_OVERLAY_H
|
||||||
|
|
||||||
#include <QFrame>
|
#include <QFrame>
|
||||||
|
#include <QRect>
|
||||||
|
|
||||||
#include "ads.h"
|
#include "ads.h"
|
||||||
|
|
||||||
@ -54,6 +55,7 @@ private:
|
|||||||
|
|
||||||
|
|
||||||
DropArea showDropOverlay(QWidget* parent);
|
DropArea showDropOverlay(QWidget* parent);
|
||||||
|
void showDropOverlay(QWidget* parent, const QRect& areaRect);
|
||||||
void hideDropOverlay();
|
void hideDropOverlay();
|
||||||
|
|
||||||
ADS_NAMESPACE_END
|
ADS_NAMESPACE_END
|
||||||
|
@ -29,12 +29,12 @@ static void deleteEmptySplitter(ContainerWidget* container)
|
|||||||
auto splitters = container->findChildren<QSplitter*>();
|
auto splitters = container->findChildren<QSplitter*>();
|
||||||
for (auto i = 0; i < splitters.count(); ++i)
|
for (auto i = 0; i < splitters.count(); ++i)
|
||||||
{
|
{
|
||||||
if (splitters[i]->count() == 0 && container->_splitter != splitters[i])
|
if (splitters[i]->count() == 0 /*&& container->_splitter != splitters[i]*/)
|
||||||
{
|
{
|
||||||
if (splitters[i] == container->_splitter)
|
if (splitters[i] == container->_splitter)
|
||||||
continue;
|
continue;
|
||||||
qDebug() << "Delete empty QSplitter";
|
qDebug() << "Delete empty QSplitter";
|
||||||
splitters[i]->deleteLater();
|
delete splitters[i];//splitters[i]->deleteLater();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -96,11 +96,7 @@ void SectionTitleWidget::mouseReleaseEvent(QMouseEvent* ev)
|
|||||||
if (sw)
|
if (sw)
|
||||||
{
|
{
|
||||||
auto loc = showDropOverlay(sw);
|
auto loc = showDropOverlay(sw);
|
||||||
if (loc == InvalidDropArea)
|
if (loc != InvalidDropArea)
|
||||||
{
|
|
||||||
qDebug() << "Invalid drop area";
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
{
|
||||||
#if !defined(ADS_ANIMATIONS_ENABLED)
|
#if !defined(ADS_ANIMATIONS_ENABLED)
|
||||||
auto data = _fw->takeContent();
|
auto data = _fw->takeContent();
|
||||||
@ -133,9 +129,28 @@ void SectionTitleWidget::mouseReleaseEvent(QMouseEvent* ev)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
// Mouse is over a outer-edge drop area
|
// Mouse is over a outer-edge drop area
|
||||||
else if (false)
|
else
|
||||||
{
|
{
|
||||||
|
DropArea dropArea = DropArea::InvalidDropArea;
|
||||||
|
if (cw->outerTopDropRect().contains(cw->mapFromGlobal(ev->globalPos())))
|
||||||
|
dropArea = DropArea::TopDropArea;
|
||||||
|
if (cw->outerRightDropRect().contains(cw->mapFromGlobal(ev->globalPos())))
|
||||||
|
dropArea = DropArea::RightDropArea;
|
||||||
|
if (cw->outerBottomDropRect().contains(cw->mapFromGlobal(ev->globalPos())))
|
||||||
|
dropArea = DropArea::BottomDropArea;
|
||||||
|
if (cw->outerLeftDropRect().contains(cw->mapFromGlobal(ev->globalPos())))
|
||||||
|
dropArea = DropArea::LeftDropArea;
|
||||||
|
|
||||||
|
if (dropArea != DropArea::InvalidDropArea)
|
||||||
|
{
|
||||||
|
#if !defined(ADS_ANIMATIONS_ENABLED)
|
||||||
|
auto data = _fw->takeContent();
|
||||||
|
_fw->deleteLater();
|
||||||
|
_fw.clear();
|
||||||
|
cw->dropContent(data, NULL, dropArea);
|
||||||
|
#else
|
||||||
|
#endif
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -169,19 +184,19 @@ void SectionTitleWidget::mouseMoveEvent(QMouseEvent* ev)
|
|||||||
// Top, Right, Bottom, Left
|
// Top, Right, Bottom, Left
|
||||||
else if (cw->outerTopDropRect().contains(cw->mapFromGlobal(QCursor::pos())))
|
else if (cw->outerTopDropRect().contains(cw->mapFromGlobal(QCursor::pos())))
|
||||||
{
|
{
|
||||||
qDebug() << "Top area...";
|
showDropOverlay(cw, cw->outerTopDropRect());
|
||||||
}
|
}
|
||||||
else if (cw->outerRightDropRect().contains(cw->mapFromGlobal(QCursor::pos())))
|
else if (cw->outerRightDropRect().contains(cw->mapFromGlobal(QCursor::pos())))
|
||||||
{
|
{
|
||||||
qDebug() << "Right area...";
|
showDropOverlay(cw, cw->outerRightDropRect());
|
||||||
}
|
}
|
||||||
else if (cw->outerBottomDropRect().contains(cw->mapFromGlobal(QCursor::pos())))
|
else if (cw->outerBottomDropRect().contains(cw->mapFromGlobal(QCursor::pos())))
|
||||||
{
|
{
|
||||||
qDebug() << "Bottom area...";
|
showDropOverlay(cw, cw->outerBottomDropRect());
|
||||||
}
|
}
|
||||||
else if (cw->outerLeftDropRect().contains(cw->mapFromGlobal(QCursor::pos())))
|
else if (cw->outerLeftDropRect().contains(cw->mapFromGlobal(QCursor::pos())))
|
||||||
{
|
{
|
||||||
qDebug() << "Left area...";
|
showDropOverlay(cw, cw->outerLeftDropRect());
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
Loading…
Reference in New Issue
Block a user