重写QTreeWidget实现节点的拖拽功能

先看效果:

 鼠标拖动操作效果:

 

 

 

 1,重写QTreeWidget类:

QTreeWidget02.h

#pragma once

#include <QtWidgets/QWidget>
#include "ui_QTreeWidget02.h"
#include <vector>
#include <iostream>
#include <QtWidgets/QTreeWidget>
#include <QtWidgets/QTreeWidgetItem>
#include <QDragEnterEvent>
using namespace std;

class QTreeWidget02 : public QTreeWidget
{
    Q_OBJECT

public:
    QTreeWidget02(QWidget *parent = Q_NULLPTR);

    //声明私有变量m_dragItemVec,用来存储拖拽的节点
	vector<QTreeWidgetItem*> m_dragItemVec;

    //重写拖拽函数
	virtual void dragEnterEvent(QDragEnterEvent *ev);
	virtual	void dragMoveEvent(QDragMoveEvent * ev);
	virtual void dropEvent(QDropEvent *ev);

private:
    Ui::QTreeWidget02Class ui;
};

 QTreeWidget02..cpp

#include "QTreeWidget02.h"

QTreeWidget02::QTreeWidget02(QWidget *parent)
	: QTreeWidget(parent)
{
	ui.setupUi(this);

	//按 ctrl 或 shift 多选
	this->setSelectionMode(QAbstractItemView::ExtendedSelection);
	//设置可拖拽性质
	this->setDefaultDropAction(Qt::MoveAction);
	this->setDragDropMode(QAbstractItemView::DragDrop);
}

//对于dragEnterEvent,将选中的items存进私有变量m_dragItemVec
void QTreeWidget02::dragEnterEvent(QDragEnterEvent *ev)
{
	ev->setDropAction(Qt::MoveAction);
	QList<QTreeWidgetItem*> selectedItem = selectedItems();
	m_dragItemVec.clear();
	for (int i = 0; i < selectedItem.size(); i++)
	{
		if (selectedItem[i] && selectedItem[i]->parent())
		{
			m_dragItemVec.push_back(selectedItem[i]);
		}
	}
	if (m_dragItemVec.size() > 0)
	{
		ev->acceptProposedAction();
		QTreeWidget::dragEnterEvent(ev);
		return;
	}
	ev->ignore();
	QTreeWidget::dragEnterEvent(ev);
}

//对于dragMoveEvent,在这里设置可拖拽区域
void QTreeWidget02::dragMoveEvent(QDragMoveEvent * ev)
{
	ev->setDropAction(Qt::MoveAction);

	QTreeWidgetItem* itemOver = itemAt(ev->pos());
	//设置可拖拽区域
	if (itemOver != NULL && itemOver->parent() != NULL)
	{
		ev->acceptProposedAction();
		QTreeWidget::dragMoveEvent(ev);
		return;
	}

	ev->ignore();
	QTreeWidget::dragMoveEvent(ev);
}

//对于dropEvent,在这里插入拖拽节点
void QTreeWidget02::dropEvent(QDropEvent *ev)
{
	QTreeWidgetItem* itemOver = itemAt(ev->pos());
// 	if (itemOver == NULL)
// 	{
// 		itemOver = new QTreeWidgetItem(this);
//	}
// 
	if ( itemOver != NULL && itemOver->parent())
	{
		//在此可以对m_dragItemVec做你想做的事

		QTreeWidget::dropEvent(ev);
		setCurrentItem(itemOver); // 设置为当前选中
		itemOver->setExpanded(true);
		return;
	}
	ev->ignore();
	QTreeWidget::dropEvent(ev);//如果不符合拖拽要求,这句可以注释掉
}

 测试类:

Test.h

class Test : public QWidget
{
	Q_OBJECT
public:
	Test(QWidget *parent = Q_NULLPTR);
	~Test();
private:
	//树控件
	QTreeWidget02 * m_Treewidget;

	//主布局
	QVBoxLayout * m_Layout;
private:
	//初始化布局
	QLayout * InitLayout();

	//初始化树控件
	void InitQTreeWidgetTest();
};

 Test.cpp

#include "Test.h"

Test::Test(QWidget *parent) : QWidget(parent)
{
	//设置窗口标题
	setWindowTitle(QString::fromLocal8Bit("树控件拖拽"));
	//设置窗口大小
	resize(800, 600);
	//设置窗口布局
	setLayout(InitLayout());
	InitQTreeWidgetTest();
}

Test::~Test()
{
}

//初始化布局
QLayout * Test::InitLayout()
{
	m_Layout = new QVBoxLayout(this);
	m_Treewidget = new QTreeWidget02(this);

	//设置布局边距
	m_Layout->setContentsMargins(0, 0, 0, 0);
	//隐藏头
	m_Treewidget->setHeaderHidden(true);
	m_Layout->addWidget(m_Treewidget);
	return m_Layout;
}

//初始化树控件
void Test::InitQTreeWidgetTest()
{
	for (int i = 0; i < 2; ++i)
	{
		QTreeWidgetItem * item = new QTreeWidgetItem(m_Treewidget, QStringList(QString::fromLocal8Bit("父节点%1").arg(i)));
		for (int j = 0; j < 3; ++j)
		{
			QTreeWidgetItem * child = new QTreeWidgetItem(item, QStringList(QString::fromLocal8Bit("%1::子节点%2").arg(i).arg(j)));
		}
	}
	//默认展开所有节点
	m_Treewidget->expandAll();
}

main.cpp

#include "QTreeWidget02.h"
#include <QtWidgets/QApplication>
#include "Test.h"
int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
	Test w;
    w.show();
    return a.exec();
}

  • 1
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
实现QTreeWidget之间的拖拽功能,需要进行以下步骤: 1.在源QTreeWidget中启用拖拽功能:调用setDragEnabled(True)方法来启用拖拽功能。 2.实现startDrag方法:当用户开始拖拽一个项目时,调用startDrag方法。该方法创建QDrag对象并将要拖动的数据存储在其中。 3.在目标QTreeWidget中启用放置功能:调用setAcceptDrops(True)方法来启用放置功能。 4.实现dragEnterEvent方法:当用户将拖动的项目拖到目标QTreeWidget上时,调用dragEnterEvent方法。该方法检查拖动的数据是否与目标兼容,并在兼容的情况下接受拖放操作。 5.实现dropEvent方法:当用户在目标QTreeWidget上放置拖动的项目时,调用dropEvent方法。该方法将项目添加到目标QTreeWidget中。 下面是一个示例代码: ```python class TreeWidget(QTreeWidget): def __init__(self, parent=None): super(TreeWidget, self).__init__(parent) self.setAcceptDrops(True) self.setDragEnabled(True) def startDrag(self, event): item = self.currentItem() if item: data = QByteArray() stream = QDataStream(data, QIODevice.WriteOnly) stream.writeQString(item.text(0)) mimeData = QMimeData() mimeData.setData('application/x-qabstractitemmodeldatalist', data) drag = QDrag(self) drag.setMimeData(mimeData) drag.exec_() def dragEnterEvent(self, event): if event.mimeData().hasFormat('application/x-qabstractitemmodeldatalist'): event.accept() else: event.ignore() def dropEvent(self, event): if event.mimeData().hasFormat('application/x-qabstractitemmodeldatalist'): data = event.mimeData().data('application/x-qabstractitemmodeldatalist') stream = QDataStream(data, QIODevice.ReadOnly) text = '' stream >> text item = QTreeWidgetItem(self) item.setText(0, text) event.accept() else: event.ignore() ``` 在上面的代码中,我们继承了QTreeWidget类,并重写了startDragdragEnterEvent和dropEvent方法。startDrag方法创建了一个QMimeData对象并存储要拖动的数据。dragEnterEvent方法检查拖动的数据是否与目标兼容,并在兼容的情况下接受拖放操作。dropEvent方法将项目添加到目标QTreeWidget中。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值