赞
踩
实现的效果为:通过黑色矩形框预操作,鼠标释放时更新窗口。效果图如下:
1.QWebEngineView
从测试效果来看,对于普通widget效果较好,但是如果是嵌入了QWebEngineView,且其位于窗口四周,就会出现问题。
其主要原因在于,当事件进入QWebEngineView后,会被其child(QtWebEngineCore::RenderWidgetHostViewQtDelegateWidget)"吃掉",导致后续事件不再进入主窗口,从而无法触发我们的代码。这时我们还可以遍历QWebEngineView的children,将事件安装到主窗口
- auto childs = view->children();
- for(auto child:childs){
- child->installEventFilter(this);
- }
但是这样显得太笨重了。而且,即使如此,鼠标样式的修改,也会被QWebEngineView刷掉。因此对于QWebEngineView下是存在一些问题的。
2.多屏幕拖动时,从低缩放比拖到高缩放比释放时,会闪烁一次,目前没有进一步分析原因。
目前网上无非两种方式:
a)通过nativeEvent()实现。c++ - Qt/Windows, resizable frameless window - Stack Overflow
b)通过窗口的eventFilter()直接实现。
但是问题是前者基于windows接口不跨平台,而后者则会出现抖动。
本文则是基于第二种方式,并参考windows窗口的拖动方式,通过预操作框避免抖动的问题。
setWindowFlags(Qt::FramelessWindowHint);
当鼠标位于不同区域时,触发不同的操作。
1.首先是九宫格的思路,了解了思路之后,实现就比较简单了
2.对于预处理框,首先是需要以全屏幕作为geometry,否则会导致拖不到非主屏幕,或者位置错误灯问题
3.其次是预处理框要实现window类似的与背景色互补(而非纯色),需要获取全屏幕图片作为背景绘制到预操作框,然后再通过QPainter::RasterOp_SourceAndNotDestination模式取反。
4.最后就是对于多屏幕的位置,缩放比灯。
目录结构如下:
其中:
详细代码如下:
- #include "cursorTransform.h"
- #include <QDebug>
-
-
- AreaType CursorTransform::calculateCursorType(const QSize &size, const QPoint &pos)
- {
- //TODO:minsize
- auto w = size.width();
- auto h = size.height();
- auto x = pos.x();
- auto y = pos.y();
- //left
- if(x<=FrameLessData::borderThickness){
- if(y<=FrameLessData::borderThickness)
- return AreaType::LeftTopArea;
- else if(y>=h-FrameLessData::borderThickness)
- return AreaType::LeftBottomArea;
- else
- return AreaType::LeftArea;
- }//right
- else if(x>=w-FrameLessData::borderThickness){
- if(y<=FrameLessData::borderThickness)
- return AreaType::RightTopArea;
- else if(y>=h-FrameLessData::borderThickness)
- return AreaType::RightBottomArea;
- else
- return AreaType::RightArea;
- }
- else{//center
- if(y<=FrameLessData::borderThickness)
- return AreaType::TopArea;
- else if(y<=FrameLessData::titleHeight)
- return AreaType::TitleArea;
- else if(y>=h-FrameLessData::borderThickness)
- return AreaType::BottomArea;
- else
- return AreaType::CenterArea;
- }
-
- }
-
- Qt::CursorShape CursorTransform::AreaType2CursorShape(AreaType type)
- {
- Qt::CursorShape cursorType(Qt::ArrowCursor);
- switch (type) {
- case AreaType::LeftTopArea:
- case AreaType::RightBottomArea:
- cursorType=Qt::SizeFDiagCursor;
- break;
- case AreaType::RightTopArea:
- case AreaType::LeftBottomArea:
- cursorType=Qt::SizeBDiagCursor;
- break;
- case AreaType::TopArea:
- case AreaType::BottomArea:
- cursorType=Qt::SizeVerCursor;
- break;
- case AreaType::LeftArea:
- case AreaType::RightArea:
- cursorType=Qt::SizeHorCursor;
- break;
- default:
- break;
- }
-
- return cursorType;
- }
-
- void CursorTransform::calculateRect(AreaType type,QRect &rect, const QPoint &lastPos,const QPoint &newPos)
- {
- int xOff=0,yOff=0,wOff=0,hOff=0;
- int posXOff=newPos.x()-lastPos.x();
- int posYOff = newPos.y()-lastPos.y();
- switch (type) {
- case AreaType::LeftTopArea:
- xOff = posXOff;
- yOff = posYOff;
- break;
- case AreaType::TopArea:
- yOff = posYOff;
- break;
- case AreaType::RightTopArea:
- yOff = posYOff;
- wOff = posXOff;
- break;
- case AreaType::LeftArea:
- xOff = posXOff;
- break;
- case AreaType::RightArea:
- wOff = posXOff;
- break;
- case AreaType::LeftBottomArea:
- xOff = posXOff;
- hOff = posYOff;
- break;
- case AreaType::BottomArea:
- hOff = posYOff;
- break;
- case AreaType::RightBottomArea:
- wOff = posXOff;
- hOff = posYOff;
- break;
- case AreaType::TitleArea: //move
- rect.moveTopLeft(rect.topLeft()+QPoint(posXOff,posYOff));
- break;
- default:
- break;
- }
- //min judget:
- if(rect.width()-xOff<=FrameLessData::minWidth)
- xOff=0;
- else if(rect.left()<newPos.x() && xOff<0)
- xOff=0;
- if(rect.width()+wOff<=FrameLessData::minWidth)
- wOff=0;
- else if(rect.right()>newPos.x() && wOff>0)
- wOff=0;
-
- if(rect.height()-yOff<=FrameLessData::minHeight)
- yOff=0;
- else if(rect.top()<newPos.y() && yOff<0)
- yOff=0;
- if(rect.height()+hOff<=FrameLessData::minHeight)
- hOff=0;
- else if(rect.bottom()>newPos.y() && hOff>0)
- hOff=0;
-
- //resize:
- rect.setTop(rect.top()+yOff);
- rect.setLeft(rect.left()+xOff);
- rect.setWidth(rect.width()+wOff);
- rect.setHeight(rect.height()+hOff);
- }
-
- #ifndef CURSORTRANSFORM_H
- #define CURSORTRANSFORM_H
- #include "framelessData.h"
- #include <QRect>
-
- class CursorTransform
- {
- public:
- static AreaType calculateCursorType(const QSize &size, const QPoint &pos);
- static enum Qt::CursorShape AreaType2CursorShape(AreaType type);
-
- static void calculateRect(AreaType type,QRect &rect,const QPoint &lastPos,const QPoint &newPos);
- private:
- };
-
- #endif // CURSORTRANSFORM_H
- #include "framelessData.h"
-
- int FrameLessData::borderThickness=4;
- int FrameLessData::titleHeight=30;
- int FrameLessData::minHeight=355;
- int FrameLessData::minWidth=220;
- QColor FrameLessData::borderColor=(Qt::white);
- QColor FrameLessData::transparentRectBkground=(Qt::transparent);
- enum Qt::PenStyle FrameLessData::borderStyle=(Qt::SolidLine);
- #ifndef FRAMELESSDATA_H
- #define FRAMELESSDATA_H
- #include <QColor>
- #include <QPoint>
- #include <QSize>
-
- //透明矩形的属性
-
- class FrameLessData{
- public:
- static int borderThickness;
- static int titleHeight;
- static int minHeight;
- static int minWidth;
- static QColor borderColor;
- static QColor transparentRectBkground;
- static enum Qt::PenStyle borderStyle;
- };
-
-
-
-
- enum class AreaType
- {
- LeftTopArea,
- TopArea,
- RightTopArea,
- LeftArea,
- RightArea,
- LeftBottomArea,
- BottomArea,
- RightBottomArea,
- CenterArea,
- TitleArea,
- None
- };
-
- enum class WidgetOperator
- {
- None,
- Resize,
- Move
- };
-
- #endif // FRAMELESSDATA_H
- #include "framelessHelper.h"
- #include "cursorTransform.h"
- #include <QEvent>
- #include <QSize>
- #include <QPoint>
- #include <QCursor>
- #include <QWidget>
- #include <QPainter>
- #include <QDebug>
-
-
-
- FrameLessHelper::FrameLessHelper(QWidget *widget)
- : m_widget(widget)
- , m_transparentRect(new TransparentRect())
- , m_widgetOperator(WidgetOperator::None)
- , m_isMove(false)
- #ifdef TITLEBAR
- , m_titleBar(nullptr)
- #endif
- {
- m_transparentRect->setRect(m_widget->frameGeometry());
- #ifdef TITLEBAR
- //if use title
- m_titleBar = new TitleBar(m_widget);
-
- connect(m_titleBar,&TitleBar::minimumSizeClick,this,&FrameLessHelper::onMinClick);
- connect(m_titleBar,&TitleBar::showNormalClick,this,&FrameLessHelper::onMaxClick);
- connect(m_titleBar,&TitleBar::closeClick,this,&FrameLessHelper::onCloseClick);
- #endif
- }
-
- bool FrameLessHelper::eventFilter(QObject *watched, QEvent *event)
- {
- int ret=false;
- switch (event->type()) {
- case QEvent::MouseButtonDblClick: //double click
- ret = onDbClickEvent(static_cast<QMouseEvent *>(event));
- break;
- case QEvent::MouseButtonPress:
- ret = onMousePressEvent(static_cast<QMouseEvent *>(event));
- break;
- case QEvent::MouseButtonRelease:
- ret = onMouseReleaseEvent(static_cast<QMouseEvent *>(event));
- break;
- case QEvent::MouseMove:
- ret = onMoveEvent(static_cast<QMouseEvent *>(event));
- break;
- case QEvent::HoverMove:
- case QEvent::HoverEnter:
- ret = onHoverEvent(watched,static_cast<QHoverEvent *>(event));
- break;
- default:
- break;
- }
- //触发返回true
- if(ret)
- return ret;
-
- return QObject::eventFilter(watched,event);
- }
-
- void FrameLessHelper::setBorderThickness(int thickness)
- {
- FrameLessData::borderThickness = thickness;
- }
-
- void FrameLessHelper::setTitleHeight(int height)
- {
- FrameLessData::titleHeight = height;
- }
-
- void FrameLessHelper::setMinHeight(int height)
- {
- FrameLessData::minHeight = height;
- }
-
- void FrameLessHelper::setMinWidth(int width)
- {
- FrameLessData::minWidth = width;
- }
- #ifdef TITLEBAR
- QWidget *FrameLessHelper::getTitleBar()
- {
- return m_titleBar;
- }
-
- void FrameLessHelper::onMinClick()
- {
- m_widget->showMinimized();
- }
-
- void FrameLessHelper::onMaxClick()
- {
- if(m_widget->isFullScreen())
- m_widget->showNormal();
- else
- m_widget->showFullScreen();
- }
-
- void FrameLessHelper::onCloseClick()
- {
- m_widget->close();
- }
- #endif
- bool FrameLessHelper::onHoverEvent(QObject *watched,QHoverEvent *event)
- {
- //操作的时候不响应hover
- if(m_widgetOperator!=WidgetOperator::None || m_widget->isFullScreen())
- return false;
- //hover move
- auto areatype = CursorTransform::calculateCursorType(m_widget->size(),event->pos());
- auto w=static_cast<QWidget *>(watched);
- if(w)
- w->setCursor(CursorTransform::AreaType2CursorShape(areatype));
- else
- m_widget->setCursor(CursorTransform::AreaType2CursorShape(areatype));
- return true;
- //hover leave -> Qt::ArrowCursor
- //not need
- }
-
- bool FrameLessHelper::onDbClickEvent(QMouseEvent *event)
- {
- if(event->button()!=Qt::LeftButton){
- return false;
- }
- auto areatype = CursorTransform::calculateCursorType(m_widget->size(),event->globalPos()-m_widget->pos());
- if(areatype==AreaType::TitleArea){
- if(m_widget->isFullScreen()){
- m_widget->showNormal();
- }
- else
- {
- m_widget->showFullScreen();
- }
- #ifdef TITLEBAR
- m_titleBar->onMaxClick();
- #endif
- }
- return true;
- }
-
- bool FrameLessHelper::onMousePressEvent(QMouseEvent *event)
- {
- if(event->button()!=Qt::LeftButton){
- return false;
- }
-
- auto type = CursorTransform::calculateCursorType(m_widget->size(),event->globalPos()-m_widget->pos());
-
- if(type<AreaType::CenterArea){
- //resize
- m_widgetOperator = WidgetOperator::Resize;
-
- // not start show rect
- m_transparentRect->setRect(m_widget->frameGeometry());
- m_transparentRect->onMousePressEvent(event,type);
-
- return true;
- }
- else if(type==AreaType::TitleArea){
- //move
- m_widgetOperator = WidgetOperator::Move;
- if(!m_widget->isFullScreen())
- m_transparentRect->setRect(m_widget->geometry());
- else{
- m_transparentRect->setRect(calMaxMoveRect(event->globalPos()));
- }
-
- m_transparentRect->onMousePressEvent(event,type);
- return true;
- }
- return false;
- }
-
- bool FrameLessHelper::onMoveEvent(QMouseEvent *event)
- {
- if(m_widgetOperator==WidgetOperator::None ||
- (m_widgetOperator == WidgetOperator::Resize && m_widget->isFullScreen())){
- return false;
- }
-
- #ifdef TITLEBAR
- if(m_widget->isFullScreen())
- m_titleBar->onMaxClick();
- #endif
-
- m_isMove =true;
- m_transparentRect->show();
- m_transparentRect->onMoveEvent(event,event->globalPos()-m_widget->pos());
- return false;
- }
-
- bool FrameLessHelper::onMouseReleaseEvent(QMouseEvent *event)
- {
- if(event->button()!=Qt::LeftButton || m_widgetOperator==WidgetOperator::None){
- return false;
- }
-
- m_transparentRect->onMouseReleaseEvent(event);
-
- m_transparentRect->hide();
- if(m_isMove){
- if(m_widget->isFullScreen())
- m_widget->showNormal();
- auto &&rect = m_transparentRect->getRect();
- m_widget->move(rect.topLeft());
- m_widget->resize(rect.size());
- }
- m_isMove = false;
- m_widgetOperator = WidgetOperator::None;
- return false;
- }
-
- QRect FrameLessHelper::calMaxMoveRect(const QPoint &evPos)
- {
- //最大化时拖动标题栏的规则:宽度分为3份,鼠标位于左侧则向左上角对齐,右侧则向右上角对齐,中间部分则按中间对齐
- auto rect = m_widget->normalGeometry();
- rect.moveTop(0);
- double gPosX=evPos.x();
- double step = m_widget->geometry().width()/3.0;
- double left=0;
- if(gPosX>step*2){
- left=step*3-rect.width();
- }
- else if(gPosX>step && gPosX<=step*2){
- left=gPosX-rect.width()/2.0;
- }
- rect.moveLeft(left);
- return rect;
- }
-
- #ifndef FRAMELESSHELPER_H
- #define FRAMELESSHELPER_H
- #include "transparentRect.h"
- #include "titleBar.h"
- #include "cursorTransform.h"
-
- #include <QObject>
- #include <QMouseEvent>
- #include <QHoverEvent>
- #include <QRect>
- #include <QWidget>
-
- /*
- FrameLessHelper
- 1.管理窗口无边框功能
- 2.输入为QWidget(构造)和QEvent(eventFilter)
- */
- class FrameLessHelper : public QObject
- {
- Q_OBJECT
- public:
- FrameLessHelper(QWidget *widget);
- bool eventFilter(QObject *watched, QEvent *event) override;
- void setBorderThickness(int thickness);
- void setTitleHeight(int height);
- void setMinHeight(int height);
- void setMinWidth(int width);
- #ifdef TITLEBAR
- QWidget *getTitleBar();
-
- void onMinClick();
- void onMaxClick();
- void onCloseClick();
- #endif
- private:
- bool onHoverEvent(QObject *watched,QHoverEvent *event);
- bool onDbClickEvent(QMouseEvent *event);
- bool onMousePressEvent(QMouseEvent *event);
- bool onMoveEvent(QMouseEvent *event);
- bool onMouseReleaseEvent(QMouseEvent *event);
-
- QRect calMaxMoveRect(const QPoint &evPos);
- //代理窗口
- QWidget *m_widget;
- //预拖动窗口
- TransparentRect *m_transparentRect;
- enum WidgetOperator m_widgetOperator;
- bool m_isMove;
- #ifdef TITLEBAR
- TitleBar *m_titleBar;
- #endif
- };
- #endif // FRAMELESSHELPER_H
- #include "titleBar.h"
- #include <QIcon>
- #include <QPalette>
-
- int iconSize=30;
-
-
- TitleBar::TitleBar(QWidget *parent,bool isMax)
- : QWidget{parent}
- , m_minBtn{new QPushButton(this)}
- , m_maxBtn{new QPushButton(this)}
- , m_closeBtn{new QPushButton(this)}
- , m_hLayout{new QHBoxLayout(this)}
- , m_spacer{new QSpacerItem(500,30,QSizePolicy::Expanding)}
- , m_isMax{isMax}
- {
- m_minBtn->setIcon(QIcon(":/img/min.png"));
- QString maxPic = m_isMax?":/img/normal.png":":/img/max.png";
- m_maxBtn->setIcon(QIcon(maxPic));
- m_closeBtn->setIcon(QIcon(":/img/close.png"));
-
- connect(m_minBtn,&QPushButton::clicked,this,&TitleBar::minimumSizeClick);
- connect(m_maxBtn,&QPushButton::clicked,this,&TitleBar::showNormalClick);
- connect(m_maxBtn,&QPushButton::clicked,this,&TitleBar::onMaxClick);
- connect(m_closeBtn,&QPushButton::clicked,this,&TitleBar::closeClick);
-
-
- m_minBtn->resize(iconSize,iconSize);
- m_maxBtn->resize(iconSize,iconSize);
- m_maxBtn->resize(iconSize,iconSize);
-
-
- m_hLayout->addSpacerItem(m_spacer);
- m_hLayout->addWidget(m_minBtn);
- m_hLayout->addWidget(m_maxBtn);
- m_hLayout->addWidget(m_closeBtn);
- m_hLayout->setSpacing(0);
- m_hLayout->setContentsMargins(0,0,0,0);
-
- QPalette palette(this->palette());
- palette.setColor(QPalette::Background, QColor(100,100,100));
- this->setAutoFillBackground(true);
- this->setPalette(palette);
- }
-
- void TitleBar::onMaxClick()
- {
- if(m_isMax){
- m_maxBtn->setIcon(QIcon(":/img/max.png"));
- m_isMax=false;
- }
- else{
- m_maxBtn->setIcon(QIcon(":/img/normal.png"));
- m_isMax=true;
- }
- }
- #ifndef TITLEBAR_H
- #define TITLEBAR_H
-
- #include <QWidget>
- #include <QPushButton>
- #include <QHBoxLayout>
- #include <QSpacerItem>
-
-
- class TitleBar : public QWidget
- {
- Q_OBJECT
- public:
- explicit TitleBar(QWidget *parent = nullptr,bool isMax=false);
- void onMaxClick();
- signals:
- void minimumSizeClick();
- void showNormalClick();
- void closeClick();
-
- private:
- QPushButton *m_minBtn;
- QPushButton *m_maxBtn;
- QPushButton *m_closeBtn;
-
- QHBoxLayout *m_hLayout;
- QSpacerItem *m_spacer;
- bool m_isMax;
- };
-
- #endif // TITLEBAR_H
- #include "transparentRect.h"
- #include "framelessData.h"
- #include <QMouseEvent>
- #include <QDesktopWidget>
- #include <QDebug>
- #include <QPainter>
- #include <QPen>
- #include <QScreen>
- #include <QGuiApplication>
- #include <QList>
-
-
-
-
- TransparentRect::TransparentRect(QWidget *parent)
- : QWidget(parent)
- , m_areaType(AreaType::None)
- {
- setWindowFlag(Qt::FramelessWindowHint);
- setAttribute(Qt::WA_TranslucentBackground);
- }
-
- void TransparentRect::setRect(const QRect &rect)
- {
- m_rect=rect;
- }
-
- QRect TransparentRect::getRect() const
- {
- return m_rect;
- }
-
- void TransparentRect::onMousePressEvent(QMouseEvent *event,AreaType type)
- {
- m_lastPos = event->pos();
- //
- auto screens = QGuiApplication::screens();
- QRect rect;
- //QPainter painter(&m_pixmap);
- for(auto s:screens){
- auto geom = s->geometry();
- rect |= geom;
- //auto pixmap = s->grabWindow(0, geom.x(), geom.y(), geom.width(), geom.height());
- //static int i = 0;
- //QFile file(QString("./test%1.png").arg(i++));
- //file.open(QIODevice::WriteOnly);
- //pixmap.save(&file);
- //file.close();
- //painter.drawPixmap(s->geometry(), pixmap);
- }
- //painter.end();
- m_startInch = QGuiApplication::screenAt(event->globalPos())->logicalDotsPerInch();
- setGeometry(rect);
- m_pixmap= QGuiApplication::primaryScreen()->grabWindow(0, rect.x(), rect.y(), rect.width(), rect.height());
- m_areaType = type;
-
- #if 0
- //
- QFile file("./test.png");
- file.open(QIODevice::WriteOnly);
- m_pixmap.save(&file);
- file.close();
- #endif // 0
- }
-
- void TransparentRect::onMoveEvent(QMouseEvent *event,const QPoint &newPos)
- {
-
- m_scaled = QGuiApplication::screenAt(event->globalPos())->logicalDotsPerInch()/ m_startInch;
-
- // auto newPos = event->pos();
- int xOff=0,yOff=0,wOff=0,hOff=0;
- int posXOff=newPos.x()-m_lastPos.x();
- int posYOff = newPos.y()-m_lastPos.y();
- switch (m_areaType) {
- case AreaType::LeftTopArea:
- xOff = posXOff;
- yOff = posYOff;
- break;
- case AreaType::TopArea:
- yOff = posYOff;
- break;
- case AreaType::RightTopArea:
- yOff = posYOff;
- wOff = posXOff;
- break;
- case AreaType::LeftArea:
- xOff = posXOff;
- break;
- case AreaType::RightArea:
- wOff = posXOff;
- break;
- case AreaType::LeftBottomArea:
- xOff = posXOff;
- hOff = posYOff;
- break;
- case AreaType::BottomArea:
- hOff = posYOff;
- break;
- case AreaType::RightBottomArea:
- wOff = posXOff;
- hOff = posYOff;
- break;
- case AreaType::TitleArea: //move
- m_rect.moveTopLeft(m_rect.topLeft()+QPoint(posXOff,posYOff));
- break;
- default:
- break;
- }
- //min judget:
- if(m_rect.width()-xOff<=FrameLessData::minWidth)
- xOff=0;
- else if(m_rect.left()<event->globalPos().x() && xOff<0)
- xOff=0;
- if(m_rect.width()+wOff<=FrameLessData::minWidth)
- wOff=0;
- else if(m_rect.right()>event->globalPos().x() && wOff>0)
- wOff=0;
-
- if(m_rect.height()-yOff<=FrameLessData::minHeight)
- yOff=0;
- else if(m_rect.top()<event->globalPos().y() && yOff<0)
- yOff=0;
- if(m_rect.height()+hOff<=FrameLessData::minHeight)
- hOff=0;
- else if(m_rect.bottom()>event->globalPos().y() && hOff>0)
- hOff=0;
-
- //resize:
- m_rect.setTop(m_rect.top()+yOff);
- m_rect.setLeft(m_rect.left()+xOff);
- m_rect.setWidth(m_rect.width()+wOff);
- m_rect.setHeight(m_rect.height()+hOff);
- m_lastPos = newPos;
- update();
- }
-
- void TransparentRect::onMouseReleaseEvent(QMouseEvent *event)
- {
- m_areaType=AreaType::None;
- //释放pixmap,
- m_pixmap = QPixmap();
-
-
-
- //重绘,触发paintEvent,否则会有闪动,
- //注意要在hide之前调用。
- repaint();
- }
-
- void TransparentRect::paintEvent(QPaintEvent *event)
- {
- QPainter painter(this);
- painter.setRenderHints(QPainter::SmoothPixmapTransform | QPainter::HighQualityAntialiasing | QPainter::Antialiasing);
- painter.setBackground(FrameLessData::transparentRectBkground);
- painter.drawPixmap(0, 0, m_pixmap);
- QPen pen(FrameLessData::borderStyle);
- pen.setWidth(FrameLessData::borderThickness);
- pen.setColor(FrameLessData::borderColor);
- painter.setPen(pen);
- //背景色取反,要求color必须是white
- painter.setCompositionMode(QPainter::RasterOp_SourceAndNotDestination);
- //rect位置相对与this的geometry
- auto rect=m_rect;
- rect.moveTopLeft(rect.topLeft()-geometry().topLeft());
-
- rect.setWidth(rect.width()*m_scaled);
- rect.setHeight(rect.height()*m_scaled);
-
- painter.drawRect(rect);
- painter.end();
- }
- #ifndef TRANSPARENTRECT_H
- #define TRANSPARENTRECT_H
- #include <QWidget>
- #include "framelessData.h"
-
- class TransparentRect : public QWidget
- {
- Q_OBJECT
- public:
- TransparentRect(QWidget *parent=nullptr);
-
- void setRect(const QRect &rect);
- QRect getRect() const;
- void onMousePressEvent(QMouseEvent *event,AreaType type);
- void onMoveEvent(QMouseEvent *event,const QPoint &pos);
- void onMouseReleaseEvent(QMouseEvent *event);
- protected:
- virtual void paintEvent(QPaintEvent *event) override;
- private:
-
- QRect m_rect;
-
- QPoint m_lastPos;
- AreaType m_areaType;
- QPixmap m_pixmap;
- double m_scaled=1.0;
- double m_startInch;
- };
-
- #endif // TRANSPARENTRECT_H
- cmake_minimum_required(VERSION 3.5)
-
- project(frameLessHelper VERSION 0.1 LANGUAGES CXX)
-
-
- add_definitions(-DTITLEBAR)
- #add_definitions(-DRUBBER)
-
- set(CMAKE_AUTOUIC ON)
- set(CMAKE_AUTOMOC ON)
- set(CMAKE_AUTORCC ON)
-
- set(CMAKE_CXX_STANDARD 17)
- set(CMAKE_CXX_STANDARD_REQUIRED ON)
-
- find_package(QT NAMES Qt6 Qt5 REQUIRED COMPONENTS Widgets WebEngineWidgets)
- find_package(Qt${QT_VERSION_MAJOR} REQUIRED COMPONENTS Widgets WebEngineWidgets)
-
- file(GLOB PROJECT_SOURCES "*.cpp" "*.h" "*.ui" "framelessHelper/*.*")
-
- if(${QT_VERSION_MAJOR} GREATER_EQUAL 6)
- qt_add_executable(frameLessHelper
- MANUAL_FINALIZATION
- ${PROJECT_SOURCES}
- )
- # Define target properties for Android with Qt 6 as:
- # set_property(TARGET frameLessHelper APPEND PROPERTY QT_ANDROID_PACKAGE_SOURCE_DIR
- # ${CMAKE_CURRENT_SOURCE_DIR}/android)
- # For more information, see https://doc.qt.io/qt-6/qt-add-executable.html#target-creation
- else()
- if(ANDROID)
- add_library(frameLessHelper SHARED
- ${PROJECT_SOURCES}
- )
- # Define properties for Android with Qt 5 after find_package() calls as:
- # set(ANDROID_PACKAGE_SOURCE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/android")
- else()
- add_executable(frameLessHelper
- ${PROJECT_SOURCES}
- framelessHelper/titleBarImg.qrc
- webview.h webview.cpp
-
-
-
- )
- endif()
- endif()
-
- target_link_libraries(frameLessHelper PRIVATE Qt${QT_VERSION_MAJOR}::Widgets Qt${QT_VERSION_MAJOR}::WebEngineWidgets)
-
- set_target_properties(frameLessHelper PROPERTIES
- MACOSX_BUNDLE_GUI_IDENTIFIER my.example.com
- MACOSX_BUNDLE_BUNDLE_VERSION ${PROJECT_VERSION}
- MACOSX_BUNDLE_SHORT_VERSION_STRING ${PROJECT_VERSION_MAJOR}.${PROJECT_VERSION_MINOR}
- MACOSX_BUNDLE TRUE
- WIN32_EXECUTABLE TRUE
- )
-
- install(TARGETS frameLessHelper
- BUNDLE DESTINATION .
- LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
- RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
- )
-
- if(QT_VERSION_MAJOR EQUAL 6)
- qt_finalize_executable(frameLessHelper)
- endif()
- #include "mainwindow.h"
- #include "./ui_mainwindow.h"
- #include <QGridLayout>
- #include <QWebEngineView>
- #include <QFrame>
- #include "webview.h"
- #include <QDebug>
-
- MainWindow::MainWindow(QWidget *parent)
- : QMainWindow(parent)
- , ui(new Ui::MainWindow)
- , m_frameHelper(new FrameLessHelper(this))
- {
- ui->setupUi(this);
- setWindowFlags(Qt::FramelessWindowHint);
- installEventFilter(this);
- #ifdef TITLEBAR
- //titleBar
- auto titleBar = m_frameHelper->getTitleBar();
- if(titleBar){
- QGridLayout *layout = new QGridLayout(centralWidget());
- layout->setSpacing(0);
- layout->setContentsMargins(0,0,0,0);
- layout->addWidget(titleBar,0,0,0,0,Qt::AlignTop);
- titleBar->setFixedHeight(32);
-
- #if 0
- WebView *view = new WebView();
- view->load(QUrl("https:www.baidu.com"));
- auto childs = view->children();
- for(auto child:childs){
- // if(child->metaObject()->className()==QString("QtWebEngineCore::RenderWidgetHostViewQtDelegateWidget"))
- child->installEventFilter(this);
- }
- view->installEventFilter(this);
- #else
- QFrame *view = new QFrame();
- #endif
- layout->addWidget(view,1,0);
- }
-
- setMouseTracking(true);
- #endif
- }
-
- MainWindow::~MainWindow()
- {
- delete ui;
- }
-
- bool MainWindow::eventFilter(QObject *watched, QEvent *event)
- {
- return m_frameHelper->eventFilter(watched,event);
- }
-
- #ifndef MAINWINDOW_H
- #define MAINWINDOW_H
-
- #include <QMainWindow>
- #include "framelessHelper/framelessHelper.h"
-
- QT_BEGIN_NAMESPACE
- namespace Ui { class MainWindow; }
- QT_END_NAMESPACE
-
- class MainWindow : public QMainWindow
- {
- Q_OBJECT
-
- public:
- MainWindow(QWidget *parent = nullptr);
- ~MainWindow();
- bool eventFilter(QObject *watched, QEvent *event) override;
- private:
- Ui::MainWindow *ui;
- FrameLessHelper *m_frameHelper;
- };
- #endif // MAINWINDOW_H
源码:
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
赞
踩
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。