您的位置:首页 > 编程语言 > Qt开发

QTabWidget 实现类似QQ聊天窗口(拖动分离出新的窗口)

2016-02-01 18:17 971 查看
新版本的QQ聊天窗口可以实现拖动,分离出新的窗口。浏览器等软件也可以实现类似操作。所以心血来潮想用Qt实现类似的功能。想用QTabWidget直接实现是很难的,仔细阅读源码,发现QTabWidget内部是由QStackedWidget和QTabBar组合实现的。所以很自然的想到,只要继承QTabBar的子类重新实现QTabBar的

[cpp] view plain copy

void mousePressEvent (QMouseEvent *e);

void mouseMoveEvent (QMouseEvent *e);

void mouseReleaseEvent (QMouseEvent *e);

这三个方法,再把子定义的TabBar设置给QTabWidget就差不多了。但是还有个问题,QTabWidget的 setTabBar方法是protected的,所以只好再自定义一个QTabWidget的子类,在子类里调用setTabBar了。以下是我的简单实现:

[cpp] view plain copy

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;

};

[cpp] view plain copy

void myTabBar::mouseMoveEvent(QMouseEvent *e)

{

int index = this->currentIndex();

if (m_isDrag)

{

QPoint Point = e->pos();

[cpp] view plain copy

//拖动的垂直距离大于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);

}

[cpp] view plain copy

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;

};

[cpp] view plain copy

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)

{

[cpp] view plain copy

//新建一个独立的窗口

removeTab(m_dragIndex);

pWidget->addTab(m_pDragWidget,m_dragTabLabel);

pWidget->show();

}
http://blog.csdn.net/hai200501019/article/details/8987379
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: