def plot_response(f_sealcombined, resp_plot_dir, plot_DR=True, plot_sel=True): """Plot basic unit activity figures.""" print('\nStarting plotting unit activity...') putil.inline_off() # Init folders. ftempl_dr = util.join([resp_plot_dir, 'direction_response', '{}.png']) ftempl_sel = util.join([resp_plot_dir, 'stimulus_selectivity', '{}.png']) # Read in Units. print(' Reading in UnitArray...') UA = util.read_objects(f_sealcombined, 'UnitArr') # Test stimulus response to all directions. if plot_DR: print(' Plotting direction response...') DR_plot(UA, ftempl_dr) # Plot feature selectivity summary plots. if plot_sel: print(' Plotting selectivity summary figures...') selectivity_summary(UA, ftempl_sel) # Re-enable inline plotting putil.inline_on()
def res_fname(res_dir, subdir, tasks, feat, nrate, ncv, Cs, n_perm, n_pshfl, sep_err_trs, sep_by, zscore_by, even_by, PDD_offset, n_most_DS, tstep): """Return full path to decoding result with given parameters.""" tasks_str = '_'.join(tasks) feat_str = util.format_to_fname(str(feat)) ncv_str = 'ncv{}'.format(ncv) Cs_str = 'nregul{}'.format(len(Cs)) if Cs != [1] else 'reguloff' prem_str = 'nperm{}'.format(n_perm) pshfl_str = 'npshfl{}'.format(n_pshfl) err_str = 'w{}err'.format('o' if sep_err_trs else '') zscore_str = ('_zscoredby' + util.format_feat_name(zscore_by, True) if not util.is_null(zscore_by) else '') even_str = ('_evenby' + util.format_feat_name(even_by, True) if not util.is_null(even_by) else '') PDD_str = ('_PDDoff{}'.format(int(PDD_offset)) if not util.is_null(PDD_offset) else '') nDS_str = ('top{}u'.format(n_most_DS) if n_most_DS != 0 else 'allu') tstep_str = 'tstep{}ms'.format(int(tstep)) dir_name = '{}{}/{}{}{}{}'.format(res_dir, tasks_str, feat_str, zscore_str, even_str, PDD_str) fname = '{}_{}_{}_{}_{}_{}_{}_{}.data'.format(nrate, ncv_str, Cs_str, prem_str, pshfl_str, err_str, nDS_str, tstep_str) fres = util.join([dir_name, subdir, fname]) return fres
def aroc_res_fname(res_dir, nrate, tstep, n_perm, offsets): """Return full path to AROC result with given parameters.""" offset_str = '_'.join([str(int(d)) for d in offsets]) fname = '{}_tstep{}ms_nperm{}_offs{}.data'.format(nrate, int(tstep), n_perm, offset_str) fpath = util.join([res_dir + 'res', fname]) return fpath
def aroc_fig_fname(res_dir, prefix, offsets, cmap, sort_prd=None): """Return full path to AROC result with given parameters.""" sort_prd_str = ('sorted_by_' + util.format_to_fname(sort_prd) if sort_prd is not None else 'unsorted') ostr = 'offset_' + '_'.join([str(int(d)) for d in offsets]) fname = 'AROC_{}_{}.png'.format(prefix, sort_prd_str) ffig = util.join([res_dir + 'heatmap', ostr, cmap, fname]) return ffig
def plot_RF_results(RF_res, stims, fdir, sup_title): """Plot receptive field results.""" # Plot distribution of coverage values. putil.set_style('poster', 'white') fig = putil.figure() ax = putil.axes() sns.distplot(RF_res.S1_cover, bins=np.arange(0, 1.01, 0.1), kde=False, rug=True, ax=ax) putil.set_limits(ax, [0, 1]) fst = util.format_to_fname(sup_title) ffig = fdir + fst + '_S1_coverage.png' putil.save_fig(ffig, fig, sup_title) # Plot RF coverage and rate during S1 on regression plot for each # recording and task. tasks = RF_res.index.get_level_values(-1).unique() for vname, ylim in [('mean_rate', [0, None]), ('max_rate', [0, None]), ('mDSI', [0, 1])]: fig, gs, axes = putil.get_gs_subplots(nrow=len(stims), ncol=len(tasks), subw=4, subh=4, ax_kws_list=None, create_axes=True) colors = sns.color_palette('muted', len(tasks)) for istim, stim in enumerate(stims): for itask, task in enumerate(tasks): # Plot regression plot. ax = axes[istim, itask] scov, sval = [stim + '_' + name for name in ('cover', vname)] df = RF_res.xs(task, level=-1) sns.regplot(scov, sval, df, color=colors[itask], ax=ax) # Add unit labels. uids = df.index.droplevel(0) putil.add_unit_labels(ax, uids, df[scov], df[sval]) # Add stats. r, p = sp.stats.pearsonr(df[sval], df[scov]) pstr = util.format_pvalue(p) txt = 'r = {:.2f}, {}'.format(r, pstr) ax.text(0.02, 0.98, txt, va='top', ha='left', transform=ax.transAxes) # Set labels. title = '{} {}'.format(task, stim) xlab, ylab = [sn.replace('_', ' ') for sn in (scov, sval)] putil.set_labels(ax, xlab, ylab, title) # Set limits. xlim = [0, 1] putil.set_limits(ax, xlim, ylim) # Save plot. fst = util.format_to_fname(sup_title) fname = '{}_cover_{}.png'.format(fst, vname) ffig = util.join([fdir, vname, fname]) putil.save_fig(ffig, fig, sup_title)
def aroc_table_fname(res_dir, task, nrate, tstep, n_perm, offsets, sort_prd, min_len, pth, vth_hi, vth_lo): """Return full path to AROC results table with given parameters.""" ostr = '_'.join([str(int(d)) for d in offsets]) ftable = ('{}_{}_tstep{}ms_nperm{}_offs{}'.format(task, nrate, int(tstep), n_perm, ostr) + '_prd{}_minlen{}_pth{}'.format(sort_prd, int(min_len), pth) + '_vthhi{}_vthlo{}'.format(vth_hi, vth_lo)) ftable = util.join( [res_dir + 'tables', util.format_to_fname(ftable) + '.xlsx']) return ftable
def plot_spike_count_results(bspk_cnts, rec, task, prds, binsize): """Plot spike count results on composite plot for multiple periods.""" # Init figure. putil.set_style('notebook', 'ticks') fig, gsp, _ = putil.get_gs_subplots(nrow=len(prds), ncol=1, subw=15, subh=4, create_axes=False) # Plot each period. for prd, sps in zip(prds, gsp): plot_prd_spike_count(bspk_cnts[prd], prd, sps, fig) # Save figure. title = '{} {}, binsize: {} ms'.format(rec, task, int(binsize)) fname = 'UpDown_spk_cnt_hist_{}_{}_bin_{}.png'.format(rec, task, int(binsize)) ffig = util.join(['results', 'UpDown', fname]) putil.save_fig(ffig, fig, title)
def plot_trial_type_distribution(UA, RecInfo, utids=None, tr_par=('S1', 'Dir'), save_plot=False, fname=None): """Plot distribution of trial types.""" # Init. par_str = util.format_to_fname(str(tr_par)) if utids is None: utids = UA.utids(as_series=True) recs = util.get_subj_date_pairs(utids) tasks = RecInfo.index.get_level_values('task').unique() tasks = [task for task in UA.tasks() if task in tasks] # reorder tasks # Init plotting. putil.set_style('notebook', 'darkgrid') fig, gsp, axs = putil.get_gs_subplots(nrow=len(recs), ncol=len(tasks), subw=4, subh=3, create_axes=True) for ir, rec in enumerate(recs): for it, task in enumerate(tasks): ax = axs[ir, it] rt = rec + (task,) if rt not in RecInfo.index: ax.set_axis_off() continue # Get includecd trials and their parameters. inc_trs = RecInfo.loc[rt, 'trials'] utid = utids.xs(rt, level=('subj', 'date', 'task'))[0] TrData = UA.get_unit(utid[:-1], utid[-1]).TrData.loc[inc_trs] # Create DF to plot. anw_df = TrData[[tr_par, 'correct']].copy() anw_df['answer'] = 'error' anw_df.loc[anw_df.correct, 'answer'] = 'correct' all_df = anw_df.copy() all_df.answer = 'all' comb_df = pd.concat([anw_df, all_df]) if not TrData.size: ax.set_axis_off() continue # Plot as countplot. sns.countplot(x=tr_par, hue='answer', data=comb_df, hue_order=['all', 'correct', 'error'], ax=ax) sns.despine(ax=ax) putil.hide_tick_marks(ax) putil.set_max_n_ticks(ax, 6, 'y') ax.legend(loc=[0.95, 0.7]) # Add title. title = '{} {}'.format(rec, task) nce = anw_df.answer.value_counts() nc, ne = [nce[c] if c in nce else 0 for c in ('correct', 'error')] pnc, pne = 100*nc/nce.sum(), 100*ne/nce.sum() title += '\n\n# correct: {} ({:.0f}%)'.format(nc, pnc) title += ' # error: {} ({:.0f}%)'.format(ne, pne) putil.set_labels(ax, title=title, xlab=par_str) # Format legend. if (ir != 0) or (it != 0): ax.legend_.remove() # Save plot. if save_plot: title = 'Trial type distribution' if fname is None: fname = util.join(['results', 'decoding', 'prepare', par_str + '_trial_type_distr.pdf']) putil.save_fig(fname, fig, title, w_pad=3, h_pad=3)
def quality_control(data_dir, proj_name, task_order, plot_qm=True, plot_stab=True, fselection=None): """Run quality control (SNR, rate drift, ISI, etc) on each recording.""" # Data directory with all recordings to be processed in subfolders. rec_data_dir = data_dir + 'recordings' # Init combined UnitArray object. combUA = unitarray.UnitArray(proj_name, task_order) print('\nStarting quality control...') putil.inline_off() for recording in sorted(os.listdir(rec_data_dir)): if recording[0] == '_': continue # Report progress. print(' ' + recording) # Init folder. rec_dir = util.join([rec_data_dir, recording]) qc_dir = util.join([rec_dir, 'quality_control']) # Read in Units. f_data = util.join([rec_dir, 'SealCells', recording + '.data']) UA = util.read_objects(f_data, 'UnitArr') # Test unit quality, save result figures, add stats to units and # exclude low quality trials and units. ftempl = util.join([qc_dir, 'QC_plots', '{}.png']) quality_test(UA, ftempl, plot_qm, fselection) # Report unit exclusion stats. report_unit_exclusion_stats(UA) # Test stability of recording session across tasks. if plot_stab: print(' Plotting recording stability...') fname = util.join([qc_dir, 'recording_stability.png']) test_stability.rec_stability_test(UA, fname) # Add to combined UA. combUA.add_recording(UA) # Add index to unit names. combUA.index_units() # Save Units with quality metrics added. print('\nExporting combined UnitArray...') fname = util.join([data_dir, 'all_recordings.data']) util.write_objects({'UnitArr': combUA}, fname) # Export unit and trial selection results. if fselection is None: print('Exporting automatic unit and trial selection results...') fname = util.joint([data_dir, 'unit_trial_selection.xlsx']) export.export_unit_trial_selection(combUA, fname) # Export unit list. print('Exporting combined unit list...') export.export_unit_list(combUA, util.join([data_dir, 'unit_list.xlsx'])) # Re-enable inline plotting putil.inline_on()
def plot_up_down_raster(Spikes, task, rec, itrs): """Plot spike raster for up-down dynamics analysis.""" # Set params for plotting. uids, trs = Spikes.index, Spikes.columns plot_trs = trs[itrs] ntrs = len(plot_trs) nunits = len(uids) tr_gap = nunits / 2 # Init figure. putil.set_style('notebook', 'ticks') fig = putil.figure(figsize=(10, ntrs)) ax = fig.add_subplot(111) # Per trial, per unit. for itr, tr in enumerate(plot_trs): for iu, uid in enumerate(uids): # Init y level and spike times. i = (tr_gap + nunits) * itr + iu spk_tr = Spikes.loc[uid, tr] # Plot (spike time, y-level) pairs. x = np.array(spk_tr.rescale('ms')) y = (i+1) * np.ones_like(x) patches = [Rectangle((xi-wsp/2, yi-hsp/2), wsp, hsp) for xi, yi in zip(x, y)] collection = PatchCollection(patches, facecolor=c, edgecolor=c) ax.add_collection(collection) # Add stimulus lines. for stim in constants.stim_dur.index: t_start, t_stop = constants.fixed_tr_prds.loc[stim] events = pd.DataFrame([(t_start, 't_start'), (t_stop, 't_stop')], index=['start', 'stop'], columns=['time', 'label']) putil.plot_events(events, add_names=False, color='grey', alpha=0.5, ls='-', lw=0.5, ax=ax) # Add inter-trial shading. for itr in range(ntrs+1): ymin = itr * (tr_gap + nunits) - tr_gap + 0.5 ax.axhspan(ymin, ymin+tr_gap, alpha=.05, color='grey') # Set tick labels. pos = np.arange(ntrs) * (tr_gap + nunits) + nunits/2 lbls = plot_trs + 1 putil.set_ytick_labels(ax, pos, lbls) # putil.sparsify_tick_labels(ax, 'y', freq=2, istart=1) putil.hide_tick_marks(ax, show_x_tick_mrks=True) # Format plot. xlim = constants.fixed_tr_prds.loc['whole trial'] ylim = [-tr_gap/2, ntrs * (nunits+tr_gap)-tr_gap/2] xlab = 'Time since S1 onset (ms)' ylab = 'Trial number' title = '{} {}'.format(rec, task) putil.format_plot(ax, xlim, ylim, xlab, ylab, title) putil.set_spines(ax, True, False, False, False) # Save figure. fname = 'UpDown_dynamics_{}_{}.pdf'.format(rec, task) ffig = util.join(['results', 'UpDown', fname]) putil.save_fig(ffig, fig, dpi=600)