[转]QT实现拖放文件

转自:http://my.oschina.net/voler/blog/345722

0. 源代码下载地址

1. 简单文件拖放

https://github.com/leichaojian/qt/tree/master/drop1

2. 复杂文件拖放

https://github.com/leichaojian/qt/tree/master/drop

3. 通过按钮来完成列表数据的转移

https://github.com/leichaojian/qt/tree/master/drop3

4. 通过拖放文件来达到效果

https://github.com/leichaojian/qt/tree/master/drop4



1. 简单文件拖放

1. 一般情况下,编辑框可以直接接收到文件名

?
1
2
3
4
5
6
7
8
MainWindow::MainWindow(QWidget *parent) :
     QMainWindow(parent),
     ui( new Ui::MainWindow)
{
     ui->setupUi( this );
     textEdit = new QTextEdit;
     setCentralWidget(textEdit);
}



2. 程序效果图


2. 复杂文件拖放

    如果我们想在主框架中得到响应的文件信息,则我们必须亲自实现文件拖放操作。

1. 关键代码如下

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
//当用户拖动文件到窗口部件上时候,就会触发dragEnterEvent事件
void MainWindow::dragEnterEvent(QDragEnterEvent *event)
{
     //如果为文件,则支持拖放
     if (event->mimeData()->hasFormat( "text/uri-list" ))
         event->acceptProposedAction();
}
 
//当用户放下这个文件后,就会触发dropEvent事件
void MainWindow::dropEvent(QDropEvent *event)
{
     //注意:这里如果有多文件存在,意思是用户一下子拖动了多个文件,而不是拖动一个目录
     //如果想读取整个目录,则在不同的操作平台下,自己编写函数实现读取整个目录文件名
     QList<QUrl> urls = event->mimeData()->urls();
     if (urls.isEmpty())
         return ;
 
     //往文本框中追加文件名
     foreach(QUrl url, urls) {
         QString file_name = url.toLocalFile();
         textEdit->append(file_name);
     }
}



2. 程序效果图


3. 通过按钮来完成列表数据的转移

1. 关键代码

?
1
2
3
4
5
6
7
8
9
10
void Dialog::moveCurrentItem(QListWidget *source,
                      QListWidget *target)
{
     if (source->currentItem()) {
         QListWidgetItem *newItem = source->currentItem()->clone();
         target->addItem(newItem);
         target->setCurrentItem(newItem);
         delete source->currentItem();
     }
}



2. 程序效果图


4. 通过拖放文件来达到效果

1. 关键代码

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
void ProjectListWidget::mousePressEvent(QMouseEvent *event)
{
     //获取鼠标按下时候的坐标
     if (event->button() == Qt::LeftButton)
         startPos = event->pos();
     QListWidget::mousePressEvent(event);
}
 
void ProjectListWidget::mouseMoveEvent(QMouseEvent *event)
{
     if (event->buttons() & Qt::LeftButton) {
         int distance = (event->pos() - startPos).manhattanLength();
         //如果长度大于推荐的拖动起始距离,则认为是拖动(存在用户手抖的情况)
         if (distance >= QApplication::startDragDistance())
             performDrag();
     }
     QListWidget::mouseMoveEvent(event);
}
 
//有文件拖动到窗口上时,触发此dragEnterEvent事件
void ProjectListWidget::dragEnterEvent(QDragEnterEvent *event)
{
     //当为同一个应用程序的一部分时,event->source()返回启动这个拖动窗口部件的指针
     ProjectListWidget *source =
             qobject_cast<ProjectListWidget *>(event->source());
     if (source && source != this ) {
         //确认是一个移动的操作
         event->setDropAction(Qt::MoveAction);
         event->accept();
     }
}
 
void ProjectListWidget::dragMoveEvent(QDragMoveEvent *event)
{
     ProjectListWidget *source =
             qobject_cast<ProjectListWidget *>(event->source());
     if (source && source != this ) {
         event->setDropAction(Qt::MoveAction);
         event->accept();
     }
}
 
void ProjectListWidget::dropEvent(QDropEvent *event)
{
     ProjectListWidget *source =
             qobject_cast<ProjectListWidget *>(event->source());
     if (source && source != this ) {
         //得到数据并增加到列表中
         addItem(event->mimeData()->text());
         event->setDropAction(Qt::MoveAction);
         event->accept();
     }
}
 
void ProjectListWidget::performDrag()
{
     //当前被拖动的选项
     QListWidgetItem *item = currentItem();
     if (item) {
         QMimeData *mimeData = new QMimeData;
         mimeData->setText(item->text());
 
         QDrag *drag = new QDrag( this );
         drag->setMimeData(mimeData);
         drag->setPixmap(QPixmap( ":/images/person.png" ));
         //进行拖动操作
         if (drag->exec(Qt::MoveAction) == Qt::MoveAction)
             delete item;
     }
}



2. 效果图(通过鼠标拖放)


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值