目录

  • 本系列目录
  • 功能考虑
    • 滑动鼠标截取当前桌面显示内容
      • 滑动鼠标截取桌面图片
      • 截图辅助功能
      • 截取部分二次处理
      • 代码实现

本系列目录

Qt 简单截图工具(一) 高仿QQ截屏 滑动截屏
Qt 简单截图工具(二) 添加菜单栏,添加取色器、切图功能


# 截屏工具分析

  • 闲来无聊,在学习qt几个月后突然想制作一个截屏工具来给自己使用。简单分析了一下,认为截屏方式共可以分为三种:
  1. 获取当前窗口或控件的界面保存为图片
  2. 滑动鼠标截取当前桌面显示内容
  3. 识别鼠标指向窗口。控件或图标保存为图片

本章主要实现滑动鼠标截取当前桌面显示内容这种方式,侧重讲解大体实现,具体功能见代码

功能考虑

  • 改功能的实现主要分为三大部分:滑动鼠标截取桌面图片截图辅助功能截取部分二次处理

滑动鼠标截取当前桌面显示内容

滑动鼠标截取桌面图片

  1. 获取当前桌面显示内容为图片,此后的所有操作都是围绕这个图片进行。
QPixmap show_top_pixmap_ ;
show_top_pixmap_ = QPixmap::grabWindow(QApplication::desktop()->winId);          //当前桌面显示内容
  1. 使用画笔将桌面图片绘制到widget上,全屏显示,并绘制阴影,截取操作实际上是在该widget对象上进行,但此时效果看起来就像在原桌面上操作。
//窗口设置
this->setWindowModality(Qt::WindowModal);                                    //设置窗口模态类型:半模态,窗口级模态对话框,阻塞父窗口、父窗口的父窗口及兄弟窗口。
this->setWindowFlag(Qt::WindowContextHelpButtonHint, false);                 //一次上下文帮助按钮
this->setWindowState(Qt::WindowActive | Qt::WindowFullScreen);               //全屏显示//阴影色效果绘制
Qpainter *_painter;
QColor shadow_color = QColor(0, 0, 0, 100);                                  //阴影色
_painter->setPen(QPen(Qt::white, 1, Qt::SolidLine, Qt::FlatCap));            //设置画笔
_painter->drawPixmap(0, 0, show_top_pixmap_ );                               //将桌面图片绘制到窗体上
_painter->fillRect(show_top_pixmap_ .rect(), shadow_color );                 //绘制阴影色效果
  1. 鼠标按下为起始位置p1,鼠标释放为结束位置p2,以p1,p2两点绘制矩形,矩形所在区域则为截屏区域。考虑到美化可以将矩形边框去掉,在矩形八个位置绘制圆形,以便之后的截屏区域二次调整。


实现上述功能需要重写的函数:

virtual void mousePressEvent(QMouseEvent *event);             //鼠标按下
virtual void mouseReleaseEvent(QMouseEvent *event);           //鼠标移动
virtual void mouseMoveEvent(QMouseEvent *event);              //鼠标释放
virtual void paintEvent(QPaintEvent *event);                  //画笔绘制
  • 裁剪矩形绘制
//通过上述函数获取鼠标起始位置
Qpoint mouse_slid_begin_point_, mouse_slid_end_point_;            //截取图片:滑动鼠标起始位置
Qpixmap pixmap_;                //截屏结果图片
QRect selected_rect = GetRect(mouse_slid_begin_point, mouse_slid_end_point_);               //根据两点计算矩形大小
_painter->drawPixmap(selected_rect .topLeft(), pixmap_);              //绘制矩形区域内裁剪图片

pixmap_对象中存放的内容就是需要保存的图片,这样基本的截图功能就已经实现。

截图辅助功能

  • 截图工具的辅助功能暂时先不考虑对图片本身进行二次操作(例如:自定义画笔,箭头,马赛克等),优先考虑将这个图片的参数信息显示,具备一些基本操作等。暂时考虑添加的信息显示:裁剪区域大小,十字形辅助线,锚点(图片局部放大显示),像素点颜色,当前鼠标位置,提示信息。

  1. 裁剪区域大小,十字形辅助线,当前鼠标位置,提示信息 这类信息就是计算好要显示的位置,然后将信息绘制到上面即可,具体实现这里不加赘述。
  2. 锚点功能。这里取17X11的图片,然后放大十倍进行显示。获取鼠标当前位置p3,以p3为中心截取17X11区域内图片,将图片放大后绘制在大小为170X110的矩形内。十字形锚点,简单来说为两个大小为170X10,10X110的蓝色透明矩形垂直交叉绘制,交叉部分绘制一个大小为10X10填充色为当前鼠标指向色的矩形。
//*******************信息框--图片区****************//矩形:图片框QRect rect_infomation_pixmap_rect(information_x, information_y, 170, 110);//放大图片处理QRect rect_information_pixmap(mouse_now_point_.x() - 8, mouse_now_point_.y() - 5, 17, 11);QPixmap information_pixmap_ = show_top_pixmap_.copy(rect_information_pixmap).scaled(170, 110, Qt::KeepAspectRatioByExpanding);_painter->drawPixmap(rect_infomation_pixmap_rect.topLeft(), information_pixmap_);//中央辅助线绘制QColor information_pixmap_color = QColor(0, 0, 255, 150);QRect information_pixmap_x(information_x, information_y + 50, 170, 10);QRect information_pixmap_y(information_x + 80, information_y, 10, 110);_painter->fillRect(information_pixmap_x, information_pixmap_color);_painter->fillRect(information_pixmap_y, information_pixmap_color);QRect information_pixmap_f(information_x + 80, information_y + 50, 10, 10);_painter->setBrush(QColor(rgb_color));_painter->drawRect(information_pixmap_f);_painter->setBrush(Qt::NoBrush);_painter->drawRect(rect_infomation_pixmap_rect);
  1. 像素点颜色。当前屏幕图片为全屏显示,所以鼠标的相对位置(event->pos())就是当前指向像素点的位置,由此获取像素点颜色。
//获取图片固定位置颜色
QRgb GetPixmapColor(QPixmap _pixmap, QPoint _position);QRgb CustomSlidScreenCapture::GetPixmapColor(QPixmap _pixmap, QPoint _position)
{QImage image_ = _pixmap.toImage();//获取一行像素点颜色QRgb *line_rgb = (QRgb *)image_.scanLine(_position.y());//取对应像素点颜色return line_rgb[_position.x()];
}
  • 像素点颜色转化为文本信息
QRgb rgb_color = GetPixmapColor(show_top_pixmap_, mouse_now_point_);
QString text_information_color = "(" + QString::number(qRed(rgb_color)) + "  ," + QString::number(qGreen(rgb_color)) + "  ," + QString::number(qBlue(rgb_color)) + ")";

截取部分二次处理

在获取截取区域矩形后,需要对当前矩形进行微调,调整分为八个方向:上、下、左、右、左上、左下、右上、右下,在判断当前鼠标所处矩形位置后,记录鼠标按下与释放的位置p4、p5,根据这两点计算出鼠标移动的距离,然后对绘制的矩形区域进行调整。除却调整矩形大小之外,矩形还应该可以拖动,实现方式与上面大同小异。对于截取部分的二次处理,主要是对数据的处理,没有太大的难度,这里不在多加赘述。

  • 设置鼠标的不同样式
this->setCursor(Qt::ArrowCursor);
  • 鼠标样式枚举枚举
枚举值 含义
Qt::ArrowCursor 数表常态
Qt::SizeVerCursor 垂直上下箭头
Qt::SizeAllCursor 全方向箭头
Qt::SizeHorCursor 水平左右箭头
Qt::SizeBDiagCursor 斜左下右上箭头
Qt::SizeFDiagCursor 斜左上右下箭头

代码实现

至此,滑动鼠标截取当前桌面显示内容功能已大致完成,代码具体实现如下:

  • custom_slid_screen_capture.h
#pragma once
#include <QDialog>
#include <QObject>
#include <QWidget>
#include <QPixmap>
#include <QImage>
#include <QPoint>
#include <QPainter>
#include <QApplication>
#include <QDesktopWidget>
#include <QStandardPaths>
#include <QKeyEvent>
#include <QMenu>
#include <QClipboard>
#include <QtGui//QWindow>
#include <QDebug>
#include <QtGui/QScreen>
#include <QFileDialog>
#include <Windows.h>
#include <vector>enum ArrowType
{Arrow_Cursor,Size_Ver_Cursor_Top,Size_Ver_Cursor_Bottom,Size_Hor_Cursor_Left,Size_Hor_Cursor_Right,Size_All_Cursor,Size_Bdiag_Cursor_Top,Size_Bdiag_Cursor_Bottom,Size_Fdiag_Cursor_Top,Size_Fdiag_Cursor_Bottom
};class CustomSlidScreenCapture:public QDialog
{Q_OBJECT
public:CustomSlidScreenCapture();~CustomSlidScreenCapture();public:void ScreenCapture();private:QPixmap show_top_pixmap_;                                       //当前桌面显示内容QPixmap pixmap_;                                              //当前图片QString pixel_color_;                                         //当前像素颜色QPoint mouse_slid_begin_point_, mouse_slid_end_point_;          //截取图片:滑动鼠标起始位置QPoint mouse_now_point_;                                      //鼠标当前位置bool mouse_slid_press_flag_;                                    //截取图片:鼠标是否按下bool mouse_slid_finish_;                                        //截取图片:截屏区域是否选择完毕QPoint mouse_rect_begin_point_, mouse_rect_end_point_;          //调整截屏区域:滑动鼠标起始位置bool mouse_rect_press_flag_;                                    //调整截屏区域:鼠标是否按下QPoint mouse_result_begin_point_, mouse_result_end_point_;        //调整结果:图片起始位置private:/*******************画笔绘制相关********************///绘制整体背景图片void DrawBackgroundPixmap(QPainter *_painter);//绘制滑动矩形框void DrawSlidRect(QPainter *_painter);//绘制辅助线void DrawBoostLine(QPainter *_painter);//绘制信息框void DrawInformationRect(QPainter *_painter);//绘制结果矩形框--大小重绘void DrawFruitRect(QPainter *_painter);//绘制结果矩形框--样式void DrawFruitRectStyle(QPainter *_painter, QPoint& _begion_point, QPoint& _end_point);//绘制结果矩形框相关判断显示void DrawFruitRectIsShow(QPainter *_painter);//获取要绘制的矩形QRect GetRect(const QPoint& _begin_Point, const QPoint& _end_Point);//获取图片固定位置颜色QRgb GetPixmapColor(QPixmap _pixmap, QPoint _position);//获取起始点的偏移QPoint GetOffsetPoint(const QPoint& _begin_Point, const QPoint& _end_Point);//判断点是否在该矩形内ArrowType PointInRect(QPoint& _point, QRect _rect);//保存图片void Save();//返回当前截图对象QPixmap GetScreenPixmap();protected:virtual void mousePressEvent(QMouseEvent *event);virtual void mouseReleaseEvent(QMouseEvent *event);virtual void mouseMoveEvent(QMouseEvent *event);virtual void paintEvent(QPaintEvent *event);virtual void keyReleaseEvent(QKeyEvent *event);};
  • custom_slid_screen_capture.cpp
#include "custom_slid_screen_capture.h"std::vector<QRect> allWindowRect;
std::vector<HWND> allWindowHwnd;
std::vector<MyRect> myRectRestlt;bool CALLBACK MyEnumWindowsProc(HWND _hwnd, LPARAM _lparam);CustomSlidScreenCapture::CustomSlidScreenCapture(): mouse_slid_press_flag_(false), mouse_slid_finish_(false), mouse_rect_press_flag_(false), pixel_color_("(0,0,0)")
{this->setWindowModality(Qt::WindowModal);this->setWindowFlag(Qt::WindowContextHelpButtonHint, false);this->setWindowState(Qt::WindowActive | Qt::WindowFullScreen);//默认鼠标移动进入鼠标移动响应函数this->setMouseTracking(true);::EnumWindows((WNDENUMPROC)MyEnumWindowsProc, 0);
}CustomSlidScreenCapture::~CustomSlidScreenCapture()
{}void CustomSlidScreenCapture::ScreenCapture()
{show_top_pixmap_ = QPixmap::grabWindow(QApplication::desktop()->winId());
}QRect CustomSlidScreenCapture::GetRect(const QPoint& _begin_Point, const QPoint& _end_Point)
{int x, y, width, height;width = qAbs(_begin_Point.x() - _end_Point.x());height = qAbs(_begin_Point.y() - _end_Point.y());x = _begin_Point.x() < _end_Point.x() ? _begin_Point.x() : _end_Point.x();y = _begin_Point.y() < _end_Point.y() ? _begin_Point.y() : _end_Point.y();QRect selected_rect = QRect(x, y, width, height);                                  //QRect类代表一个矩形区域if (selected_rect.width() == 0){selected_rect.setWidth(1);}if (selected_rect.height() == 0){selected_rect.setHeight(1);}return selected_rect;
}QRgb CustomSlidScreenCapture::GetPixmapColor(QPixmap _pixmap, QPoint _position)
{QImage image_ = _pixmap.toImage();QRgb *line_rgb = (QRgb *)image_.scanLine(_position.y());return line_rgb[_position.x()];
}QPoint CustomSlidScreenCapture::GetOffsetPoint(const QPoint& _begin_Point, const QPoint& _end_Point)
{return QPoint(_end_Point.x() - _begin_Point.x(), _end_Point.y() - _begin_Point.y());
}ArrowType CustomSlidScreenCapture::PointInRect(QPoint& _point, QRect _rect)
{int x1 = _rect.topLeft().x();int y1 = _rect.topLeft().y();int x2 = _rect.bottomRight().x();int y2 = _rect.bottomRight().y();int range_size = (_rect.width() ? _rect.height() : _rect.width()>_rect.height())/3;//全if (_point.x() >= x1 + range_size && _point.x() <= x2 - range_size && _point.y() >= y1 + range_size && _point.y() <= y2 - range_size)return Size_All_Cursor;//水平-左if (_point.x() >= x1 - 100 && _point.x() <= x1 + range_size && _point.y() >= y1 + range_size && _point.y() <= y2 - range_size)return Size_Hor_Cursor_Left;//水平-右if (_point.x() >= x2 - range_size && _point.x() <= x2 + 100 && _point.y() >= y1 + range_size && _point.y() <= y2 - range_size)return Size_Hor_Cursor_Right;//垂直-上if (_point.x() >= x1 + range_size && _point.x() <= x2 - range_size && _point.y() >= y1 - 100 && _point.y() <= y1 + range_size)return Size_Ver_Cursor_Top;//垂直-下if (_point.x() >= x1 + range_size && _point.x() <= x2 - range_size && _point.y() >= y2 - range_size && _point.y() <= y2 + 100)return Size_Ver_Cursor_Bottom;//斜下-上if (_point.x() >= x1 - 100 && _point.x() <= x1 + range_size && _point.y() >= y1 - 100 && _point.y() <= y1 + range_size)return Size_Fdiag_Cursor_Top;//斜下-下if (_point.x() >= x2 - range_size && _point.x() <= x2 + 100 && _point.y() >= y2 - range_size && _point.y() <= y2 + 100)return Size_Fdiag_Cursor_Bottom;//斜上-上if (_point.x() >= x2 - range_size && _point.x() <= x2 + 100 && _point.y() >= y1 - 100 && _point.y() <= y1 + range_size)return Size_Bdiag_Cursor_Top;//斜上-下if (_point.x() >= x1 - 100 && _point.x() <= x1 + range_size && _point.y() >= y2 - range_size && _point.y() <= y2 + 100)return Size_Bdiag_Cursor_Bottom;return Arrow_Cursor;
}void CustomSlidScreenCapture::CalculataRectDistance(QRect rect)
{int dis = rect.width() + rect.height();MyRect temp_myrect;temp_myrect.myRect_ = rect;temp_myrect.distance_ = dis;myRectRestlt.push_back(temp_myrect);
}void CustomSlidScreenCapture::Save()
{QString file_name = QFileDialog::getSaveFileName(this, QStringLiteral("截图文件保存"), "picture1.jpg", tr("Images(*.png,*.bmp,*.jpg)"));pixmap_.save(file_name);
}QPixmap CustomSlidScreenCapture::GetScreenPixmap()
{return pixmap_;
}void CustomSlidScreenCapture::mousePressEvent(QMouseEvent *event)
{//滑动获取截屏区域if (event->button() == Qt::LeftButton&&!mouse_slid_finish_){mouse_slid_press_flag_ = true;mouse_slid_begin_point_ = event->pos();}//拖动截屏区域if (event->button() == Qt::LeftButton&&!mouse_rect_press_flag_&&mouse_slid_finish_&&PointInRect(mouse_now_point_, GetRect(mouse_slid_begin_point_, mouse_slid_end_point_))!=Arrow_Cursor){mouse_rect_press_flag_ = true;mouse_rect_begin_point_ = event->pos();mouse_rect_end_point_ = event->pos();mouse_result_begin_point_ = mouse_slid_begin_point_;mouse_result_end_point_ = mouse_slid_end_point_;}
#if 0//点击截取屏幕if (event->button() == Qt::LeftButton&&!mouse_rect_press_flag_&&mouse_slid_finish_&&PointInRect(mouse_now_point_, GetRect(mouse_slid_begin_point_, mouse_slid_end_point_)) != Arrow_Cursor){mouse_rect_end_point_ = event->pos();mouse_rect_press_flag_ = false;mouse_slid_begin_point_ = mouse_result_begin_point_;mouse_slid_end_point_ = mouse_result_end_point_;}
#endifupdate();return QWidget::mousePressEvent(event);
}void CustomSlidScreenCapture::mouseReleaseEvent(QMouseEvent *event)
{//滑动获取截屏区域if (mouse_slid_press_flag_){mouse_slid_end_point_ = event->pos();mouse_slid_press_flag_ = false;mouse_slid_finish_ = true;mouse_result_begin_point_ = mouse_slid_begin_point_;mouse_result_end_point_ = mouse_slid_end_point_;}//拖动截屏区域if (mouse_rect_press_flag_){mouse_rect_end_point_ = event->pos();mouse_rect_press_flag_ = false;/*QRect rect_f = GetRect(mouse_result_begin_point_, mouse_result_end_point_);mouse_slid_begin_point_ = rect_f.topLeft();mouse_slid_end_point_ = rect_f.bottomRight();*/mouse_slid_begin_point_ = mouse_result_begin_point_;mouse_slid_end_point_ = mouse_result_end_point_;}update();return QWidget::mouseReleaseEvent(event);
}void CustomSlidScreenCapture::mouseMoveEvent(QMouseEvent *event)
{mouse_now_point_ = event->pos();//滑动获取截屏区域if (mouse_slid_press_flag_){mouse_slid_end_point_ = event->pos();                                                                }//拖动截屏区域if (mouse_rect_press_flag_){mouse_rect_end_point_ = event->pos();}//调用该函数时会调用paintEvent函数update(); return QWidget::mouseMoveEvent(event);
}void CustomSlidScreenCapture::keyReleaseEvent(QKeyEvent *event)
{//退出if (event->key() == Qt::Key_Escape){close();}//保存颜色if (event->key() == Qt::Key_C){QApplication::clipboard()->setText(pixel_color_);}//复制内容到剪切板if (event->matches(QKeySequence::Copy)){QApplication::clipboard()->setPixmap(pixmap_);}//重置if (event->key() == Qt::Key_Enter){mouse_slid_press_flag_ = false;mouse_slid_finish_ = false;}//保存图片if (event->matches(QKeySequence::Save)){Save();mouse_slid_press_flag_ = false;mouse_slid_finish_ = false;}update();
}void CustomSlidScreenCapture::DrawBackgroundPixmap(QPainter *_painter)
{QColor shadowColor = QColor(0, 0, 0, 100);                                            //阴影色_painter->setPen(QPen(Qt::white, 1, Qt::SolidLine, Qt::FlatCap));                   //设置画笔_painter->drawPixmap(0, 0, show_top_pixmap_);                                      //将获取的图片画到窗体上_painter->fillRect(show_top_pixmap_.rect(), shadowColor);                           //画影罩效果
}void CustomSlidScreenCapture::DrawSlidRect(QPainter *_painter)
{//绘制截取区域QRect selected_rect = GetRect(mouse_slid_begin_point_, mouse_slid_end_point_);pixmap_ = show_top_pixmap_.copy(selected_rect);_painter->drawPixmap(selected_rect.topLeft(), pixmap_);DrawFruitRectStyle(_painter, mouse_slid_begin_point_, mouse_slid_end_point_);//截取区域大小信息QString pixmap_size = QString::number(selected_rect.width()) + " X " + QString::number(selected_rect.height());QColor information_color = QColor(0, 0, 0, 150);QFontMetrics fm(_painter->font());QRect fm_rect = fm.boundingRect(pixmap_size);QRect pixmap_size_rect(selected_rect.topLeft().x(), selected_rect.topLeft().y() -20, fm_rect.width() + 5, 20);_painter->fillRect(pixmap_size_rect, information_color);_painter->drawText(pixmap_size_rect,Qt::AlignCenter, pixmap_size);
}void CustomSlidScreenCapture::DrawBoostLine(QPainter *_painter)
{//绘制辅助线QLine line_boost_x(QPoint(0, mouse_slid_end_point_.y()), QPoint(show_top_pixmap_.width(), mouse_slid_end_point_.y()));QLine line_boost_y(QPoint(mouse_slid_end_point_.x(), 0), QPoint(mouse_slid_end_point_.x(), show_top_pixmap_.height()));_painter->drawLine(line_boost_x);_painter->drawLine(line_boost_y);
}void CustomSlidScreenCapture::DrawInformationRect(QPainter *_painter)
{//绘制辅助信息框位置int information_x = mouse_now_point_.x() +50;int information_y = mouse_now_point_.y() +50;//*******************信息框--整体****************QRect rect_infomation(information_x, information_y, 170, 170);//整体颜色基调QColor information_color = QColor(0, 0, 0, 150);_painter->fillRect(rect_infomation, information_color);//*******************信息框--文本内容****************//文本:位置信息QRect rect_infomation_position(information_x, information_y + 110, 170, 20);QString text_information_position = "(" + QString::number(mouse_now_point_.x()) + "," + QString::number(mouse_now_point_.y()) + ")";_painter->drawText(rect_infomation_position, Qt::AlignCenter, text_information_position);//文本:颜色信息QRect rect_infomation_color(information_x, information_y + 130, 170, 20);//颜色显示小框QRect rect_infomation_color_f(information_x + 5, information_y + 135, 10, 10);QRgb rgb_color = GetPixmapColor(show_top_pixmap_, mouse_now_point_);QString text_information_color = "(" + QString::number(qRed(rgb_color)) + "  ," + QString::number(qGreen(rgb_color)) + "  ," + QString::number(qBlue(rgb_color)) + ")";pixel_color_ = text_information_color;_painter->drawText(rect_infomation_color, Qt::AlignCenter, text_information_color);_painter->setBrush(QColor(rgb_color));_painter->drawRect(rect_infomation_color_f);_painter->setBrush(Qt::NoBrush);//文本:提示信息QRect rect_infomation_text(information_x, information_y + 150, 170, 20);QString text_information_text = QStringLiteral("按C复制颜色值");_painter->drawText(rect_infomation_text, Qt::AlignCenter, text_information_text);//*******************信息框--图片区****************//图片框QRect rect_infomation_pixmap_rect(information_x, information_y, 170, 110);//放大图片QRect rect_information_pixmap(mouse_now_point_.x() - 8, mouse_now_point_.y() - 5, 17, 11);QPixmap information_pixmap_ = show_top_pixmap_.copy(rect_information_pixmap).scaled(170, 110, Qt::KeepAspectRatioByExpanding);_painter->drawPixmap(rect_infomation_pixmap_rect.topLeft(), information_pixmap_);//中央辅助线QColor information_pixmap_color = QColor(0, 0, 255, 150);QRect information_pixmap_x(information_x, information_y + 50, 170, 10);QRect information_pixmap_y(information_x + 80, information_y, 10, 110);_painter->fillRect(information_pixmap_x, information_pixmap_color);_painter->fillRect(information_pixmap_y, information_pixmap_color);QRect information_pixmap_f(information_x + 80, information_y + 50, 10, 10);_painter->setBrush(QColor(rgb_color));_painter->drawRect(information_pixmap_f);_painter->setBrush(Qt::NoBrush);_painter->drawRect(rect_infomation_pixmap_rect);
}void CustomSlidScreenCapture::DrawFruitRect(QPainter *_painter)
{//绘制结果矩形框//计算偏移if (mouse_rect_press_flag_){QRect rect_f = GetRect(mouse_slid_begin_point_, mouse_slid_begin_point_);QPoint rect_f_begin = rect_f.topLeft();QPoint rect_f_end = rect_f.bottomRight();ArrowType flag = PointInRect(mouse_now_point_, GetRect(mouse_result_begin_point_, mouse_result_end_point_));int offset_x = GetOffsetPoint(mouse_rect_begin_point_, mouse_rect_end_point_).x();int offset_y = GetOffsetPoint(mouse_rect_begin_point_, mouse_rect_end_point_).y();switch (flag){case Arrow_Cursor:break;case Size_Ver_Cursor_Top:mouse_result_begin_point_ = QPoint(mouse_slid_begin_point_.x(), mouse_slid_begin_point_.y() + offset_y);mouse_result_end_point_ = QPoint(mouse_slid_end_point_.x(), mouse_slid_end_point_.y());break;case Size_Ver_Cursor_Bottom:mouse_result_begin_point_ = QPoint(mouse_slid_begin_point_.x(), mouse_slid_begin_point_.y());mouse_result_end_point_ = QPoint(mouse_slid_end_point_.x(), mouse_slid_end_point_.y() + offset_y);break;case Size_Hor_Cursor_Left:mouse_result_begin_point_ = QPoint(mouse_slid_begin_point_.x() + offset_x, mouse_slid_begin_point_.y());mouse_result_end_point_ = QPoint(mouse_slid_end_point_.x(), mouse_slid_end_point_.y() + offset_y);break;case Size_Hor_Cursor_Right:mouse_result_begin_point_ = QPoint(mouse_slid_begin_point_.x(), mouse_slid_begin_point_.y());mouse_result_end_point_ = QPoint(mouse_slid_end_point_.x() + offset_x, mouse_slid_end_point_.y());break;case Size_All_Cursor:mouse_result_begin_point_ = QPoint(mouse_slid_begin_point_.x() + offset_x, mouse_slid_begin_point_.y() + offset_y);mouse_result_end_point_ = QPoint(mouse_slid_end_point_.x() + offset_x, mouse_slid_end_point_.y() + offset_y);break;case Size_Bdiag_Cursor_Top:mouse_result_begin_point_ = QPoint(mouse_slid_begin_point_.x(), mouse_slid_begin_point_.y() + offset_y);mouse_result_end_point_ = QPoint(mouse_slid_end_point_.x() + offset_x, mouse_slid_end_point_.y());break;case Size_Bdiag_Cursor_Bottom:mouse_result_begin_point_ = QPoint(mouse_slid_begin_point_.x() + offset_x, mouse_slid_begin_point_.y());mouse_result_end_point_ = QPoint(mouse_slid_end_point_.x(), mouse_slid_end_point_.y() + offset_y);break;case Size_Fdiag_Cursor_Top:mouse_result_begin_point_ = QPoint(mouse_slid_begin_point_.x() + offset_x, mouse_slid_begin_point_.y() + offset_y);mouse_result_end_point_ = QPoint(mouse_slid_end_point_.x(), mouse_slid_end_point_.y());break;case Size_Fdiag_Cursor_Bottom:mouse_result_begin_point_ = QPoint(mouse_slid_begin_point_.x(), mouse_slid_begin_point_.y());mouse_result_end_point_ = QPoint(mouse_slid_end_point_.x() + offset_x, mouse_slid_end_point_.y() + offset_y);break;default:break;}}//绘制截取区域QRect selected_rect = GetRect(mouse_result_begin_point_, mouse_result_end_point_);pixmap_ = show_top_pixmap_.copy(selected_rect);_painter->drawPixmap(selected_rect.topLeft(), pixmap_);DrawFruitRectStyle(_painter, mouse_result_begin_point_, mouse_result_end_point_);//截取区域大小信息QString pixmap_size = QString::number(selected_rect.width()) + " X " + QString::number(selected_rect.height());QColor information_color = QColor(0, 0, 0, 150);QFontMetrics fm(_painter->font());QRect fm_rect = fm.boundingRect(pixmap_size);QRect pixmap_size_rect(selected_rect.topLeft().x(), selected_rect.topLeft().y() -20, fm_rect.width() + 5, 20);_painter->fillRect(pixmap_size_rect, information_color);_painter->drawText(pixmap_size_rect, Qt::AlignCenter, pixmap_size);}void CustomSlidScreenCapture::DrawFruitRectStyle(QPainter *_painter, QPoint& _begion_point, QPoint& _end_point)
{int radius_roll = 4;int x1 = _begion_point.x();int y1 = _begion_point.y();int x2 = _end_point.x();int y2 = _end_point.y();QVector<QPoint> points;points.push_back(QPoint(x1, y1));points.push_back(QPoint((x1 + x2) / 2, y1));points.push_back(QPoint(x2, y1));points.push_back(QPoint(x2, (y1 + y2) / 2));points.push_back(QPoint(x2, y2));points.push_back(QPoint((x1 + x2) / 2, y2));points.push_back(QPoint(x1, y2));points.push_back(QPoint(x1, (y1 + y2) / 2));_painter->setBrush(Qt::blue);for (int i = 0; i < 8; i++){_painter->drawEllipse(points.at(i),radius_roll,radius_roll);}}void CustomSlidScreenCapture::DrawFruitRectIsShow(QPainter *_painter)
{ArrowType flag = PointInRect(mouse_now_point_, GetRect(mouse_result_begin_point_, mouse_result_end_point_));switch (flag){case Arrow_Cursor:this->setCursor(Qt::ArrowCursor);break;case Size_Ver_Cursor_Top:this->setCursor(Qt::SizeVerCursor);break;case Size_Ver_Cursor_Bottom:this->setCursor(Qt::SizeVerCursor);break;case Size_Hor_Cursor_Left:this->setCursor(Qt::SizeHorCursor);break;case Size_Hor_Cursor_Right:this->setCursor(Qt::SizeHorCursor);break;case Size_All_Cursor:this->setCursor(Qt::SizeAllCursor);break;case Size_Bdiag_Cursor_Top:this->setCursor(Qt::SizeBDiagCursor);break;case Size_Bdiag_Cursor_Bottom:this->setCursor(Qt::SizeBDiagCursor);break;case Size_Fdiag_Cursor_Top:this->setCursor(Qt::SizeFDiagCursor);break;case Size_Fdiag_Cursor_Bottom:this->setCursor(Qt::SizeFDiagCursor);break;default:break;}if (flag&&!mouse_rect_press_flag_)DrawInformationRect(_painter);                    //绘制信息框
}void CustomSlidScreenCapture::paintEvent(QPaintEvent *event)
{QPainter *painter = new QPainter(this);painter->save();DrawBackgroundPixmap(painter);                          //绘制整体背景图片//滑动截取图片if (mouse_slid_press_flag_){DrawBoostLine(painter);                               //绘制辅助线DrawSlidRect(painter);                               //绘制滑动矩形框DrawInformationRect(painter);                      //绘制信息框}//截取图片二次处理if (mouse_slid_finish_){DrawFruitRect(painter);                               //绘制结果矩形框--大小重绘DrawFruitRectIsShow(painter);                        //绘制结果矩形框相关判断显示}if (!mouse_slid_finish_){DrawFruitRect(painter);                                //绘制结果矩形框--大小重绘//DrawFruitRectIsShow(painter);                      //绘制结果矩形框相关判断显示}painter->restore();
}

后续功能添加在完善后会陆续上传,新人第一次发博客,如果此文帮助到你( •̀ ω •́ )✧,动动小手点个赞可好O(∩_∩)O。
原创文章,转载请标明本文出处。

Qt 简单截图工具(一) 高仿QQ截屏 滑动截屏相关推荐

  1. 【Android】史上最简单,一步集成侧滑(删除)菜单,高仿QQ、IOS。

    本篇文章已授权微信公众号 guolin_blog (郭霖)独家发布 转载请标明出处: http://blog.csdn.net/zxt0601/article/details/53157090 本文出 ...

  2. android 自定义特效,Android自定义View之高仿QQ健康

    我们都知道自定义View一般有三种直接继承View.继承原有的控件对控件的进行修改.重新拼装组合,最后一种主要针对于ViewGroup.具体的怎么做不是本文的所涉及的内容(本文是基于第一种方式实现的) ...

  3. 用Vue高仿qq音乐官网-pc端

    用Vue高仿qq音乐官网-pc端 一直想做一个vue项目 然后呢 我就做了http://www.tuicool.com/articles/eymeiiN 效果预览 部分地方不全部根据原版,也有自由发挥 ...

  4. 高仿QQ即时聊天软件开发系列之三登录窗口用户选择下拉框

    上一篇高仿QQ即时聊天软件开发系列之二登录窗口界面写了一个大概的布局和原理 这一篇详细说下拉框的实现原理 先上最终效果图 一开始其实只是想给下拉框加一个placeholder效果,让下拉框在未选择未输 ...

  5. 高仿QQ的手机管家的小火箭加速

    高仿QQ的手机管家的小火箭加速 1.前言 腾讯的手机管家,用过这个App的人都应该知道桌面的火箭一键加速这个功能,研究一下这个小火箭是怎么做出来的.先来了解一下小火箭有神马动作,首先在没有触碰它时,就 ...

  6. android qq底部图片选择器,Android 高仿QQ图片选择器

    当做一款APP,需要选择本地图片时,首先考虑的无疑是系统相册,但是Android手机五花八门,再者手机像素的提升,大图无法返回等异常因数,导致适配机型比较困难,微信.QQ都相继的在自己的APP里集成了 ...

  7. 新版2022高仿QQ,利用Java swing1:1模仿qq编写的聊天程序

    基于MVC Swing的高仿QQ聊天软件 FakeQQ是一个基于MVC架构构建的GUI聊天项目.前端使用swing作为前端框架.服务端采用mysql存储数据,使用sorket传输数据,实现了一些基本的 ...

  8. 基于Qt的截图工具,实现截图后进行编辑

    20220712更:新增撤销前一次编辑痕迹功能,代码中通过设置"点击行为"栈,来进行控制 基于Qt的截图工具,采用了类似QQ截图的控制面板,先上效果图. 1.基本截图 2.画箭头 ...

  9. 安卓高仿QQ头像截取升级版

    观看此篇文章前,请先阅读上篇文章:高仿QQ头像截取: 本篇之所以为升级版,是在截取头像界面添加了与qq类似的阴影层(裁剪区域以外的部分),且看效果图:   为了适应大家不同需求,这次打了两个包,及上图 ...

  10. 如何使用MFC编写自定义UI界面【附高仿QQ 2014登陆界面范例程序】

    地址: http://blog.csdn.net/hujkay作者:Jekkay Hu(34538980@qq.com)关键词:MFC, 编写异行窗体,自定义UI控件,VC++,异形控件,高仿QQ登陆 ...

最新文章

  1. codeforces 610D D. Vika and Segments(离散化+线段树+扫描线算法)
  2. 1013 Battle Over Cities (25分)(用割点做)
  3. 在Visual Studio 2008中编译snort-2.8.6.1.tar.gz
  4. python入门指南bl-入门 第一个python可视化程序 基于pyqt5
  5. 2019CCPC-江西省赛(重现赛)- 感谢南昌大学
  6. mysql 外键关联
  7. Yii2 源码分析 - 入口文件执行流程
  8. spring boot中的注解
  9. Faster R-CNN源码中RPN的解析(自用)
  10. 解决pycharm debug时 界面下方不出现step等按钮以及变量值的情况
  11. JTT1078-2016道路运输车辆卫星定位系统视频通信协议-音视频上传部分
  12. centos 7查看CPU温度
  13. 以神奇“三”为本的逻辑与指号学----皮尔斯逻辑之三
  14. pat1034Head of a Gang (30)
  15. 7-6 然后是几点(15 分)
  16. javascript es6常用语法
  17. 【推荐】AI智慧安监企业安全生产监督管理平台建设技术解决方案合集(共342份,863M)
  18. vs2015下pthread的使用
  19. C++学生信息管理系统(含文件流)部分心得含源码
  20. 华为云大数据智能数据湖FusionInsight

热门文章

  1. 计算机网络之网络安全基础-消息完整性与数字签名
  2. 黑苹果E430c, 安装过程
  3. 新浪UC,這些人你咋就不管?
  4. 中国重汽:香港上市在十月
  5. Python——程序设计:商贷月供计算器!谁还没点月供了!
  6. 企业级业务架构如何设计?
  7. 国外最流行的几个外包接活网站 简要介绍
  8. vue3 权限菜单( 树形菜单)无限循环
  9. 区间对比_预算10-15万元区间 国内在售街车综合实力对比
  10. 网站建设需遵循的六个步骤