Example #1
0
def caiman_motion_correct(fnames, opts):
    '''do the motion correction of the Caiman pipeline and save results.
    Parameters
    ----------
    fnames : string
        name of tiff movie
    opts : caiman object with the options for motion correction'''

    #%% start a cluster for parallel processing (if a cluster already exists it will be closed and a new session will be opened)
    if 'dview' in locals():
        cm.stop_server(dview=dview)
    c, dview, n_processes = cm.cluster.setup_cluster(backend='local',
                                                     n_processes=None,
                                                     single_thread=False)

    # first we create a motion correction object with the parameters specified
    mc = MotionCorrect(fnames, dview=dview, **opts.get_group('motion'))
    mc.motion_correct(save_movie=True)
    border_to_0 = 0 if mc.border_nan is 'copy' else mc.border_to_0
    # memory map the file in order 'C'
    fname_new = cm.save_memmap(mc.mmap_file,
                               base_name='memmap_',
                               order='C',
                               border_to_0=border_to_0,
                               dview=dview)  # exclude borders
    cm.stop_server(dview=dview)
Example #2
0
    def motion_correct_rigid(self, fname):
        dview = None
        try:

            c, dview, n_processes = cm.cluster.setup_cluster(
                backend='local', n_processes=None, single_thread=False)

            niter_rig = 1  # number of iterations for rigid motion correction
            max_shifts = self.get_dict_param('max_shifts_rigid', 'tuple_int')
            # for parallelization split the movies in  num_splits chuncks across time
            splits_rig = self.get_dict_param('splits_rig', 'single_int')
            # first we create a motion correction object with the parameters specified
            min_mov = cm.load(fname[0], subindices=range(200)).min()
            # this will be subtracted from the movie to make it non-negative

            mc = MotionCorrect(fname,
                               min_mov,
                               dview=dview,
                               max_shifts=max_shifts,
                               niter_rig=niter_rig,
                               splits_rig=splits_rig,
                               border_nan='copy',
                               shifts_opencv=True,
                               nonneg_movie=True)

            mc.motion_correct_rigid(save_movie=True)

            self.motion_correct = mc
        except Exception as e:
            raise e
        finally:
            cm.cluster.stop_server(dview=dview)
Example #3
0
def preprocess_data(base,
                    image_folder='z0',
                    scale=0.5,
                    name='movie.tif',
                    edge=5,
                    corrected_name='movie_corrected.tif'):
    for root, dirs, files in os.walk(base):
        offset = -1 * len(image_folder)
        if image_folder == root[offset:]:
            print('Preprocessing ', root)
            fname = root
            oname = root[:(-1 - len(image_folder))]

            # Convert and crop stack
            try:
                saved_path = convert_and_crop_stack(fname, oname, scale, name)
            except (FileExistsError, FileNotFoundError) as e:
                print(oname, ' cannot be preprocessed, skipping...')
                continue

            # Motion correction, cut off edges
            mc = MotionCorrect(saved_path, 0)
            mc.motion_correct_rigid()
            with tifffile.TiffWriter(oname + os.sep + corrected_name,
                                     imagej=True) as tif:
                shifted = mc.apply_shifts_movie(saved_path)
                shifted = shifted[:, edge:-edge, edge:-edge]

                converted_stack = np.array(shifted * (2**16), dtype='uint16')
                tif.save(converted_stack)
Example #4
0
def motion_correct_file(args, n_iter=0, max_iter=10):
    try:
        in_fn, file_index, template, mc_args, \
            subidx, apply_subidx, apply_ofn = args
        max_shifts, strides, overlaps, \
            max_deviation_rigid, shifts_opencv, border_nan = mc_args
        mc = MotionCorrect(in_fn,
                           dview=None,
                           max_shifts=max_shifts,
                           strides=strides,
                           overlaps=overlaps,
                           max_deviation_rigid=max_deviation_rigid,
                           shifts_opencv=shifts_opencv,
                           nonneg_movie=True,
                           splits_els=1,
                           splits_rig=1,
                           border_nan=border_nan,
                           subidx=subidx)
        mc.motion_correct(template=template, save_movie=False)
        if apply_subidx is not None:
            applied_mov = mc.apply_shifts_movie(in_fn, apply_subidx)
            applied_mov.save(apply_ofn)
        return (file_index, np.mean(mc.templates_rig, axis=0))
    except Exception as e:
        if n_iter < max_iter:
            print("Retrying %s due to %s" % (in_fn, e))
            return motion_correct_file(args, n_iter=n_iter + 1)
        else:
            return Exception("Failed max_iter: %s times" % max_iter)
Example #5
0
def mc_vids(vids_fpath, mc_rigid_template):
    start = time.time()
    # estimated minimum value of the movie to produce an output that is positive
    min_mov = np.array([
        cm.motion_correction.high_pass_filter_space(m_, gSig_filt)
        for m_ in cm.load(vids_fpath[0], subindices=range(400))
    ]).min()
    mc = MotionCorrect(vids_fpath,
                       min_mov,
                       dview=dview,
                       max_shifts=max_shifts,
                       niter_rig=1,
                       splits_rig=splits_rig,
                       num_splits_to_process_rig=None,
                       shifts_opencv=True,
                       nonneg_movie=True,
                       gSig_filt=gSig_filt,
                       border_nan=border_nan,
                       is3D=False)

    mc.motion_correct_rigid(save_movie=(not doPwRigid),
                            template=mc_rigid_template)

    shifts_rig = mc.shifts_rig
    template_rig = mc.total_template_rig

    if doPwRigid:
        mc.motion_correct_pwrigid(save_movie=True, template=template_rig)
        mc.total_template_rig = template_rig

    duration = time.time() - start
    logging.info('Motion correction done in %s', str(duration))
    return mc, duration, shifts_rig
Example #6
0
    def _run_motion_correction(self, file_name, max_shifts, strides, overlaps,
                               upsample_factor_grid, max_deviation_rigid):
        """
        Private function that initiates motion correction from CaImAn package,
        and return the motion corrected file names and their respective pixel
        shifts.
        """

        offset_orig = np.nanmin(self.data_orig[:1000])
        G6Image = MotionCorrect(file_name,
                                offset_orig,
                                max_shifts=max_shifts,
                                niter_rig=1,
                                splits_rig=56,
                                strides=strides,
                                overlaps=overlaps,
                                splits_els=56,
                                upsample_factor_grid=upsample_factor_grid,
                                shifts_opencv=True,
                                max_deviation_rigid=max_deviation_rigid,
                                nonneg_movie=True)

        G6Image.motion_correct_rigid(save_movie=True)

        G6Image.motion_correct_pwrigid(save_movie=True,
                                       template=G6Image.total_template_rig)
        name_rig = G6Image.fname_tot_rig
        name_pwrig = G6Image.fname_tot_els
        shifts_rig = G6Image.shifts_rig
        x_shifts_pwrig = G6Image.x_shifts_els
        y_shifts_pwrig = G6Image.y_shifts_els
        template_shape = G6Image.total_template_els.shape

        return name_rig, name_pwrig, shifts_rig, x_shifts_pwrig, y_shifts_pwrig, template_shape
 def motion_correct_red(self):
     self.motion_corrected_images = []
     for plane in list(range(self.planes)):
         print(f'Starting motion correction plane {plane}')
         self.mc = MotionCorrect(self.file_list[plane],
                                 dview=self.dview,
                                 **self.opts.get_group('motion'))
         self.mc.motion_correct()
         self.motion_corrected_images.append(self.mc.total_template_els)
Example #8
0
    def motion_correct_pwrigid(self, fname):
        dview = None
        try:
            c, dview, n_processes = cm.cluster.setup_cluster(
                backend='local', n_processes=None, single_thread=False)

            niter_rig = 1  # number of iterations for rigid motion correction
            max_shifts = self.get_dict_param(
                'max_shifts_pwrigid', 'tuple_int')  # maximum allow rigid shift
            # for parallelization split the movies in  num_splits chuncks across time
            splits_rig = self.get_dict_param('splits_rig', 'single_int')
            # start a new patch for pw-rigid motion correction every x pixels
            strides = self.get_dict_param('strides', 'tuple_int')
            # overlap between pathes (size of patch strides+overlaps)
            overlaps = self.get_dict_param('overlaps', 'tuple_int')
            # for parallelization split the movies in  num_splits chuncks across time
            splits_els = self.get_dict_param('splits_els', 'single_int')

            upsample_factor_grid = self.get_dict_param(
                'upsample_factor_grid', 'single_int'
            )  # upsample factor to avoid smearing when merging patches
            # maximum deviation allowed for patch with respect to rigid shifts
            max_deviation_rigid = self.get_dict_param('max_deviation_rigid',
                                                      'single_int')
            # first we create a motion correction object with the parameters specified
            min_mov = cm.load(fname[0], subindices=range(200)).min()
            # this will be subtracted from the movie to make it non-negative

            print(
                str([
                    max_shifts, splits_rig, strides, overlaps, splits_els,
                    upsample_factor_grid, max_deviation_rigid, min_mov
                ]))
            mc = MotionCorrect(fname,
                               min_mov,
                               dview=dview,
                               max_shifts=max_shifts,
                               niter_rig=niter_rig,
                               splits_rig=splits_rig,
                               strides=strides,
                               overlaps=overlaps,
                               splits_els=splits_els,
                               border_nan='copy',
                               upsample_factor_grid=upsample_factor_grid,
                               max_deviation_rigid=max_deviation_rigid,
                               shifts_opencv=True,
                               nonneg_movie=True)

            mc.motion_correct_pwrigid(save_movie=True)
            self.motion_correct = mc

        except Exception as e:
            raise e
        finally:
            cm.cluster.stop_server(dview=dview)
Example #9
0
 def motion_correct_red(self):
     c, dview, n_processes = cm.cluster.setup_cluster(
         backend='local', n_processes=None, single_thread=False)
     
     self.motion_corrected_images = []
     for plane in list(range(self.planes)):
         print(f'Starting motion correction plane {plane}')
         self.mc = MotionCorrect(self.file_list[plane], dview=dview, **self.opts.get_group('motion'))
         self.mc.motion_correct()
         self.motion_corrected_images.append(self.mc.total_template_els)
     cm.stop_server(dview=dview)
    def motion_correct_file(folder, dview):
        import caiman as cm
        from caiman.motion_correction import MotionCorrect
        from caiman.source_extraction.cnmf import params as params
        print(folder)

        mc_dict = {
            'fnames': [os.path.join(folder, 'movie_total.hdf5')],
            'fr': 7,
            'decay_time': 1.5,
            'dxy': [1.15, 1.15],
            'pw_rigid': False,
            'max_shifts': [5,5],
            'strides': None,
            'overlaps': None,
            'max_deviation_rigid': None,
            'border_nan': 'copy'
        }

        opts = params.CNMFParams(params_dict=mc_dict)
        mc = MotionCorrect(mc_dict['fnames'], dview=dview, **opts.get_group('motion'))
        mc.motion_correct(save_movie=True)
Example #11
0
    def motion_correct(self):
        """
        Do motion correction.

        """
        # Set up motion correction object and load parameters.
        mc = MotionCorrect(self.fnames,
                           dview=self.dview,
                           **self.opts.get_group('motion'))

        # Do motion correction.
        mc.motion_correct(save_movie=True)

        # Plot motion correction statistics.
        fname_mc = mc.fname_tot_els if self.opts.motion[
            'pw_rigid'] else mc.fname_tot_rig
        if self.opts.motion['pw_rigid']:
            self.bord_px = np.ceil(
                np.maximum(np.max(np.abs(mc.x_shifts_els)),
                           np.max(np.abs(mc.y_shifts_els)))).astype(np.int)
        else:
            self.bord_px = np.ceil(np.max(np.abs(mc.shifts_rig))).astype(
                np.int)
            plt.subplot(1, 2, 1)
            plt.imshow(mc.total_template_rig)  # % plot template
            plt.subplot(1, 2, 2)
            plt.plot(mc.shifts_rig)  # % plot rigid shifts
            plt.legend(['x shifts', 'y shifts'])
            plt.xlabel('frames')
            plt.ylabel('pixels')

        # Save memory map.
        self.bord_px = 0 if self.opts.motion[
            'border_nan'] is 'copy' else self.bord_px
        self.fname_new = cm.save_memmap(fname_mc,
                                        base_name='full',
                                        order='C',
                                        border_to_0=self.bord_px)
Example #12
0
def motion_corr(fnames, dview, opts, disp_movie, is_3d=False):
    """Perform motion correction"""
    # Create a motion correction object with the parameters specified. Note
    # that the file is not loaded in memory
    mc = MotionCorrect(fnames, dview=dview, **opts.get_group('motion'))

    # Run piecewise-rigid motion correction using NoRMCorre
    mc.motion_correct(save_movie=True)

    # Determine maximum shift to be used for trimming against NaNs
    border_to_0 = 0 if mc.border_nan is 'copy' else mc.border_to_0

    # Compare with original movie
    if disp_movie and not is_3d:
        m_els = cm.load(mc.fname_tot_els)
        m_orig = cm.load_movie_chain(fnames)
        ds_ratio = 0.2
        cm.concatenate([
            m_orig.resize(1, 1, ds_ratio) - mc.min_mov * mc.nonneg_movie,
            m_els.resize(1, 1, ds_ratio)
        ],
                       axis=2).play(fr=60, gain=15, magnification=2,
                                    offset=0)  # press q to exit
    return mc, border_to_0
def motion_correct(video_path, max_shift, patch_stride, patch_overlap, use_multiprocessing=True):
    full_video_path = video_path

    directory = os.path.dirname(full_video_path)
    filename  = os.path.basename(full_video_path)

    memmap_video = tifffile.memmap(video_path)

    if use_multiprocessing:
        if os.name == 'nt':
            backend = 'multiprocessing'
        else:
            backend = 'ipyparallel'

        # Create the cluster
        cm.stop_server()
        c, dview, n_processes = cm.cluster.setup_cluster(backend=backend, n_processes=None, single_thread=False)
    else:
        dview = None

    z_range = list(range(memmap_video.shape[1]))

    new_video_path = os.path.join(directory, "mc_video_temp.tif")

    shutil.copyfile(video_path, new_video_path)

    mc_video = tifffile.memmap(new_video_path).astype(np.uint16)

    mc_borders = [ None for z in z_range ]

    counter = 0

    for z in z_range:
        print("Motion correcting plane z={}...".format(z))
        video_path = os.path.join(directory, os.path.splitext(filename)[0] + "_z_{}_temp.tif".format(z))
        tifffile.imsave(video_path, memmap_video[:, z, :, :])

        mc_video[:, z, :, :] *= 0

        # --- PARAMETERS --- #

        params_movie = {'fname': video_path,
                        'max_shifts': (max_shift, max_shift),  # maximum allow rigid shift (2,2)
                        'niter_rig': 3,
                        'splits_rig': 1,  # for parallelization split the movies in  num_splits chuncks across time
                        'num_splits_to_process_rig': None,  # if none all the splits are processed and the movie is saved
                        'strides': (patch_stride, patch_stride),  # intervals at which patches are laid out for motion correction
                        'overlaps': (patch_overlap, patch_overlap),  # overlap between pathes (size of patch strides+overlaps)
                        'splits_els': 1,  # for parallelization split the movies in  num_splits chuncks across time
                        'num_splits_to_process_els': [None],  # if none all the splits are processed and the movie is saved
                        'upsample_factor_grid': 4,  # upsample factor to avoid smearing when merging patches
                        'max_deviation_rigid': 3,  # maximum deviation allowed for patch with respect to rigid shift         
                        }

        # load movie (in memory!)
        fname = params_movie['fname']
        niter_rig = params_movie['niter_rig']
        # maximum allow rigid shift
        max_shifts = params_movie['max_shifts']  
        # for parallelization split the movies in  num_splits chuncks across time
        splits_rig = params_movie['splits_rig']  
        # if none all the splits are processed and the movie is saved
        num_splits_to_process_rig = params_movie['num_splits_to_process_rig']
        # intervals at which patches are laid out for motion correction
        strides = params_movie['strides']
        # overlap between pathes (size of patch strides+overlaps)
        overlaps = params_movie['overlaps']
        # for parallelization split the movies in  num_splits chuncks across time
        splits_els = params_movie['splits_els'] 
        # if none all the splits are processed and the movie is saved
        num_splits_to_process_els = params_movie['num_splits_to_process_els']
        # upsample factor to avoid smearing when merging patches
        upsample_factor_grid = params_movie['upsample_factor_grid'] 
        # maximum deviation allowed for patch with respect to rigid
        # shift
        max_deviation_rigid = params_movie['max_deviation_rigid']

        # --- RIGID MOTION CORRECTION --- #

        # Load the original movie
        m_orig = tifffile.memmap(fname)
        # m_orig = cm.load(fname)
        min_mov = np.min(m_orig) # movie must be mostly positive for this to work

        offset_mov = -min_mov

        # Create motion correction object
        mc = MotionCorrect(fname, min_mov,
                           dview=dview, max_shifts=max_shifts, niter_rig=niter_rig, splits_rig=splits_rig, 
                           num_splits_to_process_rig=num_splits_to_process_rig, 
                        strides= strides, overlaps= overlaps, splits_els=splits_els,
                        num_splits_to_process_els=num_splits_to_process_els, 
                        upsample_factor_grid=upsample_factor_grid, max_deviation_rigid=max_deviation_rigid, 
                        shifts_opencv = True, nonneg_movie = True, border_nan='min')

        # Do rigid motion correction
        mc.motion_correct_rigid(save_movie=False)

        # --- ELASTIC MOTION CORRECTION --- #

        # Do elastic motion correction
        mc.motion_correct_pwrigid(save_movie=True, template=mc.total_template_rig, show_template=False)

        # # Save elastic shift border
        bord_px_els = np.ceil(np.maximum(np.max(np.abs(mc.x_shifts_els)),
                                 np.max(np.abs(mc.y_shifts_els)))).astype(np.int)  
        # np.savez(mc.fname_tot_els + "_bord_px_els.npz", bord_px_els)

        fnames = mc.fname_tot_els   # name of the pw-rigidly corrected file.
        border_to_0 = bord_px_els     # number of pixels to exclude
        fname_new = cm.save_memmap(fnames, base_name='memmap_z_{}'.format(z), order = 'C',
                                   border_to_0 = bord_px_els) # exclude borders

        # now load the file
        Yr, dims, T = cm.load_memmap(fname_new)
        d1, d2 = dims
        images = np.reshape(Yr.T, [T] + list(dims), order='F') 

        mc_borders[z] = bord_px_els

        # images += np.amin(images)

        # print(np.amax(images))
        # print(np.amin(images))
        # print(type(images))

        mc_video[:, z, :, :] = (images - np.amin(images)).astype(np.uint16)

        del m_orig
        os.remove(video_path)

        try:
            os.remove(mc.fname_tot_rig)
            os.remove(mc.fname_tot_els)
        except:
            pass

        counter += 1

    if use_multiprocessing:
        if backend == 'multiprocessing':
            dview.close()
        else:
            try:
                dview.terminate()
            except:
                dview.shutdown()
        cm.stop_server()

    mmap_files = glob.glob(os.path.join(directory, '*.mmap'))
    for mmap_file in mmap_files:
        try:
            os.remove(mmap_file)
        except:
            pass

    log_files = glob.glob('Yr*_LOG_*')
    for log_file in log_files:
        os.remove(log_file)

    return mc_video, new_video_path, mc_borders
Example #14
0
c, dview, n_processes = cm.cluster.setup_cluster(backend='local',
                                                 n_processes=None,
                                                 single_thread=False)

#%%% MOTION CORRECTION
# first we create a motion correction object with the parameters specified
min_mov = cm.load(fname[0], subindices=range(200)).min()
# this will be subtracted from the movie to make it non-negative

mc = MotionCorrect(fname[0],
                   min_mov,
                   dview=dview,
                   max_shifts=max_shifts,
                   niter_rig=niter_rig,
                   splits_rig=splits_rig,
                   strides=strides,
                   overlaps=overlaps,
                   splits_els=splits_els,
                   upsample_factor_grid=upsample_factor_grid,
                   max_deviation_rigid=max_deviation_rigid,
                   shifts_opencv=True,
                   nonneg_movie=True)
# note that the file is not loaded in memory

#%% Run piecewise-rigid motion correction using NoRMCorre
mc.motion_correct_pwrigid(save_movie=True)
m_els = cm.load(mc.fname_tot_els)
bord_px_els = np.ceil(
    np.maximum(np.max(np.abs(mc.x_shifts_els)),
               np.max(np.abs(mc.y_shifts_els)))).astype(np.int)
# maximum shift to be used for trimming against NaNs
Example #15
0
def test_computational_performance(fnames, path_ROIs, n_processes):
    import os
    import cv2
    import glob
    import logging
    import matplotlib.pyplot as plt
    import numpy as np
    import tensorflow as tf
    import h5py
    from time import time

    try:
        cv2.setNumThreads(0)
    except:
        pass

    try:
        if __IPYTHON__:
            # this is used for debugging purposes only. allows to reload classes
            # when changed
            get_ipython().magic('load_ext autoreload')
            get_ipython().magic('autoreload 2')
    except NameError:
        pass

    import caiman as cm
    from caiman.motion_correction import MotionCorrect
    from caiman.utils.utils import download_demo, download_model
    from caiman.source_extraction.volpy.volparams import volparams
    from caiman.source_extraction.volpy.volpy import VOLPY
    from caiman.source_extraction.volpy.mrcnn import visualize, neurons
    import caiman.source_extraction.volpy.mrcnn.model as modellib
    from caiman.paths import caiman_datadir
    from caiman.summary_images import local_correlations_movie_offline
    from caiman.summary_images import mean_image
    from caiman.source_extraction.volpy.utils import quick_annotation
    from multiprocessing import Pool

    time_start = time()
    print('Start MOTION CORRECTION')

    # %%  Load demo movie and ROIs
    fnames = fnames
    path_ROIs = path_ROIs

    #%% dataset dependent parameters
    # dataset dependent parameters
    fr = 400  # sample rate of the movie

    # motion correction parameters
    pw_rigid = False  # flag for pw-rigid motion correction
    gSig_filt = (3, 3)  # size of filter, in general gSig (see below),
    # change this one if algorithm does not work
    max_shifts = (5, 5)  # maximum allowed rigid shift
    strides = (
        48, 48
    )  # start a new patch for pw-rigid motion correction every x pixels
    overlaps = (24, 24
                )  # overlap between pathes (size of patch strides+overlaps)
    max_deviation_rigid = 3  # maximum deviation allowed for patch with respect to rigid shifts
    border_nan = 'copy'

    opts_dict = {
        'fnames': fnames,
        'fr': fr,
        'pw_rigid': pw_rigid,
        'max_shifts': max_shifts,
        'gSig_filt': gSig_filt,
        'strides': strides,
        'overlaps': overlaps,
        'max_deviation_rigid': max_deviation_rigid,
        'border_nan': border_nan
    }

    opts = volparams(params_dict=opts_dict)

    # %% start a cluster for parallel processing
    dview = Pool(n_processes)
    #dview = None
    # %%% MOTION CORRECTION
    # first we create a motion correction object with the specified parameters
    mc = MotionCorrect(fnames, dview=dview, **opts.get_group('motion'))
    # Run correction
    mc.motion_correct(save_movie=True)

    time_mc = time() - time_start
    print(time_mc)
    print('START MEMORY MAPPING')

    # %% restart cluster to clean up memory
    dview.terminate()
    dview = Pool(n_processes)

    # %% MEMORY MAPPING
    border_to_0 = 0 if mc.border_nan == 'copy' else mc.border_to_0
    # you can include the boundaries of the FOV if you used the 'copy' option
    # during motion correction, although be careful about the components near
    # the boundaries

    # memory map the file in order 'C'
    fname_new = cm.save_memmap_join(mc.mmap_file,
                                    base_name='memmap_',
                                    add_to_mov=border_to_0,
                                    dview=dview,
                                    n_chunks=1000)  # exclude border

    time_mmap = time() - time_start - time_mc
    print('Start Segmentation')
    # %% SEGMENTATION
    # create summary images
    img = mean_image(mc.mmap_file[0], window=1000, dview=dview)
    img = (img - np.mean(img)) / np.std(img)
    Cn = local_correlations_movie_offline(mc.mmap_file[0],
                                          fr=fr,
                                          window=1500,
                                          stride=1500,
                                          winSize_baseline=400,
                                          remove_baseline=True,
                                          dview=dview).max(axis=0)
    img_corr = (Cn - np.mean(Cn)) / np.std(Cn)
    summary_image = np.stack([img, img, img_corr], axis=2).astype(np.float32)

    #%% three methods for segmentation
    methods_list = [
        'manual_annotation',  # manual annotation needs user to prepare annotated datasets same format as demo ROIs 
        'quick_annotation',  # quick annotation annotates data with simple interface in python
        'maskrcnn'
    ]  # maskrcnn is a convolutional network trained for finding neurons using summary images
    method = methods_list[0]
    if method == 'manual_annotation':
        with h5py.File(path_ROIs, 'r') as fl:
            ROIs = fl['mov'][()]  # load ROIs

    elif method == 'quick_annotation':
        ROIs = quick_annotation(img_corr, min_radius=4, max_radius=10)

    elif method == 'maskrcnn':
        config = neurons.NeuronsConfig()

        class InferenceConfig(config.__class__):
            # Run detection on one image at a time
            GPU_COUNT = 1
            IMAGES_PER_GPU = 1
            DETECTION_MIN_CONFIDENCE = 0.7
            IMAGE_RESIZE_MODE = "pad64"
            IMAGE_MAX_DIM = 512
            RPN_NMS_THRESHOLD = 0.7
            POST_NMS_ROIS_INFERENCE = 1000

        config = InferenceConfig()
        config.display()
        model_dir = os.path.join(caiman_datadir(), 'model')
        DEVICE = "/cpu:0"  # /cpu:0 or /gpu:0
        with tf.device(DEVICE):
            model = modellib.MaskRCNN(mode="inference",
                                      model_dir=model_dir,
                                      config=config)
        weights_path = download_model('mask_rcnn')
        model.load_weights(weights_path, by_name=True)
        results = model.detect([summary_image], verbose=1)
        r = results[0]
        ROIs = r['masks'].transpose([2, 0, 1])

        display_result = False
        if display_result:
            _, ax = plt.subplots(1, 1, figsize=(16, 16))
            visualize.display_instances(summary_image,
                                        r['rois'],
                                        r['masks'],
                                        r['class_ids'], ['BG', 'neurons'],
                                        r['scores'],
                                        ax=ax,
                                        title="Predictions")

    time_seg = time() - time_mmap - time_mc - time_start
    print('Start SPIKE EXTRACTION')

    # %% restart cluster to clean up memory
    dview.terminate()
    dview = Pool(n_processes, maxtasksperchild=1)

    # %% parameters for trace denoising and spike extraction
    fnames = fname_new  # change file
    ROIs = ROIs  # region of interests
    index = list(range(len(ROIs)))  # index of neurons
    weights = None  # reuse spatial weights

    tau_lp = 5  # parameter for high-pass filter to remove photobleaching
    threshold = 4  # threshold for finding spikes, increase threshold to find less spikes
    contextSize = 35  # number of pixels surrounding the ROI to censor from the background PCA
    flip_signal = True  # Important! Flip signal or not, True for Voltron indicator, False for others

    opts_dict = {
        'fnames': fnames,
        'ROIs': ROIs,
        'index': index,
        'weights': weights,
        'tau_lp': tau_lp,
        'threshold': threshold,
        'contextSize': contextSize,
        'flip_signal': flip_signal
    }

    opts.change_params(params_dict=opts_dict)

    #%% Trace Denoising and Spike Extraction
    vpy = VOLPY(n_processes=n_processes, dview=dview, params=opts)
    vpy.fit(n_processes=n_processes, dview=dview)

    # %% STOP CLUSTER and clean up log files
    #dview.terminate()
    log_files = glob.glob('*_LOG_*')
    for log_file in log_files:
        os.remove(log_file)

    time_ext = time() - time_mmap - time_mc - time_start - time_seg

    #%%
    print('file:' + fnames)
    print('number of processes' + str(n_processes))
    print(time_mc)
    print(time_mmap)
    print(time_seg)
    print(time_ext)
    time_list = [time_mc, time_mmap, time_seg, time_ext]

    return time_list
Example #16
0
def correct_single_movie(folder_path):

    #=======================================setup parameters==============================================
    # number of iterations for rigid motion correction
    niter_rig = 5

    # maximum allowed rigid shift in pixels (view the movie to get a sense of motion)
    max_shifts = (30, 30)

    # for parallelization split the movies in  num_splits chuncks across time
    # if none all the splits are processed and the movie is saved
    splits_rig = 56

    # intervals at which patches are laid out for motion correction
    # num_splits_to_process_rig = None

    # create a new patch every x pixels for pw-rigid correction
    strides = (48, 48)

    # overlap between pathes (size of patch strides+overlaps)
    overlaps = (24, 24)

    # for parallelization split the movies in  num_splits chuncks across time
    splits_els = 56

    # num_splits_to_process_els = [28, None]

    # upsample factor to avoid smearing when merging patches
    upsample_factor_grid = 4

    # maximum deviation allowed for patch with respect to rigid shifts
    max_deviation_rigid = 3

    # if True, apply shifts fast way (but smoothing results) by using opencv
    shifts_opencv = True

    # if True, make the SAVED movie and template mostly nonnegative by removing min_mov from movie
    nonneg_movie = False
    # =======================================setup parameters==============================================

    offset_mov = 0.

    file_path = [f for f in os.listdir(folder_path) if f[-4:] == '.tif']
    if len(file_path) == 0:
        raise LookupError(
            'no tif file found in folder: {}'.format(folder_path))
    elif len(file_path) > 1:
        raise LookupError(
            'more than one tif files found in folder: {}'.format(folder_path))
    else:
        file_path = os.path.join(folder_path, file_path[0])

    # create a motion correction object# creat
    mc = MotionCorrect(file_path,
                       offset_mov,
                       dview=None,
                       max_shifts=max_shifts,
                       niter_rig=niter_rig,
                       splits_rig=splits_rig,
                       strides=strides,
                       overlaps=overlaps,
                       splits_els=splits_els,
                       upsample_factor_grid=upsample_factor_grid,
                       max_deviation_rigid=max_deviation_rigid,
                       shifts_opencv=shifts_opencv,
                       nonneg_movie=nonneg_movie)

    mc.motion_correct_rigid(save_movie=True)
    # load motion corrected movie
    m_rig = cm.load(mc.fname_tot_rig)
    m_rig = m_rig.astype(np.int16)
    save_name = os.path.splitext(file_path)[0] + '_corrected.tif'
    tf.imsave(os.path.join(folder_path, save_name), m_rig)
    tf.imsave(os.path.join(folder_path, 'corrected_mean_projection.tif'),
              np.mean(m_rig, axis=0).astype(np.float32))
    tf.imsave(os.path.join(folder_path, 'corrected_max_projection.tif'),
              np.max(m_rig, axis=0).astype(np.float32))

    offset_f = h5py.File(os.path.join(folder_path, 'correction_offsets.hdf5'))
    offsets = mc.shifts_rig
    offsets = np.array([np.array(o) for o in offsets]).astype(np.float32)
    offset_dset = offset_f.create_dataset(name='file_0000', data=offsets)
    offset_dset.attrs['format'] = 'height, width'
    offset_dset.attrs['path'] = file_path

    os.remove(mc.fname_tot_rig[0])
Example #17
0
def main():
    pass  # For compatibility between running under Spyder and the CLI

    #%% First setup some parameters

    # dataset dependent parameters
    display_images = False  # Set this to true to show movies and plots
    fname = ['Sue_2x_3000_40_-46.tif']  # filename to be processed
    fr = 30  # imaging rate in frames per second
    decay_time = 0.4  # length of a typical transient in seconds

    # motion correction parameters
    niter_rig = 1  # number of iterations for rigid motion correction
    max_shifts = (6, 6)  # maximum allow rigid shift
    # for parallelization split the movies in  num_splits chuncks across time
    splits_rig = 56
    # start a new patch for pw-rigid motion correction every x pixels
    strides = (48, 48)
    # overlap between pathes (size of patch strides+overlaps)
    overlaps = (24, 24)
    # for parallelization split the movies in  num_splits chuncks across time
    splits_els = 56
    upsample_factor_grid = 4  # upsample factor to avoid smearing when merging patches
    # maximum deviation allowed for patch with respect to rigid shifts
    max_deviation_rigid = 3

    # parameters for source extraction and deconvolution
    p = 1  # order of the autoregressive system
    gnb = 2  # number of global background components
    merge_thresh = 0.8  # merging threshold, max correlation allowed
    # half-size of the patches in pixels. e.g., if rf=25, patches are 50x50
    rf = 15
    stride_cnmf = 6  # amount of overlap between the patches in pixels
    K = 4  # number of components per patch
    gSig = [4, 4]  # expected half size of neurons
    # initialization method (if analyzing dendritic data using 'sparse_nmf')
    init_method = 'greedy_roi'
    is_dendrites = False  # flag for analyzing dendritic data
    # sparsity penalty for dendritic data analysis through sparse NMF
    alpha_snmf = None

    # parameters for component evaluation
    min_SNR = 2.5  # signal to noise ratio for accepting a component
    rval_thr = 0.8  # space correlation threshold for accepting a component
    cnn_thr = 0.8  # threshold for CNN based classifier

    #%% download the dataset if it's not present in your folder
    if fname[0] in ['Sue_2x_3000_40_-46.tif', 'demoMovie.tif']:
        fname = [download_demo(fname[0])]

#%% play the movie
# playing the movie using opencv. It requires loading the movie in memory. To
# close the video press q

    m_orig = cm.load_movie_chain(fname[:1])
    downsample_ratio = 0.2
    offset_mov = -np.min(m_orig[:100])
    moviehandle = m_orig.resize(1, 1, downsample_ratio)
    if display_images:
        moviehandle.play(gain=10, offset=offset_mov, fr=30, magnification=2)

#%% start a cluster for parallel processing
    c, dview, n_processes = cm.cluster.setup_cluster(backend='local',
                                                     n_processes=None,
                                                     single_thread=False)

    #%%% MOTION CORRECTION
    # first we create a motion correction object with the parameters specified
    min_mov = cm.load(fname[0], subindices=range(200)).min()
    # this will be subtracted from the movie to make it non-negative

    mc = MotionCorrect(fname[0],
                       min_mov,
                       dview=dview,
                       max_shifts=max_shifts,
                       niter_rig=niter_rig,
                       splits_rig=splits_rig,
                       strides=strides,
                       overlaps=overlaps,
                       splits_els=splits_els,
                       upsample_factor_grid=upsample_factor_grid,
                       max_deviation_rigid=max_deviation_rigid,
                       shifts_opencv=True,
                       nonneg_movie=True)
    # note that the file is not loaded in memory

    #%% Run piecewise-rigid motion correction using NoRMCorre
    mc.motion_correct_pwrigid(save_movie=True)
    m_els = cm.load(mc.fname_tot_els)
    bord_px_els = np.ceil(
        np.maximum(np.max(np.abs(mc.x_shifts_els)),
                   np.max(np.abs(mc.y_shifts_els)))).astype(np.int)
    # maximum shift to be used for trimming against NaNs
    #%% compare with original movie
    moviehandle = cm.concatenate([
        m_orig.resize(1, 1, downsample_ratio) + offset_mov,
        m_els.resize(1, 1, downsample_ratio)
    ],
                                 axis=2)
    display_images = False
    if display_images:
        moviehandle.play(fr=60, q_max=99.5, magnification=2,
                         offset=0)  # press q to exit

#%% MEMORY MAPPING
# memory map the file in order 'C'
    fnames = mc.fname_tot_els  # name of the pw-rigidly corrected file.
    border_to_0 = bord_px_els  # number of pixels to exclude
    fname_new = cm.save_memmap(fnames,
                               base_name='memmap_',
                               order='C',
                               border_to_0=bord_px_els)  # exclude borders

    # now load the file
    Yr, dims, T = cm.load_memmap(fname_new)
    d1, d2 = dims
    images = np.reshape(Yr.T, [T] + list(dims), order='F')
    # load frames in python format (T x X x Y)

    #%% restart cluster to clean up memory
    cm.stop_server(dview=dview)
    c, dview, n_processes = cm.cluster.setup_cluster(backend='local',
                                                     n_processes=None,
                                                     single_thread=False)

    #%% RUN CNMF ON PATCHES

    # First extract spatial and temporal components on patches and combine them
    # for this step deconvolution is turned off (p=0)
    t1 = time.time()

    cnm = cnmf.CNMF(n_processes=1,
                    k=K,
                    gSig=gSig,
                    merge_thresh=merge_thresh,
                    p=0,
                    dview=dview,
                    rf=rf,
                    stride=stride_cnmf,
                    memory_fact=1,
                    method_init=init_method,
                    alpha_snmf=alpha_snmf,
                    only_init_patch=False,
                    gnb=gnb,
                    border_pix=bord_px_els)
    cnm = cnm.fit(images)

    #%% plot contours of found components
    Cn = cm.local_correlations(images.transpose(1, 2, 0))
    Cn[np.isnan(Cn)] = 0
    plt.figure()
    crd = plot_contours(cnm.A, Cn, thr=0.9)
    plt.title('Contour plots of found components')

    #%% COMPONENT EVALUATION
    # the components are evaluated in three ways:
    #   a) the shape of each component must be correlated with the data
    #   b) a minimum peak SNR is required over the length of a transient
    #   c) each shape passes a CNN based classifier

    idx_components, idx_components_bad, SNR_comp, r_values, cnn_preds = \
        estimate_components_quality_auto(images, cnm.A, cnm.C, cnm.b, cnm.f,
                                         cnm.YrA, fr, decay_time, gSig, dims,
                                         dview=dview, min_SNR=min_SNR,
                                         r_values_min=rval_thr, use_cnn=False,
                                         thresh_cnn_min=cnn_thr)

    #%% PLOT COMPONENTS

    if display_images:
        plt.figure()
        plt.subplot(121)
        crd_good = cm.utils.visualization.plot_contours(cnm.A[:,
                                                              idx_components],
                                                        Cn,
                                                        thr=.8,
                                                        vmax=0.75)
        plt.title('Contour plots of accepted components')
        plt.subplot(122)
        crd_bad = cm.utils.visualization.plot_contours(
            cnm.A[:, idx_components_bad], Cn, thr=.8, vmax=0.75)
        plt.title('Contour plots of rejected components')

#%% VIEW TRACES (accepted and rejected)

    if display_images:
        view_patches_bar(Yr,
                         cnm.A.tocsc()[:, idx_components],
                         cnm.C[idx_components],
                         cnm.b,
                         cnm.f,
                         dims[0],
                         dims[1],
                         YrA=cnm.YrA[idx_components],
                         img=Cn)

        view_patches_bar(Yr,
                         cnm.A.tocsc()[:, idx_components_bad],
                         cnm.C[idx_components_bad],
                         cnm.b,
                         cnm.f,
                         dims[0],
                         dims[1],
                         YrA=cnm.YrA[idx_components_bad],
                         img=Cn)

#%% RE-RUN seeded CNMF on accepted patches to refine and perform deconvolution
    A_in, C_in, b_in, f_in = cnm.A[:, idx_components], cnm.C[
        idx_components], cnm.b, cnm.f
    cnm2 = cnmf.CNMF(n_processes=1,
                     k=A_in.shape[-1],
                     gSig=gSig,
                     p=p,
                     dview=dview,
                     merge_thresh=merge_thresh,
                     Ain=A_in,
                     Cin=C_in,
                     b_in=b_in,
                     f_in=f_in,
                     rf=None,
                     stride=None,
                     gnb=gnb,
                     method_deconvolution='oasis',
                     check_nan=True)

    cnm2 = cnm2.fit(images)

    #%% Extract DF/F values

    F_dff = detrend_df_f(cnm2.A,
                         cnm2.b,
                         cnm2.C,
                         cnm2.f,
                         YrA=cnm2.YrA,
                         quantileMin=8,
                         frames_window=250)

    #%% Show final traces
    cnm2.view_patches(Yr, dims=dims, img=Cn)

    #%% STOP CLUSTER and clean up log files
    cm.stop_server(dview=dview)
    log_files = glob.glob('*_LOG_*')
    for log_file in log_files:
        os.remove(log_file)

#%% reconstruct denoised movie
    denoised = cm.movie(cnm2.A.dot(cnm2.C) + cnm2.b.dot(cnm2.f)).reshape(
        dims + (-1, ), order='F').transpose([2, 0, 1])

    #%% play along side original data
    moviehandle = cm.concatenate([
        m_els.resize(1, 1, downsample_ratio),
        denoised.resize(1, 1, downsample_ratio)
    ],
                                 axis=2)
    if display_images:
        moviehandle.play(fr=60, gain=15, magnification=2,
                         offset=0)  # press q to exit
Example #18
0
def main():
    pass  # For compatibility between running under Spyder and the CLI

    # %% start the cluster
    try:
        cm.stop_server()  # stop it if it was running
    except ():
        pass

    c, dview, n_processes = cm.cluster.setup_cluster(
        backend='local',
        n_processes=
        24,  # number of process to use, if you go out of memory try to reduce this one
        single_thread=False)

    # %% First setup some parameters for motion correction
    # dataset dependent parameters
    fnames = ['data_endoscope.tif']  # filename to be processed
    fnames = [download_demo(fnames[0])]  # download file if not already present
    filename_reorder = fnames
    fr = 10  # movie frame rate
    decay_time = 0.4  # length of a typical transient in seconds

    # motion correction parameters
    motion_correct = True  # flag for motion correction
    pw_rigid = False  # flag for pw-rigid motion correction

    gSig_filt = (3, 3)  # size of filter, in general gSig (see below),
    #                      change this one if algorithm does not work
    max_shifts = (5, 5)  # maximum allowed rigid shift
    strides = (
        48, 48
    )  # start a new patch for pw-rigid motion correction every x pixels
    overlaps = (24, 24
                )  # overlap between pathes (size of patch strides+overlaps)
    # maximum deviation allowed for patch with respect to rigid shifts
    max_deviation_rigid = 3
    border_nan = 'copy'

    mc_dict = {
        'fnames': fnames,
        'fr': fr,
        'decay_time': decay_time,
        'pw_rigid': pw_rigid,
        'max_shifts': max_shifts,
        'gSig_filt': gSig_filt,
        'strides': strides,
        'overlaps': overlaps,
        'max_deviation_rigid': max_deviation_rigid,
        'border_nan': border_nan
    }

    opts = params.CNMFParams(params_dict=mc_dict)

    # %% MOTION CORRECTION
    #  The pw_rigid flag set above, determines where to use rigid or pw-rigid
    #  motion correction
    if motion_correct:
        # do motion correction rigid
        mc = MotionCorrect(fnames, dview=dview, **opts.get_group('motion'))
        mc.motion_correct(save_movie=True)
        fname_mc = mc.fname_tot_els if pw_rigid else mc.fname_tot_rig
        if pw_rigid:
            bord_px = np.ceil(
                np.maximum(np.max(np.abs(mc.x_shifts_els)),
                           np.max(np.abs(mc.y_shifts_els)))).astype(np.int)
        else:
            bord_px = np.ceil(np.max(np.abs(mc.shifts_rig))).astype(np.int)
            plt.subplot(1, 2, 1)
            plt.imshow(mc.total_template_rig)  # % plot template
            plt.subplot(1, 2, 2)
            plt.plot(mc.shifts_rig)  # % plot rigid shifts
            plt.legend(['x shifts', 'y shifts'])
            plt.xlabel('frames')
            plt.ylabel('pixels')

        bord_px = 0 if border_nan == 'copy' else bord_px
        fname_new = cm.save_memmap(fname_mc,
                                   base_name='memmap_',
                                   order='C',
                                   border_to_0=bord_px)
    else:  # if no motion correction just memory map the file
        fname_new = cm.save_memmap(filename_reorder,
                                   base_name='memmap_',
                                   order='C',
                                   border_to_0=0,
                                   dview=dview)

    # load memory mappable file
    Yr, dims, T = cm.load_memmap(fname_new)
    images = Yr.T.reshape((T, ) + dims, order='F')

    # %% Parameters for source extraction and deconvolution (CNMF-E algorithm)

    p = 1  # order of the autoregressive system
    K = None  # upper bound on number of components per patch, in general None for 1p data
    gSig = (
        3, 3
    )  # gaussian width of a 2D gaussian kernel, which approximates a neuron
    gSiz = (13, 13)  # average diameter of a neuron, in general 4*gSig+1
    Ain = None  # possibility to seed with predetermined binary masks
    merge_thr = .7  # merging threshold, max correlation allowed
    rf = 40  # half-size of the patches in pixels. e.g., if rf=40, patches are 80x80
    stride_cnmf = 20  # amount of overlap between the patches in pixels
    #                     (keep it at least large as gSiz, i.e 4 times the neuron size gSig)
    tsub = 2  # downsampling factor in time for initialization,
    #                     increase if you have memory problems
    ssub = 1  # downsampling factor in space for initialization,
    #                     increase if you have memory problems
    #                     you can pass them here as boolean vectors
    low_rank_background = None  # None leaves background of each patch intact,
    #                     True performs global low-rank approximation if gnb>0
    gnb = 0  # number of background components (rank) if positive,
    #                     else exact ring model with following settings
    #                         gnb= 0: Return background as b and W
    #                         gnb=-1: Return full rank background B
    #                         gnb<-1: Don't return background
    nb_patch = 0  # number of background components (rank) per patch if gnb>0,
    #                     else it is set automatically
    min_corr = .8  # min peak value from correlation image
    min_pnr = 10  # min peak to noise ration from PNR image
    ssub_B = 2  # additional downsampling factor in space for background
    ring_size_factor = 1.4  # radius of ring is gSiz*ring_size_factor

    opts.change_params(
        params_dict={
            'dims': dims,
            'method_init': 'corr_pnr',  # use this for 1 photon
            'K': K,
            'gSig': gSig,
            'gSiz': gSiz,
            'merge_thr': merge_thr,
            'p': p,
            'tsub': tsub,
            'ssub': ssub,
            'rf': rf,
            'stride': stride_cnmf,
            'only_init': True,  # set it to True to run CNMF-E
            'nb': gnb,
            'nb_patch': nb_patch,
            'method_deconvolution': 'oasis',  # could use 'cvxpy' alternatively
            'low_rank_background': low_rank_background,
            'update_background_components':
            True,  # sometimes setting to False improve the results
            'min_corr': min_corr,
            'min_pnr': min_pnr,
            'normalize_init': False,  # just leave as is
            'center_psf': True,  # leave as is for 1 photon
            'ssub_B': ssub_B,
            'ring_size_factor': ring_size_factor,
            'del_duplicates':
            True,  # whether to remove duplicates from initialization
            'border_pix': bord_px
        })  # number of pixels to not consider in the borders)

    # %% compute some summary images (correlation and peak to noise)
    # change swap dim if output looks weird, it is a problem with tiffile
    cn_filter, pnr = cm.summary_images.correlation_pnr(images[::1],
                                                       gSig=gSig[0],
                                                       swap_dim=False)
    # if your images file is too long this computation will take unnecessarily
    # long time and consume a lot of memory. Consider changing images[::1] to
    # images[::5] or something similar to compute on a subset of the data

    # inspect the summary images and set the parameters
    inspect_correlation_pnr(cn_filter, pnr)
    # print parameters set above, modify them if necessary based on summary images
    print(min_corr)  # min correlation of peak (from correlation image)
    print(min_pnr)  # min peak to noise ratio

    # %% RUN CNMF ON PATCHES
    cnm = cnmf.CNMF(n_processes=n_processes, dview=dview, Ain=Ain, params=opts)
    cnm.fit(images)

    # %% ALTERNATE WAY TO RUN THE PIPELINE AT ONCE
    #   you can also perform the motion correction plus cnmf fitting steps
    #   simultaneously after defining your parameters object using
    #    cnm1 = cnmf.CNMF(n_processes, params=opts, dview=dview)
    #    cnm1.fit_file(motion_correct=True)

    # %% DISCARD LOW QUALITY COMPONENTS
    min_SNR = 2.5  # adaptive way to set threshold on the transient size
    r_values_min = 0.85  # threshold on space consistency (if you lower more components
    #                        will be accepted, potentially with worst quality)
    cnm.params.set('quality', {
        'min_SNR': min_SNR,
        'rval_thr': r_values_min,
        'use_cnn': False
    })
    cnm.estimates.evaluate_components(images, cnm.params, dview=dview)

    print(' ***** ')
    print('Number of total components: ', len(cnm.estimates.C))
    print('Number of accepted components: ', len(cnm.estimates.idx_components))

    # %% PLOT COMPONENTS
    cnm.dims = dims
    display_images = True  # Set to true to show movies and images
    if display_images:
        cnm.estimates.plot_contours(img=cn_filter,
                                    idx=cnm.estimates.idx_components)
        cnm.estimates.view_components(images, idx=cnm.estimates.idx_components)

# %% MOVIES
    display_images = False  # Set to true to show movies and images
    if display_images:
        # fully reconstructed movie
        cnm.estimates.play_movie(images,
                                 q_max=99.5,
                                 magnification=2,
                                 include_bck=True,
                                 gain_res=10,
                                 bpx=bord_px)
        # movie without background
        cnm.estimates.play_movie(images,
                                 q_max=99.9,
                                 magnification=2,
                                 include_bck=False,
                                 gain_res=4,
                                 bpx=bord_px)

# %% STOP SERVER
    cm.stop_server(dview=dview)
Example #19
0
# movie must be mostly positive for this to work
# TODO : document
# setting timer to see how the changement in functions make the code react on a same computer.

min_mov = cm.load(fname[0], subindices=range(400)).min()
mc_list = []
new_templ = None
print('Start motion correction loop')
for each_file in fname:
    print(each_file)
    # TODO: needinfo how the classes works
    mc = MotionCorrect(each_file,
                       min_mov,
                       dview=dview,
                       max_shifts=max_shifts,
                       niter_rig=niter_rig,
                       splits_rig=splits_rig,
                       num_splits_to_process_rig=num_splits_to_process_rig,
                       shifts_opencv=True,
                       nonneg_movie=True)

    mc.motion_correct_rigid(save_movie=True, template=new_templ)
    print("DONE")
    new_templ = mc.total_template_rig
    m_rig = cm.load(mc.fname_tot_rig)
    bord_px_rig = np.ceil(np.max(mc.shifts_rig)).astype(np.int)

    # TODO : needinfo
    if isscreen:
        pl.imshow(new_templ, cmap='gray')
        pl.pause(.1)
Example #20
0
def run_caiman_pipeline(movie, fr, fnames, savedir, usematlabroi):
    #%%

    cpu_num = 7
    cpu_num_spikepursuit = 2
    #gsig_filt_micron = (4, 4)
    #max_shifts_micron = (6,6)
    #strides_micron = (60,60)
    #overlaps_micron = (30, 30)

    gsig_filt_micron = (4, 4)
    max_shifts_micron = (6, 6)
    strides_micron = (30, 30)
    overlaps_micron = (15, 15)

    max_deviation_rigid_micron = 4

    pixel_size = movie['movie_pixel_size']

    ROIs = None  # Region of interests
    index = None  # index of neurons
    weights = None  # reuse spatial weights by
    # opts.change_params(params_dict={'weights':vpy.estimates['weights']})
    # motion correction parameters
    pw_rigid = False  # flag for pw-rigid motion correction
    gSig_filt = tuple(
        np.asarray(np.round(np.asarray(gsig_filt_micron) / float(pixel_size)),
                   int))  # size of filter, in general gSig (see below),
    # change this one if algorithm does not work
    max_shifts = tuple(
        np.asarray(np.round(np.asarray(max_shifts_micron) / float(pixel_size)),
                   int))
    strides = tuple(
        np.asarray(np.round(np.asarray(strides_micron) / float(pixel_size)),
                   int)
    )  # start a new patch for pw-rigid motion correction every x pixels
    overlaps = tuple(
        np.asarray(np.round(np.asarray(overlaps_micron) / float(pixel_size)),
                   int)
    )  # start a new patch for pw-rigid motion correction every x pixels
    # overlap between pathes (size of patch strides+overlaps)
    max_deviation_rigid = int(
        round(max_deviation_rigid_micron / pixel_size)
    )  # maximum deviation allowed for patch with respect to rigid shifts
    border_nan = 'copy'
    opts_dict = {
        'fnames': fnames,
        'fr': fr,
        'index': index,
        'ROIs': ROIs,
        'weights': weights,
        'pw_rigid': pw_rigid,
        'max_shifts': max_shifts,
        'gSig_filt': gSig_filt,
        'strides': strides,
        'overlaps': overlaps,
        'max_deviation_rigid': max_deviation_rigid,
        'border_nan': border_nan
    }
    opts = volparams(params_dict=opts_dict)

    # %% play the movie (optional)
    # playing the movie using opencv. It requires loading the movie in memory.
    # To close the video press q
    display_images = False

    if display_images:
        m_orig = cm.load(fnames)
        ds_ratio = 0.2
        moviehandle = m_orig.resize(1, 1, ds_ratio)
        moviehandle.play(q_max=99.5, fr=60, magnification=2)

    # %% start a cluster for parallel processing

    c, dview, n_processes = cm.cluster.setup_cluster(backend='local',
                                                     n_processes=cpu_num,
                                                     single_thread=False)

    # % MOTION CORRECTION
    # Create a motion correction object with the specified parameters
    mcrig = MotionCorrect(fnames, dview=dview, **opts.get_group('motion'))
    # Run piecewise rigid motion correction
    #%
    mcrig.motion_correct(save_movie=True)
    dview.terminate()

    # % MOTION CORRECTION2
    opts.change_params({'pw_rigid': True})
    c, dview, n_processes = cm.cluster.setup_cluster(backend='local',
                                                     n_processes=cpu_num,
                                                     single_thread=False)
    # Create a motion correction object with the specified parameters
    mc = MotionCorrect(mcrig.mmap_file,
                       dview=dview,
                       **opts.get_group('motion'))
    # Run piecewise rigid motion correction
    mc.motion_correct(save_movie=True)
    dview.terminate()

    # %% motion correction compared with original movie
    display_images = False
    if display_images:
        m_orig = cm.load(fnames)
        m_rig = cm.load(mcrig.mmap_file)
        m_pwrig = cm.load(mc.mmap_file)
        ds_ratio = 0.2
        moviehandle = cm.concatenate([
            m_orig.resize(1, 1, ds_ratio) - mc.min_mov * mc.nonneg_movie,
            m_rig.resize(1, 1, ds_ratio),
            m_pwrig.resize(1, 1, ds_ratio)
        ],
                                     axis=2)
        moviehandle.play(fr=60, q_max=99.5, magnification=2)  # press q to exit
        # % movie subtracted from the mean
        m_orig2 = (m_orig - np.mean(m_orig, axis=0))
        m_rig2 = (m_rig - np.mean(m_rig, axis=0))
        m_pwrig2 = (m_pwrig - np.mean(m_pwrig, axis=0))
        moviehandle1 = cm.concatenate([
            m_orig2.resize(1, 1, ds_ratio),
            m_rig2.resize(1, 1, ds_ratio),
            m_pwrig2.resize(1, 1, ds_ratio)
        ],
                                      axis=2)
        moviehandle1.play(fr=60, q_max=99.5, magnification=2)

    # %% Memory Mapping
    c, dview, n_processes = cm.cluster.setup_cluster(backend='local',
                                                     n_processes=cpu_num,
                                                     single_thread=False)
    border_to_0 = 0 if mc.border_nan == 'copy' else mc.border_to_0
    fname_new = cm.save_memmap_join(mc.mmap_file,
                                    base_name='memmap_',
                                    add_to_mov=border_to_0,
                                    dview=dview,
                                    n_chunks=10)
    dview.terminate()

    # %% change fnames to the new motion corrected one
    opts.change_params(params_dict={'fnames': fname_new})

    # %% SEGMENTATION

    roidir = savedir[:savedir.find('VolPy')] + 'Spikepursuit' + savedir[
        savedir.find('VolPy') + len('Volpy'):]
    try:
        files = os.listdir(roidir)
    except:
        files = []
    if usematlabroi and 'ROIs.mat' in files:
        ROIs = loadmat(os.path.join(roidir, 'ROIs.mat'))['ROIs']
        if len(np.shape(ROIs)) == 3:
            ROIs = np.moveaxis(np.asarray(ROIs, bool), 2, 0)
        else:
            ROIs = np.asarray([ROIs])
        all_rois = ROIs
        opts.change_params(
            params_dict={
                'ROIs': ROIs,
                'index': list(range(ROIs.shape[0])),
                'method': 'SpikePursuit'
            })

    else:
        #%
        print('WTF')
        # Create mean and correlation image
        use_maskrcnn = True  # set to True to predict the ROIs using the mask R-CNN
        if not use_maskrcnn:  # use manual annotations
            with h5py.File(path_ROIs, 'r') as fl:
                ROIs = fl['mov'][()]  # load ROIs
            opts.change_params(
                params_dict={
                    'ROIs': ROIs,
                    'index': list(range(ROIs.shape[0])),
                    'method': 'SpikePursuit'
                })
        else:
            try:
                m = cm.load(mc.mmap_file[0], subindices=slice(0, 20000))
            except:
                m = cm.load(
                    '/home/rozmar/Data/Voltage_imaging/Voltage_rig_1P/rozsam/20200120/40x_1xtube_10A_7_000_rig__d1_128_d2_512_d3_1_order_F_frames_2273_._els__d1_128_d2_512_d3_1_order_F_frames_2273_.mmap',
                    subindices=slice(0, 20000))
            m.fr = fr
            img = m.mean(axis=0)
            img = (img - np.mean(img)) / np.std(img)
            m1 = m.computeDFF(secsWindow=1, in_place=True)[0]
            m = m - m1
            Cn = m.local_correlations(swap_dim=False, eight_neighbours=True)
            img_corr = (Cn - np.mean(Cn)) / np.std(Cn)
            summary_image = np.stack([img, img, img_corr],
                                     axis=2).astype(np.float32)
            del m
            del m1

            # %
            # Mask R-CNN
            config = neurons.NeuronsConfig()

            class InferenceConfig(config.__class__):
                # Run detection on one image at a time
                GPU_COUNT = 1
                IMAGES_PER_GPU = 1
                DETECTION_MIN_CONFIDENCE = 0.7
                IMAGE_RESIZE_MODE = "pad64"
                IMAGE_MAX_DIM = 512
                RPN_NMS_THRESHOLD = 0.7
                POST_NMS_ROIS_INFERENCE = 1000

            config = InferenceConfig()
            config.display()
            model_dir = os.path.join(caiman_datadir(), 'model')
            DEVICE = "/cpu:0"  # /cpu:0 or /gpu:0
            with tf.device(DEVICE):
                model = modellib.MaskRCNN(mode="inference",
                                          model_dir=model_dir,
                                          config=config)
            weights_path = download_model('mask_rcnn')
            model.load_weights(weights_path, by_name=True)
            results = model.detect([summary_image], verbose=1)
            r = results[0]
            ROIs_mrcnn = r['masks'].transpose([2, 0, 1])

            # %% visualize the result
            display_result = False
            if display_result:
                _, ax = plt.subplots(1, 1, figsize=(16, 16))
                visualize.display_instances(summary_image,
                                            r['rois'],
                                            r['masks'],
                                            r['class_ids'], ['BG', 'neurons'],
                                            r['scores'],
                                            ax=ax,
                                            title="Predictions")
        # %% set rois
            opts.change_params(
                params_dict={
                    'ROIs': ROIs_mrcnn,
                    'index': list(range(ROIs_mrcnn.shape[0])),
                    'method': 'SpikePursuit'
                })
            #all_rois = ROIs_mrcnn

    # %% Trace Denoising and Spike Extraction

    c, dview, n_processes = cm.cluster.setup_cluster(
        backend='local',
        n_processes=cpu_num_spikepursuit,
        single_thread=False,
        maxtasksperchild=1)
    #dview=None
    vpy = VOLPY(n_processes=n_processes, dview=dview, params=opts)
    vpy.fit(n_processes=n_processes, dview=dview)

    #%%
    print('saving parameters')
    parameters = dict()
    parameters['motion'] = opts.motion
    parameters['data'] = opts.data
    parameters['volspike'] = opts.volspike
    with open(os.path.join(savedir, 'parameters.pickle'), 'wb') as outfile:
        pickle.dump(parameters, outfile)
    #%%
    volspikedata = dict()
    volspikedata['estimates'] = vpy.estimates
    volspikedata['params'] = vpy.params.data
    with open(os.path.join(savedir, 'spikepursuit.pickle'), 'wb') as outfile:
        pickle.dump(volspikedata, outfile)
    #%%

    for mcidx, mc_now in enumerate([mcrig, mc]):
        motioncorr = dict()
        motioncorr['fname'] = mc_now.fname
        motioncorr['fname_tot_rig'] = mc_now.fname_tot_rig
        motioncorr['mmap_file'] = mc_now.mmap_file
        motioncorr['min_mov'] = mc_now.min_mov
        motioncorr['shifts_rig'] = mc_now.shifts_rig
        motioncorr['shifts_opencv'] = mc_now.shifts_opencv
        motioncorr['niter_rig'] = mc_now.niter_rig
        motioncorr['min_mov'] = mc_now.min_mov
        motioncorr['templates_rig'] = mc_now.templates_rig
        motioncorr['total_template_rig'] = mc_now.total_template_rig
        try:
            motioncorr['x_shifts_els'] = mc_now.x_shifts_els
            motioncorr['y_shifts_els'] = mc_now.y_shifts_els
        except:
            pass
        with open(
                os.path.join(savedir, 'motion_corr_' + str(mcidx) + '.pickle'),
                'wb') as outfile:
            pickle.dump(motioncorr, outfile)
    #%% saving stuff
    print('moving files')
    for mmap_file in mcrig.mmap_file:
        fname = pathlib.Path(mmap_file).name
        os.remove(mmap_file)
        #shutil.move(mmap_file, os.path.join(savedir,fname))
    for mmap_file in mc.mmap_file:
        fname = pathlib.Path(mmap_file).name
        os.remove(mmap_file)
        #shutil.move(mmap_file, os.path.join(savedir,fname))

    fname = pathlib.Path(fname_new).name
    shutil.move(fname_new, os.path.join(savedir, fname))
    #print('waiting')
    #time.sleep(1000)
    # %% some visualization
    plotstuff = False
    if plotstuff:
        print(np.where(vpy.estimates['passedLocalityTest'])
              [0])  # neurons that pass locality test
        n = 0

        # Processed signal and spikes of neurons
        plt.figure()
        plt.plot(vpy.estimates['trace'][n])
        plt.plot(vpy.estimates['spikeTimes'][n],
                 np.max(vpy.estimates['trace'][n]) *
                 np.ones(vpy.estimates['spikeTimes'][n].shape),
                 color='g',
                 marker='o',
                 fillstyle='none',
                 linestyle='none')
        plt.title('signal and spike times')
        plt.show()
        # Location of neurons by Mask R-CNN or manual annotation
        plt.figure()
        if use_maskrcnn:
            plt.imshow(ROIs_mrcnn[n])
        else:
            plt.imshow(ROIs[n])
        mv = cm.load(fname_new)
        plt.imshow(mv.mean(axis=0), alpha=0.5)

        # Spatial filter created by algorithm
        plt.figure()
        plt.imshow(vpy.estimates['spatialFilter'][n])
        plt.colorbar()
        plt.title('spatial filter')
        plt.show()

    # %% STOP CLUSTER and clean up log files

    cm.stop_server(dview=dview)
    log_files = glob.glob('*_LOG_*')
    for log_file in log_files:
        os.remove(log_file)
def run_alignmnet(selected_rows, parameters, dview):
    '''
    This is the main function for the alignment step. It applies methods
    from the CaImAn package used originally in motion correction
    to do alignment.

    Args:
        df: pd.DataFrame
            A dataframe containing the analysis states you want to have aligned.
        parameters: dict
            The alignment parameters.
        dview: object
            The dview object

    Returns:
        df: pd.DataFrame
            A dataframe containing the aligned analysis states.
    '''

    # Sort the dataframe correctly
    df = selected_rows.copy()
    df = df.sort_values(by=paths.multi_index_structure)

    # Determine the mouse and session of the dataset
    index = df.iloc[0].name
    mouse, session, *r = index
    # alignment_v = index[len(paths.data_structure) + step_index]
    alignment_v = len(df)
    alignment_index = (mouse, session, alignment_v)

    # Determine the output .mmap file name
    file_name = f'mouse_{mouse}_session_{session}_v{alignment_v}'
    output_mmap_file_path = os.environ['DATA_DIR'] + f'data/interim/alignment/main/{file_name}.mmap'

    try:
        df.reset_index()[['session','trial', 'is_rest']].set_index(['session','trial', 'is_rest'], verify_integrity=True)
    except ValueError:
        logging.error('You passed multiple of the same trial in the dataframe df')
        return df

    output = {
        'meta': {
            'analysis': {
                'analyst': os.environ['ANALYST'],
                'date': datetime.datetime.today().strftime("%m-%d-%Y"),
                'time': datetime.datetime.today().strftime("%H:%M:%S")
            },
            'duration': {}
        }
    }

    # Get necessary parameters
    motion_correction_parameters_list = []
    motion_correction_output_list = []
    input_mmap_file_list = []
    trial_index_list = []
    x_ = []
    _x = []
    y_ = []
    _y = []
    for idx, row in df.iterrows():
        motion_correction_parameters_list.append(eval(row.loc['motion_correction_parameters']))
        motion_correction_output = eval(row.loc['motion_correction_output'])
        motion_correction_output_list.append(motion_correction_output)
        input_mmap_file_list.append(motion_correction_output['main'])
        trial_index_list.append(db.get_trial_name(idx[2], idx[3]))
        [x1,x2,y1,y2] = motion_correction_output['meta']['cropping_points']
        x_.append(x1)
        _x.append(x2)
        y_.append(y1)
        _y.append(y2)

    new_x1 = max(x_)
    new_x2 = max(_x)
    new_y1 = max(y_)
    new_y2 = max(_y)
    m_list = []
    for i in range(len(input_mmap_file_list)):
        m = cm.load(input_mmap_file_list[i])
        motion_correction_output = eval(df.iloc[i].loc['motion_correction_output'])
        [x1,x2,y1,y2] = motion_correction_output['meta']['cropping_points']
        m = m.crop(new_x1 - x1, new_x2 - x2, new_y1 - y1, new_y2 - y2, 0, 0)
        m_list.append(m)

    # Concatenate them using the concat function
    m_concat = cm.concatenate(m_list, axis=0)
    data_dir = os.environ['DATA_DIR'] + 'data/interim/alignment/main/'
    file_name = db.create_file_name(step_index, index)
    fname= m_concat.save(data_dir + file_name + '.mmap', order='C')

    #meta_pkl_dict['pw_rigid']['cropping_points'] = [x_, _x, y_, _y]
    #output['meta']['cropping_points'] = [x_, _x, y_, _y]
    # Save the movie
    #fname_tot_els  = m_els.save(data_dir + 'main/' + file_name + '_els' + '.mmap',  order='C')
    #logging.info(f'{index} Cropped and saved rigid movie as {fname_tot_els}')

    # MOTION CORRECTING EACH INDIVIDUAL MOVIE WITH RESPECT TO A TEMPLATE MADE OF THE FIRST MOVIE
    logging.info(f'{alignment_index} Performing motion correction on all movies with respect to a template made of \
    the first movie.')
    t0 = datetime.datetime.today()

    # Create a template of the first movie
    template_index = trial_index_list.index(parameters['make_template_from_trial'])
    m0 = cm.load(input_mmap_file_list[template_index ])
    [x1, x2, y1, y2] = motion_correction_output_list[template_index]['meta']['cropping_points']
    m0 = m0.crop(new_x1 - x1, new_x2 - x2, new_y1 - y1, new_y2 - y2, 0, 0)
    m0_filt = cm.movie(
        np.array([high_pass_filter_space(m_, parameters['gSig_filt']) for m_ in m0]))
    template0 = cm.motion_correction.bin_median(
        m0_filt.motion_correct(5, 5, template=None)[0])  # may be improved in the future

    # Setting the parameters
    opts = params.CNMFParams(params_dict=parameters)

    # Create a motion correction object
    mc = MotionCorrect(fname, dview=dview, **opts.get_group('motion'))

    # Perform non-rigid motion correction
    mc.motion_correct(template=template0, save_movie=True)

    # Cropping borders
    x_ = math.ceil(abs(np.array(mc.shifts_rig)[:, 1].max()) if np.array(mc.shifts_rig)[:, 1].max() > 0 else 0)
    _x = math.ceil(abs(np.array(mc.shifts_rig)[:, 1].min()) if np.array(mc.shifts_rig)[:, 1].min() < 0 else 0)
    y_ = math.ceil(abs(np.array(mc.shifts_rig)[:, 0].max()) if np.array(mc.shifts_rig)[:, 0].max() > 0 else 0)
    _y = math.ceil(abs(np.array(mc.shifts_rig)[:, 0].min()) if np.array(mc.shifts_rig)[:, 0].min() < 0 else 0)

    # Load the motion corrected movie into memory
    movie= cm.load(mc.fname_tot_rig[0])
    # Crop all movies to those border pixels
    movie.crop(x_, _x, y_, _y, 0, 0)
    output['meta']['cropping_points'] = [x_, _x, y_, _y]

    #save motion corrected and cropped movie
    output_mmap_file_path_tot = movie.save(data_dir + file_name  + '.mmap', order='C')
    logging.info(f'{index} Cropped and saved rigid movie as {output_mmap_file_path_tot}')
    # Save the path in teh output dictionary
    output['main'] = output_mmap_file_path_tot
    # Remove the remaining non-cropped movie
    os.remove(mc.fname_tot_rig[0])

    # Create a timeline and store it
    timeline = [[trial_index_list[0], 0]]
    timepoints = [0]
    for i in range(1, len(m_list)):
        m = m_list[i]
        timeline.append([trial_index_list[i], timeline[i - 1][1] + m.shape[0]])
        timepoints.append(timepoints[i-1]+ m.shape[0])
        timeline_pkl_file_path = os.environ['DATA_DIR'] + f'data/interim/alignment/meta/timeline/{file_name}.pkl'
        with open(timeline_pkl_file_path,'wb') as f:
            pickle.dump(timeline,f)
    output['meta']['timeline'] = timeline_pkl_file_path
    timepoints.append(movie.shape[0])

    dt = int((datetime.datetime.today() - t0).seconds / 60)  # timedelta in minutes
    output['meta']['duration']['concatenation'] = dt
    logging.info(f'{alignment_index} Performed concatenation. dt = {dt} min.')

    for idx, row in df.iterrows():
        df.loc[idx, 'alignment_output'] = str(output)
        df.loc[idx, 'alignment_parameters'] = str(parameters)

    ## modify all motion correction file to the aligned version
    data_dir = os.environ['DATA_DIR'] + 'data/interim/motion_correction/main/'
    for i in range(len(input_mmap_file_list)):
        row = df.iloc[i].copy()
        motion_correction_output_list.append(motion_correction_output)
        aligned_movie = movie[timepoints[i]:timepoints[i+1]]
        file_name = db.create_file_name(2, selected_rows.iloc[i].name)
        motion_correction_output_aligned = aligned_movie.save(data_dir + file_name + '_els' + '.mmap',  order='C')
        new_output= {'main' : motion_correction_output_aligned }
        new_dict = eval(row['motion_correction_output'])
        new_dict.update(new_output)
        row['motion_correction_output'] = str(new_dict)
        df = db.append_to_or_merge_with_states_df(df, row)

    #    # Delete the motion corrected movies
    #    for fname in mc.fname_tot_rig:
    #        os.remove(fname)

    return df
Example #22
0
    def _estimate(self, dataset):
        """

        Parameters
        ----------

        Returns
        -------
        displacements : array
            (2, num_frames*num_cycles)-array of integers giving the
            estimated displacement of each frame
        """
        ncpus = int(mp.cpu_count() / 4.0)
        if ncpus == 0:
            ncpus = 1
        verbose = self._params['verbose']
        if self._params['max_displacement'] is None:
            max_displacement = (1e15, 1e15)
        else:
            max_displacement = self._params['max_displacement']

        displacements = []
        if 'dview' in locals():
            dview.terminate()
        # c, dview, n_processes = cb.cluster.setup_cluster(
        #     backend='local', n_processes=ncpus, single_thread=False)
        dview = None
        num_iter = 3  # number of times the algorithm is run
        splits = ncpus * 2  # for parallelization split the movies in  num_splits chuncks across time
        shifts_opencv = True  # apply shifts fast way (but smoothing results)
        save_movie_rigid = False  # save the movies vs just get the template
        upsample_factor_grid = 4
        max_deviation_rigid = 3
        for sequence in dataset:
            t0 = time.time()
            num_frames = sequence.shape[0]
            num_planes = sequence.shape[1]
            num_channels = sequence.shape[4]
            strides = (int(sequence.shape[2] / 10.0),
                       int(sequence.shape[3] / 10.0))
            overlaps = (int(sequence.shape[2] / 20.0),
                        int(sequence.shape[3] / 20.0))
            if num_channels > 1:
                raise NotImplementedError("Error: only one colour channel \
                    can be used for DFT motion correction. Using channel 1.")

            # get results into a shape sima likes
            frame_shifts = np.zeros((num_frames, num_planes, 2))
            for plane_idx in range(num_planes):
                min_mov = np.min(sequence[:100, :, :, :, :])
                mc = MotionCorrect(self._params['savedir'],
                                   min_mov,
                                   dview=dview,
                                   max_shifts=max_displacement,
                                   niter_rig=num_iter,
                                   splits_rig=splits,
                                   strides=strides,
                                   overlaps=overlaps,
                                   splits_els=splits,
                                   upsample_factor_grid=upsample_factor_grid,
                                   max_deviation_rigid=max_deviation_rigid,
                                   shifts_opencv=shifts_opencv,
                                   nonneg_movie=True)
                sys.stdout.write("Applying motion correction... ")
                sys.stdout.flush()
                mc.motion_correct_rigid(save_movie=save_movie_rigid)
                sys.stdout.write("done\n")
                # fname_tot_rig, total_template_rig, templates_rig, shifts_rig = \
                #     cb.motion_correction.motion_correct_batch_rigid(
                #         self._params['savedir'], max_displacement, dview = dview, splits = splits,
                #         num_splits_to_process = num_splits_to_process, num_iter = num_iter,
                #         template = None, shifts_opencv = shifts_opencv,
                #         save_movie_rigid = save_movie_rigid)

                frame_shifts[:,
                             plane_idx] = mc.shifts_rig  # (mc.x_shifts_els, mc.y_shifts_els)# shifts_rig

            displacements.append(np.round(frame_shifts).astype(np.int))

            total_time = time.time() - t0
            if verbose:
                print('    Total time for plane ' + str(plane_idx + 1) + ': ' +
                      str(total_time) + ' s')

        cb.cluster.stop_server()
        return displacements
def main():
    pass  # For compatibility between running under Spyder and the CLI

    #%%
    """
    General parameters
    """
    play_movie = 1
    plot_extras = 1
    plot_extras_cell = 1
    compute_mc_metrics = 1

    #%% Select file(s) to be processed (download if not present)
    """
    Load file
    """

    #fnames = ['Sue_2x_3000_40_-46.tif']  # filename to be processed
    #if fnames[0] in ['Sue_2x_3000_40_-46.tif', 'demoMovie.tif']:
    #    fnames = [download_demo(fnames[0])]

    #fnames = ['/home/yuriy/Desktop/Data/rest1_5_9_19_cut.tif']

    #f_dir = 'C:\\Users\\rylab_dataPC\\Desktop\\Yuriy\\caiman_data\\short\\'
    f_dir = 'G:\\analysis\\190828-calcium_voltage\\soma_dendrites\\pCAG_jREGECO1a_ASAP3_anesth_001\\'
    f_name = 'Ch1'
    f_ext = 'tif'
    fnames = [f_dir + f_name + '.' + f_ext]

    #fnames = ['C:/Users/rylab_dataPC/Desktop/Yuriy/caiman_data/rest1_5_9_19_2_cut_ca.hdf5']

    #%% First setup some parameters for data and motion correction
    """
    Parameters
    """

    # dataset dependent parameters
    fr = 30  # imaging rate in frames per second
    decay_time = 1
    #0.4    # length of a typical transient in seconds
    dxy = (2., 2.)  # spatial resolution in x and y in (um per pixel)
    # note the lower than usual spatial resolution here
    max_shift_um = (12., 12.)  # maximum shift in um
    patch_motion_um = (100., 100.)  # patch size for non-rigid correction in um

    # motion correction parameters
    pw_rigid = True  # flag to select rigid vs pw_rigid motion correction
    # maximum allowed rigid shift in pixels
    #max_shifts = [int(a/b) for a, b in zip(max_shift_um, dxy)]
    max_shifts = [6, 6]
    # start a new patch for pw-rigid motion correction every x pixels
    #strides = tuple([int(a/b) for a, b in zip(patch_motion_um, dxy)])
    strides = [48, 48]
    # overlap between pathes (size of patch in pixels: strides+overlaps)
    overlaps = (24, 24)
    # maximum deviation allowed for patch with respect to rigid shifts
    max_deviation_rigid = 3

    mc_dict = {
        'fnames': fnames,
        'fr': fr,
        'decay_time': decay_time,
        'dxy': dxy,
        'pw_rigid': pw_rigid,
        'max_shifts': max_shifts,
        'strides': strides,
        'overlaps': overlaps,
        'max_deviation_rigid': max_deviation_rigid,
        'border_nan': 'copy'
    }

    opts = params.CNMFParams(params_dict=mc_dict)

    # %% play the movie (optional)
    # playing the movie using opencv. It requires loading the movie in memory.
    # To close the video press q

    if play_movie:
        m_orig = cm.load_movie_chain(fnames)
        ds_ratio = 0.2
        moviehandle = m_orig.resize(1, 1, ds_ratio)
        moviehandle.play(q_max=99.5, fr=60, magnification=2)

    # %% start a cluster for parallel processing
    c, dview, n_processes = cm.cluster.setup_cluster(backend='local',
                                                     n_processes=None,
                                                     single_thread=False)

    # %%% MOTION CORRECTION
    # first we create a motion correction object with the specified parameters
    mc = MotionCorrect(fnames, dview=dview, **opts.get_group('motion'))
    # note that the file is not loaded in memory

    # %% Run (piecewise-rigid motion) correction using NoRMCorre
    mc.motion_correct(save_movie=True)

    # type "mc."and press TAB to see all interesting associated variables and self. outputs
    # interesting outputs
    # saved file is mc.fname_tot_els / mc.fname_tot_rig
    # mc.x_shifts_els / mc.y_shifts_els: shifts in x/y per frame per patch
    # mc.coord_shifts_els: coordinates associated to patches with shifts
    # mc.total_template_els: updated template for pw
    # mc.total_template_rig: updated template for rigid
    # mc.templates_rig: templates for each iteration in rig

    #%% # compute metrics for the results (TAKES TIME!!)
    if compute_mc_metrics:
        # not finished
        bord_px_els = np.ceil(
            np.maximum(np.max(np.abs(mc.x_shifts_els)),
                       np.max(np.abs(mc.y_shifts_els)))).astype(np.int)

        final_size = np.subtract(
            mc.total_template_els.shape,
            2 * bord_px_els)  # remove pixels in the boundaries
        winsize = 100
        swap_dim = False
        resize_fact_flow = .2  # downsample for computing ROF

        tmpl_rig, correlations_orig, flows_orig, norms_orig, crispness_orig = cm.motion_correction.compute_metrics_motion_correction(
            fnames[0],
            final_size[0],
            final_size[1],
            swap_dim,
            winsize=winsize,
            play_flow=False,
            resize_fact_flow=resize_fact_flow)

        plt.figure()
        plt.plot(correlations_orig)

    # %% compare with original movie
    if play_movie:
        m_orig = cm.load_movie_chain(fnames)
        m_els = cm.load(mc.mmap_file)
        ds_ratio = 0.2
        moviehandle = cm.concatenate([
            m_orig.resize(1, 1, ds_ratio) - mc.min_mov * mc.nonneg_movie,
            m_els.resize(1, 1, ds_ratio)
        ],
                                     axis=2)
        moviehandle.play(fr=60, q_max=99.5, magnification=2)  # press q to exit
        del m_orig
        del m_els

    if plot_extras:
        # plot total template
        plt.figure()
        plt.imshow(mc.total_template_els)
        plt.title('Template after iteration')
        # plot x and y corrections
        plt.figure()
        plt.plot(mc.shifts_rig)
        plt.title('Rigid motion correction xy movement')
        plt.legend(['x shift', 'y shift'])
        plt.xlabel('frames')

    # %% MEMORY MAPPING
    border_to_0 = 0 if mc.border_nan is 'copy' else mc.border_to_0
    # you can include the boundaries of the FOV if you used the 'copy' option
    # during motion correction, although be careful about the components near
    # the boundaries

    # memory map the file in order 'C'
    fname_new = cm.save_memmap(mc.mmap_file,
                               base_name='memmap_',
                               order='C',
                               border_to_0=border_to_0)  # exclude borders

    # now load the file
    Yr, dims, T = cm.load_memmap(fname_new)
    images = np.reshape(Yr.T, [T] + list(dims), order='F')
    # load frames in python format (T x X x Y)

    # %% restart cluster to clean up memory
    cm.stop_server(dview=dview)
    c, dview, n_processes = cm.cluster.setup_cluster(backend='local',
                                                     n_processes=None,
                                                     single_thread=False)

    # %%  parameters for source extraction and deconvolution

    p = 2  # order of the autoregressive system
    gnb = 2  # number of global background components
    merge_thr = 0.85  # merging threshold, max correlation allowed
    rf = 15  # half-size of the patches in pixels. e.g., if rf=25, patches are 50x50
    stride_cnmf = 6  # amount of overlap between the patches in pixels
    K = 2  # number of components per patch
    gSig = [15, 15]  # expected half size of neurons in pixels
    # initialization method (if analyzing dendritic data using 'sparse_nmf')
    method_init = 'greedy_roi'
    ssub = 1  # spatial subsampling during initialization
    tsub = 1  # temporal subsampling during intialization

    # parameters for component evaluation
    opts_dict = {
        'fnames': fnames,
        'fr': fr,
        'nb': gnb,
        'rf': rf,
        'K': K,
        'gSig': gSig,
        'stride': stride_cnmf,
        'method_init': method_init,
        'rolling_sum': True,
        'merge_thr': merge_thr,
        'n_processes': n_processes,
        'only_init': True,
        'ssub': ssub,
        'tsub': tsub
    }

    opts.change_params(params_dict=opts_dict)
    # %% RUN CNMF ON PATCHES
    # First extract spatial and temporal components on patches and combine them
    # for this step deconvolution is turned off (p=0)

    opts.change_params({'p': 0})
    cnm = cnmf.CNMF(n_processes, params=opts, dview=dview)
    cnm = cnm.fit(images)

    if plot_extras_cell:
        num_cell_plot = 51
        plt.figure()
        plt.plot(cnm.estimates.C[num_cell_plot, :])
        plt.title('Temporal component')
        plt.legend(['Cell ' + str(num_cell_plot)])
        # plot component sptial profile A
        # first convert back to dense components
        plot_spat_A = cnm.estimates.A[:, num_cell_plot].toarray().reshape(
            list(dims))
        plt.figure()
        plt.imshow(plot_spat_A)
        plt.title('Spatial component cell ' + str(num_cell_plot))

    # %% ALTERNATE WAY TO RUN THE PIPELINE AT ONCE
    #   you can also perform the motion correction plus cnmf fitting steps
    #   simultaneously after defining your parameters object using
    #  cnm1 = cnmf.CNMF(n_processes, params=opts, dview=dview)
    #  cnm1.fit_file(motion_correct=True)

    # %% plot contours of found components
    Cn = cm.local_correlations(images, swap_dim=False)
    Cn[np.isnan(Cn)] = 0
    cnm.estimates.plot_contours(img=Cn)
    plt.title('Contour plots of found components')

    if plot_extras:
        plt.figure()
        plt.imshow(Cn)
        plt.title('Local correlations')

    # %% RE-RUN seeded CNMF on accepted patches to refine and perform deconvolution
    cnm.params.change_params({'p': p})
    cnm2 = cnm.refit(images, dview=dview)
    # %% COMPONENT EVALUATION
    # the components are evaluated in three ways:
    #   a) the shape of each component must be correlated with the data
    #   b) a minimum peak SNR is required over the length of a transient
    #   c) each shape passes a CNN based classifier
    min_SNR = 2  # signal to noise ratio for accepting a component
    rval_thr = 0.90  # space correlation threshold for accepting a component
    cnn_thr = 0.99  # threshold for CNN based classifier
    cnn_lowest = 0.1  # neurons with cnn probability lower than this value are rejected

    cnm2.params.set(
        'quality', {
            'decay_time': decay_time,
            'min_SNR': min_SNR,
            'rval_thr': rval_thr,
            'use_cnn': True,
            'min_cnn_thr': cnn_thr,
            'cnn_lowest': cnn_lowest
        })
    cnm2.estimates.evaluate_components(images, cnm2.params, dview=dview)

    # %% PLOT COMPONENTS
    cnm2.estimates.plot_contours(img=Cn, idx=cnm2.estimates.idx_components)
    plt.suptitle('Component selection: min_SNR=' + str(min_SNR) +
                 '; rval_thr=' + str(rval_thr) + '; cnn prob range=[' +
                 str(cnn_lowest) + ' ' + str(cnn_thr) + ']')

    # %% VIEW TRACES (accepted and rejected)

    if plot_extras:
        cnm2.estimates.view_components(images,
                                       img=Cn,
                                       idx=cnm2.estimates.idx_components)
        plt.suptitle('Accepted')
        cnm2.estimates.view_components(images,
                                       img=Cn,
                                       idx=cnm2.estimates.idx_components_bad)
        plt.suptitle('Rejected')

    #plt.figure();
    #plt.plot(cnm2.estimates.YrA[0,:]+cnm2.estimates.C[0,:])
    #
    #
    #
    #
    #plt.figure();
    #plt.plot(cnm2.estimates.R[0,:]-cnm2.estimates.YrA[0,:]);
    #plt.plot();
    #plt.show();
    #
    #
    #plt.figure();
    #plt.plot(cnm2.estimates.detrend_df_f[1,:])

    # these store the good and bad components, and next step sorts them
    # cnm2.estimates.idx_components
    # cnm2.estimates.idx_components_bad

    #%% update object with selected components
    #cnm2.estimates.select_components(use_object=True)
    #%% Extract DF/F values
    cnm2.estimates.detrend_df_f(quantileMin=8, frames_window=250)

    #%% Show final traces

    cnm2.estimates.view_components(img=Cn)
    plt.suptitle("Final results")

    #%% Save the mc data as in cmn struct as well

    ##
    #mc_out = dict(
    #            pw_rigid            = mc.pw_rigid,
    #            fname               = mc.fname,
    #            mmap_file           = mc.mmap_file,
    #            total_template_els  = mc.total_template_els,
    #            total_template_rig  = mc.total_template_rig,
    #            border_nan          = mc.border_nan,
    #            border_to_0         = mc.border_to_0,
    #            x_shifts_els        = mc.x_shifts_els,
    #            y_shifts_els        = mc.y_shifts_els,
    #            Cn                  = Cn
    #            )
    #
    #
    #deepdish.io.save(fnames[0] + '_mc_data.hdf5', mc_out)

    #%% reconstruct denoised movie (press q to exit)
    if play_movie:
        cnm2.estimates.play_movie(images,
                                  q_max=99.9,
                                  gain_res=2,
                                  magnification=2,
                                  bpx=border_to_0,
                                  include_bck=False)  # background not shown

    #%% STOP CLUSTER and clean up log files
    cm.stop_server(dview=dview)
    log_files = glob.glob('*_LOG_*')
    for log_file in log_files:
        os.remove(log_file)

    save_results = True
    if save_results:
        cnm2.save(fnames[0][:-4] + '_results.hdf5')
Example #24
0
def test_general():
    """  General Test of pipeline with comparison against ground truth
    A shorter version than the demo pipeline that calls comparison for the real test work



        Raises:
      ---------
        params_movie

        params_cnmf

        rig correction

        cnmf on patch

        cnmf full frame

        not able to read the file

        no groundtruth


    """
    #\bug
    #\warning

    global params_movie
    global params_diplay
    fname = params_movie['fname']
    niter_rig = params_movie['niter_rig']
    max_shifts = params_movie['max_shifts']
    splits_rig = params_movie['splits_rig']
    num_splits_to_process_rig = params_movie['num_splits_to_process_rig']

    cwd = os.getcwd()
    fname = download_demo(fname[0])
    m_orig = cm.load(fname)
    min_mov = m_orig[:400].min()
    comp = comparison.Comparison()
    comp.dims = np.shape(m_orig)[1:]

    ################ RIG CORRECTION #################
    t1 = time.time()
    mc = MotionCorrect(fname,
                       min_mov,
                       max_shifts=max_shifts,
                       niter_rig=niter_rig,
                       splits_rig=splits_rig,
                       num_splits_to_process_rig=num_splits_to_process_rig,
                       shifts_opencv=True,
                       nonneg_movie=True)
    mc.motion_correct_rigid(save_movie=True)
    m_rig = cm.load(mc.fname_tot_rig)
    bord_px_rig = np.ceil(np.max(mc.shifts_rig)).astype(np.int)
    comp.comparison['rig_shifts']['timer'] = time.time() - t1
    comp.comparison['rig_shifts']['ourdata'] = mc.shifts_rig
    ###########################################

    if 'max_shifts' not in params_movie:
        fnames = params_movie['fname']
        border_to_0 = 0
    else:  # elif not params_movie.has_key('overlaps'):
        fnames = mc.fname_tot_rig
        border_to_0 = bord_px_rig
        m_els = m_rig

    idx_xy = None
    add_to_movie = -np.nanmin(m_els) + 1  # movie must be positive
    remove_init = 0
    downsample_factor = 1
    base_name = fname[0].split('/')[-1][:-4]
    name_new = cm.save_memmap_each(fnames,
                                   base_name=base_name,
                                   resize_fact=(1, 1, downsample_factor),
                                   remove_init=remove_init,
                                   idx_xy=idx_xy,
                                   add_to_movie=add_to_movie,
                                   border_to_0=border_to_0)
    name_new.sort()

    if len(name_new) > 1:
        fname_new = cm.save_memmap_join(name_new,
                                        base_name='Yr',
                                        n_chunks=params_movie['n_chunks'],
                                        dview=None)
    else:
        logging.warning('One file only, not saving!')
        fname_new = name_new[0]

    Yr, dims, T = cm.load_memmap(fname_new)
    images = np.reshape(Yr.T, [T] + list(dims), order='F')
    Y = np.reshape(Yr, dims + (T, ), order='F')

    if np.min(images) < 0:
        # TODO: should do this in an automatic fashion with a while loop at the 367 line
        raise Exception('Movie too negative, add_to_movie should be larger')
    if np.sum(np.isnan(images)) > 0:
        # TODO: same here
        raise Exception(
            'Movie contains nan! You did not remove enough borders')

    Cn = cm.local_correlations(Y)
    Cn[np.isnan(Cn)] = 0
    p = params_movie['p']
    merge_thresh = params_movie['merge_thresh']
    rf = params_movie['rf']
    stride_cnmf = params_movie['stride_cnmf']
    K = params_movie['K']
    init_method = params_movie['init_method']
    gSig = params_movie['gSig']
    alpha_snmf = params_movie['alpha_snmf']

    if params_movie['is_dendrites'] == True:
        if params_movie['init_method'] is not 'sparse_nmf':
            raise Exception('dendritic requires sparse_nmf')
        if params_movie['alpha_snmf'] is None:
            raise Exception('need to set a value for alpha_snmf')

################ CNMF PART PATCH #################
    t1 = time.time()
    cnm = cnmf.CNMF(n_processes=1,
                    k=K,
                    gSig=gSig,
                    merge_thresh=params_movie['merge_thresh'],
                    p=params_movie['p'],
                    dview=None,
                    rf=rf,
                    stride=stride_cnmf,
                    memory_fact=params_movie['memory_fact'],
                    method_init=init_method,
                    alpha_snmf=alpha_snmf,
                    only_init_patch=params_movie['only_init_patch'],
                    gnb=params_movie['gnb'],
                    method_deconvolution='oasis')
    comp.cnmpatch = copy.copy(cnm)
    comp.cnmpatch.estimates = None
    cnm = cnm.fit(images)
    A_tot = cnm.estimates.A
    C_tot = cnm.estimates.C
    YrA_tot = cnm.estimates.YrA
    b_tot = cnm.estimates.b
    f_tot = cnm.estimates.f
    # DISCARDING
    logging.info(('Number of components:' + str(A_tot.shape[-1])))
    final_frate = params_movie['final_frate']
    # threshold on space consistency
    r_values_min = params_movie['r_values_min_patch']
    # threshold on time variability
    fitness_min = params_movie['fitness_delta_min_patch']
    fitness_delta_min = params_movie['fitness_delta_min_patch']
    Npeaks = params_movie['Npeaks']
    traces = C_tot + YrA_tot
    idx_components, idx_components_bad = estimate_components_quality(
        traces,
        Y,
        A_tot,
        C_tot,
        b_tot,
        f_tot,
        final_frate=final_frate,
        Npeaks=Npeaks,
        r_values_min=r_values_min,
        fitness_min=fitness_min,
        fitness_delta_min=fitness_delta_min)
    #######
    A_tot = A_tot.tocsc()[:, idx_components]
    C_tot = C_tot[idx_components]
    comp.comparison['cnmf_on_patch']['timer'] = time.time() - t1
    comp.comparison['cnmf_on_patch']['ourdata'] = [A_tot.copy(), C_tot.copy()]
    #################### ########################

    ################ CNMF PART FULL #################
    t1 = time.time()
    cnm = cnmf.CNMF(n_processes=1,
                    k=A_tot.shape,
                    gSig=gSig,
                    merge_thresh=merge_thresh,
                    p=p,
                    Ain=A_tot,
                    Cin=C_tot,
                    f_in=f_tot,
                    rf=None,
                    stride=None,
                    method_deconvolution='oasis')
    cnm = cnm.fit(images)
    # DISCARDING
    A, C, b, f, YrA, sn = cnm.estimates.A, cnm.estimates.C, cnm.estimates.b, cnm.estimates.f, cnm.estimates.YrA, cnm.estimates.sn
    final_frate = params_movie['final_frate']
    # threshold on space consistency
    r_values_min = params_movie['r_values_min_full']
    # threshold on time variability
    fitness_min = params_movie['fitness_delta_min_full']
    fitness_delta_min = params_movie['fitness_delta_min_full']
    Npeaks = params_movie['Npeaks']
    traces = C + YrA
    idx_components, idx_components_bad, fitness_raw, fitness_delta, r_values = estimate_components_quality(
        traces,
        Y,
        A,
        C,
        b,
        f,
        final_frate=final_frate,
        Npeaks=Npeaks,
        r_values_min=r_values_min,
        fitness_min=fitness_min,
        fitness_delta_min=fitness_delta_min,
        return_all=True)
    ##########
    A_tot_full = A_tot.tocsc()[:, idx_components]
    C_tot_full = C_tot[idx_components]
    comp.comparison['cnmf_full_frame']['timer'] = time.time() - t1
    comp.comparison['cnmf_full_frame']['ourdata'] = [
        A_tot_full.copy(), C_tot_full.copy()
    ]
    #################### ########################
    comp.save_with_compare(istruth=False, params=params_movie, Cn=Cn)
    log_files = glob.glob('*_LOG_*')
    try:
        for log_file in log_files:
            os.remove(log_file)
    except:
        logging.warning('Cannot remove log files')
############ assertions ##################
    pb = False
    if (comp.information['differences']['params_movie']):
        logging.error(
            "you need to set the same movie parameters than the ground truth to have a real comparison (use the comp.see() function to explore it)"
        )
        pb = True
    if (comp.information['differences']['params_cnm']):
        logging.warning(
            "you need to set the same cnmf parameters than the ground truth to have a real comparison (use the comp.see() function to explore it)"
        )
        # pb = True
    if (comp.information['diff']['rig']['isdifferent']):
        logging.error("the rigid shifts are different from the groundtruth ")
        pb = True
    if (comp.information['diff']['cnmpatch']['isdifferent']):
        logging.error(
            "the cnmf on patch produces different results than the groundtruth "
        )
        pb = True
    if (comp.information['diff']['cnmfull']['isdifferent']):
        logging.error(
            "the cnmf full frame produces different  results than the groundtruth "
        )
        pb = True

    assert (not pb)
Example #25
0
def main():
    pass  # For compatibility between running under Spyder and the CLI

#%% Select file(s) to be processed (download if not present)
    fnames = ['Sue_2x_3000_40_-46.tif']  # filename to be processed
    if fnames[0] in ['Sue_2x_3000_40_-46.tif', 'demoMovie.tif']:
        fnames = [download_demo(fnames[0])]

#%% First setup some parameters for data and motion correction

    # dataset dependent parameters
    fr = 30             # imaging rate in frames per second
    decay_time = 0.4    # length of a typical transient in seconds
    dxy = (2., 2.)      # spatial resolution in x and y in (um per pixel)
    # note the lower than usual spatial resolution here
    max_shift_um = (12., 12.)       # maximum shift in um
    patch_motion_um = (100., 100.)  # patch size for non-rigid correction in um

    # motion correction parameters
    pw_rigid = True       # flag to select rigid vs pw_rigid motion correction
    # maximum allowed rigid shift in pixels
    max_shifts = [int(a/b) for a, b in zip(max_shift_um, dxy)]
    # start a new patch for pw-rigid motion correction every x pixels
    strides = tuple([int(a/b) for a, b in zip(patch_motion_um, dxy)])
    # overlap between pathes (size of patch in pixels: strides+overlaps)
    overlaps = (24, 24)
    # maximum deviation allowed for patch with respect to rigid shifts
    max_deviation_rigid = 3

    mc_dict = {
        'fnames': fnames,
        'fr': fr,
        'decay_time': decay_time,
        'dxy': dxy,
        'pw_rigid': pw_rigid,
        'max_shifts': max_shifts,
        'strides': strides,
        'overlaps': overlaps,
        'max_deviation_rigid': max_deviation_rigid,
        'border_nan': 'copy'
    }

    opts = params.CNMFParams(params_dict=mc_dict)

# %% play the movie (optional)
    # playing the movie using opencv. It requires loading the movie in memory.
    # To close the video press q
    display_images = True

    if display_images:
        m_orig = cm.load_movie_chain(fnames)
        ds_ratio = 0.2
        moviehandle = m_orig.resize(1, 1, ds_ratio)
        moviehandle.play(q_max=99.5, fr=60, magnification=2)

# %% start a cluster for parallel processing
    c, dview, n_processes = cm.cluster.setup_cluster(
        backend='local', n_processes=None, single_thread=False)

# %%% MOTION CORRECTION
    # first we create a motion correction object with the specified parameters
    mc = MotionCorrect(fnames, dview=dview, **opts.get_group('motion'))
    # note that the file is not loaded in memory

# %% Run (piecewise-rigid motion) correction using NoRMCorre
    mc.motion_correct(save_movie=True)

# %% compare with original movie
    if display_images:
        m_orig = cm.load_movie_chain(fnames)
        m_els = cm.load(mc.mmap_file)
        ds_ratio = 0.2
        moviehandle = cm.concatenate([m_orig.resize(1, 1, ds_ratio) - mc.min_mov*mc.nonneg_movie,
                                      m_els.resize(1, 1, ds_ratio)], axis=2)
        moviehandle.play(fr=60, q_max=99.5, magnification=2)  # press q to exit

# %% MEMORY MAPPING
    border_to_0 = 0 if mc.border_nan is 'copy' else mc.border_to_0
    # you can include the boundaries of the FOV if you used the 'copy' option
    # during motion correction, although be careful about the components near
    # the boundaries

    # memory map the file in order 'C'
    fname_new = cm.save_memmap(mc.mmap_file, base_name='memmap_', order='C',
                               border_to_0=border_to_0)  # exclude borders

    # now load the file
    Yr, dims, T = cm.load_memmap(fname_new)
    images = np.reshape(Yr.T, [T] + list(dims), order='F')
    # load frames in python format (T x X x Y)

# %% restart cluster to clean up memory
    cm.stop_server(dview=dview)
    c, dview, n_processes = cm.cluster.setup_cluster(
        backend='local', n_processes=None, single_thread=False)

# %%  parameters for source extraction and deconvolution
    p = 1                    # order of the autoregressive system
    gnb = 2                  # number of global background components
    merge_thr = 0.85         # merging threshold, max correlation allowed
    rf = 15
    # half-size of the patches in pixels. e.g., if rf=25, patches are 50x50
    stride_cnmf = 6          # amount of overlap between the patches in pixels
    K = 4                    # number of components per patch
    gSig = [4, 4]            # expected half size of neurons in pixels
    # initialization method (if analyzing dendritic data using 'sparse_nmf')
    method_init = 'greedy_roi'
    ssub = 2                     # spatial subsampling during initialization
    tsub = 2                     # temporal subsampling during intialization

    # parameters for component evaluation
    opts_dict = {'fnames': fnames,
                 'p': p,
                 'fr': fr,
                 'nb': gnb,
                 'rf': rf,
                 'K': K,
                 'gSig': gSig,
                 'stride': stride_cnmf,
                 'method_init': method_init,
                 'rolling_sum': True,
                 'merge_thr': merge_thr,
                 'n_processes': n_processes,
                 'only_init': True,
                 'ssub': ssub,
                 'tsub': tsub}

    opts.change_params(params_dict=opts_dict);
# %% RUN CNMF ON PATCHES
    # First extract spatial and temporal components on patches and combine them
    # for this step deconvolution is turned off (p=0). If you want to have
    # deconvolution within each patch change params.patch['p_patch'] to a
    # nonzero value

    #opts.change_params({'p': 0})
    cnm = cnmf.CNMF(n_processes, params=opts, dview=dview)
    cnm = cnm.fit(images)

# %% ALTERNATE WAY TO RUN THE PIPELINE AT ONCE
    #   you can also perform the motion correction plus cnmf fitting steps
    #   simultaneously after defining your parameters object using
    #  cnm1 = cnmf.CNMF(n_processes, params=opts, dview=dview)
    #  cnm1.fit_file(motion_correct=True)

# %% plot contours of found components
    Cns = local_correlations_movie_offline(mc.mmap_file[0],
                                           remove_baseline=True, window=1000, stride=1000,
                                           winSize_baseline=100, quantil_min_baseline=10,
                                           dview=dview)
    Cn = Cns.max(axis=0)
    Cn[np.isnan(Cn)] = 0
    cnm.estimates.plot_contours(img=Cn)
    plt.title('Contour plots of found components')
#%% save results
    cnm.estimates.Cn = Cn
    cnm.save(fname_new[:-5]+'_init.hdf5')

# %% RE-RUN seeded CNMF on accepted patches to refine and perform deconvolution
    cnm2 = cnm.refit(images, dview=dview)
    # %% COMPONENT EVALUATION
    # the components are evaluated in three ways:
    #   a) the shape of each component must be correlated with the data
    #   b) a minimum peak SNR is required over the length of a transient
    #   c) each shape passes a CNN based classifier
    min_SNR = 2  # signal to noise ratio for accepting a component
    rval_thr = 0.85  # space correlation threshold for accepting a component
    cnn_thr = 0.99  # threshold for CNN based classifier
    cnn_lowest = 0.1 # neurons with cnn probability lower than this value are rejected

    cnm2.params.set('quality', {'decay_time': decay_time,
                               'min_SNR': min_SNR,
                               'rval_thr': rval_thr,
                               'use_cnn': True,
                               'min_cnn_thr': cnn_thr,
                               'cnn_lowest': cnn_lowest})
    cnm2.estimates.evaluate_components(images, cnm2.params, dview=dview)
    # %% PLOT COMPONENTS
    cnm2.estimates.plot_contours(img=Cn, idx=cnm2.estimates.idx_components)

    # %% VIEW TRACES (accepted and rejected)

    if display_images:
        cnm2.estimates.view_components(images, img=Cn,
                                      idx=cnm2.estimates.idx_components)
        cnm2.estimates.view_components(images, img=Cn,
                                      idx=cnm2.estimates.idx_components_bad)
    #%% update object with selected components
    cnm2.estimates.select_components(use_object=True)
    #%% Extract DF/F values
    cnm2.estimates.detrend_df_f(quantileMin=8, frames_window=250)

    #%% Show final traces
    cnm2.estimates.view_components(img=Cn)
    #%%
    cnm2.estimates.Cn = Cn
    cnm2.save(cnm2.mmap_file[:-4] + 'hdf5')
    #%% reconstruct denoised movie (press q to exit)
    if display_images:
        cnm2.estimates.play_movie(images, q_max=99.9, gain_res=2,
                                  magnification=2,
                                  bpx=border_to_0,
                                  include_bck=False)  # background not shown

    #%% STOP CLUSTER and clean up log files
    cm.stop_server(dview=dview)
    log_files = glob.glob('*_LOG_*')
    for log_file in log_files:
        os.remove(log_file)
# %% INITIALIZING
t1 = time.time()
# movie must be mostly positive for this to work
# TODO : document
# setting timer to see how the changement in functions make the code react on a same computer.

min_mov = cm.load(fname[0], subindices=range(400)).min()
mc_list = []
new_templ = None
for each_file in fname:
    # TODO: needinfo how the classes works
    mc = MotionCorrect(each_file, min_mov,
                       dview=dview, max_shifts=max_shifts, niter_rig=niter_rig, splits_rig=splits_rig,
                       num_splits_to_process_rig=num_splits_to_process_rig,
                       strides=strides, overlaps=overlaps, splits_els=splits_els,
                       num_splits_to_process_els=num_splits_to_process_els,
                       upsample_factor_grid=upsample_factor_grid, max_deviation_rigid=max_deviation_rigid,
                       shifts_opencv=True, nonneg_movie=True)
    mc.motion_correct_rigid(save_movie=True, template=new_templ)
    new_templ = mc.total_template_rig
    m_rig = cm.load(mc.fname_tot_rig)
    bord_px_rig = np.ceil(np.max(mc.shifts_rig)).astype(np.int)

    # TODO : needinfo
    pl.imshow(new_templ, cmap='gray')
    pl.pause(.1)
    mc_list.append(mc)
# we are going to keep this part because it helps the user understand what we need.
# needhelp why it is not the same as in the notebooks ?
# TODO: show screenshot 2,3
Example #27
0
def correct_single_movie(data_folder, identifier, dview):

    #=======================================setup parameters==============================================
    # number of iterations for rigid motion correction
    niter_rig = 5

    # maximum allowed rigid shift in pixels (view the movie to get a sense of motion)
    max_shifts = (30, 30)

    # for parallelization split the movies in  num_splits chuncks across time
    # if none all the splits are processed and the movie is saved
    splits_rig = 56

    # intervals at which patches are laid out for motion correction
    # num_splits_to_process_rig = None

    # create a new patch every x pixels for pw-rigid correction
    strides = (48, 48)

    # overlap between pathes (size of patch strides+overlaps)
    overlaps = (24, 24)

    # for parallelization split the movies in  num_splits chuncks across time
    splits_els = 56

    # num_splits_to_process_els = [28, None]

    # upsample factor to avoid smearing when merging patches
    upsample_factor_grid = 4

    # maximum deviation allowed for patch with respect to rigid shifts
    max_deviation_rigid = 3

    # if True, apply shifts fast way (but smoothing results) by using opencv
    shifts_opencv = True

    # if True, make the SAVED movie and template mostly nonnegative by removing min_mov from movie
    nonneg_movie = False
    # =======================================setup parameters==============================================


    fname = [f for f in os.listdir(data_folder) if f[-4:] == '.tif' and identifier in f]

    if len(fname) == 0:
        print('\ndid not find movie file in directory: {}.'.format(data_folder))
        print('Do nothing.')
        return
    elif len(fname) > 1:
        fname.sort()
        print('\n')
        print('\n'.join(fname))
        warnings.warn('more than one movie file in directory: {}. skip ...'.format(data_folder))
        return
    else:
        fname = fname[0]
        print('\ncorrecting {} in directory {}.'.format(fname, data_folder))

        # m_orig = cm.load(os.path.join(data_folder, fname))
        # offset_mov = np.min(m_orig)  # if the data has very negative values compute an offset value

        offset_mov = 0.

        # create a motion correction object# creat
        mc = MotionCorrect(os.path.join(data_folder, fname), offset_mov,
                           dview=dview, max_shifts=max_shifts, niter_rig=niter_rig,
                           splits_rig=splits_rig, strides=strides, overlaps=overlaps,
                           splits_els=splits_els, upsample_factor_grid=upsample_factor_grid,
                           max_deviation_rigid=max_deviation_rigid,
                           shifts_opencv=shifts_opencv, nonneg_movie=nonneg_movie)

        mc.motion_correct_rigid(save_movie=True)
        # load motion corrected movie
        m_rig = cm.load(mc.fname_tot_rig)
        m_rig = m_rig.astype(np.int16)
        save_name = os.path.splitext(fname)[0] + '_corrected.tif'
        tf.imsave(os.path.join(data_folder, save_name), m_rig)
        tf.imsave(os.path.join(data_folder, 'corrected_mean_projection.tif'),
                  np.mean(m_rig, axis=0).astype(np.float32))
        tf.imsave(os.path.join(data_folder, 'corrected_max_projection.tif'),
                  np.max(m_rig, axis=0).astype(np.float32))

        offset_f = h5py.File(os.path.join(data_folder, 'correction_offsets.hdf5'))
        offsets = mc.shifts_rig
        offsets = np.array([np.array(o) for o in offsets]).astype(np.float32)
        offset_dset = offset_f.create_dataset(name='file_0000', data=offsets)
        offset_dset.attrs['format'] = 'height, width'
        offset_dset.attrs['path'] = os.path.join(data_folder, fname)

        os.remove(mc.fname_tot_rig[0])
Example #28
0
def run(
    file_path,
    n_cpus,
    motion_correct: bool = True,
    mc_settings: dict = {},
    job_name: str = "job",
    output_directory: str = "",
):
    mkl = os.environ.get("MKL_NUM_THREADS")
    blas = os.environ.get("OPENBLAS_NUM_THREADS")
    vec = os.environ.get("VECLIB_MAXIMUM_THREADS")
    print(f"MKL: {mkl}")
    print(f"blas: {blas}")
    print(f"vec: {vec}")

    # we import the pipeline upon running so they aren't required for all installs
    import caiman as cm
    from caiman.motion_correction import MotionCorrect
    from caiman.source_extraction.cnmf import params as params

    # print the directory caiman is imported from
    caiman_path = os.path.abspath(cm.__file__)
    print(f"caiman path: {caiman_path}")
    sys.stdout.flush()

    # setup the logger
    logger_file = os.path.join(output_directory, "caiman.log")
    logging.basicConfig(
        format=LOGGER_FORMAT,
        filename=logger_file,
        filemode="w",
        level=logging.DEBUG,
    )

    # if indices to perform mcorr are set, format them
    if "indices" in mc_settings:
        indices = mc_settings["indices"]

        indices_formatted = ()
        for axis_slice in indices:
            start = axis_slice[0]
            stop = axis_slice[1]
            if len(axis_slice) == 3:
                step = axis_slice[2]
            else:
                step = 1
            indices_formatted += (slice(start, stop, step), )
        mc_settings["indices"] = indices_formatted
    # load and update the pipeline settings
    mc_parameters = DEFAULT_MCORR_SETTINGS
    for k, v in mc_settings.items():
        mc_parameters[k] = v

    opts = params.CNMFParams(params_dict=mc_parameters)

    # get the filenames
    if os.path.isfile(file_path):
        print(file_path)
        fnames = [file_path]
    else:
        file_pattern = os.path.join(file_path, "*.tif*")
        fnames = sorted(glob.glob(file_pattern))
    print(fnames)
    opts.set("data", {"fnames": fnames})

    if n_cpus > 1:
        print("starting server")
        # start the server
        n_proc = np.max([(n_cpus - 1), 1])
        c, dview, n_processes = cm.cluster.setup_cluster(backend="local",
                                                         n_processes=n_proc,
                                                         single_thread=False)
        sleep(30)
    else:
        print("multiprocessing disabled")
        dview = None
        n_processes = 1
    print(n_processes)
    print("starting motion correction")
    sys.stdout.flush()

    mc = MotionCorrect(fnames, dview=dview, **opts.get_group("motion"))
    mc.motion_correct(save_movie=True)
    pw_rigid = mc_parameters["pw_rigid"]
    fname_mc = mc.fname_tot_els if pw_rigid else mc.fname_tot_rig
    if pw_rigid:
        bord_px = np.ceil(
            np.maximum(np.max(np.abs(mc.x_shifts_els)),
                       np.max(np.abs(mc.y_shifts_els)))).astype(np.int)
    else:
        bord_px = np.ceil(np.max(np.abs(mc.shifts_rig))).astype(np.int)

    border_nan = mc_parameters["border_nan"]
    bord_px = 0 if border_nan == "copy" else bord_px
    _ = cm.save_memmap(fname_mc,
                       base_name="memmap_",
                       order="C",
                       border_to_0=bord_px)

    # if motion correction was performed, save the file
    # we save as hdf5 for better reading performance
    # downstream
    if motion_correct:
        print("saving motion corrected file")
        results_filebase = os.path.join(output_directory, job_name)
        mcorr_fname = results_filebase + "_mcorr.hdf5"
        dataset_name = opts.data["var_name_hdf5"]
        # fnames = opts.data["fnames"]
        # memmap_files = []
        # for f in fnames:
        #     if isinstance(f, bytes):
        #         f = f.decode()
        #     base_file = os.path.splitext(f)[0]
        #     if pw_rigid:
        #         memmap_pattern = base_file + "*_els_*"
        #     else:
        #         memmap_pattern = base_file + "*_rig_*"
        #     memmap_files += sorted(glob.glob(memmap_pattern))

        if pw_rigid:
            memmap_files = mc.fname_tot_els
        else:
            memmap_files = mc.fname_tot_rig

        # get the frame shape
        mov = cm.load(memmap_files[0])
        frame_shape = mov.shape[-2::]

        write_hdf5_movie(
            movie_name=mcorr_fname,
            memmap_files=memmap_files,
            frame_shape=frame_shape,
            dataset_name=dataset_name,
            compression="gzip",
        )

    # save the parameters in the same dir as the results
    final_params = opts.to_dict()
    params_file = os.path.join(output_directory, "all_mcorr_parameters.pkl")
    with open(params_file, "wb") as fp:
        pickle.dump(final_params, fp)

    # deleting mcorr unused memmap files
    if pw_rigid:
        memmap_files = mc.fname_tot_els
    else:
        memmap_files = mc.fname_tot_rig
    print(f"deleting {memmap_files}")
    for f in memmap_files:
        os.remove(f)

    print("stopping server")
    cm.stop_server(dview=dview)
Example #29
0
    'fr': fr,
    'decay_time': decay_time,
    'pw_rigid': pw_rigid,
    'max_shifts': max_shifts,
    'gSig_filt': gSig_filt,
    'strides': strides,
    'overlaps': overlaps,
    'max_deviation_rigid': max_deviation_rigid,
    'border_nan': border_nan
}

opts = params.CNMFParams(params_dict=mc_dict)

if motion_correct:
    # do motion correction rigid
    mc = MotionCorrect(fnames, dview=dview, **opts.get_group('motion'))
    mc.motion_correct(save_movie=True)
    fname_mc = mc.fname_tot_els if pw_rigid else mc.fname_tot_rig
    if pw_rigid:
        bord_px = np.ceil(np.maximum(np.max(np.abs(mc.x_shifts_els)),
                                     np.max(np.abs(mc.y_shifts_els)))).astype(np.int)
    else:
        bord_px = np.ceil(np.max(np.abs(mc.shifts_rig))).astype(np.int)
        plt.subplot(1, 2, 1); plt.imshow(mc.total_template_rig)  # % plot template
        plt.subplot(1, 2, 2); plt.plot(mc.shifts_rig)  # % plot rigid shifts
        plt.legend(['x shifts', 'y shifts'])
        plt.xlabel('frames')
        plt.ylabel('pixels');plt.savefig(newpath + r'/' + "shift.pdf",edgecolor='w',format='pdf',transparent=True)

    bord_px = 0 if border_nan is 'copy' else bord_px
    fname_new = cm.save_memmap(fname_mc, base_name='memmap_', order='C',
def main():
    pass  # For compatibility between running under Spyder and the CLI

    # %%  Load demo movie and ROIs
    fnames = download_demo('demo_voltage_imaging.hdf5', 'volpy')  # file path to movie file (will download if not present)
    path_ROIs = download_demo('demo_voltage_imaging_ROIs.hdf5', 'volpy')  # file path to ROIs file (will download if not present)

    # %% Setup some parameters for data and motion correction
    # dataset parameters
    fr = 400                                        # sample rate of the movie
    ROIs = None                                     # Region of interests
    index = None                                    # index of neurons
    weights = None                                  # reuse spatial weights by 
                                                    # opts.change_params(params_dict={'weights':vpy.estimates['weights']})
    # motion correction parameters
    pw_rigid = False                                # flag for pw-rigid motion correction
    gSig_filt = (3, 3)                              # size of filter, in general gSig (see below),
                                                    # change this one if algorithm does not work
    max_shifts = (5, 5)                             # maximum allowed rigid shift
    strides = (48, 48)                              # start a new patch for pw-rigid motion correction every x pixels
    overlaps = (24, 24)                             # overlap between pathes (size of patch strides+overlaps)
    max_deviation_rigid = 3                         # maximum deviation allowed for patch with respect to rigid shifts
    border_nan = 'copy'

    opts_dict = {
        'fnames': fnames,
        'fr': fr,
        'index': index,
        'ROIs': ROIs,
        'weights': weights,
        'pw_rigid': pw_rigid,
        'max_shifts': max_shifts,
        'gSig_filt': gSig_filt,
        'strides': strides,
        'overlaps': overlaps,
        'max_deviation_rigid': max_deviation_rigid,
        'border_nan': border_nan
    }

    opts = volparams(params_dict=opts_dict)

    # %% play the movie (optional)
    # playing the movie using opencv. It requires loading the movie in memory.
    # To close the video press q
    display_images = False

    if display_images:
        m_orig = cm.load(fnames)
        ds_ratio = 0.2
        moviehandle = m_orig.resize(1, 1, ds_ratio)
        moviehandle.play(q_max=99.5, fr=60, magnification=2)

    # %% start a cluster for parallel processing

    c, dview, n_processes = cm.cluster.setup_cluster(
        backend='local', n_processes=None, single_thread=False)

    # %%% MOTION CORRECTION
    # Create a motion correction object with the specified parameters
    mc = MotionCorrect(fnames, dview=dview, **opts.get_group('motion'))
    # Run piecewise rigid motion correction
    mc.motion_correct(save_movie=True)
    dview.terminate()

    # %% motion correction compared with original movie
    display_images = False

    if display_images:
        m_orig = cm.load(fnames)
        m_rig = cm.load(mc.mmap_file)
        ds_ratio = 0.2
        moviehandle = cm.concatenate([m_orig.resize(1, 1, ds_ratio) - mc.min_mov * mc.nonneg_movie,
                                      m_rig.resize(1, 1, ds_ratio)], axis=2)
        moviehandle.play(fr=60, q_max=99.5, magnification=2)  # press q to exit

    # % movie subtracted from the mean
        m_orig2 = (m_orig - np.mean(m_orig, axis=0))
        m_rig2 = (m_rig - np.mean(m_rig, axis=0))
        moviehandle1 = cm.concatenate([m_orig2.resize(1, 1, ds_ratio),
                                       m_rig2.resize(1, 1, ds_ratio)], axis=2)
        moviehandle1.play(fr=60, q_max=99.5, magnification=2)

   # %% Memory Mapping
    c, dview, n_processes = cm.cluster.setup_cluster(
        backend='local', n_processes=None, single_thread=False)

    border_to_0 = 0 if mc.border_nan == 'copy' else mc.border_to_0
    fname_new = cm.save_memmap_join(mc.mmap_file, base_name='memmap_',
                               add_to_mov=border_to_0, dview=dview, n_chunks=10)

    dview.terminate()

    # %% change fnames to the new motion corrected one
    opts.change_params(params_dict={'fnames': fname_new})

    # %% SEGMENTATION
    # Create mean and correlation image
    use_maskrcnn = True  # set to True to predict the ROIs using the mask R-CNN
    if not use_maskrcnn:                 # use manual annotations
        with h5py.File(path_ROIs, 'r') as fl:
            ROIs = fl['mov'][()]  # load ROIs
        opts.change_params(params_dict={'ROIs': ROIs,
                                        'index': list(range(ROIs.shape[0])),
                                        'method': 'SpikePursuit'})
    else:
        m = cm.load(mc.mmap_file[0], subindices=slice(0, 20000))
        m.fr = fr
        img = m.mean(axis=0)
        img = (img-np.mean(img))/np.std(img)
        m1 = m.computeDFF(secsWindow=1, in_place=True)[0]
        m = m - m1
        Cn = m.local_correlations(swap_dim=False, eight_neighbours=True)
        img_corr = (Cn-np.mean(Cn))/np.std(Cn)
        summary_image = np.stack([img, img, img_corr], axis=2).astype(np.float32)
        del m
        del m1

        # %%
        # Mask R-CNN
        config = neurons.NeuronsConfig()

        class InferenceConfig(config.__class__):
            # Run detection on one image at a time
            GPU_COUNT = 1
            IMAGES_PER_GPU = 1
            DETECTION_MIN_CONFIDENCE = 0.7
            IMAGE_RESIZE_MODE = "pad64"
            IMAGE_MAX_DIM = 512
            RPN_NMS_THRESHOLD = 0.7
            POST_NMS_ROIS_INFERENCE = 1000

        config = InferenceConfig()
        config.display()
        model_dir = os.path.join(caiman_datadir(), 'model')
        DEVICE = "/cpu:0"  # /cpu:0 or /gpu:0
        with tf.device(DEVICE):
            model = modellib.MaskRCNN(mode="inference", model_dir=model_dir,
                                      config=config)
        weights_path = download_model('mask_rcnn')
        model.load_weights(weights_path, by_name=True)
        results = model.detect([summary_image], verbose=1)
        r = results[0]
        ROIs_mrcnn = r['masks'].transpose([2, 0, 1])

    # %% visualize the result
        display_result = False

        if display_result:
            _, ax = plt.subplots(1,1, figsize=(16,16))
            visualize.display_instances(summary_image, r['rois'], r['masks'], r['class_ids'], 
                                    ['BG', 'neurons'], r['scores'], ax=ax,
                                    title="Predictions")

    # %% set rois
        opts.change_params(params_dict={'ROIs':ROIs_mrcnn,
                                        'index':list(range(ROIs_mrcnn.shape[0])),
                                        'method':'SpikePursuit'})

    # %% Trace Denoising and Spike Extraction
    c, dview, n_processes = cm.cluster.setup_cluster(
            backend='local', n_processes=None, single_thread=False, maxtasksperchild=1)
    vpy = VOLPY(n_processes=n_processes, dview=dview, params=opts)
    vpy.fit(n_processes=n_processes, dview=dview)

    # %% some visualization
    print(np.where(vpy.estimates['passedLocalityTest'])[0])    # neurons that pass locality test
    n = 0
    
    # Processed signal and spikes of neurons
    plt.figure()
    plt.plot(vpy.estimates['trace'][n])
    plt.plot(vpy.estimates['spikeTimes'][n],
             np.max(vpy.estimates['trace'][n]) * np.ones(vpy.estimates['spikeTimes'][n].shape),
             color='g', marker='o', fillstyle='none', linestyle='none')
    plt.title('signal and spike times')
    plt.show()

    # Location of neurons by Mask R-CNN or manual annotation
    plt.figure()
    if use_maskrcnn:
        plt.imshow(ROIs_mrcnn[n])
    else:
        plt.imshow(ROIs[n])
    mv = cm.load(fname_new)
    plt.imshow(mv.mean(axis=0),alpha=0.5)
    
    # Spatial filter created by algorithm
    plt.figure()
    plt.imshow(vpy.estimates['spatialFilter'][n])
    plt.colorbar()
    plt.title('spatial filter')
    plt.show()
    
    

    # %% STOP CLUSTER and clean up log files
    cm.stop_server(dview=dview)
    log_files = glob.glob('*_LOG_*')
    for log_file in log_files:
        os.remove(log_file)