【发布时间】:2011-11-20 17:04:19
【问题描述】:
我想将二进制蒙版应用于彩色图像。 请提供一个基本的代码示例,并正确解释代码的工作原理。
另外,是否有一些选项可以永久应用掩码,以便所有功能仅在掩码内运行?
【问题讨论】:
标签: c++ image image-processing opencv mask
我想将二进制蒙版应用于彩色图像。 请提供一个基本的代码示例,并正确解释代码的工作原理。
另外,是否有一些选项可以永久应用掩码,以便所有功能仅在掩码内运行?
【问题讨论】:
标签: c++ image image-processing opencv mask
虽然@perrejba 的答案是正确的,但它使用了遗留的 C 风格函数。由于问题标记为 C++,因此您可能希望使用一种方法:
inputMat.copyTo(outputMat, maskMat);
所有对象的类型都是cv::Mat。
请注意,屏蔽是二进制的。掩码中的任何非零值都被解释为“复制”。即使蒙版是灰度图像。
还要注意 .copyTo() 函数在复制前不会清除输出。
如果您想永久更改原始图像,则必须进行额外的复制/克隆/分配。没有为重叠的输入/输出图像定义 copyTo() 函数。所以你不能使用相同的图像作为输入和输出。
【讨论】:
copyTo 仅对于部分重叠的图像未定义,因此您应该能够使用它来应用蒙版而无需创建新矩阵。来自 docs.opencv.org/modules/core/doc/… :“虽然 m.copyTo(m); 完美运行,但该函数无法处理源矩阵和目标矩阵之间部分重叠的情况。”
您不会对图像应用二进制掩码。您(可选)在处理函数调用中使用二进制掩码来告诉函数您要处理图像的哪些像素。如果我完全误解了你的问题,你应该添加更多细节来澄清。
【讨论】:
好吧,这个问题出现在搜索结果的顶部,所以我相信我们需要这里的代码示例。这是 Python 代码:
import cv2
def apply_mask(frame, mask):
"""Apply binary mask to frame, return in-place masked image."""
return cv2.bitwise_and(frame, frame, mask=mask)
蒙版和框架必须具有相同的大小,因此蒙版为1 的像素保持原样,而蒙版像素为0 的像素设置为零。
而对于C++ 则有点不同:
cv::Mat inFrame; // Original (non-empty) image
cv::Mat mask; // Original (non-empty) mask
// ...
cv::Mat outFrame; // Result output
inFrame.copyTo(outFrame, mask);
【讨论】:
您可以使用蒙版仅将原始图像的感兴趣区域复制到目标区域:
cvCopy(origImage,destImage,mask);
其中mask 应该是一个 8 位单通道数组。
在OpenCV docs查看更多信息
【讨论】:
下面是一些代码,用于在从网络摄像头获取的视频帧序列上应用二进制掩码。 注释并取消注释“bitwise_not(Mon_mask,Mon_mask);”行并查看效果。
最好的, 艾哈迈德。
#include "cv.h" // include it to used Main OpenCV functions.
#include "highgui.h" //include it to use GUI functions.
using namespace cv;
using namespace std;
int main(int argc, char** argv)
{
int c;
int radius=100;
CvPoint2D32f center;
//IplImage* color_img;
Mat image, image0,image1;
IplImage *tmp;
CvCapture* cv_cap = cvCaptureFromCAM(0);
while(1) {
tmp = cvQueryFrame(cv_cap); // get frame
// IplImage to Mat
Mat imgMat(tmp);
image =tmp;
center.x = tmp->width/2;
center.y = tmp->height/2;
Mat Mon_mask(image.size(), CV_8UC1, Scalar(0,0,0));
circle(Mon_mask, center, radius, Scalar(255,255,255), -1, 8, 0 ); //-1 means filled
bitwise_not(Mon_mask,Mon_mask);// commenté ou pas = RP ou DMLA
if(tmp != 0)
imshow("Glaucom", image); // show frame
c = cvWaitKey(10); // wait 10 ms or for key stroke
if(c == 27)
break; // if ESC, break and quit
}
/* clean up */
cvReleaseCapture( &cv_cap );
cvDestroyWindow("Glaucom");
}
【讨论】: