QT实现自定义窗口

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了QT实现自定义窗口相关的知识,希望对你有一定的参考价值。

参考技术A 1.去掉窗口默认边框。

2.自定义窗口标题栏。

3.可拖动、调用窗口大小。

4.实现放大、缩小、还原。

Qt中如何利用 png 图片来实现自定义形状的窗口

使用 Qt::WindowFlags 可以实现一些不同类型的窗口,如:用 Qt::FramelessWindowHint 来实现无边框窗口,用 Qt::Popup 来实现弹出式的窗口,用 Qt::Tool 来实现工具窗口,用Qt::CustomizeWindowHint 来关闭窗口标题栏以及与 Qt::WindowCloseButton(添加关闭按钮),Qt::WindowMaximumButtonSize(添加最大化按钮)联用来建立只有关闭按钮和最大化按钮的窗口,用 Qt::WindowStaysOnTopHint 使窗口永远在最前端等。 Qt::WidgetAttribute 使窗口支持透明背景以及在关闭后主动销毁。其它一些常用的 Attribute 有:Qt::WA_AcceptDrops 使 widget 支持拖拽操作,Qt::WA_MouseTracking 使 widget 及时响应鼠标移动事件(MouseMoveEvent)。 Qt::setMask() 函数对窗口进行部分区域遮掩来实现各种形状的窗口。部分代码解释:头文件: 1:#ifndef SHAPEDWIDGET_H 2:#define SHAPEDWIDGET_H 3: 4:#include <QWidget> 5:class QPoint; 6:class QPixmap; 7:class ShapedWidget : public QWidget 8: 9: Q_OBJECT 10:public: 11:explicit ShapedWidget(QWidget *parent = 0); 12: ~ShapedWidget(); 13: 14:private slots: 15:void changeSkin(); 16: 17:protected: 18:void mousePressEvent(QMouseEvent *); 19:void mouseMoveEvent(QMouseEvent *); 20:void paintEvent(QPaintEvent *); 21: 22:private: 23:void initData(); 24:void initVisualComponents(); 25:void setupContextMenu(); 26: 27: QPoint* dragPos_; 28: QPixmap* backgroundPixmap_; 29: ; 30: 31:#endif // SHAPEDWIDGET_H构造: 1: ShapedWidget::ShapedWidget(QWidget *parent) : 2: QWidget(parent, Qt::FramelessWindowHint) //无边框窗体 3: 4: initData(); //初始化数据,这个demo里面就两个,具体下面有解释 5: initVisualComponents(); //初始化私有可视部件,这个demo里面没有私有的其它部件,所以只做了窗口的一些属性设置 6: setupContextMenu(); //设置右键菜单,分配各种QAction内存空间以及连接SIGNALS和SLOTS 7: setAttribute(Qt::WA_DeleteOnClose); //关闭事件发生后就主动从内存中销毁窗口 8: setAttribute(Qt::WA_TranslucentBackground); //透明背景支持 9: 拖拽移动窗体(下面有图示): 1:void ShapedWidget::mousePressEvent(QMouseEvent *event) 2: 3:if(event->button() == Qt::LeftButton) 4: 5: *dragPos_ = event->globalPos() - frameGeometry().topLeft(); 6: event->accept(); 7: 8: 9: 10:void ShapedWidget::mouseMoveEvent(QMouseEvent *event) 11: 12:if(event->buttons() & Qt::LeftButton) 13: 14: move(event->globalPos() - *dragPos_); 15: event->accept(); 16: 17: 窗口绘制: 1:void ShapedWidget::paintEvent(QPaintEvent *) 2: 3: QPainter painter(this); 4: painter.fillRect(0, 0, backgroundPixmap_->width(), backgroundPixmap_->height(), *backgroundPixmap_); 5: 更换皮肤: 1:void ShapedWidget::changeSkin() 2: 3: QAction* source = qobject_cast<QAction*>(sender()); //获取发送该信号的信号源,并转换对象 4: backgroundPixmap_->load(source->data().toString()); //因为给每个 QAction 赋了图片的地址的字符串 5://所以可以通过 data() 来获取该值,并更新背景图片的内容 6: resize(backgroundPixmap_->width(), backgroundPixmap_->height()); //窗口大小尽可能小 参考技术A   1.可以设置QWidget的窗口属性Qt::WA_TranslucentBackground为true来实现。但是利用这个属性有很大的限制。在window平台下,你必须设置Qt::FramelessWindowHint属性为true,设置窗口为一个没有标题栏的窗口。在X11平台下,你还要依靠 a compositing window manager.局限很多
  2利用setMask()函数来实现,
  void QWidget::setMask ( const QRegion & region )
可以使得仅和region重叠的区域可见。但是,如果这个区域包括widget的rect()以外的像素,窗口控制的这个区域可见不可见,将取决于具体的平台。

  所以,如果获得这个不规则的区域,然后在resizeEvent函数中调用这个函数,就可以获得一个不规则的形状的窗口。
  
  下面的代码是如何使得窗口成为一个圆角矩形。
  void resizeEvent(QEvent* event)
  
  QPainterPath path;
  QRectF rect = QRectF(0,0,200,100);
  path.addRoundedRect(rect,20,15);
  
  QPolygon polygon= path.toFillPolygon().toPolygon();//获得这个路径上的所有的点
QRegion region(polygon);//根据这个点构造这个区域
setMask(region);

  
  由于QPainterPath可以构造很多不规则的形状,所以我们可以构造很多不规则形状的窗口

以上是关于QT实现自定义窗口的主要内容,如果未能解决你的问题,请参考以下文章

QT自定义控件消息实现

Qt中如何利用 png 图片来实现自定义形状的窗口

29.QT-自定义窗口拖动自定义QToolButton/QPushButton开关按钮界面阴影

Qt之自定义布局管理器(QFlowLayout)

QT笔记之自定义窗口拖拽移动

QT自定义窗口