The image is below, I want all black pixels to be transparent and save it to png file.
CodePudding user response:
You can do it fast and vectorised like this:
import cv2
import numpy as np
# Load image as Numpy array in BGR order
na = cv2.imread('I5jKW.png')
# Make a True/False mask of pixels whose BGR values sum to more than zero
alpha = np.sum(na, axis=-1) > 0
# Convert True/False to 0/255 and change type to "uint8" to match "na"
alpha = np.uint8(alpha * 255)
# Stack new alpha layer with existing image to go from BGR to BGRA, i.e. 3 channels to 4 channels
res = np.dstack((na, alpha))
# Save result
cv2.imwrite('result.png', res)
Notes:
1 You could equally use cv2.merge()
in place of np.dstack()
and it is probably faster.
2 You could equally use PIL/Pillow in place of the OpenCV functions to read/save images.
CodePudding user response:
Since I am not familiar with python, I coded the steps in C . Sorry for that.
#include <iostream>
#include <opencv2/highgui.hpp>
#include <opencv2/imgproc.hpp>
int main()
{
cv::Mat img = cv::imread("/ur/input/img.png",cv::IMREAD_COLOR);
cv::Mat mask = cv::Mat::zeros(cv::Size(img.cols,img.rows),CV_8UC4);
cv::namedWindow("Input",0);
cv::namedWindow("Output",0);
for(int i=0; i<mask.cols; i )
{
for(int j=0; j<mask.rows; j )
{
if(img.at<cv::Vec3b>(cv::Point(i,j))[0] == 0 &&
img.at<cv::Vec3b>(cv::Point(i,j))[1] == 0 &&
img.at<cv::Vec3b>(cv::Point(i,j))[2] == 0)
{
mask.at<cv::Vec4b>(cv::Point(i,j))[0] = img.at<cv::Vec3b>(cv::Point(i,j))[0];
mask.at<cv::Vec4b>(cv::Point(i,j))[1] = img.at<cv::Vec3b>(cv::Point(i,j))[1];
mask.at<cv::Vec4b>(cv::Point(i,j))[2] = img.at<cv::Vec3b>(cv::Point(i,j))[2];
mask.at<cv::Vec4b>(cv::Point(i,j))[3] = 0;
}
else {
mask.at<cv::Vec4b>(cv::Point(i,j))[0] = img.at<cv::Vec3b>(cv::Point(i,j))[0];
mask.at<cv::Vec4b>(cv::Point(i,j))[1] = img.at<cv::Vec3b>(cv::Point(i,j))[1];
mask.at<cv::Vec4b>(cv::Point(i,j))[2] = img.at<cv::Vec3b>(cv::Point(i,j))[2];
mask.at<cv::Vec4b>(cv::Point(i,j))[3] = 255;
}
}
}
cv::imshow("Input",img);
cv::imshow("Output",mask);
cv::imwrite("/ur/writing/dir/transparent.png",mask);
cv::waitKey(0);
return 0;
}