void mousePressEvent (QMouseEvent *e); void mouseMoveEvent (QMouseEvent *e); void mouseReleaseEvent (QMouseEvent *e);
这三个方法,再把子定义的TabBar设置给QTabWidget就差不多了。但是还有个问题,QTabWidget的 setTabBar方法是protected的,所以只好再自定义一个QTabWidget的子类,在子类里调用setTabBar了。以下是我的简单实现:
class myTabBar:public QTabBar { Q_OBJECT public: myTabBar(QWidget *parent = NULL); ~myTabBar(); protected: void mousePressEvent (QMouseEvent *e); void mouseMoveEvent (QMouseEvent *e); void mouseReleaseEvent (QMouseEvent *e); signals: void starDragTab(int index); void endDragTab(); private: void drag(); bool m_isDrag; QPoint m_mousePressPoint; QPoint m_mouseReleasePoint; };
void myTabBar::mouseMoveEvent(QMouseEvent *e) { int index = this->currentIndex(); if (m_isDrag) { QPoint Point = e->pos();
//拖动的垂直距离大于Bar的高度的话就新建一个窗口,这个应该比较好理解啊 if (qAbs(m_mousePressPoint.y() - Point.y()) > this->height()) { emit starDragTab(index); } } QTabBar::mouseMoveEvent(e); } void myTabBar::mousePressEvent(QMouseEvent *e) { if (e->button() == Qt::LeftButton) { m_isDrag = true; m_mousePressPoint = e->pos(); } QTabBar::mousePressEvent(e); } void myTabBar::mouseReleaseEvent(QMouseEvent *e) { if (e->button() == Qt::LeftButton) { m_mouseReleasePoint = e->pos(); if (qAbs(m_mousePressPoint.y() - m_mouseReleasePoint.y()) > this->height()) { emit endDragTab(); } } QTabBar::mouseReleaseEvent(e); }
class myTabWidget:public QTabWidget { Q_OBJECT public: myTabWidget(QWidget *parent = NULL); ~myTabWidget(); private slots: void starDrag(int index); void endDrag(); private: myTabBar *m_pTabBar; QString m_dragTabLabel; QWidget *m_pDragWidget; int m_dragIndex; };
myTabWidget::myTabWidget(QWidget *parent/* = NULL*/):QTabWidget(parent) { this->setAcceptDrops(true); setMouseTracking(true); m_pTabBar = new myTabBar(this); m_pTabBar->setMovable(true); setTabBar(m_pTabBar); //设置自定义的Bar给TabWidget m_pDragWidget = NULL; connect(m_pTabBar,SIGNAL(starDragTab(int)),this,SLOT(starDrag(int))); connect(m_pTabBar,SIGNAL(endDragTab()),this,SLOT(endDrag())); } void myTabWidget::starDrag(int index) { m_dragTabLabel = this->tabText(index); m_pDragWidget = this->widget(index); m_dragIndex = index; QPixmap pix; //pix = QPixmap::grabWidget(m_pDragWidget); pix = QPixmap::grabWindow(this->winId()); if (pix.isNull()) { int i; } QMimeData *mimeData = new QMimeData; //mimeData->setText("drag tab"); QDrag *drag = new QDrag(this); drag->setMimeData(mimeData); drag->setPixmap(pix.scaled(QSize(200,200))); //这里主要是想想QQ一样,可以拖动的过程显示被拖动窗口的图片。但是效果还不是很好 drag->exec(); } void myTabWidget::endDrag() { myTabWidget *pWidget = new myTabWidget(NULL); if (m_pDragWidget) {
//新建一个独立的窗口 removeTab(m_dragIndex); pWidget->addTab(m_pDragWidget,m_dragTabLabel); pWidget->show(); } }