第一个Qt开发的OpenCV程序

OpenCV计算机视觉开发实践:基于Qt C++ - 商品搜索 - 京东

下载安装Qt:https://download.qt.io/archive/qt/5.14/5.14.2/qt-opensource-windows-x86-5.14.2.exe

下载安装OpenCV:https://opencv.org/releases/

下载安装CMake:Download CMake

这些软件安装完成完成后,我们可以开始用Qt编写OpenCV程序了。

【例2.2】第一个Qt开发的OpenCV程序

(1)在桌面上找到Qt Creator 4.11.1 (Community),双击打开Qt Creator,我们准备新建一个控制台项目,项目名是hello。在Qt Creator主界面的Projects旁点击New按钮,如图2-31所示。

图2-31

然后在出现的"新建项目",选中"Qt Console Application",如图2-32所示。

图2-32

点击Choose按钮,然后输入项目名称和创建路径,路径建议用全英文路径,如图2-33所示。

图2-33

随后连续点击下一步,直到向导结束出现编辑窗口,我们可以看到一个自动生成了一个main函数了。我们来简单修改下程序,使之既能输出图形对话框,又能在命令窗口中输出字符串,代码如下:

复制代码
#include <QApplication>
#include <QMessageBox>

int main(int argc, char *argv[])
{
    QApplication a(argc, argv); 		//定义应用程序对象
    QString text = "helloworld"; 		//定义一个字符串并赋值
    // 创建并显示消息对话框
    QMessageBox::information(nullptr, "hi", text);
    puts("helloworld"); 					//在控制台窗口输出字符串
    return a.exec(); 					//进入事件循环
}

QApplication是Qt应用程序中必不可少的一部分,它负责管理应用程序的生命周期,处理事件循环,设置应用的整体样式等。QString是Qt框架中处理文本数据的核心类之一。它提供了强大的字符串处理能力,支持多种文本编码和操作,我们定义字符串text,并通过QMessageBox::information将其在消息对话框上输出。然后,用C函数puts在控制台上输出字符串helloworld。程序很简单,没啥好讲,若学过Qt,一看便懂。

由于这个项目原本是控制台项目,因此如果要输出图形消息框,还需要在项目配置文件中进行一些修改,打开hello.pro,在文件开头添加"QT+=widgets",如下所示:

复制代码
QT+=widgets

Widgets是在Qt中创建用户界面的主要元素。Widgets可以显示数据和状态信息,接收用户输入,并为应该组合在一起的其他小部件提供容器。QT+的意思是加上widgets模块。如果此时运行程序,则可以出现消息对话框并可以在控制台上输出字符串helloworld。

(2)Qt项目能运行了,但还不是一个OpenCV程序,下面我们加上OpenCV代码。首先要在工程配置文件中添加OpenCV库和头文件的路径,在hello.pro的末尾添加代码如下:

复制代码
INCLUDEPATH += D:/opencvBuild/install/include/

LIBS += -L D:/opencvBuild/install/x64/mingw/lib/libopencv_*.a

宏INCLUDEPATH用来指定头文件所在路径,LIBS用来指定库文件所在路径,两个宏都要用一个+,并且LIBS+=右边要用-L来指定路径,这个写法和gcc指定库路径写法类似。

下面我们添加源代码,在Qt Creator中打开main.cpp,输入代码如下:

复制代码
#include <QApplication>
#include <QMessageBox>
#include <opencv2/opencv.hpp>
#include <QDebug>
#include <QDir>
#include <iostream>

using namespace cv;  //所有OpenCV类都在命名空间cv下
using namespace std;

void f()   //自定义函数,实现两幅图片混合
{
    double alpha = 0.5; double beta; double input;
    Mat src1, src2, dst; //创建Mat对象,Mat用于存储图片的矩阵类,dst用于存放混合后的图片

    //提示用户输入第一幅图片的权值alpha
    qDebug() <<"线性混合:";
    qDebug() << "输入第一幅图片的权重alpha [0.0-1.0]: ";
    cin >> input;   //用户输入

    //如果用户输入值介于0和1之间,则用该输入值作为alpha的值
    if (input >= 0 && input <= 1)
        alpha = input;

    QString currentPath = QDir::currentPath();  //获取当前路径
    qDebug() <<"当前路径是:"<< currentPath;

    //读取两幅大小必须一样的JPG图片
    src1 = imread("p1.jpg");
    src2 = imread("sbh.jpg");

    if (src1.empty()) { cout << "Error loading src1" << endl; return; }
    if (src2.empty()) { cout << "Error loading src2" << endl; return; }

    beta = (1.0 - alpha);
    addWeighted(src1, alpha, src2, beta, 0.0, dst);//将图1与图2线性混合
    imshow("res",dst); 	//显示混合后的图片
    waitKey(0); 			//等待按键响应后退出,0改为5000就是5秒后自动退出
}

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);   	//定义应用程序对象
    QString text = "helloworld";  	//定义一个字符串并赋值

    cv::Mat image = cv::imread("d:/test.jpg");  //读取d盘上test.jpg文件
    if (image.empty()) { 			//判断文件是否为空
       return -1;  					//为空返回-1,结束程序
    }
   std::string strTitle = text.toStdString(); //把QString字符串转为std::string字符串
    
   namedWindow(strTitle, cv::WINDOW_AUTOSIZE); //创建一个标题是strTitle窗口
   imshow(strTitle, image); 	//在标题为strTitle的窗口中显示图像
   waitKey(0); 					//等待用户按键
   destroyWindow(strTitle);		//销毁标题是strTitle的窗口

   // 创建并显示消息对话框
   QMessageBox::information(nullptr, "hi", text);
   f();
   return a.exec();
}

上述代码的自定义函数f功能将图片p1.jpg和sbh.jpg两幅图片进行混合,它们的大小必须一样。这两幅图片必须复制到D:\ex\build-hello-Desktop_Qt_5_14_2_MinGW_64_bit-Debug目录下。其中,OpenCV库中的API函数imread用来从文件中读取图片。API函数addWeighted用于将两张相同大小、相同类型的图片进行融合,第二个参数alpha表示第一幅图片所占的权重,第四个参数beta表示第2个图片所占的权重。权重越大的图片显示得越多,比如我们输入alpha为0.9,则主要显示第一幅图片。main中的代码比较简单,主要是从d盘读取一个图片文件test.jpg,然后调用f。

(2)复制动态链接库到exe文件所在文件夹。首先我们打开以下路径来查看exe文件:

复制代码
D:\ex\build-hello-Desktop_Qt_5_14_2_MinGW_64_bit-Debug\debug

图2-4

这个路径是我们程序生成的hello.exe文件所在的路径,hello.exe是一个Windows下的可执行文件,是不是觉得很神奇,MinGW能在编译阶段加载Linux下的静态库(.a)文件,最终生成了Windows下的.exe文件。但hello.exe还需要加载OpenCV源码编译出来的动态链接库后才能运行。打开目录D:\opencvBuild\install\x64\mingw\bin\,把该目录下的libopencv_core4100.dll、libopencv_highgui4100.dll、libopencv_imgcodecs4100.dll和libopencv_imgproc4100.dll四个文件复制到hello.exe文件所在文件夹。

(3)运行程序,在Qt Creator中点击点击左下角的三角运行按钮或直接按快捷键Ctrl+R来运行项目。运行结果如图2-4所示。

随便按一个键盘键,则会显示helloworld信息框,关闭信息框,会让我们在控制台窗口上输入权值,这里我们输入0.9,可以看到输入第一幅图片权重是0.9后,sbh.jpg显示的效果就淡了很多,如图2-5所示。

图2-5

如图图片不能加载,请确认p1.jgp和sbh.jpg是否复制到以下路径:

复制代码
D:\ex\build-hello-Desktop_Qt_5_14_2_MinGW_64_bit-Debug

以及,test.jpg是否复制到d盘。在这个程序中,我们即加载了绝对路径下的图片文件(test.jpg),也加载了当前路径下的图片文件(p1.jpg和sbh.jpg)。这3个文件平时可以到工程目录的res文件夹下找到。

至此,基于Qt Creator的OpenCV的开发环境搭建起来了。

相关推荐
不会就选b11 分钟前
C++补充部分(一)--lambda 表达式
开发语言·c++
Pniubi3 小时前
HashMap的扩容和树化边界
java·开发语言
gCode Teacher 格码致知5 小时前
Pandas教学-17:Series与Dataframe的关系
开发语言·python·pandas
发量惊人的中年网工5 小时前
分公司访问总部ERP慢怎么办?SD-WAN组网的排查与验收要点
服务器·开发语言·php
下页、再停留5 小时前
【C#桌面客户端系列学习-15】生成可视化图表之折线图、柱状图、饼状图
开发语言·c#
ShineWinsu5 小时前
对于JavaScript:操作元素的解析
开发语言·前端·javascript·面试·web·dom·元素
zhanghaha13146 小时前
Qt 类本质就是 C++ 的类,只是 Qt 框架扩展了一套【QObject 对象模型】
qt
益莱储中国7 小时前
深度解析:RF 实验室从 5G迈向 6G 的过程中保持技术领先与设备升级的路径
开发语言·php
benchmark_cc8 小时前
Python 量化系统如何设计统一的数据访问接口:从策略解耦到数据层架构
开发语言·python·数据分析·pandas·量化交易·股票数据·quantdash
const_qiu8 小时前
第四章 00:开篇 —— 从「会聊天」到「记得住、会干活、能协作」
java·开发语言·人工智能·python