我正在尝试将我的C ++ opencv应用程序移植到iOs, 但我总是得到这个错误:
OpenCV Error: Unsupported format or combination of formats () in cvFloodFill, file /Users/user/slave/ios_framework/src/opencv/modules/imgproc/src/floodfill.cpp, line 618
libc++abi.dylib: terminate called throwing an exception
这是我的代码:
- (cv::MatND)calc_Hist
{
using namespace cv;
UIImage *temp = [UIImage imageNamed:@"file.png"];
Mat src = [self cvMatFromUIImage:temp];
Mat hsv;
Mat mask;
MatND hist;
int lo = 151; int up = 170;
cv::Point seed = cv::Point( 1029, 270 );
int newMaskVal = 255;
Scalar newVal = Scalar( 120, 120, 120 );
int connectivity = 8;
int h_bins = 30; int s_bins = 32;
int histSize[] = { h_bins, s_bins };
float h_range[] = { 0, 179 };
float s_range[] = { 0, 255 };
const float* ranges[] = { h_range, s_range };
int channels[] = { 0, 1 };
cvtColor(src, hsv, CV_BGR2HSV);
int flags = connectivity + (newMaskVal << 8 ) + cv::FLOODFILL_FIXED_RANGE + cv::FLOODFILL_MASK_ONLY;
cv::Mat mask2 = cv::Mat::zeros( src.rows + 2, src.cols + 2, CV_8UC1 );
UIImage *imgs = [self UIImageFromCVMat:hsv];
[_viewer setImage:imgs];
floodFill( src, mask2, seed, newVal, 0, cv::Scalar( lo, lo, lo ), cv::Scalar( up, up, up), flags );
mask = mask2( cv::Range( 1, mask2.rows - 1 ), cv::Range( 1, mask2.cols - 1 ) );
calcHist( &hsv, 1, channels, mask, hist, 2, histSize, ranges, true, false );
normalize( hist, hist, 0, 255, cv::NORM_MINMAX, -1, cv::Mat() );
return hist;
}
这个功能在我的Mac上运行正常,所以我首先想到的是图像没有正确转换,但如果我在UIImageView中显示它,它会显示图像。
这是转换方法
- (cv::Mat)cvMatFromUIImage:(UIImage *)image
{
CGColorSpaceRef colorSpace = CGImageGetColorSpace(image.CGImage);
CGFloat cols = image.size.width;
CGFloat rows = image.size.height;
cv::Mat cvMat(rows, cols, CV_8UC4); // 8 bits per component, 4 channels
CGContextRef contextRef = CGBitmapContextCreate(cvMat.data, // Pointer to data
cols, // Width of bitmap
rows, // Height of bitmap
8, // Bits per component
cvMat.step[0], // Bytes per row
colorSpace, // Colorspace
kCGImageAlphaNoneSkipLast |
kCGBitmapByteOrderDefault); // Bitmap info flags
CGContextDrawImage(contextRef, CGRectMake(0, 0, cols, rows), image.CGImage);
CGContextRelease(contextRef);
CGColorSpaceRelease(colorSpace);
return cvMat;
}
与“普通”框架相比,iOS框架是否有任何减少? 我用谷歌搜索但我没有找到任何解决我问题的方法。
答案 0 :(得分:2)
我在Android上遇到了完全相同的问题。在我的案例中,“问题”是我将BGRA与BGR混为一谈。在我的情况下,洪水填充的输入/输出矩阵应该有3个通道,但我意外地给出了一个带有4个通道的矩阵(BGRA)。我想同样的问题发生在你身上。
它发生在我身上,因为我从Android OpenCV SDK的教程代码“Mixed Processing 2”开始。有一个误导性的名称(第四个频道消失了):
Mat& mRgb = *(Mat*)addrRgba;
我必须将4通道矩阵转换为3通道矩阵,然后填充工作正常。
答案 1 :(得分:1)
当函数遇到函数无法处理的矩阵类型时,会发生错误。使用src.type()检查floodFill的输入矩阵的类型。根据OpenCV手册
图像 - 输入/输出1或3通道,8位或浮点图像。 除非FLOODFILL_MASK_ONLY标志是,否则它由函数修改 set(在函数的第二个变体中;见下文)