How to load png images with 4 channels?

后端 未结 5 1220
暗喜
暗喜 2020-12-03 00:45

I have been trying to load .png files with transparency channel (RGB and Alph) with no luck. It appears that openCV strips the 4th channel out of the image. Is there any met

相关标签:
5条回答
  • 2020-12-03 01:13

    The best possible way to load a png image with all 4 channels is ;

    img= cv2.imread('imagepath.jpg',negative value)
    

    As per openCV documentation,
    If Flag value is,
    1) =0 Return a grayscale image.
    2) <0 Return the loaded image as is (with alpha channel).

    0 讨论(0)
  • 2020-12-03 01:15

    According to the documentation, OpenCV supports alpha channel on PNGs.

    Just call the imread function using CV_LOAD_IMAGE_UNCHANGED as flags like this:

    cvLoadImage("file.png", CV_LOAD_IMAGE_UNCHANGED)
    
    0 讨论(0)
  • 2020-12-03 01:19

    If you are using OpenCV 2 or OpenCV 3 you should use IMREAD_* flags (as mentioned at here).

    C++

    using namespace cv;
    Mat image = imread("image.png", IMREAD_UNCHANGED);
    

    Python

    import cv2
    im = cv2.imread("image.png", cv2.IMREAD_UNCHANGED)
    
    0 讨论(0)
  • 2020-12-03 01:23

    If you wanna draw this transparent image over another image, open your image as answered by @satya-mallick, then use this method:

    /**
     * @brief Draws a transparent image over a frame Mat.
     * 
     * @param frame the frame where the transparent image will be drawn
     * @param transp the Mat image with transparency, read from a PNG image, with the IMREAD_UNCHANGED flag
     * @param xPos x position of the frame image where the image will start.
     * @param yPos y position of the frame image where the image will start.
     */
    void drawTransparency(Mat frame, Mat transp, int xPos, int yPos) {
        Mat mask;
        vector<Mat> layers;
    
        split(transp, layers); // seperate channels
        Mat rgb[3] = { layers[0],layers[1],layers[2] };
        mask = layers[3]; // png's alpha channel used as mask
        merge(rgb, 3, transp);  // put together the RGB channels, now transp insn't transparent 
        transp.copyTo(frame.rowRange(yPos, yPos + transp.rows).colRange(xPos, xPos + transp.cols), mask);
    }
    
    0 讨论(0)
  • 2020-12-03 01:28

    The right way to read a transparent PNG is to use the 4th channel as alpha channel. Most of the times one wants a white background, if that is the case then below code can be used for alpha compositing.

    def read_transparent_png(filename):
        image_4channel = cv2.imread(filename, cv2.IMREAD_UNCHANGED)
        alpha_channel = image_4channel[:,:,3]
        rgb_channels = image_4channel[:,:,:3]
    
        # White Background Image
        white_background_image = np.ones_like(rgb_channels, dtype=np.uint8) * 255
    
        # Alpha factor
        alpha_factor = alpha_channel[:,:,np.newaxis].astype(np.float32) / 255.0
        alpha_factor = np.concatenate((alpha_factor,alpha_factor,alpha_factor), axis=2)
    
        # Transparent Image Rendered on White Background
        base = rgb_channels.astype(np.float32) * alpha_factor
        white = white_background_image.astype(np.float32) * (1 - alpha_factor)
        final_image = base + white
        return final_image.astype(np.uint8)
    

    A detailed blog on this is here here.

    0 讨论(0)
提交回复
热议问题