一、概述

  需求:

    1.编写一个小工具实现图片压缩

    2.图片仅支持JPEG和PNG格式

    3.目的是压缩图片在磁盘中所占用的大小

    4.使用的开发语言是Qt、C++、OpenCV

    5.压缩的质量可以动态调节

    如下图所示:

  ps:

    1.如果图片是jpeg压缩质量可以设置10~100,值越大质量越好,图片所占用的磁盘空间也就越大。综合测试下来值设置30的时候压缩的最为合理,且图片不失真,如果图片要求质量较高建议设置40以上。

    2.如果图片是png格式,压缩质量是从0~9,值越大压缩率越高,如果没有特殊要求直接设置压缩率为9,直接压缩到最小就行。

二、代码示例

点击查看代码

#include "ImageCompressTool.h" ImageCompressTool::ImageCompressTool(QWidget* parent)
: CommonGraphicsView{ parent }
{
this->setWindowTitle("图片压缩");
this->setFixedSize(QSize(320, 800));
QVBoxLayout* vLayout = new QVBoxLayout(this); QHBoxLayout* hLayout = new QHBoxLayout(this);
EditText* et = new EditText(this);
et->setEnabled(false);
et->setFixedHeight(30);
Button* btnChoiceBtn = new Button(this);
btnChoiceBtn->setText("请选择图片"); hLayout->addWidget(et);
hLayout->addWidget(btnChoiceBtn);
hLayout->setAlignment(Qt::AlignTop); QHBoxLayout* radioTypeHLayout = new QHBoxLayout(this);
QButtonGroup* group = new QButtonGroup(this);
QRadioButton* radioButtonJPEG = new QRadioButton("JPEG", this);
radioButtonJPEG->setFixedSize(60, 30);
QRadioButton* radioButton2PNG = new QRadioButton("PNG", this);
radioButton2PNG->setFixedSize(60, 30);
group->addButton(radioButtonJPEG, 1);
group->addButton(radioButton2PNG, 2);
radioTypeHLayout->addWidget(radioButtonJPEG);
radioTypeHLayout->addWidget(radioButton2PNG);
radioTypeHLayout->setAlignment(Qt::AlignLeft); //图片质量(JPEG)
qualitLabel = new QLabel(this);
qualitLabel->setText("图片质量:" + QString::number(mKsize));
qualitLabel->setFixedHeight(15);
//显示原图大小(KB)
srcImageKb = new QLabel(this);
srcImageKb->setText("原图大小:");
srcImageKb->setFixedHeight(15);
//显示压缩后图片大小(KB)
compressImageKb = new QLabel(this);
compressImageKb->setText("压缩后图片大小:");
compressImageKb->setFixedHeight(15);
//开始压缩按钮
Button* startCompressBtn = new Button(this);
startCompressBtn->resize(60, 30);
startCompressBtn->setText("开始压缩"); QLabel* comBoxLabel = new QLabel(this);
comBoxLabel->setText("请选择图片质量:");
comBoxLabel->setFixedHeight(15);
//ComBox选择图片质量
comBox = new ComboBox(this);
for (int i = 10;i <= 100;i += 10) {
comBox->addItem(QString::number(i));
}
QHBoxLayout* comBoxHLayout2 = new QHBoxLayout(this);
comBoxHLayout2->addWidget(comBoxLabel);
comBoxHLayout2->addWidget(comBox); imageViewResult = new QLabel(this); vLayout->addLayout(hLayout);
vLayout->addLayout(radioTypeHLayout);
//vLayout->addWidget(imageViewSrc);
vLayout->addWidget(imageViewResult);
vLayout->setAlignment(Qt::AlignTop); vLayout->addWidget(qualitLabel);
vLayout->addWidget(srcImageKb);
vLayout->addWidget(compressImageKb);
vLayout->addLayout(comBoxHLayout2);
vLayout->addWidget(startCompressBtn);
this->setLayout(vLayout); connect(btnChoiceBtn, &Button::clicked, this, [=]() {
QFileInfo fileInfo;
filePath = QFileDialog::getOpenFileName(this, tr("请选择图片"), "C:/Users/DBF-DEV-103/Downloads/", tr("Image Files(*.jpg *.png *.jpeg)"));
et->setText(filePath);
fileInfo = QFileInfo(filePath);
//获取文件后缀名
QString fileSuffix = fileInfo.suffix();
qDebug() << "文件的后缀名为:" << fileSuffix;
if (fileSuffix == "jpeg" || fileSuffix == "jpg") {
imageType = 0;
radioButtonJPEG->setChecked(true);
comBox->clear();
for (int i = 10;i <= 100; i += 10) {
comBox->addItem(QString::number(i));
}
}
else if (fileSuffix == "png") {
imageType = 1;
radioButton2PNG->setChecked(true);
comBox->clear();
for (int i = 0;i <= 10; i++) {
comBox->addItem(QString::number(i));
}
}
//compressImage();
}); //选择了JPEG
connect(radioButtonJPEG, &QRadioButton::clicked, this, [=]() {
imageType = 0;
qDebug() << "图片类型" << imageType;
});
//选择了PNG
connect(radioButton2PNG, &QRadioButton::clicked, this, [=]() {
imageType = 1;
qDebug() << "图片类型:" << imageType;
}); //开始压缩按钮信号槽(点击事件)
connect(startCompressBtn, &Button::clicked, this, [=]() {
compressImage(); }); //选择图片质量信号槽
connect(comBox, &ComboBox::currentTextChanged, [=](const QString value) {
qDebug() << "选择的value值:" << value;
mKsize = value.toInt();
qualitLabel->setText("图片质量:" + QString::number(mKsize));
}); }
//压缩图片
void ImageCompressTool::compressImage() {
cv::Mat src = cv::imread(this->filePath.toStdString().c_str());
//imshow("src", src);
double srcKb = matSizeInKB(filePath.toStdString());
srcImageKb->setText("原图大小:" + QString::number(srcKb));
std::cout << "原图大小:" << srcKb << std::endl;
std::vector<int> compression_params;
if (imageType == 0) {
compression_params.push_back(cv::IMWRITE_JPEG_QUALITY);
//压缩级别范围从0~100,值越小压缩率越高,即在磁盘占用的空间越小,相应的图片的质量越差
compression_params.push_back(mKsize);
}
else {
compression_params.push_back(cv::IMWRITE_PNG_COMPRESSION);
if (mKsize > 10) {
mKsize = 3;
}
compression_params.push_back(mKsize); // 压缩级别范围从0到9,9是最高压缩
}
//将图片以jpg的格式存入文件
char* compressImgPath = "E://opencv_compress_img.jpeg";
if (imageType == 1) {
compressImgPath = "E://opencv_compress_img.png";
}
bool result = cv::imwrite(compressImgPath, src, compression_params);
if (!result) {
std::cout << "压缩图片失败" << endl;
return;
}
QFile compressFile = QFile(compressImgPath);
double compressSizeKb = matSizeInKB(compressImgPath);
compressImageKb->setText("压缩后的图片大小:" + QString::number(compressSizeKb));
std::cout << "压缩后的图片大小为:" << compressSizeKb << std::endl;
std::cout << "压缩图片成功,存储路径为:" << compressImgPath << std::endl;
} long ImageCompressTool::matSizeInKB(std::string filePath) {
std::ifstream mFile(filePath, std::ifstream::binary);
if (mFile) {
mFile.seekg(0, mFile.end);
long size = mFile.tellg(); // 获取文件大小(字节)
mFile.close();
return size / 1024; // 转换为KB
}
return -1; // 文件打开失败,返回-1
} ImageCompressTool::~ImageCompressTool()
{
}

Qt+OpenCV实现图片压缩(JPEG、PNG)的更多相关文章

  1. 使用 opencv 将图片压缩到指定文件尺寸

    前言 图片压缩应用很广泛,如生成缩略图等.前期我在进行图片处理的过程中碰到了一个问题,就是如何将图片压缩到指定尺寸,此处尺寸指的是生成图片文件的大小. 我使用 opencv 进行图片处理,于是想着直接 ...

  2. 搭建Android+QT+OpenCV环境,实现“单色图片着色”效果

               OpenCV是我们大家非常熟悉的图像处理开源类库:在其新版本将原本在Contrib分库中的DNN模块融合到了主库中,并且更新了相应文档.这样我们就能够非常方便地利用OpenCV实 ...

  3. Qt OpenCV Support Image Type 支持读写的图像格式

    Qt 支持的图片格式如下: Format Description Qt's support BMP Windows Bitmap Read/write GIF Graphic Interchange ...

  4. Golang 编写的图片压缩程序,质量、尺寸压缩,批量、单张压缩

    目录: 前序 效果图 简介 全部代码 前序: 接触 golang 不久,一直是边学边做,边总结,深深感到这门语言的魅力,等下要跟大家分享是最近项目 服务端 用到的图片压缩程序,我单独分离了出来,做成了 ...

  5. 三款不错的图片压缩上传插件(webuploader+localResizeIMG4+LUploader)

    涉及到网页图片的交互,少不了图片的压缩上传,相关的插件有很多,相信大家都有用过,这里我就推荐三款,至于好处就仁者见仁喽: 1.名气最高的WebUploader,由Baidu FEX 团队开发,以H5为 ...

  6. Java中图片压缩处理

    原文http://cuisuqiang.iteye.com/blog/2045855 整理文档,搜刮出一个Java做图片压缩的代码,稍微整理精简一下做下分享. 首先,要压缩的图片格式不能说动态图片,你 ...

  7. android 图片压缩

    引用:http://104zz.iteye.com/blog/1694762 第一:我们先看下质量压缩方法: private Bitmap compressImage(Bitmap image) { ...

  8. HTML5 CANVAS 实现图片压缩和裁切

    原文地址:http://leonshi.com/2015/10/31/html5-canvas-image-compress-crop/?utm_source=tuicool&utm_medi ...

  9. C# 图片压缩

    /// <summary>        /// 图片压缩方法        /// </summary>        /// <param name="sF ...

  10. Html5+asp.net mvc 图片压缩上传

    在做图片上传时,大图片如果没有压缩直接上传时间会非常长,因为有的图片太大,传到服务器上再压缩太慢了,而且损耗流量. 思路是将图片抽样显示在canvas上,然后用通过canvas.toDataURL方法 ...

随机推荐

  1. JavaFx helloworld 坑

    系统 Linux Mint IDEA 创建的 hello world 项目,用 IDEA 运行就僵住,然而用 mvn clean javafx:run 却能成功----在系统 terminal能成功, ...

  2. 【Spring】Sring基础概念(黑马SSM学习笔记)

    目录 Spring简介 Spring是什么 Spring发展 Spring优势 Spring体系结构 Spring快速入门 Spring程序开发步骤 不用Spring的一般步骤 使用Spring框架 ...

  3. 如何安装和使用 Latte Dock

    你知道什么是"停靠区Dock" 吧,它通常是你的应用程序"停靠"的底栏,以便快速访问. 许多发行版和桌面环境都提供了某种停靠实现.如果你的发行版没有" ...

  4. JVM简介—3.JVM的执行子系统

    大纲 1.Class文件结构 2.Class文件格式概述 3.Class文件格式详解 4.字节码指令 5.类的生命周期和初始化 6.类加载的全过程 7.类加载器 8.双亲委派模型 9.栈桢详解 11. ...

  5. Qt编写可视化大屏电子看板系统19-横向柱状图

    一.前言 横向柱状图的绘制这玩意当初还着实花费了一些时间,因为从v1版本开始,默认XY坐标轴是没有交换位置的处理的,也只有垂直的柱状图,要想换成横向的柱状图必须是自己拿到数据重新绘制,数据值的设置一般 ...

  6. 大型IM稳定性监测实践:手Q客户端性能防劣化系统的建设之路

    本文来自腾讯手Q基础架构团队杨萧玉.邱少雄.张自蹊.王褚重天.姚伟斌的分享,原题"QQ 客户端性能稳定性防劣化系统 Hodor 技术方案",下文进行了排版和内容优化. 1.引言 接 ...

  7. 即时通讯安全篇(十):IM聊天系统安全手段之通信连接层加密技术

    本文由融云技术团队分享,原题"互联网通信安全之端到端加密技术",内容有修订和改动. 1.引言 随着移动互联网的普及,IM即时通讯类应用几乎替代了传统运营商的电话.短信等功能.得益于 ...

  8. 收藏几个常用的vue自定义组件,抄自 他人,以防丢失

    在 Vue,除了核心功能默认内置的指令 ( v-model 和 v-show ),Vue 也允许注册自定义指令.它的作用价值在于当开发人员在某些场景下需要对普通 DOM 元素进行操作. Vue自定义指 ...

  9. Django使用问题记录

    1.python3下出现问题(首先安装pymysql与mysqlclient):django.core.exceptions.ImproperlyConfigured: mysqlclient 1.3 ...

  10. SQL只取日期的年月日部分

    方法一: select CONVERT(varchar, getdate(), 120 ) 2004-09-12 11:06:08 select replace(replace(replace(CON ...