python-3.xscikit-imagerasteriosatellite-imagesentinel2

Crop TIFF using JPG mask


I'm currently working on cloud removals from satellite data (I'm pretty new).

This is the image I'm working on (TIFF)

enter image description here

And this is the mask, where black pixels represent clouds (JPG) enter image description here

I'm trying to remove the clouds from the TIFF, using the mask to identify the position of the cloud, and the cloudless image itself, like this (the area is the same, but the period is different):

enter image description here

I'm kindly ask how can I achieve that. A Python solution, with libraries like Rasterio or skimage is particularly appreciated.

Thanks in advance.


Solution

  • You can read the images with rasterio, PIL, OpenCV or tifffile, so I use OpenCV

    import cv2
    import numpy as np
    
    # Load the 3 images
    cloudy = cv2.imread('cloudy.png')
    mask   = cv2.imread('mask.jpg')
    clear  = cv2.imread('clear.png')
    

    Then just use Numpy where() to choose whether you want the clear or cloudy image at each location according to the mask:

    res = np.where(mask<128, clear, cloudy)
    

    enter image description here


    Note that if your mask was a single channel PNG rather than JPEG, or if it was read as greyscale like this:

    mask   = cv2.imread('mask.jpg', cv2.IMREAD_GRAYSCALE)
    

    you would have to make it broadcastable to the 3 channels of the other two arrays by adding a new axis like this:

    res = np.where(mask[...,np.newaxis]<128, clear, cloudy)