Alpha Channel in OpenCV

Does OpenCV support alpha channel? Or is there a way to work with transparent png? I need to combine two images, where the first is the background and the second is the image that was rotated by cvWarpAffine. I can do this by combining the pixels one by one and dropping the pixels with some value that I set in cvScalar in cvWarpAffine. However, I do not think this is the intended solution. Thanks for the suggestions.

+4
source share
3 answers

Updated answer: use the CV_LOAD_IMAGE_UNCHANGED flag to load all four channels (including Alpha) from the image. Then use mixChannels() and / or split() to separate the alpha channel from the others and set a threshold for it, as described below.

Very old answer:

OpenCV does not support alpha channel, only masking. If you want to read in PNG format with an alpha channel, first use imagemagick to extract the alpha channel:

 convert input.png -channel Alpha -negate -separate input-mask.png 

Then in OpenCV you can do the following:

 Mat_<float> mask = imread("input-mask.png", 0); threshold(mask, mask, 254., 1., THRESH_BINARY); 

... to get a real mask (which can be used as a mask matrix in OpenCV operations). Or you can use it in your own operations without a threshold. To apply the mask, it would be nice to expand it to three channels:

 std::vector<Mat> marr(3, mask); Mat_<Vec<float, 3> > maskRGB; merge(marr, maskRGB); 

After that you can check it like this:

 imshow("Target", target); imshow("Mask", mask*255); imshow("Applied", target.mul(maskRGB)); waitKey(); 

Note. This is OpenCV 2.0 code.

+8
source

Here is the bash script that I put together to perform the ImageMagick conversion given by ypnos in all png files in the directory. You can make it recursive by replacing * in the third line with the find command.

 #!/bin/bash for file in * do if [[ $file =~ (.+)-mask\.png ]]; then echo "Ignoring mask $file" elif [[ $file =~ (.+)\.png ]]; then echo "Generating mask for $file" basefn=${BASH_REMATCH[1]} convert "$basefn.png" -channel Alpha -negate -separate "$basefn-mask.png" fi done 
+2
source

Input: cam_frame-background, media_frame-foreground, media_frame_alpha - alpha. Yield: mixed alpha clear. If media_frame_alpha is IPL_DEPTH_8U, use "cv :: merge" because the matrices must have equal sizes, sizes, channels. Work fast if opencv builds using sse or avx. And faster, if you use cv: GpuMat, you must have nvidia cuda support and build opencv with cuda. A.

 inline cv::Mat frame_mix_alpha(cv::Mat &cam_frame, cv::Mat &media_frame, cv::Mat &media_frame_alpha) { Mat suba = media_frame_alpha; //Mat alpha = cvCreateImage(media_frame_alpha.size(), IPL_DEPTH_8U, 1); //cvtColor(media_frame_alpha, alpha, CV_BGR2GRAY); //Mat suba; //Mat rgba[3] = { alpha, alpha, alpha }; //merge(rgba, 3, suba); Mat subb = ~suba; //Mat mincam = min(cam_frame, suba); //Mat minmedia = min(media_frame, subb); //Mat result = (cam_frame - mincam) + (media_frame - minmedia); Mat result = (cam_frame - suba) + (media_frame - subb); return result; } 
0
source

All Articles