QT实现拖拽TabWidget选项卡形成单独的窗口选项卡里面含多个控件,双击标题栏可还原多个控件回选项卡的功能
时间: 2023-05-12 21:03:45 浏览: 136
可以使用QTabBar的setMovable()函数将TabWidget设置为可拖拽,然后在TabBar上设置鼠标事件,当鼠标按下时,记录下当前Tab的位置和大小,创建一个新的窗口并将Tab上的控件移动到新窗口中,同时设置新窗口的标题为当前Tab的标题。当双击新窗口的标题栏时,将窗口中的控件移动回原来的Tab中,同时关闭该窗口。以下是示例代码:
```cpp
void MyTabWidget::mousePressEvent(QMouseEvent *event)
{
if (event->button() == Qt::LeftButton) {
m_dragStartPosition = event->pos();
}
}
void MyTabWidget::mouseMoveEvent(QMouseEvent *event)
{
if (!(event->buttons() & Qt::LeftButton))
return;
if ((event->pos() - m_dragStartPosition).manhattanLength()
< QApplication::startDragDistance())
return;
int index = currentIndex();
if (index < 0)
return;
QWidget *widget = widget(index);
if (!widget)
return;
QMimeData *mimeData = new QMimeData;
QByteArray widgetData;
QDataStream dataStream(&widgetData, QIODevice::WriteOnly);
dataStream << QPoint(event->pos() - widget->pos());
dataStream << widget->size();
mimeData->setData("application/x-dnditemdata", widgetData);
QDrag *drag = new QDrag(this);
drag->setMimeData(mimeData);
drag->setPixmap(*widget->grab());
drag->setHotSpot(event->pos() - widget->pos());
if (drag->exec(Qt::CopyAction | Qt::MoveAction, Qt::CopyAction) == Qt::MoveAction) {
widget->close();
}
}
void MyTabWidget::dragEnterEvent(QDragEnterEvent *event)
{
if (event->mimeData()->hasFormat("application/x-dnditemdata")) {
if (event->source() == this) {
event->setDropAction(Qt::MoveAction);
event->accept();
} else {
event->acceptProposedAction();
}
} else {
event->ignore();
}
}
void MyTabWidget::dragMoveEvent(QDragMoveEvent *event)
{
if (event->mimeData()->hasFormat("application/x-dnditemdata")) {
if (event->source() == this) {
event->setDropAction(Qt::MoveAction);
event->accept();
} else {
event->acceptProposedAction();
}
} else {
event->ignore();
}
}
void MyTabWidget::dropEvent(QDropEvent *event)
{
if (event->mimeData()->hasFormat("application/x-dnditemdata")) {
QByteArray widgetData = event->mimeData()->data("application/x-dnditemdata");
QDataStream dataStream(&widgetData, QIODevice::ReadOnly);
QPoint offset;
QSize size;
dataStream >> offset >> size;
QWidget *widget = new QWidget(this);
widget->setGeometry(QRect(event->pos() - offset, size));
widget->show();
event->setDropAction(Qt::MoveAction);
event->accept();
} else {
event->ignore();
}
}
void MyTabWidget::tabCloseRequested(int index)
{
QWidget *widget = this->widget(index);
if (widget) {
widget->close();
}
}
void MyTabWidget::tabDoubleClick(int index)
{
QWidget *widget = this->widget(index);
if (widget) {
widget->setParent(this);
widget->show();
setCurrentIndex(index);
}
}
```
其中,MyTabWidget继承自QTabWidget,重载了鼠标事件和Tab关闭事件。在鼠标事件中,记录下当前Tab的位置和大小,并创建一个新的窗口并将Tab上的控件移动到新窗口中。在Tab关闭事件中,关闭窗口并将控件移动回原来的Tab中。