Qt Designer 的出现,让我们很容易通过控件的方式设计出我们自己的软件界面。但有时,Designer提供给我们的控件,无法满足我们的需求,需要根据实际情况采取继承的方式进行设计。
本文通过QListWidget和QTreeWidget之间的拖曳进行说明。工程文件
如图1个工程文件
3个头文件
4个源文件
1个form文件
各文件源码
1.根据实际情况,创建类
//qlistwidget_ex.h #ifndef QLISTWIDGET_EX_H #define QLISTWIDGET_EX_H #include <QListWidget> #include <QPoint> #include <QMouseEvent> class QListWidget_ex : public QListWidget { Q_OBJECT public: QListWidget_ex(); protected: void mousePressEvent(QMouseEvent *event); void mouseMoveEvent(QMouseEvent *e); private: QPoint m_beginPos; }; #endif // QLISTWIDGET_EX_H
//qlistwidget_ex.cpp #include "qlistwidget_ex.h" #include <QDrag> #include <QMimeData> #include <QDebug> #include <QImage> #include <QApplication> QListWidget_ex::QListWidget_ex() { } void QListWidget_ex::mousePressEvent(QMouseEvent *event) { if(event->button()==Qt::LeftButton) { m_beginPos=event->pos(); //qDebug()<<m_beginPos.rx()<<"+"<<m_beginPos.ry(); } QListWidget::mousePressEvent(event); } void QListWidget_ex::mouseMoveEvent(QMouseEvent *e) { if(e->buttons()&Qt::LeftButton) { int nDistance=(e->pos()-m_beginPos).manhattanLength(); if(nDistance>=QApplication::startDragDistance()) { // qDebug()<<nDistance; QListWidgetItem *item=currentItem(); if(item) { QMimeData *mimeData=new QMimeData; mimeData->setText(item->text()); // qDebug()<<mimeData->text(); QDrag *drag=new QDrag(this); drag->setMimeData(mimeData); QImage image;//(128,128,QImage::Format_ARGB32); if(image.load("../images/qt.png")==true) drag->setPixmap(QPixmap::fromImage(image)); if(Qt::MoveAction==drag->exec(Qt::MoveAction)) { delete item; // qDebug()<<"delete item"; } } } } QListWidget::mouseMoveEvent(e); }
//qtreewidget_ex.h class Qtreewidget_ex : public QTreeWidget { Q_OBJECT public: explicit Qtreewidget_ex(); protected: void dragEnterEvent(QDragEnterEvent *event); void dragMoveEvent(QDragMoveEvent *event); void dropEvent(QDropEvent *event); };
//qtreewidget_ex.cpp Qtreewidget_ex::Qtreewidget_ex() { setAcceptDrops(true); } void Qtreewidget_ex::dragEnterEvent(QDragEnterEvent *event) { QListWidget_ex *source=qobject_cast<QListWidget_ex*>(event->source()); if(source) { event->setDropAction(Qt::MoveAction); event->accept(); //qDebug()<<source; } } void Qtreewidget_ex::dragMoveEvent(QDragMoveEvent *event) { QListWidget_ex *source=qobject_cast<QListWidget_ex*>(event->source()); if(source) { event->setDropAction(Qt::MoveAction); event->accept(); } } void Qtreewidget_ex::dropEvent(QDropEvent *event) { QListWidget_ex *source=qobject_cast<QListWidget_ex*>(event->source()); if(source) { QModelIndex currentId=indexAt(event->pos()); if(currentId.isValid()) { QTreeWidgetItem *item=itemFromIndex(currentId); model()->insertRow(item->childCount(),currentId); QModelIndex childId=model()->index(item->childCount()-1,0,currentId); model()->setData(childId,QVariant(event->mimeData()->text()),Qt::DisplayRole); event->setDropAction(Qt::MoveAction); event->accept(); } } }
2.写MainWindow.cpp文件
//mainwindow.cpp #include "mainwindow.h" #include "ui_mainwindow.h" #include <QGridLayout> #include <QHBoxLayout> MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent), ui(new Ui::MainWindow) { ui->setupUi(this); m_listWidget=new QListWidget_ex; m_treeWidget=new Qtreewidget_ex; QWidget *centerWindow = new QWidget; this->setCentralWidget(centerWindow); QHBoxLayout *hLayout=new QHBoxLayout; m_listWidget->addItem("drag1"); m_listWidget->addItem("drag2"); m_listWidget->addItem("drag3"); QTreeWidgetItem *item=new QTreeWidgetItem(QStringList(QString("first"))); QTreeWidgetItem *item2=new QTreeWidgetItem(QStringList(QString("second"))); m_treeWidget->setHeaderLabel("treeWidget"); m_treeWidget->addTopLevelItem(item); m_treeWidget->addTopLevelItem(item2); hLayout->addWidget(m_listWidget); hLayout->addWidget(m_treeWidget); centerWindow->setLayout(hLayout); } MainWindow::~MainWindow() { delete ui; }
3.由于重写了控件,main.cpp保存原样即可
//main.cpp #include "mainwindow.h" #include <QApplication> int main(int argc, char *argv[]) { QApplication a(argc, argv); MainWindow w; w.show(); return a.exec(); }
程序截图
小结
由于本人当时对Qt的理解不够,没明白如何添加相应的控件到UI,特此记录一下。