def run_denoised_caiman_pipeline(movie, fr, loaddir, savedir, usematlabroi, onlyspikepursuit=False): #%% filenames = os.listdir(loaddir) for filename in filenames: # findinf mmap file if filename[-4:] == 'mmap': break filename = os.path.join(loaddir, filename) cpu_num = 4 cpu_num_spikepursuit = 2 #%% gsig_filt_micron = (4, 4) max_shifts_micron = (6, 6) strides_micron = (50, 50) overlaps_micron = (25, 25) 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': filename, '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) # %% start a cluster for parallel processing if onlyspikepursuit: finishedfilenames = os.listdir(savedir) for fnow in finishedfilenames: if fnow[:6] == 'memmap': opts.change_params( params_dict={'fnames': os.path.join(savedir, fnow)}) break #%% else: 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(filename, 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(filename) 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('denoised_volpy' )] + 'Spikepursuit' + savedir[ savedir.find('denoised_volpy') + len('denoised_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) #%% if not onlyspikepursuit: 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) 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 #os.remove(str(mcrig.fname)) 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)) #%% 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) #%% #%% #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_volpy(fnames, options=None, do_motion_correction=True, do_memory_mapping=True, fr=400): #pass # For compatibility between running under Spyder and the CLI # %% Load demo movie and ROIs file_dir = os.path.split(fnames)[0] path_ROIs = [file for file in os.listdir(file_dir) if 'ROIs_gt' in file] if len(path_ROIs) > 0: path_ROIs = path_ROIs[0] #path_ROIs = '/home/nel/NEL-LAB Dropbox/NEL/Datasets/voltage_lin/peyman_golshani/ROIs.hdf5' #%% dataset dependent parameters # dataset dependent parameters fr = fr # 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 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')) # Run correction do_motion_correction = do_motion_correction if do_motion_correction: mc.motion_correct(save_movie=True) else: mc_list = [ file for file in os.listdir(file_dir) if (os.path.splitext(os.path.split(fnames)[-1])[0] in file and '.mmap' in file) ] mc.mmap_file = [os.path.join(file_dir, mc_list[0])] print(f'reuse previously saved motion corrected file:{mc.mmap_file}') # %% MEMORY MAPPING do_memory_mapping = do_memory_mapping if do_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_' + os.path.splitext(os.path.split(fnames)[-1])[0], add_to_mov=border_to_0, dview=dview) # exclude border else: mmap_list = [ file for file in os.listdir(file_dir) if ('memmap_' + os.path.splitext(os.path.split(fnames)[-1])[0]) in file ] fname_new = os.path.join(file_dir, mmap_list[0]) print(f'reuse previously saved memory mapping file:{fname_new}') # %% SEGMENTATION # create summary images img = mean_image(mc.mmap_file[0], window=1000, dview=dview) img = (img - np.mean(img)) / np.std(img) gaussian_blur = False # Use gaussian blur when there is too much noise in the video Cn = local_correlations_movie_offline(mc.mmap_file[0], fr=fr, window=fr * 4, stride=fr * 4, winSize_baseline=fr, remove_baseline=True, gaussian_blur=gaussian_blur, dview=dview).max(axis=0) img_corr = (Cn - np.mean(Cn)) / np.std(Cn) summary_images = np.stack([img, img, img_corr], axis=0).astype(np.float32) # ! save summary image, it is used in GUI cm.movie(summary_images).save(fnames[:-5] + '_summary_images.tif') #plt.imshow(summary_images[0]) #%% three methods for segmentation methods_list = [ 'manual_annotation', # manual annotation needs user to prepare annotated datasets same format as demo ROIs 'gui_annotation', # use gui to manually annotate neurons, but this is still under developing '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'][()] ROIs = np.load(os.path.join(file_dir, path_ROIs)) elif method == 'gui_annotation': # run volpy_gui file in the caiman/source_extraction/volpy folder # load the summary images you have just saved # save the ROIs to the video folder path_ROIs = caiman_datadir() + '/example_movies/volpy/gui_roi.hdf5' with h5py.File(path_ROIs, 'r') as fl: ROIs = fl['mov'][()] elif method == 'maskrcnn': # Important!! make sure install keras before using mask rcnn weights_path = download_model('mask_rcnn') weights_path = '/home/nel/Code/NEL_LAB/Mask_RCNN/logs/neurons20200824T1032/mask_rcnn_neurons_0040.h5' ROIs = utils.mrcnn_inference( img=summary_images.transpose([1, 2, 0]), size_range=[5, 100], weights_path=weights_path, display_result=True ) # size parameter decides size range of masks to be selected #np.save(os.path.join(file_dir, 'ROIs'), ROIs) # %% 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, maxtasksperchild=1) # %% parameters for trace denoising and spike extraction ROIs = ROIs # region of interests index = list(range(len(ROIs))) # index of neurons weights = None # reuse spatial weights context_size = 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 hp_freq_pb = 1 / 3 # parameter for high-pass filter to remove photobleaching threshold_method = 'adaptive_threshold' # 'simple' or 'adaptive_threshold' min_spikes = 30 # minimal spikes to be found threshold = 4 # threshold for finding spikes, increase threshold to find less spikes do_plot = False # plot detail of spikes, template for the last iteration ridge_bg = 0.01 # ridge regression regularizer strength for background removement, larger value specifies stronger regularization sub_freq = 20 # frequency for subthreshold extraction weight_update = 'ridge' # 'ridge' or 'NMF' for weight update n_iter = 2 opts_dict = { 'fnames': fname_new, 'ROIs': ROIs, 'index': index, 'weights': weights, 'context_size': context_size, 'flip_signal': flip_signal, 'hp_freq_pb': hp_freq_pb, 'threshold_method': threshold_method, 'min_spikes': min_spikes, 'threshold': threshold, 'do_plot': do_plot, 'ridge_bg': ridge_bg, 'sub_freq': sub_freq, 'weight_update': weight_update, 'n_iter': n_iter } opts.change_params(params_dict=opts_dict) if options is not None: print('using external options') opts.change_params(params_dict=options) else: print('not using external options') #%% TRACE DENOISING AND SPIKE DETECTION vpy = VOLPY(n_processes=n_processes, dview=dview, params=opts) vpy.fit(n_processes=n_processes, dview=dview) #%% visualization display_images = False if display_images: print(np.where( vpy.estimates['locality'])[0]) # neurons that pass locality test idx = np.where(vpy.estimates['locality'] > 0)[0] utils.view_components(vpy.estimates, img_corr, idx) #%% reconstructed movie # note the negative spatial weights is cutoff if display_images: mv_all = utils.reconstructed_movie(vpy.estimates, fnames=mc.mmap_file, idx=idx, scope=(0, 1000), flip_signal=flip_signal) mv_all.play(fr=40) #%% save the result in .npy format save_result = True if save_result: vpy.estimates['ROIs'] = ROIs save_name = f'volpy_{os.path.split(fnames)[1][:-5]}_{opts.volspike["threshold_method"]}_{opts.volspike["threshold"]}_{opts.volspike["weight_update"]}_bg_{opts.volspike["ridge_bg"]}' np.save(os.path.join(file_dir, save_name), vpy.estimates) # %% 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_caiman_pipeline(movie, fr, fnames, savedir, caiman_parameters): #%% usematlabroi = caiman_parameters['usematlabroi'] cpu_num = 16 cpu_num_spikepursuit = 3 #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) #%% if not caiman_parameters['motion_correction_already_done']: # %% 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}) else: #%% files = os.listdir(savedir) for file in files: if '.mmap' in file: break fname_new = os.path.join(savedir, file) opts.change_params(params_dict={'fnames': fname_new}) # %% SEGMENTATION if caiman_parameters['dospikepursuit']: roidir_matlab = savedir[:savedir.find( 'VolPy')] + 'Spikepursuit' + savedir[savedir.find('VolPy') + len('Volpy'):] try: files_matlab = os.listdir(roidir) except: files_matlab = [] roidir_volpy = savedir[:savedir.find('VolPy')] + 'ROI' + savedir[ savedir.find('VolPy') + len('Volpy'):] try: files_volpy = os.listdir(roidir_volpy) except: files_volpy = [] if usematlabroi and 'ROIs.mat' in files_matlab: ROIs = loadmat(os.path.join(roidir_matlab, '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' }) elif caiman_parameters['usevolpyroi'] and 'VolPy.npy' in files_volpy: ROIs_original = np.load(os.path.join(roidir_volpy, 'VolPy.npy')) roinum = int(np.max(np.unique(ROIs_original))) ROIs = np.asarray( np.zeros([ int(roinum), ROIs_original.shape[0], ROIs_original.shape[1] ]), bool) for i in range(1, roinum + 1): ROIs[i - 1, ROIs_original == i] = True all_rois = ROIs opts.change_params( params_dict={ 'ROIs': ROIs, 'index': list(range(ROIs.shape[0])), 'method': 'SpikePursuit' }) else: #% print('WTF') # %% 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) #%% if caiman_parameters['dospikepursuit']: 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) if not caiman_parameters['motion_correction_already_done']: print('saving parameters') parameters = dict() parameters['motion'] = opts.motion parameters['data'] = opts.data if caiman_parameters['dospikepursuit']: parameters['volspike'] = opts.volspike with open(os.path.join(savedir, 'parameters.pickle'), 'wb') as outfile: pickle.dump(parameters, 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 #Thread(target=shutil.copy, args=[fname_new, os.path.join(savedir,fname)]).start() 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_modified_caiman_pipeline(movie, fr, fnames, savedir, registered_movie_file, usematlabroi): #%% cpu_num = 12 cpu_num_spikepursuit = 3 #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': registered_movie_file, '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) # %% SEGMENTATION roidir = savedir[:savedir.find('VolPy_modified' )] + 'Spikepursuit' + savedir[ savedir.find('VolPy_modified') + len('VolPy_modified'):] 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.. no ROIs defined.. sleeping') time.sleep(1000) # %% 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_modified = VOLPY(n_processes=n_processes, dview=dview, params=opts) vpy_modified.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 #Thread(target=shutil.copy, args=[fname_new, os.path.join(savedir,fname)]).start() 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 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) file_dir = os.path.split(fnames)[0] #%% 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) # %% play the movie (optional) # playing the movie using opencv. It requires loading the movie in memory. # To close the movie 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=40, magnification=4) # %% 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')) # Run correction do_motion_correction = True if do_motion_correction: mc.motion_correct(save_movie=True) else: mc_list = [ file for file in os.listdir(file_dir) if (os.path.splitext(os.path.split(fnames)[-1])[0] in file and '.mmap' in file) ] mc.mmap_file = [os.path.join(file_dir, mc_list[0])] print(f'reuse previously saved motion corrected file:{mc.mmap_file}') # %% compare with original movie 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), m_rig.resize(1, 1, ds_ratio)], axis=2) moviehandle.play(fr=40, q_max=99.5, magnification=4) # press q to exit # %% MEMORY MAPPING do_memory_mapping = True if do_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_' + os.path.splitext(os.path.split(fnames)[-1])[0], add_to_mov=border_to_0, dview=dview) # exclude border else: mmap_list = [ file for file in os.listdir(file_dir) if ('memmap_' + os.path.splitext(os.path.split(fnames)[-1])[0]) in file ] fname_new = os.path.join(file_dir, mmap_list[0]) print(f'reuse previously saved memory mapping file:{fname_new}') # %% SEGMENTATION # create summary images img = mean_image(mc.mmap_file[0], window=1000, dview=dview) img = (img - np.mean(img)) / np.std(img) gaussian_blur = False # Use gaussian blur when there is too much noise in the video Cn = local_correlations_movie_offline(mc.mmap_file[0], fr=fr, window=fr * 4, stride=fr * 4, winSize_baseline=fr, remove_baseline=True, gaussian_blur=gaussian_blur, dview=dview).max(axis=0) img_corr = (Cn - np.mean(Cn)) / np.std(Cn) summary_images = np.stack([img, img, img_corr], axis=0).astype(np.float32) # save summary images which are used in the VolPy GUI cm.movie(summary_images).save(fnames[:-5] + '_summary_images.tif') fig, axs = plt.subplots(1, 2) axs[0].imshow(summary_images[0]) axs[1].imshow(summary_images[2]) axs[0].set_title('mean image') axs[1].set_title('corr image') #%% methods for segmentation methods_list = [ 'manual_annotation', # manual annotations need prepared annotated datasets in the same format as demo_voltage_imaging_ROIs.hdf5 'maskrcnn', # Mask R-CNN is a convolutional neural network trained for detecting neurons in summary images 'gui_annotation' ] # use VolPy GUI to correct outputs of Mask R-CNN or annotate new datasets method = methods_list[0] if method == 'manual_annotation': with h5py.File(path_ROIs, 'r') as fl: ROIs = fl['mov'][()] elif method == 'maskrcnn': # Important!! Make sure install keras before using mask rcnn. weights_path = download_model( 'mask_rcnn' ) # also make sure you have downloaded the new weight. The weight was updated on Dec 1st 2020. ROIs = utils.mrcnn_inference( img=summary_images.transpose([1, 2, 0]), size_range=[5, 22], weights_path=weights_path, display_result=True ) # size parameter decides size range of masks to be selected cm.movie(ROIs).save(fnames[:-5] + 'mrcnn_ROIs.hdf5') elif method == 'gui_annotation': # run volpy_gui.py file in the caiman/source_extraction/volpy folder gui_ROIs = caiman_datadir() + '/example_movies/volpy/gui_roi.hdf5' with h5py.File(gui_ROIs, 'r') as fl: ROIs = fl['mov'][()] fig, axs = plt.subplots(1, 2) axs[0].imshow(summary_images[0]) axs[1].imshow(ROIs.sum(0)) axs[0].set_title('mean image') axs[1].set_title('masks') # %% 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, maxtasksperchild=1) # %% parameters for trace denoising and spike extraction ROIs = ROIs # region of interests index = list(range(len(ROIs))) # index of neurons weights = None # reuse spatial weights context_size = 35 # number of pixels surrounding the ROI to censor from the background PCA visualize_ROI = False # whether to visualize the region of interest inside the context region flip_signal = True # Important!! Flip signal or not, True for Voltron indicator, False for others hp_freq_pb = 1 / 3 # parameter for high-pass filter to remove photobleaching clip = 100 # maximum number of spikes to form spike template threshold_method = 'adaptive_threshold' # adaptive_threshold or simple min_spikes = 10 # minimal spikes to be found pnorm = 0.5 # a variable deciding the amount of spikes chosen for adaptive threshold method threshold = 3 # threshold for finding spikes only used in simple threshold method, Increase the threshold to find less spikes do_plot = False # plot detail of spikes, template for the last iteration ridge_bg = 0.01 # ridge regression regularizer strength for background removement, larger value specifies stronger regularization sub_freq = 20 # frequency for subthreshold extraction weight_update = 'ridge' # ridge or NMF for weight update n_iter = 2 # number of iterations alternating between estimating spike times and spatial filters opts_dict = { 'fnames': fname_new, 'ROIs': ROIs, 'index': index, 'weights': weights, 'context_size': context_size, 'visualize_ROI': visualize_ROI, 'flip_signal': flip_signal, 'hp_freq_pb': hp_freq_pb, 'clip': clip, 'threshold_method': threshold_method, 'min_spikes': min_spikes, 'pnorm': pnorm, 'threshold': threshold, 'do_plot': do_plot, 'ridge_bg': ridge_bg, 'sub_freq': sub_freq, 'weight_update': weight_update, 'n_iter': n_iter } opts.change_params(params_dict=opts_dict) #%% TRACE DENOISING AND SPIKE DETECTION vpy = VOLPY(n_processes=n_processes, dview=dview, params=opts) vpy.fit(n_processes=n_processes, dview=dview) #%% visualization display_images = True if display_images: print(np.where( vpy.estimates['locality'])[0]) # neurons that pass locality test idx = np.where(vpy.estimates['locality'] > 0)[0] utils.view_components(vpy.estimates, img_corr, idx) #%% reconstructed movie # note the negative spatial weights is cutoff if display_images: mv_all = utils.reconstructed_movie(vpy.estimates.copy(), fnames=mc.mmap_file, idx=idx, scope=(0, 1000), flip_signal=flip_signal) mv_all.play(fr=40) #%% save the result in .npy format save_result = True if save_result: vpy.estimates['ROIs'] = ROIs vpy.estimates['params'] = opts save_name = f'volpy_{os.path.split(fnames)[1][:-5]}_{threshold_method}' np.save(os.path.join(file_dir, save_name), vpy.estimates) # %% 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 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) #%% 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) # %% play the movie (optional) # playing the movie using opencv. It requires loading the movie in memory. # To close the movie 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=40, magnification=6) # %% 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')) # Run correction mc.motion_correct(save_movie=True) # %% compare with original movie 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=4) # press q to exit # %% 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) # exclude border # %% SEGMENTATION # create summary images img = mean_image(mc.mmap_file[0], window=1000, dview=dview) img = (img - np.mean(img)) / np.std(img) gaussian_blur = False # Use gaussian blur when the quality of corr image(Cn) is bad Cn = local_correlations_movie_offline(mc.mmap_file[0], fr=fr, window=fr * 4, stride=fr * 4, winSize_baseline=fr, remove_baseline=True, gaussian_blur=gaussian_blur, 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'][()] elif method == 'quick_annotation': ROIs = utils.quick_annotation(img, min_radius=4, max_radius=8) elif method == 'maskrcnn': # Important!! make sure install keras before using mask rcnn weights_path = download_model('mask_rcnn') ROIs = utils.mrcnn_inference(img=summary_image, weights_path=weights_path, display_result=True) # %% 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, maxtasksperchild=1) # %% parameters for trace denoising and spike extraction ROIs = ROIs # region of interests index = list(range(len(ROIs))) # index of neurons weights = None # reuse spatial weights context_size = 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 hp_freq_pb = 1 / 3 # parameter for high-pass filter to remove photobleaching threshold_method = 'simple' # 'simple' or 'adaptive_threshold' min_spikes = 10 # minimal spikes to be found threshold = 3.5 # threshold for finding spikes, increase threshold to find less spikes do_plot = False # plot detail of spikes, template for the last iteration ridge_bg = 0.001 # ridge regression regularizer strength for background removement sub_freq = 20 # frequency for subthreshold extraction weight_update = 'ridge' # 'ridge' or 'NMF' for weight update opts_dict = { 'fnames': fname_new, 'ROIs': ROIs, 'index': index, 'weights': weights, 'context_size': context_size, 'flip_signal': flip_signal, 'hp_freq_pb': hp_freq_pb, 'threshold_method': threshold_method, 'min_spikes': min_spikes, 'threshold': threshold, 'do_plot': do_plot, 'ridge_bg': ridge_bg, 'sub_freq': sub_freq, 'weight_update': weight_update } opts.change_params(params_dict=opts_dict) #%% TRACE DENOISING AND SPIKE DETECTION vpy = VOLPY(n_processes=n_processes, dview=dview, params=opts) vpy.fit(n_processes=n_processes, dview=dview) #%% visualization if display_images: print(np.where( vpy.estimates['locality'])[0]) # neurons that pass locality test idx = np.where(vpy.estimates['locality'] > 0)[0] utils.view_components(vpy.estimates, img_corr, idx) #%% reconstructed movie # note the negative spatial weights is cutoff if display_images: mv_all = utils.reconstructed_movie(vpy.estimates, fnames=mc.mmap_file, idx=idx, scope=(0, 1000), flip_signal=flip_signal) mv_all.play(fr=40) # %% 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)