(im_ms, im_labels, cloud_mask, buffer_size, im_ref_buffer)
return contours_mwi, t_mwi
New robust method for extracting shorelines. Incorporates the classification
    component to refine the treshold and make it specific to the sand/water interface.

    KV WRL 2018

    Arguments:
    -----------
    im_ms: np.array
        RGB + downsampled NIR and SWIR
    im_labels: np.array
        3D image containing a boolean image for each class in the order (sand, swash, water)
    cloud_mask: np.array
        2D cloud mask with True where cloud pixels are
    buffer_size: int
        size of the buffer around the sandy beach over which the pixels are considered in the
        thresholding algorithm.
    im_ref_buffer: np.array
        binary image containing a buffer around the reference shoreline

    Returns:    
    -----------
    contours_mwi: list of np.arrays
        contains the coordinates of the contour lines extracted from the
        MNDWI (Modified Normalized Difference Water Index) image
    t_mwi: float
        Otsu sand/water threshold used to map the contours
New robust method for extracting shorelines. Incorporates the classification
    component to refine the treshold and make it specific to the sand/water interface.
New robust method for extracting shorelines . Incorporates the classification component to refine the treshold and make it specific to the sand / water interface .
def find_wl_contours2(im_ms, im_labels, cloud_mask, buffer_size, im_ref_buffer):
    """
    New robust method for extracting shorelines. Incorporates the classification
    component to refine the treshold and make it specific to the sand/water interface.

    KV WRL 2018

    Arguments:
    -----------
    im_ms: np.array
        RGB + downsampled NIR and SWIR
    im_labels: np.array
        3D image containing a boolean image for each class in the order (sand, swash, water)
    cloud_mask: np.array
        2D cloud mask with True where cloud pixels are
    buffer_size: int
        size of the buffer around the sandy beach over which the pixels are considered in the
        thresholding algorithm.
    im_ref_buffer: np.array
        binary image containing a buffer around the reference shoreline

    Returns:    
    -----------
    contours_mwi: list of np.arrays
        contains the coordinates of the contour lines extracted from the
        MNDWI (Modified Normalized Difference Water Index) image
    t_mwi: float
        Otsu sand/water threshold used to map the contours

    """

    nrows = cloud_mask.shape[0]
    ncols = cloud_mask.shape[1]

    # calculate Normalized Difference Modified Water Index (SWIR - G)
    im_mwi = SDS_tools.nd_index(im_ms[:,:,4], im_ms[:,:,1], cloud_mask)
    # calculate Normalized Difference Modified Water Index (NIR - G)
    im_wi = SDS_tools.nd_index(im_ms[:,:,3], im_ms[:,:,1], cloud_mask)
    # stack indices together
    im_ind = np.stack((im_wi, im_mwi), axis=-1)
    vec_ind = im_ind.reshape(nrows*ncols,2)

    # reshape labels into vectors
    vec_sand = im_labels[:,:,0].reshape(ncols*nrows)
    vec_water = im_labels[:,:,2].reshape(ncols*nrows)

    # create a buffer around the sandy beach
    se = morphology.disk(buffer_size)
    im_buffer = morphology.binary_dilation(im_labels[:,:,0], se)
    vec_buffer = im_buffer.reshape(nrows*ncols)

    # select water/sand/swash pixels that are within the buffer
    int_water = vec_ind[np.logical_and(vec_buffer,vec_water),:]
    int_sand = vec_ind[np.logical_and(vec_buffer,vec_sand),:]

    # make sure both classes have the same number of pixels before thresholding
    if len(int_water) > 0 and len(int_sand) > 0:
        if np.argmin([int_sand.shape[0],int_water.shape[0]]) == 1:
            int_sand = int_sand[np.random.choice(int_sand.shape[0],int_water.shape[0], replace=False),:]
        else:
            int_water = int_water[np.random.choice(int_water.shape[0],int_sand.shape[0], replace=False),:]

    # threshold the sand/water intensities
    int_all = np.append(int_water,int_sand, axis=0)
    t_mwi = filters.threshold_otsu(int_all[:,0])
    t_wi = filters.threshold_otsu(int_all[:,1])

    # find contour with MS algorithm
    im_wi_buffer = np.copy(im_wi)
    im_wi_buffer[~im_ref_buffer] = np.nan
    im_mwi_buffer = np.copy(im_mwi)
    im_mwi_buffer[~im_ref_buffer] = np.nan
    contours_wi = measure.find_contours(im_wi_buffer, t_wi)
    contours_mwi = measure.find_contours(im_mwi_buffer, t_mwi)
    # remove contour points that are NaNs (around clouds)
    contours_wi = process_contours(contours_wi)
    contours_mwi = process_contours(contours_mwi)

    # only return MNDWI contours and threshold
    return contours_mwi, t_mwi
def find_wl_contours2 ( im_ms , im_labels , cloud_mask , buffer_size , im_ref_buffer ) : nrows = cloud_mask . shape [ 0 ] ncols = cloud_mask . shape [ 1 ] # calculate Normalized Difference Modified Water Index (SWIR - G) im_mwi = SDS_tools . nd_index ( im_ms [ : , : , 4 ] , im_ms [ : , : , 1 ] , cloud_mask ) # calculate Normalized Difference Modified Water Index (NIR - G) im_wi = SDS_tools . nd_index ( im_ms [ : , : , 3 ] , im_ms [ : , : , 1 ] , cloud_mask ) # stack indices together im_ind = np . stack ( ( im_wi , im_mwi ) , axis = - 1 ) vec_ind = im_ind . reshape ( nrows * ncols , 2 ) # reshape labels into vectors vec_sand = im_labels [ : , : , 0 ] . reshape ( ncols * nrows ) vec_water = im_labels [ : , : , 2 ] . reshape ( ncols * nrows ) # create a buffer around the sandy beach se = morphology . disk ( buffer_size ) im_buffer = morphology . binary_dilation ( im_labels [ : , : , 0 ] , se ) vec_buffer = im_buffer . reshape ( nrows * ncols ) # select water/sand/swash pixels that are within the buffer int_water = vec_ind [ np . logical_and ( vec_buffer , vec_water ) , : ] int_sand = vec_ind [ np . logical_and ( vec_buffer , vec_sand ) , : ] # make sure both classes have the same number of pixels before thresholding if len ( int_water ) > 0 and len ( int_sand ) > 0 : if np . argmin ( [ int_sand . shape [ 0 ] , int_water . shape [ 0 ] ] ) == 1 : int_sand = int_sand [ np . random . choice ( int_sand . shape [ 0 ] , int_water . shape [ 0 ] , replace = False ) , : ] else : int_water = int_water [ np . random . choice ( int_water . shape [ 0 ] , int_sand . shape [ 0 ] , replace = False ) , : ] # threshold the sand/water intensities int_all = np . append ( int_water , int_sand , axis = 0 ) t_mwi = filters . threshold_otsu ( int_all [ : , 0 ] ) t_wi = filters . threshold_otsu ( int_all [ : , 1 ] ) # find contour with MS algorithm im_wi_buffer = np . copy ( im_wi ) im_wi_buffer [ ~ im_ref_buffer ] = np . nan im_mwi_buffer = np . copy ( im_mwi ) im_mwi_buffer [ ~ im_ref_buffer ] = np . nan contours_wi = measure . find_contours ( im_wi_buffer , t_wi ) contours_mwi = measure . find_contours ( im_mwi_buffer , t_mwi ) # remove contour points that are NaNs (around clouds) contours_wi = process_contours ( contours_wi ) contours_mwi = process_contours ( contours_mwi ) # only return MNDWI contours and threshold return contours_mwi , t_mwi