I have an image I am trying to segment by colouring each pixel either red green or blue. I have calculated a confidence score for each pixel and want to adjust the alpha transparency of the pixel to reflect confidence, i.e. low confidence means almost transparent. Is there a way to do this in OpenCV? If not can anyone suggest a minimally invasive library (C++)?
I have tries using a 4 channel 8-bit Mat
as suggested by Aurellius, here is the code:
cv::Mat m = cv::Mat(20,20, CV_8UC4);
for(int i = 0; i < m.rows; i++){
for(int j = 0; j < m.cols; j++){
Vec4b& v = m.at<Vec4b>(i,j);
v[0] = 255;
v[1] = 0;
v[2] = 0;
v[3] = 0.5;
}
}
imwrite("alpha.png", m);
namedWindow("m");
imshow("m", m);
waitKey(0);
The image shown is just all blue (no transparency) and the image just fully transparent.
There are many ways to accomplish this. One possible way is to access and modify each individual pixel. Assuming image
is a four-channel, 8-bit cv::Mat
:
auto& pixel = image.at<cv::Vec4b>(i,j);
pixel[3] = confidence;
where i
and j
are the indices of the pixel in the image.
There are other methods that are probably more elegant, but they will depend on your current code.
UPDATE:
The behavior you describe is to be expected. Apparently cv::imshow()
does not support transparency. This explains why your displayed image is all blue.
As for the saved image, it is important to remember that the image is of type CV_8UC4
. That means that each channel element is stored as a uchar
. Assigning a value of 0.5
will truncate to zero, hence the fully transparent saved image.
If your confidence is a float value in the range [0,1]
, scale it by 255 to put it in the range supported by 8-bit images. Thus,
v[3] = 0.5;
becomes
v[3] = 0.5 * 255;
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With