在之前大神的Halcon 与 OpenCV 图像数据类型的转换过程中,使用了C 接口的 Halcon 函数,如 read_image()在C++接口中则为ReadImage();
由Help可知,Halcon 中 C 接口与 C++ 接口支持的数据类型并不完全一样,因为,本人需要在C++环境下开发,所以,之前的代码,许多地方不能
使用,所以,在前人的基础上,对代码进行修改,修改后进行测试,发现通过读取灰度值的方式与直接用指针操作,时间消耗差别不大,以代码中
的样本图片为例,以指针的形式进行访问,在 Halcon 转 OpenCV 的时间消耗为:600ms 左右,以读取灰度值的方式,也在600 ms 左右;
但由OpenCV 转 Halcon 时间消耗很少,大约只有 10 几 ms;
代码如下所示:
#include <HalconCpp.h>
#include <opencv2/opencv.hpp>
#include <iostream>
#include <windows.h>
using namespace std;
using namespace HalconCpp;
using namespace cv;
HObject IplImageToHImage(cv::Mat& pImage);
cv::Mat HImageToIplImage(HObject &Hobj);
//IplImage* HImageToIplImage(HObject &Hobj);
int main(int argc, char* argv[])
{
//Hobject Image, GrayImage;
HObject Image, GrayImage;
ReadImage(&Image, "lena.jpg");
Rgb1ToGray(Image, &GrayImage);
//Mat img = imread("lena.jpg");
SYSTEMTIME tm;
GetLocalTime(&tm);
int t1 = tm.wSecond * 1000 + tm.wMilliseconds;
//HObject hObj = IplImageToHImage(img);
cv::Mat opencvImg = HImageToIplImage(GrayImage);
GetLocalTime(&tm);
int t2 = tm.wSecond * 1000 + tm.wMilliseconds;
int t = t2 - t1;
cout << "时间消耗:" << t << "ms" << endl;
// HTuple winHandle;
// HTuple w, h;
// GetImageSize(hObj, &w, &h);
// OpenWindow(0, 0, w, h, 0, "", "", &winHandle);
// DispObj(hObj, winHandle);
// int t1 = tm.wSecond * 1000 + tm.wMilliseconds;
//
// cv::Mat opencvImg = HImageToIplImage(Image);
//
// GetLocalTime(&tm);
// int t2 = tm.wSecond * 1000 + tm.wMilliseconds;
//
// int t = t2 - t1;
//
// cout << "时间消耗为:" << t << "ms" << endl;
namedWindow("img", 1);
imshow("img", opencvImg);
waitKey();
system("pause");
return 0;
}
cv::Mat HImageToIplImage(HObject &Hobj)
{
//get_grayval(Image : : Row, Column : Grayval)
cv::Mat pImage;
HTuple htChannels;
HTuple width, height;
width = height = 0;
//转换图像格式
ConvertImageType(Hobj, &Hobj, "byte");
CountChannels(Hobj, &htChannels);
HTuple cType;
HTuple grayVal;
if (htChannels.I() == 1)
{
GetImageSize(Hobj, &width, &height);
pImage = cv::Mat(height, width, CV_8UC1);
pImage = Mat::zeros(height, width, CV_8UC1);
for (int i = 0; i < height.I(); ++i)
{
for (int j = 0; j < width.I(); ++j)
{
GetGrayval(Hobj, i, j, &grayVal);
pImage.at<uchar>(i, j) = (uchar)grayVal.I();
}
}
}
else if (htChannels.I() == 3)
{
GetImageSize(Hobj, &width, &height);
pImage = cv::Mat(height, width, CV_8UC3);
for (int row = 0; row < height.I(); row++)
{
for (int col = 0; col < width.I(); col++)
{
GetGrayval(Hobj, row, col, &grayVal);
pImage.at<uchar>(row, col * 3) = (uchar)grayVal[2].I();
pImage.at<uchar>(row, col * 3 + 1) = (uchar)grayVal[1].I();
pImage.at<uchar>(row, col * 3 + 2) = (uchar)grayVal[0].I();
}
}
}
return pImage;
}
HObject IplImageToHImage(cv::Mat& pImage)
{
HObject Hobj;
if (3 == pImage.channels())
{
cv::Mat pImageRed, pImageGreen, pImageBlue;
std::vector<cv::Mat> sbgr(3);
cv::split(pImage, sbgr);
int length = pImage.rows * pImage.cols;
uchar *dataBlue = new uchar[length];
uchar *dataGreen = new uchar[length];
uchar *dataRed = new uchar[length];
int height = pImage.rows;
int width = pImage.cols;
for (int row = 0; row < height; row++)
{
uchar* ptr = pImage.ptr<uchar>(row);
for (int col = 0; col < width; col++)
{
dataBlue[row * width + col] = ptr[3 * col];
dataGreen[row * width + col] = ptr[3 * col + 1];
dataRed[row * width + col] = ptr[3 * col + 2];
}
}
GenImage3(&Hobj, "byte", width, height, (Hlong)(dataRed), (Hlong)(dataGreen), (Hlong)(dataBlue));
delete[] dataRed;
delete[] dataGreen;
delete[] dataBlue;
}
else if (1 == pImage.channels())
{
int height = pImage.rows;
int width = pImage.cols;
uchar *dataGray = new uchar[width * height];
memcpy(dataGray, pImage.data, width * height);
GenImage1(&Hobj, "byte", width, height, (Hlong)(dataGray));
delete[] dataGray;
}
return Hobj;
}