def __call__(self, x, pos=None): if x in [1, 10]: return LogFormatterMathtext.__call__(self, x, pos=None) else: return ' '
def __call__(self, x, pos=None): if x in [0.001, 0.01, 0.1]: return str(x) elif x in [1., 10., 100., 1000.]: return str(int(x)) else: return LogFormatterMathtext.__call__(self, x, pos=pos)
def _polish(self, f): # Handle properties of axes directly #a = plt.gca() # Current set of axes formatter_scalar = ScalarFormatter(useOffset=True, useMathText=False) formatter_scalar.set_powerlimits((-3, 3)) formatter_log = LogFormatterMathtext(base=10.0, labelOnlyBase=False) # Neaten axes formatters for ax in f.get_axes(): if not isinstance(ax.xaxis.get_major_formatter(), NullFormatter): if ax.xaxis.get_scale() == "log": ax.xaxis.set_major_locator( LogLocator(base=10.0, subs=[1.0], numdecs=1)) ax.xaxis.set_major_formatter(formatter_log) else: ax.xaxis.set_major_formatter(formatter_scalar) if not isinstance(ax.yaxis.get_major_formatter(), NullFormatter): if ax.yaxis.get_scale() == "log": ax.yaxis.set_major_locator( LogLocator(base=10.0, subs=[1.0], numdecs=1)) ax.yaxis.set_major_formatter(formatter_log) #ax.yaxis.set_minor_locator(LogLocator(base=10.0, subs=[10], numdecs=1)) # why is this necessary? else: ax.yaxis.set_major_formatter(formatter_scalar)
def lazy_field_coverage(field, log=False, polar=False): # set up figure fig = plt.figure(figsize=(8,8),dpi=100) if polar: ax = fig.add_subplot(111, projection='polar') else: ax = fig.add_subplot(111, aspect='equal') limit = np.ceil(np.max([np.abs(field.min()),np.abs(field.max())])) # create image if log: im = ax.imshow(field+1,cmap='jet',extent=(-12,12,-12,12),norm=LogNorm(),vmin=-limit,vmax=limit) cb = plt.colorbar(im, format=LogFormatterMathtext(),) else: im = ax.imshow(field,cmap='jet',extent=(-12,12,-12,12),vmin=-limit,vmax=limit) cb = plt.colorbar(im) # beautify plt.xticks(np.arange(-12,13,3),fontsize='16') plt.yticks(np.arange(-12,13,3),fontsize='16') plt.xlabel('degrees in X',fontsize='20') plt.ylabel('degrees in Y',fontsize='20') plt.xlim((-12,12)) plt.ylim((-12,12)) plt.subplots_adjust(left=0.12, right=0.98, top=0.98, bottom=.06) plt.grid('on',c='w') plt.show() return None
def plot_prob_density(x, y, cmap=cm.get_cmap('summer'), xscale='log', yscale='log', xParam=1.5, yParam=1.5, ax=None, use_gridspec=False): """ Plots the normalized probability density. See :py:func:`plot_counts` for explanations of the input variables. """ fig, ax, cax = _get_fig_ax_and_colorbar_ax(xscale, yscale, ax=ax) X, Y, counts_matrix, bin_centers, means, Bins2D = \ _get_count_data_to_plot(x, y, xscale, yscale, xParam, yParam) prob_density = counts_matrix / (Bins2D.sizes.T * np.sum(counts_matrix)) assert np.abs(np.sum(prob_density * Bins2D.sizes.T) - 1) < 0.000001 im = ax.pcolor(X, Y, prob_density, cmap=cmap, norm=colors.LogNorm()) ax.plot(bin_centers, means, "go-") cbar = fig.colorbar(im, cax, ax=ax, use_gridspec=use_gridspec, orientation='vertical', format=LogFormatterMathtext()) return fig, ax, cbar, im
def __call__(self, x, pos = None): if x < 0.01: return LogFormatterMathtext.__call__(self, x, pos = None) else: return ' '
def plot_conf_xval(xval_conf, ax=None, xlim=(1.01, 1000), probs=(2.5, 97.5), line=False, **kwargs): if not line and len(probs) != 2: raise ValueError( "Need exactly two 'probs' when plotting 'fill_between'") LAMBDA = xval_conf['LAMBDA'] ax, plot_LAMBDA, kwargs = __prepare_plot_xval__(ax, LAMBDA, **kwargs) conf_retv = xval_conf['conf_retv'] ret = xval_conf['ret'] xmin = np.max([1.00001 / LAMBDA, xlim[0], np.min(ret)]) xmax = np.min([xlim[1], np.max(ret)]) xlim = np.asarray([xmin, xmax]) plot_x = Y_of_T(xlim, LAMBDA=plot_LAMBDA) plot_x = np.linspace(*plot_x) xx = Y_of_T(ret, LAMBDA=plot_LAMBDA) av_probs = xval_conf['probs'] IDX = [] for i in probs: x = np.nonzero(i == av_probs)[0] if len(x): IDX.append(x[0]) if not len(IDX): raise ValueError("desired prob not available") if line: kwargs.setdefault('lw', 0.5) for i in IDX: # y = sp.interpolate.interp1d(xx, conf_retv[i, ], kind='cubic', bounds_error=False)(plot_x) y = sp.interpolate.UnivariateSpline(xx, conf_retv[i, ], k=3)(plot_x) ax.semilogx(np.e**plot_x, y, **kwargs) else: y1 = sp.interpolate.UnivariateSpline(xx, conf_retv[0, ], k=3)(plot_x) y2 = sp.interpolate.UnivariateSpline(xx, conf_retv[1, ], k=3)(plot_x) # add some options for the plot if not set already kwargs.setdefault('alpha', 0.15) kwargs.setdefault('zorder', -1000) kwargs.setdefault('lw', 0) ax.fill_between(np.e**plot_x, y1, y2, **kwargs) ax.xaxis.set_major_formatter(LogFormatterMathtext())
def set_default_locators_and_formatters(self, axis): # Copy of Symmetric LogScale version of this function axis.set_major_locator(SymmetricalLogLocator(self.get_transform())) axis.set_major_formatter(LogFormatterMathtext(self.base)) axis.set_minor_locator( SymmetricalLogLocator(self.get_transform(), self.subs)) axis.set_minor_formatter(NullFormatter())
def set_default_locators_and_formatters(self, axis): """ Set the locators and formatters to specialized versions for log scaling. """ axis.set_major_locator(LogLocator(self.base)) axis.set_major_formatter(LogFormatterMathtext(self.base)) axis.set_minor_locator(LogLocator(self.base, self.subs)) axis.set_minor_formatter(NullFormatter())
def set_default_locators_and_formatters(self, axis): """ Set the locators and formatters to reasonable defaults for linear scaling. """ axis.set_major_locator(HlogMajorLocator()) axis.set_major_formatter(LogFormatterMathtext(10)) axis.set_minor_locator(HlogMinorLocator()) axis.set_minor_formatter(NullFormatter())
def plot_matrix(self, mat, x=None, y=None, aspect=None, zscale=None, vmin=None, vmax=None, ticks_fmt=None, num_label=None, colorbar=True, barloc="right", flip_axis=True, barsize=0.05, barpad=0.1, contour=False, norm=None, extent=None, formatter=None, **kwargs): if x is None: x = np.arange(mat.shape[1]) if y is None: y = np.arange(mat.shape[0]) x_size, y_size = len(x), len(y) if extent is None: extent = [0, x_size, 0, y_size] # setting aspect of figure if aspect == "square": aspect = x_size / y_size # setting zscale if zscale == "log": norm = LogNorm(vmin=vmin, vmax=vmax) formatter = LogFormatterMathtext() elif zscale == "discrete": if norm is not None: norm = BoundaryNorm(norm, len(norm)) else: norm = None # is contour if contour: im = self.contour(x, y, mat, norm=norm, extent=extent, vmin=vmin, vmax=vmax, **kwargs) else: im = self.imshow(mat[::-1], norm=norm, extent=extent, aspect=aspect, vmin=vmin, vmax=vmax, **kwargs) if flip_axis: self.invert_yaxis() if colorbar: divider = make_axes_locatable(self) cax = divider.append_axes( barloc, size="{}%".format(100 * barsize), pad=barpad) cb = self.figure.colorbar(im, cax=cax, format=formatter) if num_label is not None: x_skip = int(x_size / num_label) y_skip = int(y_size / num_label) self.set_xticks(np.arange(x_size)[::x_skip]) self.set_yticks(np.arange(y_size)[::y_skip]) if ticks_fmt is None: self.set_xticklabels(x[::x_skip]) self.set_yticklabels(y[::x_skip]) else: xlabels = [ticks_fmt.format(_) for _ in x] ylabels = [ticks_fmt.format(_) for _ in y] self.set_xticklabels(xlabels[::x_skip]) self.set_yticklabels(ylabels[::y_skip]) if colorbar: return im, cb else: return im
def plot_counts(x, y, cmap=cm.get_cmap('summer'), xscale='log', yscale='log', xParam=1.5, yParam=1.5, ax=None, use_gridspec=False): """ Plots the counts as a heatmap. Parameters ---------- x : list-like (1D numpy array) values on x-axis y : list-like (1D numpy array) values on x-axis if xbins and ybins are both given cmap : matplotlib.cm colormap to use for the plot, defaulting to summer xscale : {"log", "linear", "linlog", ...}, optional see binner.binner or binner.bins for more info on the options yscale : {"log", "linear", "linlog", ...}, optional see binner.binner or binner.bins for more info on the options xParam : varies according to xscale if xscale == 'log' xParam equals to the multiplier if xscale == 'lin' xParam equals to the number of bins yParam : varies according to yscale see xParam ax : axis object give this if plotting is used as a subroutine for existing axis. Created if None. use_gridspec : bool set true if subroutine plotting to a subplot with gridspec fixes the colorbar to the correct subplot """ fig, ax, cax = _get_fig_ax_and_colorbar_ax(xscale, yscale, ax=ax) X, Y, counts_matrix, bin_centers, means, Bins2D = \ _get_count_data_to_plot(x, y, xscale, yscale, xParam, yParam) im = ax.pcolor(X, Y, counts_matrix, cmap=cmap, norm=colors.LogNorm()) ax.plot(bin_centers, means, "go-") cbar = fig.colorbar(im, cax, ax=ax, use_gridspec=use_gridspec, orientation='vertical', format=LogFormatterMathtext()) return fig, ax, cbar, im
def build_chart(x_data, y_data, label_req, dur, scatter = False ): matplotlib.rcParams.update({'font.family': 'monospace'}) label = labels[label_req] dates = mdate.epoch2num(x_data) fig, ax = plt.subplots() if scatter: plt.scatter(dates, y_data,s=.01) else: ax.plot(dates, y_data,linewidth=.5,color = 'black') if dur !='1M': label['x-axis'] ='Year' if label['scale']: if 'ℳ' in list(label['y-axis']) : plt.ylabel('ℳ', fontdict = {'family': 'sans'}) ax.set(xlabel = label['x-axis'], ylabel = label['y-axis'], title = label['title'], yscale = label['scale']) else: ax.set(xlabel = label['x-axis'], ylabel = label['y-axis'], title = label['title']) if label['scale']=='log': ax.yaxis.set_major_locator(LogLocator(base=10)) ax.yaxis.set_minor_locator(LogLocator(base=10,subs=[0.0, 0.1,0.2,0.3,0.4,0.5,0.6,0.7,0.8,0.9,1])) ax.yaxis.set_major_formatter(LogFormatterMathtext(labelOnlyBase=True)) if dur == '1M': date_formatter = mdate.DateFormatter('%m/%d/%y') ax.xaxis.set_minor_locator(mdate.DayLocator()) ax.xaxis.set_major_locator(mdate.WeekdayLocator(byweekday = mdate.SU)) ax.xaxis.set_major_formatter(date_formatter) elif dur == '1Y': date_formatter = mdate.DateFormatter("%b.%y") ax.xaxis.set_minor_locator(mdate.MonthLocator()) ax.xaxis.set_major_locator(mdate.MonthLocator(bymonth=[1,4,7,10])) ax.xaxis.set_major_formatter(date_formatter) else: date_formatter = mdate.DateFormatter('%y') ax.xaxis.set_minor_locator(mdate.MonthLocator(bymonth=[1,4,7,10])) ax.xaxis.set_major_locator(mdate.YearLocator()) ax.xaxis.set_major_formatter(date_formatter) ax.grid(which='major',linestyle = '--') ax.grid(which='minor',linestyle = ':') ax.grid(True) fig.set_size_inches(8,5) fig.savefig("static/data/"+ label['file-name'] +"_" + dur + ".png",dpi=150) plt.cla() plt.clf() plt.close('all') return True
def field_coverage(x, y, s, deg_x, deg_y, log=False, polar=False): # set up figure fig = plt.figure(figsize=(8, 8), dpi=100) if polar: ax = fig.add_subplot(111, projection='polar') else: ax = fig.add_subplot(111, aspect='equal') # set up a blank field field = np.zeros_like(deg_x) # create the RFs for r in np.arange(len(x)): rf = generate_og_receptive_field(x[r], y[r], s[r], deg_x, deg_y) # d = np.sqrt((x[r]-deg_x)**2 + (y[r]-deg_y)**2)<s[r] field += rf # normalize field /= np.max(field) field *= 100 # create image if log: im = ax.imshow(field, cmap='viridis', extent=(-12, 12, -12, 12), norm=LogNorm(), vmin=1e0, vmax=1e2) cb = plt.colorbar( im, format=LogFormatterMathtext(), ) else: im = ax.imshow(field, cmap='viridis', extent=(-12, 12, -12, 12), vmin=1e0, vmax=1e2) cb = plt.colorbar(im) # beautify plt.xticks(np.arange(-12, 13, 3), fontsize='16') plt.yticks(np.arange(-12, 13, 3), fontsize='16') plt.xlabel('degrees in X', fontsize='20') plt.ylabel('degrees in Y', fontsize='20') plt.xlim((-12, 12)) plt.ylim((-12, 12)) plt.subplots_adjust(left=0.12, right=0.98, top=0.98, bottom=.06) plt.grid('on', c='w') plt.show() return field
def update_ticks(axes, coord, components, is_log): """ Changes the axes to have the proper tick formatting based on the type of component. Returns `None` or the number of categories if components is Categorical. Parameters ---------- axes : `~matplotlib.axes.Axes` A matplotlib axis object to alter coord : { 'x' | 'y' } The coordinate axis on which to update the ticks components : iterable A list of components that are plotted along this axis if_log : boolean Whether the axis has a log-scale """ if coord == 'x': axis = axes.xaxis elif coord == 'y': axis = axes.yaxis else: raise TypeError("coord must be one of x,y") is_cat = any(comp.categorical for comp in components) is_date = any(comp.datetime for comp in components) if is_date: loc = AutoDateLocator() fmt = AutoDateFormatter(loc) axis.set_major_locator(loc) axis.set_major_formatter(fmt) elif is_log: axis.set_major_locator(LogLocator()) axis.set_major_formatter(LogFormatterMathtext()) elif is_cat: all_categories = np.empty((0, ), dtype=np.object) for comp in components: all_categories = np.union1d(comp.categories, all_categories) locator = MaxNLocator(10, integer=True) locator.view_limits(0, all_categories.shape[0]) format_func = partial(tick_linker, all_categories) formatter = FuncFormatter(format_func) axis.set_major_locator(locator) axis.set_major_formatter(formatter) return all_categories.shape[0] else: axis.set_major_locator(AutoLocator()) axis.set_major_formatter(ScalarFormatter())
def plot_finish(contours, spectrum=None, contour_labels=True, autofit=True): # plot spectrum? if spectrum is not None: pyplot.plot(numpy.real(spectrum), numpy.imag(spectrum), 'o') if autofit: vertices = [] for collection in contours.collections: for path in collection.get_paths(): vertices.append(path.vertices[:, 0] + 1j * path.vertices[:, 1]) vertices = numpy.concatenate(vertices) pyplot.xlim(numpy.min(vertices.real), numpy.max(vertices.real)) pyplot.ylim(numpy.min(vertices.imag), numpy.max(vertices.imag)) # plot contour labels? from matplotlib.ticker import LogFormatterMathtext if contour_labels: pyplot.clabel(contours, inline=1, fmt=LogFormatterMathtext())
def save_figure_frank_tamm(path, wavelength_start=250e-9, wavelength_end=700e-9): altitudes = np.logspace(np.log10(1e3), np.log10(100e3), 128) energies = np.logspace(np.log10(1e7 * tas.UNIT_CHARGE), np.log10(1e9 * tas.UNIT_CHARGE), 128) cherenkov_yield = np.zeros(shape=(altitudes.shape[0], energies.shape[0])) for aidx, altitude in enumerate(altitudes): for eidx, energy in enumerate(energies): current_n = tas.refraction_in_air(altitude) current_beta = tas.natural_velocity( kinetic_energy=energy, rest_energy=tas.ELECTRON_REST_ENERGY) if current_beta < 1. / current_n: cherenkov_yield[aidx, eidx] = 0. else: cherenkov_yield[aidx, eidx] = -tas.dE_over_dz( q=tas.UNIT_CHARGE, beta=current_beta, n=current_n, mu=tas.PERMABILITY_AIR, wavelength_start=wavelength_start, wavelength_end=wavelength_end) dpi = 200 fig = plt.figure(figsize=(8, 4.5), dpi=dpi) ax = fig.add_axes((0.1, 0.1, 0.9, 0.85)) im = ax.pcolormesh( energies / tas.UNIT_CHARGE, # GeV altitudes, # m cherenkov_yield / tas.UNIT_CHARGE, # eV/m norm=LogNorm()) ax.loglog() ax.set_xlabel(r"E / eV") ax.set_ylabel(r"z (above sea level)/ m") ax.set_title("Wavelength: {:.0f}nm - {:.0f}nm".format( wavelength_start * 1e9, wavelength_end * 1e9)) ax.grid(color='k', linestyle='-', linewidth=0.66, alpha=0.1) cbar = plt.colorbar(im, format=LogFormatterMathtext()) cbar.ax.set_ylabel(r'dE/dz / eV m$^{-1}$') fig.savefig(path)
def show_beta(x, data, z, fname="attbsc.png", label="Attenuated Backscatter coefficient", maxalt=0.0, maxdays=0.0): x_low, data_low, z_low = resampling(x, data, z, maxalt, maxdays) data_low = np.ma.masked_invalid(data_low) levs1 = [i * 1E-4 for i in [1, 2, 4, 6, 8, 10]] levs2 = [i * 1E-3 for i in [1.25, 1.5, 1.75, 2, 2.25, 2.5, 2.75, 3]] levs3 = [i * 1E-3 for i in [4, 5, 6]] levs4 = [i * 1E-3 for i in [7, 8, 9, 10, 20, 40, 60, 80, 100]] my_cmap, my_norm = build_palette4(levs1, levs2, levs3, levs4) auto_tick = maxdays > 12 fig, ax = get_figure(auto_tick) CS = ax.pcolormesh( x_low, z_low, data_low, cmap=my_cmap, norm=my_norm, ) my_ticks = np.array([1E-4, 1E-3, 1E-2, 1E-1]) cbar = plt.colorbar( CS, ticks=my_ticks, extend='both', format=LogFormatterMathtext(), orientation='horizontal', aspect=30, shrink=0.6, ) ax.set_title(label + r" $[/sr \, /km]$") ax.patch.set(hatch='/', edgecolor='black') plt.xlabel('') plt.ylabel('Height AGL [km]') fig.savefig(fname, bbox_inches='tight', dpi=150)
def plot_conditional_prob_density(x, y, cmap=cm.get_cmap('summer'), xscale='log', yscale='log', xParam=np.sqrt(2), yParam=np.sqrt(2), ax=None, use_gridspec=False, plot_mean=True): """ Plots the conditional probability density. (P(y|x)). See plot_counts for explanations of the input variables. """ fig, ax, cax = _get_fig_ax_and_colorbar_ax(xscale, yscale, ax=ax) X, Y, counts_matrix, bin_centers, means, Bins2D = \ _get_count_data_to_plot(x, y, xscale, yscale, xParam, yParam) # count vals for each x-bin x_counts = np.sum(counts_matrix, axis=0) # normalize the counts for each x-bin by the total number norm_x_counts_mat = counts_matrix / x_counts[None, :] # to get the prob density, normalize by the bin widths cond_prob = norm_x_counts_mat / Bins2D.widths[1][:, None] im = ax.pcolor(X, Y, cond_prob, cmap=cmap, norm=colors.LogNorm()) if plot_mean: ax.plot(bin_centers, means, "go-") cbar = fig.colorbar(im, cax, ax=ax, use_gridspec=use_gridspec, orientation='vertical', format=LogFormatterMathtext()) return fig, ax, cbar, im
def update_ticks(axes, coord, components, is_log): """ Changes the axes to have the proper tick formatting based on the type of component. :param axes: A matplotlib axis object to alter :param coord: 'x' or 'y' :param components: A list() of components that are plotted along this axis :param is_log: Boolean for log-scale. :kwarg max_categories: The maximum number of categories to display. :return: None or #categories if components is Categorical """ if coord == 'x': axis = axes.xaxis elif coord == 'y': axis = axes.yaxis else: raise TypeError("coord must be one of x,y") is_cat = all(comp.categorical for comp in components) if is_log: axis.set_major_locator(LogLocator()) axis.set_major_formatter(LogFormatterMathtext()) elif is_cat: all_categories = np.empty((0, ), dtype=np.object) for comp in components: all_categories = np.union1d(comp.categories, all_categories) locator = MaxNLocator(10, integer=True) locator.view_limits(0, all_categories.shape[0]) format_func = partial(tick_linker, all_categories) formatter = FuncFormatter(format_func) axis.set_major_locator(locator) axis.set_major_formatter(formatter) return all_categories.shape[0] else: axis.set_major_locator(AutoLocator()) axis.set_major_formatter(ScalarFormatter())
def plot_conf_sampled_xval(params, ax=None, LAMBDA=1, xlim=(1.01, 1000), probs=(2.5, 97.5), line=False, **kwargs): """ plot uncertainty of GEV given the sampled parameters Parameters ---------- params : array_like The three parameters of a GEV: alpha, chi, k ax : a matplotlib axes object or None If no ax is given, uses plt.gca() to create a new one. xlim : two-element list defines the x limit of the plotted line probs : tuple probability for which to plot the uncertainty bounds line : bool if true uses line else fill_between kwargs : named arguments passed to the plot/ fill_between plotting function Returns ------- handle : handle of the plot/ fill_between object """ if not line and len(probs) != 2: msg = "Need exactly two 'probs' when plotting 'fill_between'" raise ValueError(msg) ax, plot_LAMBDA, kwargs = __prepare_plot_xval__(ax, LAMBDA, **kwargs) xmin = np.amax([1.00001 / LAMBDA, xlim[0]]) xmax = xlim[1] xlim = np.log(np.asarray([xmin, xmax])) t_fit = np.linspace(xlim[0], xlim[1]) n_samples = params.shape[0] n_plot_points = t_fit.shape[0] sampled = np.empty(shape=(n_samples, n_plot_points)) ft = F_of_T(T_of_Y(t_fit, plot_LAMBDA), LAMBDA) for i, param in enumerate(params): y_fit = XGEV(ft, *param) sampled[i, :] = y_fit y = np.percentile(sampled, probs, axis=0) if line: kwargs.setdefault('lw', 0.5) y = y.transpose() return ax.semilogx(np.e**t_fit, y, basex=10, **kwargs) else: y1 = y[0, :] y2 = y[1, :] # add some options for the plot if not set already kwargs.setdefault('alpha', 0.15) kwargs.setdefault('zorder', -1000) kwargs.setdefault('lw', 0) ax.set_xscale('log', basex=10) ax.xaxis.set_major_formatter(LogFormatterMathtext()) return ax.fill_between(np.e**t_fit, y1, y2, **kwargs)
def plot_df(self, var, time, nlev=31, zlim=None, xlim=None, ylim=None, target=None, loc=111, title=None, add_cbar=True, clabel=None, show_pts=False, dolog=False, add_body=True, figsize=(8.34, 7), *args, **kwargs): ''' Create a plot of variable *var* at a given time. If kwarg **target** is None (default), a new figure is generated from scratch. If target is a matplotlib Figure object, a new axis is created to fill that figure at subplot location **loc**. If **target** is a matplotlib Axes object, the plot is placed into that axis. ''' import matplotlib.pyplot as plt from matplotlib.colors import (LogNorm, Normalize) from matplotlib.patches import Circle from matplotlib.ticker import (LogLocator, LogFormatter, LogFormatterMathtext, MultipleLocator) from matplotlib.patches import Wedge # Grab the slice of data that we want: if type(time) == type(self['time'][0]): if time not in self['time']: raise ValueError('Time not in object') time = np.arange(self.attrs['nTime'])[self['time'] == time][0] fig, ax = set_target(target, loc=loc, figsize=figsize) ax.set_aspect('equal') # Grab values from correct time/location. x = self['Vperp[cm/s]'][time, :] y = self['Vpar[cm/s]'][time, :] value = self[var][time, :] # Get max/min if none given. if zlim == None: zlim = [0, 0] zlim[0] = value.min() zlim[1] = value.max() if dolog and zlim[0] <= 0: zlim[0] = np.min([0.0001, zlim[1] / 1000.0]) # Create levels and set norm based on dolog. if dolog: levs = np.power( 10, np.linspace(np.log10(zlim[0]), np.log10(zlim[1]), nlev)) z = np.where(value > zlim[0], value, 1.01 * zlim[0]) norm = LogNorm() ticks = LogLocator() fmt = LogFormatterMathtext() else: levs = np.linspace(zlim[0], zlim[1], nlev) z = value norm = None ticks = None fmt = None # Create contour plot. cont=ax.tricontourf(np.asarray(x), np.asarray(y), np.asarray(z), \ np.asarray(levs), *args, norm=norm, **kwargs) if show_pts: ax.plot(x, y, '+w') if xlim != None: ax.set_xlim(xlim[0], xlim[1]) if ylim != None: ax.set_ylim(ylim[0], ylim[1]) # Add cbar if necessary. if add_cbar: cbar = plt.colorbar(cont, ticks=ticks, format=fmt, pad=0.01) if clabel == None: clabel = "%s" % (var) cbar.set_label(clabel) else: cbar = None # Need to return something, even if none. # Set title, labels, axis ranges (use defaults where applicable.) if title: ax.set_title(title) #ax.set_yticks([]), ax.set_xticks([]) ax.set_xlabel('Vpar [cm/s]') ax.set_ylabel('Vperp [cm/s]') return fig, ax, cont, cbar
def add_slice(self, var, time, nlev=31, zlim=None, target=None, loc=111, title=None, latoffset=1.05, rlim=50., add_cbar=True, clabel=None, show_pts=False, dolog=False, lats=[75., 60.], colats=None, figsize=(8.34, 7), *args, **kwargs): ''' Create a plot of variable *var*. If kwarg **target** is None (default), a new figure is generated from scratch. If target is a matplotlib Figure object, a new axis is created to fill that figure at subplot location **loc**. If **target** is a matplotlib Axes object, the plot is placed into that axis. ''' import matplotlib.pyplot as plt from matplotlib.colors import (LogNorm, Normalize) from matplotlib.patches import Circle from matplotlib.ticker import (LogLocator, LogFormatter, LogFormatterMathtext, MultipleLocator) # Grab the slice of data that we want: if type(time) == type(self['time'][0]): if time not in self['time']: raise ValueError('Time not in object') time = np.arange(self.attrs['nTime'])[self['time'] == time][0] fig, ax = set_target(target, loc=loc, figsize=figsize) ax.set_aspect('equal') # Create values in Cartesian plane. self._get_latlon() # Grab values from correct time/location. x = self._xLat[time, :] y = self._yLat[time, :] value = self[var][time, :] # Get max/min if none given. if zlim == None: zlim = [0, 0] zlim[0] = value.min() zlim[1] = value.max() if dolog and zlim[0] <= 0: zlim[0] = np.min([0.0001, zlim[1] / 1000.0]) # Create levels and set norm based on dolog. if dolog: levs = np.power( 10, np.linspace(np.log10(zlim[0]), np.log10(zlim[1]), nlev)) z = np.where(value > zlim[0], value, 1.01 * zlim[0]) norm = LogNorm() ticks = LogLocator() fmt = LogFormatterMathtext() else: levs = np.linspace(zlim[0], zlim[1], nlev) z = value norm = None ticks = None fmt = None # Create contour plot. cont=ax.tricontourf(np.asarray(x), np.asarray(y), np.asarray(z), \ np.asarray(levs), *args, norm=norm, **kwargs) if show_pts: ax.plot(x, y, '+w') # Add cbar if necessary. if add_cbar: cbar = plt.colorbar(cont, ticks=ticks, format=fmt, pad=0.01) if clabel == None: clabel = "%s (%s)" % (var, self[var].attrs['units']) cbar.set_label(clabel) else: cbar = None # Need to return something, even if none. # Set title, labels, axis ranges (use defaults where applicable.) if title: ax.set_title(title) ax.set_yticks([]), ax.set_xticks([]) ax.set_ylabel(r'Sun $\rightarrow$') colat_lim = 90. - rlim ax.set_xlim([-1 * colat_lim, colat_lim]) ax.set_ylim([-1 * colat_lim, colat_lim]) if colats: for colat in colats: r = latoffset * colat / np.sqrt(2) ax.add_patch( Circle([0, 0], colat, fc='none', ec='k', ls='dashed')) ax.text(r, r, '{:.0f}'.format(colat) + r'$^{\circ}$', rotation=315, ha='center', va='center') else: for lat in lats: colat = 90 - lat r = latoffset * colat / np.sqrt(2) ax.add_patch( Circle([0, 0], colat, fc='none', ec='k', ls='dashed')) ax.text(r, r, '{:.0f}'.format(lat) + r'$^{\circ}$', rotation=315, ha='center', va='center') return fig, ax, cont, cbar
def __call__(self, x, pos=None): if pos==0: return '' # pos=0 is the first tick else: return LogFormatterMathtext.__call__(self, x, pos)
def _make_contour(self, **kwargs): """ method for generalizanting contour and colorbar plotting kwargs cax = matplotlib.Axes used to print colorbar. Default use make_axes_locatable """ Z = self.data.copy() if self.kwargs['vlim'] is not None: vmin, vmax = self.kwargs['vlim'] else: vmin, vmax = [Z.min().min(), Z.max().max()] #np.nanpercentile(Z,[2.5,97.5]) # print vmin, vmax colorbarKwd = {'extend': 'both'} contourKwd = { 'cmap': self.colormap } #'levels':np.linspace(vmin,vmax,100), if self.kwargs['colorbarKind'] == 'Linear': contourKwd['norm'] = Normalize(vmin, vmax) elif self.kwargs['colorbarKind'] == 'Anomaly': contourKwd['norm'] = MidpointNormalize(midpoint=0., vmin=vmin, vmax=vmax) colorbarKwd['format'] = self.kwargs['format'] elif self.kwargs['colorbarKind'] == 'Log': Z.mask(Z <= 0, inplace=True) if self.kwargs['vlim'] is None: vmin, vmax = [Z.min().min(), Z.max().max()] # np.nanpercentile(Z,[1,99]))) # Z[Z < vmin] = vmin # Z[Z > vmax] = vmax contourKwd['norm'] = LogNorm(vmin, vmax) print vmin, vmax minorTicks = np.hstack( [np.arange(1, 10, 1) * log for log in np.logspace(-2, 16, 19)]) minorTicks = minorTicks[(minorTicks >= vmin) & (minorTicks <= vmax)] colorbarKwd.update( dict(format=LogFormatterMathtext(10), ticks=LogLocator(10))) args = (self.x, self.y, Z) cf = self.axes[0].pcolormesh(*args, **contourKwd) # cf = ax.contourf(X,Y,Z,**contourKwd) #extend='both') if 'cax' not in kwargs.keys(): divider = make_axes_locatable(self.axes[0]) cax = divider.append_axes("right", size="3%", pad='1%') else: cax = kwargs['cax'] cbar = plt.colorbar(cf, cax=cax, **colorbarKwd) cbar.set_label(self.kwargs['cbarLabel'], weight='bold') if self.kwargs['colorbarKind'] == 'Log': cbar.ax.yaxis.set_ticks(cf.norm(minorTicks), minor=True) cbar.ax.tick_params(which='minor', width=1, length=4) cbar.ax.tick_params(which='major', width=1, length=6) # ax.yaxis.set_minor_locator(LogLocator(10,subs=np.arange(2,10))) self.kwargs['colorbarKind'] = 'Linear' return cf, cbar
pl = ( ggplot(across_samples[across_samples.n > 6], aes(x="tradeoff", y="rho")) + geom_hline(yintercept=0, linetype="dashed") + geom_point() + geom_line(aes(group=1)) + labs(x="tradeoff", y="Pearson rho")) pl.save("figures/across_sample_correlations.svg", width=5, height=5) across_samples.to_csv("data/correlation_all.csv") rates["log_rates"] = np.log10(rates.growth_rate) rates.loc[rates.growth_rate <= 0, "log_rates"] = -16 fig, axes = jp.joyplot(rates, by="tradeoff", column="log_rates", color="cornflowerblue") lf = LogFormatterMathtext() xax = axes[-1].xaxis xax.set_ticklabels(lf(10.0**ex) for ex in xax.get_ticklocs()) plt.xlabel("growth rate [1/h]") plt.ylabel("tradeoff") plt.savefig("figures/dists.svg") plt.close() non_zero = (rates.groupby([ "id", "tradeoff" ]).apply(lambda df: (df.growth_rate > 1e-6).sum() / df.shape[0]).reset_index( name="non_zero")) pl = (ggplot(non_zero, aes(x="tradeoff", y="non_zero")) + geom_boxplot(outlier_color="none") + geom_jitter(width=0.15, height=0, alpha=0.5, stroke=0) +
def update_ticks(axes, coord, kinds, is_log, categories, projection='rectilinear'): """ Changes the axes to have the proper tick formatting based on the type of component. Returns `None` or the number of categories if components is Categorical. Parameters ---------- axes : `~matplotlib.axes.Axes` A matplotlib axis object to alter coord : { 'x' | 'y' } The coordinate axis on which to update the ticks components : iterable A list of components that are plotted along this axis if_log : boolean Whether the axis has a log-scale projection: str The name of the matplotlib projection for the axes object. Defaults to 'rectilinear'. Currently only the scatter viewer supports different projections. """ # Short circuit the full-sphere projections if projection in ['aitoff', 'hammer', 'mollweide', 'lambert']: return if coord == 'x': axis = axes.xaxis elif coord == 'y': axis = axes.yaxis else: raise TypeError("coord must be one of x,y") is_cat = 'categorical' in kinds is_date = 'datetime' in kinds if is_date: loc = AutoDateLocator() fmt = AutoDateFormatter(loc) axis.set_major_locator(loc) axis.set_major_formatter(fmt) elif is_log: axis.set_major_locator(LogLocator()) axis.set_major_formatter(LogFormatterMathtext()) elif is_cat: locator = MaxNLocator(10, integer=True) locator.view_limits(0, categories.shape[0]) format_func = partial(tick_linker, categories) formatter = FuncFormatter(format_func) axis.set_major_locator(locator) axis.set_major_formatter(formatter) # Have to treat the theta axis of polar plots differently elif projection == 'polar' and coord == 'x': axis.set_major_locator(ThetaLocator(AutoLocator())) axis.set_major_formatter(ThetaFormatter()) else: axis.set_major_locator(AutoLocator()) axis.set_major_formatter(ScalarFormatter())
def show(self, location='right', width=0.2, pad=0.05, ticks=None, labels=True, log_format=False, box=None, box_orientation='vertical', axis_label_text=None, axis_label_rotation=None, axis_label_pad=5): """ Show a colorbar on the side of the image. Parameters ---------- location : str, optional Where to place the colorbar. Should be one of 'left', 'right', 'top', 'bottom'. width : float, optional The width of the colorbar relative to the canvas size. pad : float, optional The spacing between the colorbar and the image relative to the canvas size. ticks : list, optional The position of the ticks on the colorbar. labels : bool, optional Whether to show numerical labels. log_format : bool, optional Whether to format ticks in exponential notation box : list, optional A custom box within which to place the colorbar. This should be in the form [xmin, ymin, dx, dy] and be in relative figure units. This overrides the location argument. box_orientation str, optional The orientation of the colorbar within the box. Can be 'horizontal' or 'vertical' axis_label_text str, optional Optional text label of the colorbar. """ self._base_settings['location'] = location self._base_settings['width'] = width self._base_settings['pad'] = pad self._base_settings['ticks'] = ticks self._base_settings['labels'] = labels self._base_settings['log_format'] = log_format self._base_settings['box'] = box self._base_settings['box_orientation'] = box_orientation self._base_settings['axis_label_text'] = axis_label_text self._base_settings['axis_label_rotation'] = axis_label_rotation self._base_settings['axis_label_pad'] = axis_label_pad if self._parent.image: if self._colorbar_axes: self._figure.delaxes(self._colorbar_axes) if box is None: divider = make_axes_locatable(self._parent.ax) if location == 'right': self._colorbar_axes = divider.new_horizontal( size=width, pad=pad, axes_class=maxes.Axes) orientation = 'vertical' elif location == 'top': self._colorbar_axes = divider.new_vertical( size=width, pad=pad, axes_class=maxes.Axes) orientation = 'horizontal' elif location == 'left': warnings.warn("Left colorbar not fully implemented") self._colorbar_axes = divider.new_horizontal( size=width, pad=pad, pack_start=True, axes_class=maxes.Axes) locator = divider.new_locator(nx=0, ny=0) self._colorbar_axes.set_axes_locator(locator) orientation = 'vertical' elif location == 'bottom': warnings.warn("Bottom colorbar not fully implemented") self._colorbar_axes = divider.new_vertical( size=width, pad=pad, pack_start=True, axes_class=maxes.Axes) locator = divider.new_locator(nx=0, ny=0) self._colorbar_axes.set_axes_locator(locator) orientation = 'horizontal' else: raise Exception("location should be one of: right/top") self._figure.add_axes(self._colorbar_axes) else: self._colorbar_axes = self._figure.add_axes(box) orientation = box_orientation if log_format: format = LogFormatterMathtext() else: format = None self._colorbar = self._figure.colorbar(self._parent.image, cax=self._colorbar_axes, orientation=orientation, format=format, ticks=ticks) if axis_label_text: if axis_label_rotation: self._colorbar.set_label(axis_label_text, rotation=axis_label_rotation) else: self._colorbar.set_label(axis_label_text) if location == 'right': for tick in self._colorbar_axes.yaxis.get_major_ticks(): tick.tick1line.set_visible(True) tick.tick2line.set_visible(True) tick.label1.set_visible(False) tick.label2.set_visible(labels) self._colorbar_axes.yaxis.set_label_position('right') self._colorbar_axes.yaxis.labelpad = axis_label_pad elif location == 'top': for tick in self._colorbar_axes.xaxis.get_major_ticks(): tick.tick1line.set_visible(True) tick.tick2line.set_visible(True) tick.label1.set_visible(False) tick.label2.set_visible(labels) self._colorbar_axes.xaxis.set_label_position('top') self._colorbar_axes.xaxis.labelpad = axis_label_pad elif location == 'left': for tick in self._colorbar_axes.yaxis.get_major_ticks(): tick.tick1line.set_visible(True) tick.tick2line.set_visible(True) tick.label1.set_visible(labels) tick.label2.set_visible(False) self._colorbar_axes.yaxis.set_label_position('left') self._colorbar_axes.yaxis.labelpad = axis_label_pad elif location == 'bottom': for tick in self._colorbar_axes.xaxis.get_major_ticks(): tick.tick1line.set_visible(True) tick.tick2line.set_visible(True) tick.label1.set_visible(labels) tick.label2.set_visible(False) self._colorbar_axes.xaxis.set_label_position('bottom') self._colorbar_axes.xaxis.labelpad = axis_label_pad else: warnings.warn( "No image is shown, therefore, no colorbar will be plotted")
def set_default_locators_and_formatters(self, axis): axis.set_major_locator(HlogMajorLocator()) axis.set_major_formatter(LogFormatterMathtext(10)) axis.set_minor_locator(HlogMinorLocator()) axis.set_minor_formatter(NullFormatter())
def plot(self, Lmax=True, Lpp=False, Kp=True, Dst=True, clims=[0, 10], title=None, values=None): """ Create a summary plot of the RadBelt object distribution function. For reference, the last closed drift shell, Dst, and Kp are all included. These can be disabled individually using the corresponding Boolean kwargs. The clims kwarg can be used to manually set the color bar range. To use, set it equal to a two-element list containing minimum and maximum Log_10 value to plot. Default action is to use [0,10] as the log_10 of the color range. This is good enough for most applications. The title of the top most plot defaults to 'Summary Plot' but can be customized using the title kwarg. The figure object and all three axis objects (PSD axis, Dst axis, and Kp axis) are all returned to allow the user to further customize the plots as necessary. If any of the plots are excluded, None is returned in their stead. Examples ======== >>> rb.plot(Lmax=False, Kp=False, clims=[2,10], title='Good work!') This command would create the summary plot with a color bar range of 100 to 10^10. The Lmax line and Kp values would be excluded. The title of the topmost plot (phase space density) would be set to 'Good work!'. """ import matplotlib.pyplot as p from matplotlib.colors import LogNorm from matplotlib.ticker import (LogLocator, LogFormatter, LogFormatterMathtext) import pdb # debugging command #pdb.set_trace() # test for default values if values is None: values = self.PSD # Initialize axis variables so that they can be returned, # even if not used. ax1 = None ax2 = None ax3 = None fig = p.figure() fig.subplots_adjust(left=0.10, right=0.999, top=0.92) # PLOT PSD if Kp or Dst: ax1 = p.subplot(2, 1, 1) else: ax1 = p.subplot(1, 1, 1) # Plot phase space density, masking out values of 0. map = ax1.pcolorfast(self.ticks.eDOY, self.Lgrid, np.where(values > 0.0, self.PSD, 10.0**-39), vmin=10.0**clims[0], vmax=10.0**clims[1], norm=LogNorm()) ax1.set_ylabel('L*') if title is not None: ax1.set_title(title) # Add color bar. cbar = p.colorbar(map, pad=0.01, shrink=.85, ticks=LogLocator(), format=LogFormatterMathtext()) cbar.set_label('Phase Space Density') # add Lmax line if Lmax: p.plot(self.ticks.eDOY, self.params['Lmax'], 'w') # Minimize time range. ax1.set_xlim([self.ticks.eDOY[0], self.ticks.eDOY[-1]]) # Finally, save the position of the plot to make next plot match. pos = ax1.get_position() if Dst is True: ax2 = p.subplot(2, 1, 2) pos2 = ax2.get_position() pos2.x1 = pos.x1 ax2.set_position(pos2) ax2.plot(self.ticks.eDOY, self.params['Dst'], color='r') ax2.set_xlabel('DOY in ' + str(self.ticks.UTC[0].year)) ax2.set_ylabel('Dst', color='r') for tl in ax2.get_yticklabels(): tl.set_color('r') ax2.set_xlim([self.ticks.eDOY[0], self.ticks.eDOY[-1]]) if Kp is True: if Dst is True: p.subplot(2, 1, 2) ax3 = p.twinx() else: ax3 = p.subplot(2, 1, 2) pos3 = ax3.get_position() pos3.x1 = pos.x1 ax3.set_position(pos3) ax3.plot(self.ticks.eDOY, self.params['Kp'], 'k:') if Dst is True: ax3.yaxis.tick_right() ax3.set_xlabel('DOY in ' + str(self.ticks.UTC[0].year)) ax3.set_ylabel('Kp') ax3.set_xlim([self.ticks.eDOY[0], self.ticks.eDOY[-1]]) #p.show() return fig, ax1, ax2, ax3
def plot_obs(self, Lmax=True, Lpp=False, Kp=True, Dst=True, clims=[0, 10], title=None, values=None): """ Create a summary plot of the observations. For reference, the last closed drift shell, Dst, and Kp are all included. These can be disabled individually using the corresponding boolean kwargs. The clims kwarg can be used to manually set the color bar range. To use, set it equal to a two-element list containing minimum and maximum Log_10 value to plot. Default action is to use [0,10] as the log_10 of the color range. This is good enough for most applications. The title of the top most plot defaults to 'Summary Plot' but can be customized using the title kwarg. The figure object and all three axis objects (PSD axis, Dst axis, and Kp axis) are all returned to allow the user to further customize the plots as necessary. If any of the plots are excluded, None is returned in their stead. Examples ======== >>> rb.plot_obs(Lmax=False, Kp=False, clims=[2,10], title='Observations Plot') This command would create the summary plot with a color bar range of 100 to 10^10. The Lmax line and Kp values would be excluded. The title of the topmost plot (phase space density) would be set to 'Good work!'. """ import spacepy.data_assimilation import matplotlib.pyplot as p from matplotlib.colors import LogNorm from matplotlib.ticker import (LogLocator, LogFormatter, LogFormatterMathtext) import pdb # debugging command #pdb.set_trace() # test for default values if values is None: values = self.PSDdata # Initialize axis variables so that they can be returned, # even if not used. ax1 = None ax2 = None ax3 = None fig = p.figure() fig.subplots_adjust(left=0.10, right=0.999, top=0.92) # compute time-window average observation value y = np.array([], dtype=float) Lobs = np.array([], dtype=float) eDOYobs = np.array([], dtype=float) nTAI = len(self.ticks) # time loop for i, Tnow, Tfut in zip( np.arange(nTAI - 1) + 1, self.ticks[:-1], self.ticks[1:]): if len(values[i - 1]) > 0: # get observations for time window ]Tnow-Twindow,Tnow] Lobs_tmp, y_tmp = spacepy.data_assimilation.average_window( values[i - 1], self.Lgrid) y = np.append(y, y_tmp) Lobs = np.append(Lobs, Lobs_tmp) eDOYobs = np.append( eDOYobs, np.ones(len(y_tmp)) * self.ticks.eDOY[i - 1]) # PLOT PSDdata if Kp or Dst: ax1 = p.subplot(2, 1, 1) else: ax1 = p.subplot(1, 1, 1) # Plot phase space density observations. map = ax1.scatter(eDOYobs, Lobs, c=y, norm=LogNorm(), vmin=10.0**clims[0], vmax=10.0**clims[1], edgecolor='none') ax1.set_ylabel('L*') if title is not None: ax1.set_title(title) ax1.set_ylim(self.Lgrid[0], self.Lgrid[len(self.Lgrid) - 1]) # Add color bar. cbar = p.colorbar(map, pad=0.01, shrink=.85, ticks=LogLocator(), format=LogFormatterMathtext()) cbar.set_label('Phase Space Density') # add Lmax line if Lmax: p.plot(self.ticks.eDOY, self.params['Lmax'], 'w') # Minimize time range. ax1.set_xlim([self.ticks.eDOY[0], self.ticks.eDOY[-1]]) # Finally, save the position of the plot to make next plot match. pos = ax1.get_position() if Dst is True: ax2 = p.subplot(2, 1, 2) pos2 = ax2.get_position() pos2.x1 = pos.x1 ax2.set_position(pos2) ax2.plot(self.ticks.eDOY, self.params['Dst'], color='r') ax2.set_xlabel('DOY in ' + str(self.ticks.UTC[0].year)) ax2.set_ylabel('Dst', color='r') for tl in ax2.get_yticklabels(): tl.set_color('r') ax2.set_xlim([self.ticks.eDOY[0], self.ticks.eDOY[-1]]) if Kp is True: if Dst is True: p.subplot(2, 1, 2) ax3 = p.twinx() else: ax3 = p.subplot(2, 1, 2) pos3 = ax3.get_position() pos3.x1 = pos.x1 ax3.set_position(pos3) ax3.plot(self.ticks.eDOY, self.params['Kp'], 'k:') if Dst is True: ax3.yaxis.tick_right() ax3.set_xlabel('DOY in ' + str(self.ticks.UTC[0].year)) ax3.set_ylabel('Kp') ax3.set_xlim([self.ticks.eDOY[0], self.ticks.eDOY[-1]]) #p.show() return fig, ax1, ax2, ax3