def __init__(self, fig, rect=[0.0, 0.0, 1.0, 1.0], *args, **kwargs): self.fig = fig azim = cbook.popd(kwargs, 'azim', -60) elev = cbook.popd(kwargs, 'elev', 30) self.xy_viewLim = unit_bbox() self.zz_viewLim = unit_bbox() self.xy_dataLim = unit_bbox() self.zz_dataLim = unit_bbox() # inihibit autoscale_view until the axises are defined # they can't be defined until Axes.__init__ has been called self._ready = 0 Axes.__init__(self, self.fig, rect, frameon=True, xticks=[], yticks=[], *args, **kwargs) self.M = None self._ready = 1 self.view_init(elev, azim) self.mouse_init() self.create_axes() self.set_top_view() #self.axesPatch.set_edgecolor((1,0,0,0)) self.axesPatch.set_linewidth(0) #self.axesPatch.set_facecolor((0,0,0,0)) self.fig.add_axes(self)
def _get_axes(*arrays): """ find list of axes from a list of axis-aligned DimArray objects """ dims = get_dims(*arrays) # all dimensions present in objects axes = Axes() for dim in dims: common_axis = None for o in arrays: # skip missing dimensions if dim not in o.dims: continue axis = o.axes[dim] # update values if common_axis is None or (common_axis.size==1 and axis.size > 1): common_axis = axis # Test alignment for non-singleton axes if not (axis.size == 1 or np.all(axis.values==common_axis.values)): raise ValueError("axes are not aligned") # append new axis axes.append(common_axis) return axes
def __init__(self, *args, **kwargs): if len(args) == 1: self.xvalues, self.yvalues = meshgrid(arange(args[0].shape[0]), arange(args[0].shape[1])) self.zvalues = args[0] else: self.xvalues, self.yvalues, self.zvalues = args # shading self.shading = kwargs.get('shading', None) # custom plot options self.pgf_options = kwargs.get('pgf_options', []) # catch common mistakes if not isinstance(self.pgf_options, list): raise TypeError('pgf_options should be a list.') # add plot to axis self.axes = kwargs.get('axes', Axes.gca()) self.axes.children.append(self) # adjust default behavior for 3D plots self.axes.axis_on_top = False self.axes.xlabel_near_ticks = False self.axes.ylabel_near_ticks = False self.axes.zlabel_near_ticks = False
def __init__(self, *args, **kwargs): """ Initializes plot properties. """ # data points if len(args) < 1: self.xvalues = asarray([]) self.yvalues = asarray([]) elif len(args) < 2: self.yvalues = asarray(args[0]).flatten() self.xvalues = arange(1, len(self.yvalues) + 1) else: self.xvalues = asarray(args[0]).flatten() self.yvalues = asarray(args[1]).flatten() # line style self.line_style = kwargs.get('line_style', None) self.line_width = kwargs.get('line_width', None) self.opacity = kwargs.get('opacity', None) self.color = kwargs.get('color', None) self.fill = kwargs.get('fill', False) # marker style self.marker = kwargs.get('marker', None) self.marker_size = kwargs.get('marker_size', None) self.marker_edge_color = kwargs.get('marker_edge_color', None) self.marker_face_color = kwargs.get('marker_face_color', None) self.marker_opacity = kwargs.get('marker_opacity', None) # error bars self.xvalues_error = asarray(kwargs.get('xvalues_error', [])).flatten() self.yvalues_error = asarray(kwargs.get('yvalues_error', [])).flatten() self.error_marker = kwargs.get('error_marker', None) self.error_color = kwargs.get('error_color', None) self.error_style = kwargs.get('error_style', None) self.error_width = kwargs.get('error_width', None) # comb (or stem) plots self.ycomb = kwargs.get('ycomb', False) self.xcomb = kwargs.get('xcomb', False) self.closed = kwargs.get('closed', False) self.const_plot = kwargs.get('const_plot', False) # legend entry for this plot self.legend_entry = kwargs.get('legend_entry', None) # custom plot options self.pgf_options = kwargs.get('pgf_options', []) # catch common mistakes if not isinstance(self.pgf_options, list): raise TypeError('pgf_options should be a list.') # add plot to axes self.axes = kwargs.get('axis', Axes.gca()) self.axes.children.append(self)
def set_w_ylim(self, *args, **kwargs): gl,self.get_ylim = self.get_ylim,self.get_w_ylim vl,self.viewLim = self.viewLim,self.xy_viewLim vmin,vmax = Axes.set_ylim(self, *args, **kwargs) self.get_ylim = gl self.viewLim = vl return vmin,vmax
def empty(axes=None, dims=None, shape=None, dtype=float): """ Initialize an empty array axes and dims have the same meaning as DimArray's initializer shape, optional: can be provided in combination with `dims` if `axes=` is omitted. >>> a = empty([('time',[2000,2001]),('items',['a','b','c'])]) >>> a.fill(3) >>> a dimarray: 6 non-null elements (0 null) dimensions: 'time', 'items' 0 / time (2): 2000 to 2001 1 / items (3): a to c array([[ 3., 3., 3.], [ 3., 3., 3.]]) >>> b = empty(dims=('time','items'), shape=(2, 3)) See also: --------- empty_like, ones, zeros, nans """ axes = Axes._init(axes, dims=dims, shape=shape) if shape is None: shape = [ax.size for ax in axes] values = np.empty(shape, dtype=dtype) return DimArray(values, axes=axes, dims=dims)
def scatter3D(self, xs, ys, zs, *args, **kwargs): had_data = self.has_data() patches = Axes.scatter(self,xs,ys,*args,**kwargs) patches = art3d.wrap_patch(patches, zs) # self.auto_scale_xyz(xs,ys,zs, had_data) return patches
def __init__(self, *args, **kwargs): if len(args) == 1: self.xvalues, self.yvalues = meshgrid( arange(args[0].shape[0]), arange(args[0].shape[1])) self.zvalues = args[0] else: self.xvalues, self.yvalues, self.zvalues = args # shading self.shading = kwargs.get('shading', None) # custom plot options self.pgf_options = kwargs.get('pgf_options', []) # catch common mistakes if not isinstance(self.pgf_options, list): raise TypeError('pgf_options should be a list.') # add plot to axis self.axes = kwargs.get('axes', Axes.gca()) self.axes.children.append(self) # adjust default behavior for 3D plots self.axes.axis_on_top = False self.axes.xlabel_near_ticks = False self.axes.ylabel_near_ticks = False self.axes.zlabel_near_ticks = False
def from_pandas(cls, data, dims=None): """ Initialize a DimArray from pandas data: pandas object (Series, DataFrame, Panel, Panel4D) dims, optional: dimension (axis) names, otherwise look at ax.name for ax in data.axes >>> import pandas as pd >>> s = pd.Series([3,5,6], index=['a','b','c']) >>> s.index.name = 'dim0' >>> DimArray.from_pandas(s) dimarray: 3 non-null elements (0 null) dimensions: 'dim0' 0 / dim0 (3): a to c array([3, 5, 6]) Also work with Multi-Index >>> panel = pd.Panel(np.arange(2*3*4).reshape(2,3,4)) >>> b = panel.to_frame() # pandas' method to convert Panel to DataFrame via MultiIndex >>> DimArray.from_pandas(b) # doctest: +SKIP dimarray: 24 non-null elements (0 null) dimensions: 'major,minor', 'x1' 0 / major,minor (12): (0, 0) to (2, 3) 1 / x1 (2): 0 to 1 ... """ try: import pandas as pd except ImportError: raise ImportError("pandas module is required to use this method") axisnames = [] axes = [] for i, ax in enumerate(data.axes): # axis name name = ax.name if dims is not None: name = dims[i] if name is None: name = 'x%i'% (i) # Multi-Index: make a Grouped Axis object if isinstance(ax, pd.MultiIndex): # level names names = ax.names for j, nm in enumerate(names): if nm is None: names[j] = '%s_%i'%(name,j) miaxes = Axes.from_arrays(ax.levels, dims=names) axis = GroupedAxis(*miaxes) # Index: Make a simple Axis else: axis = Axis(ax.values, name) axes.append(axis) #axisnames, axes = zip(*[(ax.name, ax.values) for ax in data.axes]) return cls(data.values, axes=axes)
def from_pandas(cls, data, dims=None): """ Initialize a DimArray from pandas data: pandas object (Series, DataFrame, Panel, Panel4D) dims, optional: dimension (axis) names, otherwise look at ax.name for ax in data.axes >>> import pandas as pd >>> s = pd.Series([3,5,6], index=['a','b','c']) >>> s.index.name = 'dim0' >>> DimArray.from_pandas(s) dimarray: 3 non-null elements (0 null) dimensions: 'dim0' 0 / dim0 (3): a to c array([3, 5, 6]) Also work with Multi-Index >>> panel = pd.Panel(np.arange(2*3*4).reshape(2,3,4)) >>> b = panel.to_frame() # pandas' method to convert Panel to DataFrame via MultiIndex >>> DimArray.from_pandas(b) # doctest: +SKIP dimarray: 24 non-null elements (0 null) dimensions: 'major,minor', 'x1' 0 / major,minor (12): (0, 0) to (2, 3) 1 / x1 (2): 0 to 1 ... """ try: import pandas as pd except ImportError: raise ImportError("pandas module is required to use this method") axisnames = [] axes = [] for i, ax in enumerate(data.axes): # axis name name = ax.name if dims is not None: name = dims[i] if name is None: name = 'x%i' % (i) # Multi-Index: make a Grouped Axis object if isinstance(ax, pd.MultiIndex): # level names names = ax.names for j, nm in enumerate(names): if nm is None: names[j] = '%s_%i' % (name, j) miaxes = Axes.from_arrays(ax.levels, dims=names) axis = GroupedAxis(*miaxes) # Index: Make a simple Axis else: axis = Axis(ax.values, name) axes.append(axis) #axisnames, axes = zip(*[(ax.name, ax.values) for ax in data.axes]) return cls(data.values, axes=axes)
def draw(self, renderer): # draw the background patch self.axesPatch.draw(renderer) self._frameon = False # add the projection matrix to the renderer self.M = self.get_proj() renderer.M = self.M renderer.vvec = self.vvec renderer.eye = self.eye renderer.get_axis_position = self.get_axis_position #self.set_top_view() self.w_xaxis.draw(renderer) self.w_yaxis.draw(renderer) self.w_zaxis.draw(renderer) Axes.draw(self, renderer)
def plot3D(self, xs, ys, zs, *args, **kwargs): had_data = self.has_data() lines = Axes.plot(self, xs,ys, *args, **kwargs) if len(lines)==1: line = lines[0] art3d.wrap_line(line, zs) # self.auto_scale_xyz(xs,ys,zs, had_data) return lines
def add_axes(self, *args, **kwargs): """ Add an a axes with axes rect [left, bottom, width, height] where all quantities are in fractions of figure width and height. kwargs are legal Axes kwargs plus "polar" which sets whether to create a polar axes rect = l,b,w,h add_axes(rect) add_axes(rect, frameon=False, axisbg='g') add_axes(rect, polar=True) add_axes(ax) # add an Axes instance If the figure already has an axes with key *args, *kwargs then it will simply make that axes current and return it. If you do not want this behavior, eg you want to force the creation of a new axes, you must use a unique set of args and kwargs. The artist "label" attribute has been exposed for this purpose. Eg, if you want two axes that are otherwise identical to be added to the figure, make sure you give them unique labels: add_axes(rect, label='axes1') add_axes(rect, label='axes2') The Axes instance will be returned The following kwargs are supported: %(Axes)s """ key = self._make_key(*args, **kwargs) if self._seen.has_key(key): ax = self._seen[key] self.sca(ax) return ax if not len(args): return if isinstance(args[0], Axes): a = args[0] assert (a.get_figure() is self) else: rect = args[0] ispolar = kwargs.pop('polar', False) if ispolar: a = PolarAxes(self, rect, **kwargs) else: a = Axes(self, rect, **kwargs) self.axes.append(a) self._axstack.push(a) self.sca(a) self._seen[key] = a return a
def add_axes(self, rect, axisbg=None, frameon=True): """ Add an a axes with axes rect [left, bottom, width, height] where all quantities are in fractions of figure width and height. The Axes instance will be returned """ if axisbg is None: axisbg = rcParams['axes.facecolor'] a = Axes(self, rect, axisbg, frameon) self.axes.append(a) return a
def __init__(self, *args, **kwargs): # legend entries self.legend_entries = args # legend properties self.at = kwargs.get('at', None) self.anchor = kwargs.get('anchor', None) self.location = kwargs.get('location', None) self.align = kwargs.get('align', 'left') self.box = kwargs.get('box', True) self.font_size = kwargs.get('font_size', None) # assign legend to axis self.axes = kwargs.get('axes', Axes.gca()) self.axes.legend = self
def __init__(self, image, **kwargs): """ @type image: string/array_like/PIL Image @param image: a filepath or an image in grayscale or RGB @param vmin: @param vmax: @param cmap: """ self.cmap = kwargs.get('cmap', 'gray') if isinstance(image, str): self.image = PILImage.open(image) elif isinstance(image, PILImage.Image): self.image = image.copy() else: if isinstance(image, ndarray): # copy array image = array(image) if image.dtype.kind != 'i': vmin = kwargs.get('vmin', min(image)) vmax = kwargs.get('vmax', max(image)) # rescale image image = (image - vmin) / (vmax - vmin) image = array(image * 256., dtype='int32') image[image < 0] = 0 image[image > 255] = 255 image = array(image, dtype='uint8') if image.ndim < 3: image = repeat(image.reshape(image.shape[0], -1, 1), 3, 2) self.image = PILImage.fromarray(image) # add image to axis self.axes = kwargs.get('axis', Axes.gca()) self.axes.children.append(self) self.idx = Image._counter Image._counter += 1
def subplot(i, j, **kwargs): fig = gcf() if not (fig.axes and isinstance(fig.axes[0], AxesGrid)): # create new axis grid fig.axes = [AxesGrid(**kwargs)] # get axis grid grid = fig.axes[0] if not (i, j) in grid.keys(): # create new axis in axis grid grid[i, j] = Axes(fig=fig, **kwargs) # make axis active; TODO: find a less hacky solution fig._ca = grid[i, j]
def add_axes(self, rect, axisbg=None, frameon=True, **kwargs): """ Add an a axes with axes rect [left, bottom, width, height] where all quantities are in fractions of figure width and height. The Axes instance will be returned """ if axisbg is None: axisbg = rcParams['axes.facecolor'] ispolar = kwargs.get('polar', False) if ispolar: a = PolarAxes(self, rect, axisbg, frameon) else: a = Axes(self, rect, axisbg, frameon) self.axes.append(a) return a
def add_axes(self, *args, **kwargs): """ Add an a axes with axes rect [left, bottom, width, height] where all quantities are in fractions of figure width and height. kwargs are legal Axes kwargs plus"polar" which sets whether to create a polar axes add_axes((l,b,w,h)) add_axes((l,b,w,h), frameon=False, axisbg='g') add_axes((l,b,w,h), polar=True) add_axes(ax) # add an Axes instance If the figure already has an axed with key *args, *kwargs then it will simply make that axes current and return it The Axes instance will be returned """ if iterable(args[0]): key = tuple(args[0]), tuple(kwargs.items()) else: key = args[0], tuple(kwargs.items()) if self._seen.has_key(key): ax = self._seen[key] self.sca(ax) return ax if not len(args): return if isinstance(args[0], Axes): a = args[0] a.set_figure(self) else: rect = args[0] ispolar = popd(kwargs, 'polar', False) if ispolar: a = PolarAxes(self, rect, **kwargs) else: a = Axes(self, rect, **kwargs) self.axes.append(a) self._axstack.push(a) self.sca(a) self._seen[key] = a return a
def plot(self, *args, **kwargs): had_data = self.has_data() zval = cbook.popd(kwargs, 'z', 0) zdir = cbook.popd(kwargs, 'dir', 'z') lines = Axes.plot(self, *args, **kwargs) # linecs = [art3d.Line2DW(l, z=zval, dir=zdir) for l in lines] # xs = lines[0].get_xdata() ys = lines[0].get_ydata() zs = [zval for x in xs] xs,ys,zs = art3d.juggle_axes(xs,ys,zs,zdir) # self.auto_scale_xyz(xs,ys,zs, had_data) # return linecs
def __init__(self, x, y, text, **kwargs): self.x = x self.y = y self.text = text # properties self.color = kwargs.get('color', None) # custom plot options self.pgf_options = kwargs.get('pgf_options', []) # catch common mistakes if not isinstance(self.pgf_options, list): raise TypeError('pgf_options should be a list.') # add text to axes self.axes = kwargs.get('axes', Axes.gca()) self.axes.children.append(self)
def new_axes(self, *args, **kwargs): ''' Add an axes to the figure. :param position: (*list*) Optional, axes position specified by *position=* [left, bottom, width height] in normalized (0, 1) units. Default is [0.13, 0.11, 0.775, 0.815]. :param outerposition: (*list*) Optional, axes size and location, including labels and margin. :param aspect: (*string*) ['equal' | 'auto'] or a number. If a number the ratio of x-unit/y-unit in screen-space. Default is 'auto'. :param bgcolor: (*Color*) Optional, axes background color. :param axis: (*boolean*) Optional, set all axis visible or not. Default is ``True`` . :param bottomaxis: (*boolean*) Optional, set bottom axis visible or not. Default is ``True`` . :param leftaxis: (*boolean*) Optional, set left axis visible or not. Default is ``True`` . :param topaxis: (*boolean*) Optional, set top axis visible or not. Default is ``True`` . :param rightaxis: (*boolean*) Optional, set right axis visible or not. Default is ``True`` . :param xaxistype: (*string*) Optional, set x axis type as 'normal', 'lon', 'lat' or 'time'. :param xreverse: (*boolean*) Optional, set x axis reverse or not. Default is ``False`` . :param yreverse: (*boolean*) Optional, set yaxis reverse or not. Default is ``False`` . :returns: The axes. ''' axestype = kwargs.pop('axestype', 'cartesian') polar = kwargs.pop('polar', False) if polar: axestype = 'polar' kwargs['figure'] = self if axestype == 'polar': ax = PolarAxes(*args, **kwargs) #self.__set_axes(ax, **kwargs) elif axestype == 'map': ax = MapAxes(*args, **kwargs) #self.__set_axesm(ax, **kwargs) elif axestype == '3d': ax = Axes3D(*args, **kwargs) #self.__set_axes3d(ax, **kwargs) else: ax = Axes(*args, **kwargs) #self.__set_axes(ax, **kwargs) #self.__set_axes_common(ax, *args, **kwargs) return ax
def __init__(self, x, y, r, **kwargs): self.x = x self.y = y self.r = r # properties self.color = kwargs.get('color', None) self.line_style = kwargs.get('line_style', None) self.line_width = kwargs.get('line_width', None) # custom plot options self.pgf_options = kwargs.get('pgf_options', []) # catch common mistakes if not isinstance(self.pgf_options, list): raise TypeError('pgf_options should be a list.') # add rectangle to axes self.axes = kwargs.get('axes', Axes.gca()) self.axes.children.append(self)
def __init__(self, x, y, dx, dy, **kwargs): self.x = x self.y = y self.dx = dx self.dy = dy # properties self.color = kwargs.get('color', None) self.arrow_style = kwargs.get('arrow_style', '-latex') self.line_style = kwargs.get('line_style', None) # custom plot options self.pgf_options = kwargs.get('pgf_options', []) # catch common mistakes if not isinstance(self.pgf_options, list): raise TypeError('pgf_options should be a list.') # add arrow to axes self.axes = kwargs.get('axis', Axes.gca()) self.axes.children.append(self)
def __create_axes(self, *args, **kwargs): """ Create an axes. :param position: (*list*) Optional, axes position specified by *position=* [left, bottom, width height] in normalized (0, 1) units. Default is [0.13, 0.11, 0.775, 0.815]. :param outerposition: (*list*) Optional, axes size and location, including labels and margin. :returns: The axes. """ if len(args) > 0: position = args[0] else: position = kwargs.pop('position', None) outerposition = kwargs.pop('outerposition', None) axestype = kwargs.pop('axestype', 'cartesian') polar = kwargs.pop('polar', False) if polar: axestype = 'polar' if axestype == 'polar': ax = PolarAxes() elif axestype == 'map': ax = MapAxes() elif axestype == '3d': ax = Axes3D() else: ax = Axes() if position is None: position = [0.13, 0.11, 0.775, 0.815] ax.active_outerposition(True) else: ax.active_outerposition(False) ax.set_position(position) if not outerposition is None: ax.set_outerposition(outerposition) ax.active_outerposition(True) return ax
def __init__(self, *args, **kwargs): # data points if len(args) < 1: self.xvalues = asarray([]) self.yvalues = asarray([]) elif len(args) < 2: self.yvalues = asarray(args[0]).reshape(shape(args[0])[0], -1) self.xvalues = arange(1, self.yvalues.shape[-1] + 1) else: self.xvalues = asarray(args[0]).flatten() self.yvalues = asarray(args[1]).reshape(shape(args[1])[0], -1) self.box_width = kwargs.get('box_width', 0.5) # custom plot options self.pgf_options = kwargs.get('pgf_options', []) # catch common mistakes if not isinstance(self.pgf_options, list): raise TypeError('pgf_options should be a list.') # add plot to axes self.axes = kwargs.get('axes', Axes.gca()) self.axes.children.append(self)
def __init__(self, *args, **kwargs): # data points if len(args) < 1: self.xvalues = asarray([]) self.yvalues = asarray([]) elif len(args) < 2: self.yvalues = asarray(args[0]).reshape(shape(args[0])[0], -1) self.xvalues = arange(1, self.yvalues.shape[-1] + 1) else: self.xvalues = asarray(args[0]).flatten() self.yvalues = asarray(args[1]).reshape(shape(args[1])[0], -1) self.box_width = kwargs.get('box_width', 0.5); # custom plot options self.pgf_options = kwargs.get('pgf_options', []) # catch common mistakes if not isinstance(self.pgf_options, list): raise TypeError('pgf_options should be a list.') # add plot to axes self.axes = kwargs.get('axis', Axes.gca()) self.axes.children.append(self)
def _take_broadcast(a, indices): """ broadcast array-indices & integers, numpy's classical Examples: --------- >>> a = da.zeros(shape=(3,4,5,6)) >>> a[:,[0, 1],:,2].shape (2, 3, 5) >>> a[:,[0, 1],2,:].shape (3, 2, 6) """ # new values newval = a.values[indices] # if the new values is a scalar, then just return it if np.isscalar(newval): return newval # new axes: broacast indices (should do the same as above, since integers are just broadcast) indices2 = broadcast_indices(indices) # assert np.all(newval == a.values[indices2]) # make a multi-axis with tuples is_array2 = np.array([np.iterable(ix) for ix in indices2]) nb_array2 = is_array2.sum() # If none or one array is present, easy if nb_array2 <= 1: newaxes = [ a.axes[i][ix] for i, ix in enumerate(indices) if not np.isscalar(ix) ] # indices or indices2, does not matter # else, finer check needed else: # same stats but on original indices is_array = np.array([np.iterable(ix) for ix in indices]) array_ix_pos = np.where(is_array)[0] # Determine where the axis will be inserted # - need to consider the integers as well (broadcast as arrays) # - if two indexed dimensions are not contiguous, new axis placed at first position... # a = zeros((3,4,5,6)) # a[:,[1,2],:,0].shape ==> (2, 3, 5) # a[:,[1,2],0,:].shape ==> (3, 2, 6) array_ix_pos2 = np.where(is_array2)[0] if np.any(np.diff(array_ix_pos2) > 1): # that mean, if two indexed dimensions are not contiguous insert = 0 else: insert = array_ix_pos2[0] # Now determine axis value # ...if originally only one array was provided, use these values correspondingly if len(array_ix_pos) == 1: i = array_ix_pos[0] values = a.axes[i].values[indices[i]] name = a.axes[i].name # ...else use a list of tuples else: values = zip(*[a.axes[i].values[indices2[i]] for i in array_ix_pos]) name = ",".join([a.axes[i].name for i in array_ix_pos]) broadcastaxis = Axis(values, name) newaxes = Axes() for i, ax in enumerate(a.axes): # axis is already part of the broadcast axis: skip if is_array2[i]: continue else: newaxis = ax[indices2[i]] ## do not append axis if scalar # if np.isscalar(newaxis): # continue newaxes.append(newaxis) # insert the right new axis at the appropriate position newaxes.insert(insert, broadcastaxis) return a._constructor(newval, newaxes, **a._metadata)
def text3D(self, x,y,z,s, *args, **kwargs): text = Axes.text(self,x,y,s,*args,**kwargs) art3d.wrap_text(text,z) return text
def clabel(self, *args, **kwargs): r = Axes.clabel(self, *args, **kwargs) return r
def __init__(self, *args, **kwargs): """ Initializes plot properties. """ # data points if len(args) < 1: self.xvalues = asarray([]) self.yvalues = asarray([]) elif len(args) < 2: self.yvalues = asarray(args[0]).flatten() self.xvalues = arange(1, len(self.yvalues) + 1) else: self.xvalues = asarray(args[0]).flatten() self.yvalues = asarray(args[1]).flatten() # labels for each data point self.labels = kwargs.get('labels', None) if isinstance(self.labels, str): self.labels = [self.labels] if self.labels and len(self.labels) != len(self.xvalues): raise ValueError('The number of labels should correspond to the number of data points.') # line style self.line_style = kwargs.get('line_style', None) self.line_width = kwargs.get('line_width', None) self.opacity = kwargs.get('opacity', None) self.color = kwargs.get('color', None) self.fill = kwargs.get('fill', False) # marker style self.marker = kwargs.get('marker', None) self.marker_size = kwargs.get('marker_size', None) self.marker_edge_color = kwargs.get('marker_edge_color', None) self.marker_face_color = kwargs.get('marker_face_color', None) self.marker_opacity = kwargs.get('marker_opacity', None) # error bars self.xvalues_error = asarray(kwargs.get('xvalues_error', [])).flatten() self.yvalues_error = asarray(kwargs.get('yvalues_error', [])).flatten() self.error_marker = kwargs.get('error_marker', None) self.error_color = kwargs.get('error_color', None) self.error_style = kwargs.get('error_style', None) self.error_width = kwargs.get('error_width', None) # PGF pattern to fill area and bar plots self.pattern = kwargs.get('pattern', None) # comb (or stem) plots self.ycomb = kwargs.get('ycomb', False) self.xcomb = kwargs.get('xcomb', False) self.closed = kwargs.get('closed', False) self.const_plot = kwargs.get('const_plot', False) # legend entry for this plot self.legend_entry = kwargs.get('legend_entry', None) # custom plot options self.pgf_options = kwargs.get('pgf_options', []) # catch common mistakes if not isinstance(self.pgf_options, list): raise TypeError('pgf_options should be a list.') # comment LaTeX code self.comment = kwargs.get('comment', '') # add plot to axes self.axes = kwargs.get('axes', Axes.gca()) self.axes.children.append(self)
if (unit_1 != unit_2): return NotImplemented return units[0] def multiplication_rule(self, units): non_null = [u for u in units if u] if (len(non_null) > 1): return NotImplemented return non_null[0] op_dict = { '__mul__': multiplication_rule, '__rmul__': multiplication_rule, '__add__': addition_rule, '__radd__': addition_rule, '__sub__': addition_rule, '__rsub__': addition_rule, } def __call__(self, operation, units): if (operation not in self.op_dict): return NotImplemented return self.op_dict[operation](self, units) unit_resolver = UnitResolver() Axes.set_default_unit_to_locator_map(lambda u: u.get_tick_locators()) Axes.set_default_unit_to_formatter_map(lambda u: u.get_tick_formatters())
class LatticeDesigner(wx.Frame): title = "Lattice Designer" configs = {} def __init__(self, parent): wx.Frame.__init__(self, None, -1, self.title) # Allow OS X users to close the window with Cmd+Q menubar = wx.MenuBar() self.SetMenuBar(menubar) self.atoms_file = self.data_files = False self.Show() self.Maximize(True) self.drawSidebar() def drawSidebar(self): layout = wx.BoxSizer(wx.HORIZONTAL) tabs = wx.Notebook(self) self.designSidebarPanel = scrolled.ScrolledPanel(tabs) self.designSidebar = wx.BoxSizer(wx.VERTICAL) self.content = content = wx.BoxSizer(wx.VERTICAL) self.grid = BitMapGrid(self) self.canvas = AtomsCanvas(self) #Grid size self.sizeBox = wx.StaticBox(self.designSidebarPanel, label='Grid size') self.sizeBoxSizer = wx.StaticBoxSizer(self.sizeBox, wx.VERTICAL) self.sizeBoxGrid = wx.GridSizer(1, 4, 10, 10) self.sizeBoxWidthLabel = wx.StaticText(self.designSidebarPanel, label="Width") self.sizeBoxWidthCtrl = wx.SpinCtrl(self.designSidebarPanel, value=str(self.grid.cols), initial=self.grid.cols, min=0, size=(50, 20)) self.sizeBoxHeightLabel = wx.StaticText(self.designSidebarPanel, label="Height") self.sizeBoxHeightCtrl = wx.SpinCtrl(self.designSidebarPanel, value=str(self.grid.rows), initial=self.grid.rows, min=0, size=(50, 20)) self.sizeBoxGrid.AddMany([ (self.sizeBoxWidthLabel, 0, wx.EXPAND), (self.sizeBoxWidthCtrl, 0, wx.EXPAND), (self.sizeBoxHeightLabel, 0, wx.EXPAND), (self.sizeBoxHeightCtrl, 0, wx.EXPAND) ]) self.sizeBoxWidthCtrl.Bind(wx.EVT_SPINCTRL, self.updateGridSize) self.sizeBoxHeightCtrl.Bind(wx.EVT_SPINCTRL, self.updateGridSize) self.sizeBoxSizer.Add(self.sizeBoxGrid) #Object parameters self.configBox = wx.StaticBox(self.designSidebarPanel, label='Object parameters') self.configBoxSizer = wx.StaticBoxSizer(self.configBox, wx.VERTICAL) self.configBoxGrid = wx.GridSizer(10, 2, 5, 5) # Number of layers self.configBoxLayersLabel = wx.StaticText(self.designSidebarPanel, label="Layers", size=(70,20)) self.configBoxLayersCtrl = wx.SpinCtrl(self.designSidebarPanel, value="3", initial=10, min=1, size=(50, 20)) # Avoid bug on OS X that auto-focus on first field and hides the default value wx.CallAfter(self.configBoxLayersCtrl.SetFocus) self.configBoxLayersCtrl.Bind(wx.EVT_SPINCTRL, self.updateParametersProxy) # Type of structure self.configBoxCellTypeLabel = wx.StaticText(self.designSidebarPanel, label="Structure") self.configBoxCellTypeSCRadio = wx.RadioButton(self.designSidebarPanel, label='SC', style=wx.RB_GROUP) self.configBoxCellTypeBCCRadio = wx.RadioButton(self.designSidebarPanel, label='BCC') self.configBoxCellTypeFCCRadio = wx.RadioButton(self.designSidebarPanel, label='FCC') self.configBoxCellTypeSCRadio.SetValue(True) self.type = "SC" self.configs['type'] = self.type self.configBoxCellTypeSCRadio.Bind(wx.EVT_RADIOBUTTON, self.updateType) self.configBoxCellTypeBCCRadio.Bind(wx.EVT_RADIOBUTTON, self.updateType) self.configBoxCellTypeFCCRadio.Bind(wx.EVT_RADIOBUTTON, self.updateType) # Net constant self.configBoxNetConstantLabel = wx.StaticText(self.designSidebarPanel, label="Lattice constant") self.configBoxNetConstantCtrl = FS.FloatSpin(self.designSidebarPanel, -1, min_val=0, increment=0.1, value=0.28, agwStyle=FS.FS_LEFT) self.configBoxNetConstantCtrl.SetFormat("%f") self.configBoxNetConstantCtrl.SetDigits(5) self.configBoxNetConstantCtrl.Bind(FS.EVT_FLOATSPIN, self.updateParametersProxy) # Size self.configBoxHeightLabel = wx.StaticText(self.designSidebarPanel, label="Height (nm)", size=(70, 20)) self.configBoxHeightCtrl = FS.FloatSpin(self.designSidebarPanel, -1, min_val=0.1, increment=0.1, value=10, agwStyle=FS.FS_LEFT) self.configBoxHeightCtrl.SetFormat("%f") self.configBoxHeightCtrl.SetDigits(2) self.configBoxHeightCtrl.Bind(FS.EVT_FLOATSPIN, self.updateParametersProxy) # Sizes self.configBoxWidthLabel = wx.StaticText(self.designSidebarPanel, label="Width (nm)", size=(70, 20)) self.configBoxWidthValue = wx.StaticText(self.designSidebarPanel, label="--", size=(70, 20)) self.configBoxLengthLabel = wx.StaticText(self.designSidebarPanel, label="Length (nm)", size=(70, 20)) self.configBoxLengthValue = wx.StaticText(self.designSidebarPanel, label="--", size=(70, 20)) # Scaling self.configBoxEtaLabel = wx.StaticText(self.designSidebarPanel, label="Eta", size=(70, 20)) self.configBoxEtaCtrl = FS.FloatSpin(self.designSidebarPanel, -1, min_val=0, increment=0.1, value=0.55, agwStyle=FS.FS_LEFT) self.configBoxEtaCtrl.SetFormat("%f") self.configBoxEtaCtrl.SetDigits(5) self.configBoxEtaCtrl.Bind(FS.EVT_FLOATSPIN, self.updateParametersProxy) self.configBoxXLabel = wx.StaticText(self.designSidebarPanel, label="X", size=(70, 20)) self.configBoxXValue = wx.StaticText(self.designSidebarPanel, label="--", size=(50, 20)) self.configBoxGrid.AddMany([ (self.configBoxLayersLabel, 0, wx.EXPAND), (self.configBoxLayersCtrl, 0, wx.EXPAND), (self.configBoxCellTypeLabel, 0, wx.EXPAND), (self.configBoxCellTypeSCRadio, 0, wx.EXPAND), (wx.StaticText(self, -1, ''), 0, wx.EXPAND), #Blank space (self.configBoxCellTypeBCCRadio, 0, wx.EXPAND), (wx.StaticText(self, -1, ''), 0, wx.EXPAND), #Blank space (self.configBoxCellTypeFCCRadio, 0, wx.EXPAND), (self.configBoxNetConstantLabel, 0, wx.EXPAND), (self.configBoxNetConstantCtrl, 0, wx.EXPAND), (self.configBoxHeightLabel, 0, wx.EXPAND), (self.configBoxHeightCtrl, 0, wx.EXPAND), (self.configBoxWidthLabel, 0, wx.EXPAND), (self.configBoxWidthValue, 0, wx.EXPAND), (self.configBoxLengthLabel, 0, wx.EXPAND), (self.configBoxLengthValue, 0, wx.EXPAND), (self.configBoxEtaLabel, 0, wx.EXPAND), (self.configBoxEtaCtrl, 0, wx.EXPAND), (self.configBoxXLabel, 0, wx.EXPAND), (self.configBoxXValue, 0, wx.EXPAND) ]) self.configBoxSizer.Add(self.configBoxGrid) # Figures self.figuresBox = wx.StaticBox(self.designSidebarPanel, label='Figures') self.figuresBoxSizer = wx.StaticBoxSizer(self.figuresBox, wx.VERTICAL) self.figuresBoxGrid = wx.FlexGridSizer(2, 1, 10, 10) # Quadrilateral self.figuresQuadPane = wx.CollapsiblePane(self.designSidebarPanel, label="Quadrilateral", style=wx.CP_DEFAULT_STYLE|wx.CP_NO_TLW_RESIZE) self.figuresQuadPane.Bind(wx.EVT_COLLAPSIBLEPANE_CHANGED, self.quadToggled) self.figuresQuadSizer = wx.GridSizer(1, 4, 10, 10) self.figuresQuadPaneWin = self.figuresQuadPane.GetPane() self.figuresQuadWidthLabel = wx.StaticText(self.figuresQuadPaneWin, label="Width") self.figuresQuadWidthCtrl = wx.SpinCtrl(self.figuresQuadPaneWin, value="1", initial=1, min=1, size=(50,20)) self.figuresQuadHeightLabel = wx.StaticText(self.figuresQuadPaneWin, label="Height") self.figuresQuadHeightCtrl = wx.SpinCtrl(self.figuresQuadPaneWin, value="1", initial=1, min=1, size=(50,20)) self.figuresQuadSizer.AddMany([ (self.figuresQuadWidthLabel, 0, wx.EXPAND), (self.figuresQuadWidthCtrl, 0, wx.EXPAND), (self.figuresQuadHeightLabel, 0, wx.EXPAND), (self.figuresQuadHeightCtrl, 0, wx.EXPAND) ]) self.figuresQuadPaneWin.SetSizer(self.figuresQuadSizer) # Circle self.figuresCirclePane = wx.CollapsiblePane(self.designSidebarPanel, label="Circle", style=wx.CP_DEFAULT_STYLE|wx.CP_NO_TLW_RESIZE) self.figuresCirclePane.Bind(wx.EVT_COLLAPSIBLEPANE_CHANGED, self.circleToggled) self.figuresCircleSizer = wx.GridSizer(2, 2, 10, 10) self.figuresCirclePaneWin = self.figuresCirclePane.GetPane() self.figuresCircleRadiusLabel = wx.StaticText(self.figuresCirclePaneWin, label="Radius") self.figuresCircleRadiusCtrl = wx.SpinCtrl(self.figuresCirclePaneWin, value="1", initial=1, min=1, size=(50,20)) self.figuresCircleRadiusCtrl.Bind(wx.EVT_SPINCTRL, self.updateCircleWidth) self.figuresCircleWidthLabel = wx.StaticText(self.figuresCirclePaneWin, label="Width (nm)") self.figuresCircleWidthValue = wx.StaticText(self.figuresCirclePaneWin, label="--") self.figuresCircleSizer.AddMany([ (self.figuresCircleRadiusLabel, 0, wx.EXPAND), (self.figuresCircleRadiusCtrl, 0, wx.EXPAND), (self.figuresCircleWidthLabel, 0, wx.EXPAND), (self.figuresCircleWidthValue, 0, wx.EXPAND) ]) self.figuresCirclePaneWin.SetSizer(self.figuresCircleSizer) self.figuresBoxGrid.AddMany([ (self.figuresQuadPane, 0, wx.EXPAND), (self.figuresCirclePane, 0, wx.EXPAND) ]) self.figuresBoxSizer.Add(self.figuresBoxGrid) self.clearButton = wx.Button(self.designSidebarPanel, label="Clear grid") self.clearButton.Bind(wx.EVT_BUTTON, self.clearGrid) self.exportFileButton = wx.Button(self.designSidebarPanel, label="Export Data") self.exportFileButton.Bind(wx.EVT_BUTTON, self.checkParametersTrigger) self.exportImagesButtonD = wx.Button(self.designSidebarPanel, label="Export Images") self.exportImagesButtonD.Bind(wx.EVT_BUTTON, self.exportImagesD) self.exportImagesButtonD.Show(False) self.previewButton = wx.Button(self.designSidebarPanel, label="Show/hide preview") self.previewButton.Bind(wx.EVT_BUTTON, self.togglePreview) self.axesBoxD = wx.StaticBox(self.designSidebarPanel, label='Axes') self.axesBoxSizerD = wx.StaticBoxSizer(self.axesBoxD, wx.VERTICAL) self.axesD = Axes(self.designSidebarPanel) self.axesBoxSizerD.Add(self.axesD) self.designSidebar.Add(self.sizeBoxSizer, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.configBoxSizer, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.figuresBoxSizer, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.clearButton, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.exportFileButton, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.exportImagesButtonD, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.previewButton, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.axesBoxSizerD, 0, wx.EXPAND | wx.ALL, 5) self.designSidebarPanel.SetSizer(self.designSidebar) wx.CallAfter(self.axesBoxD.Show, False) wx.CallAfter(self.axesD.Show, False) self.visualizationSidebarPanel = scrolled.ScrolledPanel(tabs) visualizationSidebar = wx.BoxSizer(wx.VERTICAL) inputDirBtn = wx.Button(self.visualizationSidebarPanel, -1, "Select Atoms file") self.Bind(wx.EVT_BUTTON, self.openFileDialog, inputDirBtn) self.statsBox = wx.StaticBox(self.visualizationSidebarPanel, label='Input Stats') self.statsSizer = wx.StaticBoxSizer(self.statsBox, wx.VERTICAL) self.statsGrid = wx.GridSizer(2, 2, 5, 5) self.statsValidPathLabel = wx.StaticText(self.visualizationSidebarPanel, label="Valid Atom file") self.statsValidPathValue = wx.StaticText(self.visualizationSidebarPanel, label="--") self.statsNumberDataFilesLabel = wx.StaticText(self.visualizationSidebarPanel, label="# of Data files") self.statsNumberDataFilesValue = wx.StaticText(self.visualizationSidebarPanel, label="--") self.statsGrid.AddMany([ (self.statsValidPathLabel, 0, wx.EXPAND), (self.statsValidPathValue, 0, wx.EXPAND), (self.statsNumberDataFilesLabel, 0, wx.EXPAND), (self.statsNumberDataFilesValue, 0, wx.EXPAND) ]) self.statsSizer.Add(self.statsGrid) self.readInputBtn = wx.Button(self.visualizationSidebarPanel, label="Read Input files") # Enable only if we have a valid directory self.readInputBtn.Enable(False) self.readInputBtn.Bind(wx.EVT_BUTTON, self.readInputFiles) viewModeBox = wx.StaticBox(self.visualizationSidebarPanel, label='View layer') self.viewModeSizer = wx.StaticBoxSizer(viewModeBox, wx.VERTICAL) viewModeGrid = wx.FlexGridSizer(2, 4, 5, 5) self.viewModeAllLayers = wx.RadioButton(self.visualizationSidebarPanel, label='All', style=wx.RB_GROUP) self.viewModeLayerX = wx.RadioButton(self.visualizationSidebarPanel, label='X') self.viewLayerX = wx.ComboBox(self.visualizationSidebarPanel, choices=["0.000"], style=wx.CB_DROPDOWN|wx.CB_READONLY, size=(60, 27)) self.viewModeLayerY = wx.RadioButton(self.visualizationSidebarPanel, label='Y') self.viewLayerY = wx.ComboBox(self.visualizationSidebarPanel, choices=["0.000"], style=wx.CB_DROPDOWN|wx.CB_READONLY, size=(60, 27)) self.viewModeLayerZ = wx.RadioButton(self.visualizationSidebarPanel, label='Z') self.viewLayerZ = wx.ComboBox(self.visualizationSidebarPanel, choices=["0.000"], style=wx.CB_DROPDOWN|wx.CB_READONLY, size=(60, 27)) self.viewModeAllLayers.SetValue(True) self.viewModeAllLayers.Enable(False) self.viewModeLayerX.Enable(False) self.viewModeLayerY.Enable(False) self.viewModeLayerZ.Enable(False) self.viewLayerX.Enable(False) self.viewLayerY.Enable(False) self.viewLayerZ.Enable(False) self.viewModeAllLayers.Bind(wx.EVT_RADIOBUTTON, self.updateViewMode) self.viewModeLayerX.Bind(wx.EVT_RADIOBUTTON, self.updateViewMode) self.viewModeLayerY.Bind(wx.EVT_RADIOBUTTON, self.updateViewMode) self.viewModeLayerZ.Bind(wx.EVT_RADIOBUTTON, self.updateViewMode) self.viewLayerX.Bind(wx.EVT_COMBOBOX, self.updateViewMode) self.viewLayerY.Bind(wx.EVT_COMBOBOX, self.updateViewMode) self.viewLayerZ.Bind(wx.EVT_COMBOBOX, self.updateViewMode) viewModeGrid.AddMany([ (self.viewModeAllLayers, 0, wx.EXPAND), (self.viewModeLayerX, 0, wx.EXPAND), (self.viewModeLayerY, 0, wx.EXPAND), (self.viewModeLayerZ, 0, wx.EXPAND), ((1,1)), #Blank space (self.viewLayerX, 0, wx.EXPAND), (self.viewLayerY, 0, wx.EXPAND), (self.viewLayerZ, 0, wx.EXPAND) ]) self.viewModeSizer.Add(viewModeGrid, flag=wx.ALL, border=1) self.exportImagesButtonV = wx.Button(self.visualizationSidebarPanel, label="Export Images") self.exportImagesButtonV.Bind(wx.EVT_BUTTON, self.exportImagesV) self.exportImagesButtonV.Show(False) self.exportVideoButton = wx.Button(self.visualizationSidebarPanel, label="Export Video") self.exportVideoButton.Bind(wx.EVT_BUTTON, self.exportVideo) self.exportVideoButton.Show(False) controlsBox = wx.StaticBox(self.visualizationSidebarPanel, label='Controls') self.controlsSizer = wx.StaticBoxSizer(controlsBox, wx.VERTICAL) controlsGrid = wx.FlexGridSizer(1, 6, 5, 5) self.playBitmap = wx.Bitmap("images/play.png", wx.BITMAP_TYPE_ANY) self.stopBitmap = wx.Bitmap("images/pause.png", wx.BITMAP_TYPE_ANY) self.backBitmap = wx.Bitmap("images/back.png", wx.BITMAP_TYPE_ANY) self.forwardBitmap = wx.Bitmap("images/forward.png", wx.BITMAP_TYPE_ANY) self.previousBitmap = wx.Bitmap("images/previous.png", wx.BITMAP_TYPE_ANY) self.nextBitmap = wx.Bitmap("images/next.png", wx.BITMAP_TYPE_ANY) self.backBtn = wx.BitmapButton(self.visualizationSidebarPanel, -1, self.backBitmap, (0,0), ((30,30))) self.previousBtn = wx.BitmapButton(self.visualizationSidebarPanel, -1, self.previousBitmap, (0,0), ((30,30))) self.playStopBtn = wx.BitmapButton(self.visualizationSidebarPanel, -1, self.playBitmap, (0,0), ((30,30))) self.nextBtn = wx.BitmapButton(self.visualizationSidebarPanel, -1, self.nextBitmap, (0,0), ((30,30))) self.forwardBtn = wx.BitmapButton(self.visualizationSidebarPanel, -1, self.forwardBitmap, (0,0), ((30,30))) self.previousBtn.Bind(wx.EVT_BUTTON, self.previousT) self.backBtn.Bind(wx.EVT_BUTTON, self.backT) self.playStopBtn.Bind(wx.EVT_BUTTON, self.playStop) self.forwardBtn.Bind(wx.EVT_BUTTON, self.forwardT) self.nextBtn.Bind(wx.EVT_BUTTON, self.nextT) self.backBtn.Enable(False) self.previousBtn.Enable(False) self.playStopBtn.Enable(False) self.forwardBtn.Enable(False) self.nextBtn.Enable(False) self.currentTCtrl = wx.TextCtrl(self.visualizationSidebarPanel, value="0", style=wx.TE_CENTRE, size=(70, 10)) font = wx.Font(18, wx.SWISS, wx.NORMAL, wx.NORMAL) self.currentTCtrl.SetFont(font) self.currentTCtrl.Enable(False) self.currentTCtrl.Bind(wx.EVT_TEXT, self.startCurrentTTimer) self.currentTTimer = wx.Timer(self) self.Bind(wx.EVT_TIMER, self.setCurrentT, self.currentTTimer) controlsGrid.AddMany([ (self.backBtn, 0, wx.EXPAND), (self.previousBtn, 0, wx.EXPAND), (self.playStopBtn, 0, wx.EXPAND), (self.nextBtn, 0, wx.EXPAND), (self.forwardBtn, 0, wx.EXPAND), (self.currentTCtrl, 0, wx.EXPAND) ]) self.controlsSizer.Add(controlsGrid) axesBoxV = wx.StaticBox(self.visualizationSidebarPanel, label='Axes') axesBoxSizerV = wx.StaticBoxSizer(axesBoxV, wx.VERTICAL) self.axesV = Axes(self.visualizationSidebarPanel) axesBoxSizerV.Add(self.axesV) self.plotBox = wx.StaticBox(self.visualizationSidebarPanel, label='Plot') plotSizer = wx.StaticBoxSizer(self.plotBox, wx.VERTICAL) self.plotter = plot.PlotCanvas(self.visualizationSidebarPanel) self.plotter.SetInitialSize(size=(220, 220)) plotSizer.Add(self.plotter) self.plotBox.Show(False) self.plotter.Show(False) visualizationSidebar.AddMany([ (inputDirBtn, 0, wx.EXPAND | wx.ALL, 5), (self.statsSizer, 0, wx.EXPAND | wx.ALL, 5), (self.readInputBtn, 0, wx.EXPAND | wx.ALL, 5), (self.controlsSizer, 0, wx.EXPAND | wx.ALL, 5), (self.viewModeSizer, 0, wx.EXPAND | wx.ALL, 5), (self.exportImagesButtonV, 0, wx.EXPAND | wx.ALL, 5), (self.exportVideoButton, 0, wx.EXPAND | wx.ALL, 5), (axesBoxSizerV, 0, wx.EXPAND | wx.ALL, 5), (plotSizer, 0, wx.EXPAND | wx.ALL, 5) ]) self.visualizationSidebarPanel.SetSizer(visualizationSidebar) self.viewModeSizer.ShowItems(False) self.controlsSizer.ShowItems(False) tabs.AddPage(self.designSidebarPanel, "Design") tabs.AddPage(self.visualizationSidebarPanel, "Visualization") tabs.Bind(wx.EVT_NOTEBOOK_PAGE_CHANGED, self.OnPageChanged) content.Add(self.grid, 1, wx.EXPAND) content.Add(self.canvas, 1, wx.EXPAND) self.grid.Show() self.canvas.Hide() self.togglePreviewStatus = 0 layout.Add(tabs, 0, wx.EXPAND) layout.Add(content, 1, wx.EXPAND) self.designSidebarPanel.SetupScrolling(scroll_x=False) self.visualizationSidebarPanel.SetupScrolling(scroll_x=False) self.SetSizer(layout) self.Layout() self.Refresh() self.grid.updateSize() self.updateParameters() def validateAtomsFile(self): line_number = 0 valid_first_line = re.compile("[0-9]+\t[0-9]+\t[0-9]+\t[0-9]+(\.[0-9+])*") valid_n_line = re.compile("[0-9]+(\t\-?[0-9]+(\.[0-9]+)*){3}(\t[0-9]+){2,}") valid = False f = open(self.atoms_file, "r") for line in f: # Verify we have at least 1 line if line_number == 0: valid = True if line_number == 0 and valid_first_line.match(line) == None: valid = False break if line_number > 0 and valid_n_line.match(line) == None: valid = False break line_number += 1 f.close() if valid: error = False self.statsValidPathValue.SetLabel("Yes") os.chdir(os.path.dirname(self.atoms_file)) data_files = glob.glob("*_*_*.dat") if(len(data_files)): self.data_files = data_files self.statsNumberDataFilesValue.SetLabel(str(len(data_files))) self.readInputBtn.Enable(True) else: error = 'No data files' else: error = 'Path does not exist' self.statsValidPathValue.SetLabel("No") if error: self.atoms_file = self.data_files = False # print "Invalid directory: %s" % error def readInputFiles(self, evt): atoms = {} dataset = {} x_param = 0 f = open(self.atoms_file, "r") first_line = True for line in f: line = line.replace("\n", "").split("\t") if first_line: x_param = float(line[3]) else: # We get the first 4 elements from the line atom_id = int(line.pop(0)) atom_x = float(line.pop(0)) atom_y = float(line.pop(0)) atom_z = float(line.pop(0)) atoms[atom_id] = (atom_x, atom_y, atom_z) first_line = False f.close() regex = re.compile(".*_([0-9]*)_.*.dat") self.max_Mx = 0 self.max_My = 0 self.max_Mz = 0 for data_file in self.data_files: data_at_t = { 'intensity': 0, 'Mx': 0, 'My': 0, 'Mz': 0, 'atoms': {} } direction = 'x' find_t = regex.search(data_file) if find_t: t = find_t.group(1) f = open(data_file) first_line = True for line in f: line = line.replace("\n", "").split("\t") try: atom_id = int(line.pop(0)) vector_x = float(line.pop(0)) vector_y = float(line.pop(0)) vector_z = float(line.pop(0)) data_at_t['Mx'] += vector_x data_at_t['My'] += vector_y data_at_t['Mz'] += vector_z data_at_t['atoms'][atom_id] = (vector_x, vector_y, vector_z) if first_line: data_at_t['intensity'] = float(line.pop(0)) except: pass first_line = False if data_at_t['Mx'] > self.max_Mx: self.max_Mx = data_at_t['Mx'] if data_at_t['My'] > self.max_My: self.max_My = data_at_t['My'] if data_at_t['Mz'] > self.max_Mz: self.max_Mz = data_at_t['Mz'] dataset[int(t)] = data_at_t f.close() first_t = None for t, data in dataset.iteritems(): if first_t == None or t < first_t: first_t = t if self.max_Mx: dataset[t]['Mx'] = (dataset[t]['Mx'] + 0.0) / self.max_Mx if self.max_My: dataset[t]['My'] = (dataset[t]['My'] + 0.0) / self.max_My if self.max_Mz: dataset[t]['Mz'] = (dataset[t]['Mz'] + 0.0) / self.max_Mz self.canvas.setDataset(atoms, dataset) self.setT(first_t) self.backBtn.Enable(True) self.previousBtn.Enable(True) self.playStopBtn.Enable(True) self.nextBtn.Enable(True) self.forwardBtn.Enable(True) self.viewModeAllLayers.Enable(True) self.viewModeLayerX.Enable(True) self.viewModeLayerY.Enable(True) self.viewModeLayerZ.Enable(True) self.currentTCtrl.Enable(True) self.readInputBtn.Show(False) self.exportImagesButtonV.Show(True) if _platform == "darwin": self.exportVideoButton.Show(True) self.statsBox.Show(False) self.statsValidPathLabel.Show(False) self.statsValidPathValue.Show(False) self.statsNumberDataFilesLabel.Show(False) self.statsNumberDataFilesValue.Show(False) self.viewModeSizer.ShowItems(True) self.controlsSizer.ShowItems(True) self.plotBox.Show(True) self.plotter.Show(True) self.designSidebarPanel.SetupScrolling(scroll_x=False) self.visualizationSidebarPanel.SetupScrolling(scroll_x=False) self.Layout() layersX = self.canvas.layersX.keys() layersX.sort() layersX = [str(x) for x in layersX] layersY = self.canvas.layersY.keys() layersY.sort() layersY = [str(x) for x in layersY] layersZ = self.canvas.layersZ.keys() layersZ.sort() layersZ = [str(x) for x in layersZ] self.viewLayerX.Clear() self.viewLayerX.AppendItems(layersX) self.viewLayerX.SetSelection(0) self.viewLayerY.Clear() self.viewLayerY.AppendItems(layersY) self.viewLayerY.SetSelection(0) self.viewLayerZ.Clear() self.viewLayerZ.AppendItems(layersZ) self.viewLayerZ.SetSelection(0) def exportImagesD(self, evt): if self.atoms_file: currentPath = os.path.dirname(self.atoms_file) dlg = wx.DirDialog(self, message="Choose a directory", style=wx.OPEN | wx.CHANGE_DIR ) exportDir = None if dlg.ShowModal() == wx.ID_OK: exportDir = dlg.GetPath() dlg.Destroy() if exportDir: os.chdir(exportDir) existingFiles = [] files = ['atoms.png', 'axes.png'] for f in files: if os.path.isfile(f): existingFiles.append(f) write = True if len(existingFiles): write = False dlg = wx.MessageDialog(self, 'The following files already exists on the directory:\n\n%s' % ('\n'.join(existingFiles)), 'Overwrite files', wx.OK | wx.CANCEL | wx.ICON_WARNING ) if dlg.ShowModal() == wx.ID_OK: write = True dlg.Destroy() if write: self.canvas.export('atoms.png') self.axesD.export('axes.png') dlg = wx.MessageDialog(self, 'The files were exported succesfully.', 'Files exported', wx.OK | wx.ICON_INFORMATION ) dlg.ShowModal() dlg.Destroy() if self.atoms_file: os.chdir(currentPath) def exportImagesV(self, evt): currentPath = os.path.dirname(self.atoms_file) dlg = wx.DirDialog(self, message="Choose a directory", style=wx.OPEN | wx.CHANGE_DIR ) exportDir = None if dlg.ShowModal() == wx.ID_OK: exportDir = dlg.GetPath() dlg.Destroy() if exportDir: os.chdir(exportDir) existingFiles = [] files = ['vectors.png', 'axes.png', 'plot.png'] for f in files: if os.path.isfile(f): existingFiles.append(f) write = True if len(existingFiles): write = False dlg = wx.MessageDialog(self, 'The following files already exists on the directory:\n\n%s' % ('\n'.join(existingFiles)), 'Overwrite files', wx.OK | wx.CANCEL | wx.ICON_WARNING ) if dlg.ShowModal() == wx.ID_OK: write = True dlg.Destroy() if write: self.canvas.export('vectors.png') self.axesV.export('axes.png') self.plotter.SaveFile('plot.png') dlg = wx.MessageDialog(self, 'The files were exported succesfully.', 'Files exported', wx.OK | wx.ICON_INFORMATION ) dlg.ShowModal() dlg.Destroy() os.chdir(currentPath) def exportVideo(self, evt): currentPath = os.path.dirname(self.atoms_file) dlg = wx.DirDialog(self, message="Choose a directory", style=wx.OPEN | wx.CHANGE_DIR ) exportDir = None if dlg.ShowModal() == wx.ID_OK: exportDir = dlg.GetPath() dlg.Destroy() if exportDir: os.chdir(exportDir) existingFiles = [] files = ['output.avi'] for f in files: if os.path.isfile(f): existingFiles.append(f) write = True if len(existingFiles): write = False dlg = wx.MessageDialog(self, 'The following files already exists on the directory:\n\n%s' % ('\n'.join(existingFiles)), 'Overwrite files', wx.OK | wx.CANCEL | wx.ICON_WARNING ) if dlg.ShowModal() == wx.ID_OK: write = True dlg.Destroy() if write: Ts = self.canvas.dataset.keys() Ts.sort() dlg = wx.ProgressDialog("Creating video", "", maximum = len(Ts), parent=self, style = 0 | wx.PD_APP_MODAL | wx.PD_CAN_ABORT #| wx.PD_CAN_SKIP #| wx.PD_ELAPSED_TIME | wx.PD_ESTIMATED_TIME | wx.PD_REMAINING_TIME #| wx.PD_AUTO_HIDE ) t = Ts.pop(0) self.currentTCtrl.ChangeValue(str(t)) self.canvas.currentT = t self.canvas.OnDraw() canvas_image = self.canvas.getCurrentImage() image = numpy.asarray(canvas_image) height, width, layers = image.shape fps = 15 capSize = (width,height) fourcc = cv2.cv.CV_FOURCC('m', 'p', '4', 'v') video = cv2.VideoWriter() success = video.open('output.avi',fourcc,fps,capSize,True) video.write(image) keepGoing = True count = 1 while len(Ts) and keepGoing: t = Ts.pop(0) count += 1 self.canvas.currentT = t self.canvas.OnDraw() canvas_image = self.canvas.getCurrentImage() image = numpy.asarray(canvas_image) video.write(image) if count%10 == 0: self.currentTCtrl.ChangeValue(str(t)) (keepGoing, skip) = dlg.Update(count) gc.collect() cv2.destroyAllWindows() video.release() dlg.Destroy() video = None os.chdir(os.path.dirname(self.atoms_file)) def plot(self, data, markerPoint, axis, max_y): line = plot.PolyLine(data, colour='red', width=1) marker = plot.PolyMarker([markerPoint]) # set up text, axis and draw gc = plot.PlotGraphics([line, marker], '', '', '') max_y = math.fabs(max_y) max_y += 0.5 self.plotter.Draw(gc, yAxis=(-1.5,1.5), xAxis=(-max_y,max_y)) def startCurrentTTimer(self, evt): self.currentTTimer.Start(500, wx.TIMER_ONE_SHOT) def validateNewT(self, t): t = int(t) if t not in self.canvas.dataset.keys(): t = self.canvas.currentT Ts = self.canvas.dataset.keys() Ts.sort() min_t = Ts[0] Ts.sort(reverse=True) max_t = Ts[0] if t > max_t: t = max_t if t < min_t: t = min_t self.setT(t) self.canvas.currentT = t self.canvas.OnDraw() def setCurrentT(self, evt): t = int(self.currentTCtrl.GetValue()) self.validateNewT(t) def previousT(self, evt): t = self.canvas.currentT - 1 Ts = self.canvas.dataset.keys() Ts.sort() min_t = Ts[0] if t < min_t: t = min_t if t > min_t: self.backBtn.Enable(True) self.previousBtn.Enable(True) self.validateNewT(t) def backT(self, evt): t = self.canvas.currentT - 50 Ts = self.canvas.dataset.keys() Ts.sort() min_t = Ts[0] if t < min_t: t = min_t if t > min_t: self.backBtn.Enable(True) self.previousBtn.Enable(True) self.validateNewT(t) def forwardT(self, evt): t = self.canvas.currentT + 50 Ts = self.canvas.dataset.keys() Ts.sort(reverse=True) max_t = Ts[0] if t > max_t: t = max_t if t < max_t: self.forwardBtn.Enable(True) self.nextBtn.Enable(True) self.validateNewT(t) def nextT(self, evt): t = self.canvas.currentT + 1 Ts = self.canvas.dataset.keys() Ts.sort(reverse=True) max_t = Ts[0] if t > max_t: t = max_t if t < max_t: self.forwardBtn.Enable(True) self.nextBtn.Enable(True) self.validateNewT(t) def setT(self, t): self.currentTCtrl.ChangeValue(str(t)) Ts = self.canvas.dataset.keys() Ts.sort() min_t = Ts[0] Ts.sort(reverse=True) max_t = Ts[0] if t == max_t: self.forwardBtn.Enable(False) self.nextBtn.Enable(False) if t == min_t: self.backBtn.Enable(False) self.previousBtn.Enable(False) plotData = self.canvas.plotData axis = self.canvas.colorDirection max_y = self.canvas.dataset[min_t]['intensity'] markerPoint = (self.canvas.dataset[t]['intensity'], self.canvas.dataset[t]['Mx']) if axis == 'y': markerPoint = (self.canvas.dataset[t]['intensity'], self.canvas.dataset[t]['My']) if axis == 'z': markerPoint = (self.canvas.dataset[t]['intensity'], self.canvas.dataset[t]['Mz']) self.plot(plotData, markerPoint, axis, max_y) def playStop(self, evt): if self.canvas.playStatus == 'stop': self.canvas.playStatus = 'play' self.playStopBtn.SetBitmapLabel(self.stopBitmap) self.currentTCtrl.Enable(False) self.backBtn.Enable(False) self.previousBtn.Enable(False) self.forwardBtn.Enable(False) self.nextBtn.Enable(False) self.canvas.play(True) else: self.canvas.playStatus = 'stop' self.currentTCtrl.Enable(True) self.backBtn.Enable(True) self.previousBtn.Enable(True) self.forwardBtn.Enable(True) self.nextBtn.Enable(True) self.playStopBtn.SetBitmapLabel(self.playBitmap) self.Layout() def openFileDialog(self, evt): self.statsValidPathValue.SetLabel("--") self.statsNumberDataFilesValue.SetLabel("--") self.statsGrid.ShowItems(True) self.readInputBtn.Enable(False) self.backBtn.Enable(False) self.previousBtn.Enable(False) self.playStopBtn.Enable(False) self.forwardBtn.Enable(False) self.nextBtn.Enable(False) self.viewModeAllLayers.Enable(False) self.viewModeLayerX.Enable(False) self.viewModeLayerY.Enable(False) self.viewModeLayerZ.Enable(False) self.readInputBtn.Show(True) self.exportImagesButtonV.Show(False) self.exportVideoButton.Show(False) self.statsBox.Show(True) self.statsValidPathLabel.Show(True) self.statsValidPathValue.Show(True) self.statsNumberDataFilesLabel.Show(True) self.statsNumberDataFilesValue.Show(True) self.viewModeSizer.ShowItems(False) self.controlsSizer.ShowItems(False) self.plotBox.Show(False) self.plotter.Show(False) self.Layout() self.canvas.playStatus = 'stop' self.playStopBtn.SetBitmapLabel(self.playBitmap) self.canvas.setDataset({}, {}) dlg = wx.FileDialog(self, message="Choose a file", style=wx.OPEN | wx.CHANGE_DIR ) if dlg.ShowModal() == wx.ID_OK: self.atoms_file = dlg.GetPath() wx.CallAfter(self.validateAtomsFile) dlg.Destroy() def OnPageChanged(self, evt): # 0 = Design # 1 = Visualization selection = evt.GetSelection() if selection == 0: self.canvas.Hide() self.grid.Show() self.togglePreviewStatus = 0 self.designSidebar.ShowItems(True) self.axesD.Show(False) self.axesBoxD.Show(False) self.sizeBoxSizer.ShowItems(True) self.exportImagesButtonD.Show(False) self.figuresBoxSizer.ShowItems(True) self.allowParameterInput(True) else: self.canvas.setAtoms({}, {}) self.canvas.restartPosition() wx.CallAfter(self.canvas.OnDraw) self.canvas.Show() self.grid.Hide() self.designSidebar.ShowItems(False) self.readInputBtn.Show(True) self.exportImagesButtonV.Show(False) self.exportVideoButton.Show(False) self.statsBox.Show(True) self.statsValidPathLabel.Show(True) self.statsValidPathValue.Show(True) self.statsNumberDataFilesLabel.Show(True) self.statsNumberDataFilesValue.Show(True) self.viewModeSizer.ShowItems(False) self.controlsSizer.ShowItems(False) self.plotBox.Show(False) self.plotter.Show(False) self.axesD.Show(True) self.axesBoxD.Show(True) self.togglePreviewStatus = 1 self.allowParameterInput(False) self.Layout() evt.Skip() def allowParameterInput(self, allow): inputs = [ self.sizeBoxWidthCtrl, self.sizeBoxHeightCtrl, self.configBoxLayersCtrl, self.configBoxCellTypeSCRadio, self.configBoxCellTypeBCCRadio, self.configBoxCellTypeFCCRadio, self.configBoxNetConstantCtrl, self.configBoxHeightCtrl, self.configBoxEtaCtrl, self.figuresQuadPane, self.figuresCirclePane, self.clearButton, ] for input in inputs: input.Enable(allow) def quadToggled(self, evt): self.Layout() if not evt.GetCollapsed(): self.grid.figure = 'quad' self.setFigure(self.figuresQuadPane) else: self.grid.figure = False def circleToggled(self, evt): self.Layout() if not evt.GetCollapsed(): self.grid.figure = 'circle' self.setFigure(self.figuresCirclePane) else: self.grid.figure = False def clearGrid(self, evt): self.grid.clearGrid() def setFigure(self, openedPane): panes = [self.figuresQuadPane, self.figuresCirclePane] for pane in panes: if not pane == openedPane: pane.Collapse() self.Layout() def updateCircleWidth(self, evt): radius = self.figuresCircleRadiusCtrl.GetValue() width = radius * self.a / (self.x ** self.eta) self.figuresCircleWidthValue.SetLabel(str(width)) def updateGridSize(self, evt): self.grid.cols = self.sizeBoxWidthCtrl.GetValue() self.grid.rows = self.sizeBoxHeightCtrl.GetValue() self.grid.updateSize() def updateType(self, evt): if self.configBoxCellTypeSCRadio.GetValue(): self.type = "SC" if self.configBoxCellTypeBCCRadio.GetValue(): self.type = "BCC" if self.configBoxCellTypeFCCRadio.GetValue(): self.type = "FCC" self.configs['type'] = self.type self.updateParameters() def updateViewMode(self, evt): self.viewLayerX.Enable(False) self.viewLayerY.Enable(False) self.viewLayerZ.Enable(False) if self.viewModeAllLayers.GetValue(): self.canvas.viewMode = 'all' if self.viewModeLayerX.GetValue(): self.canvas.viewMode = 'x' self.viewLayerX.Enable(True) self.canvas.viewLayer = float(self.viewLayerX.GetStringSelection()) if self.viewModeLayerY.GetValue(): self.canvas.viewMode = 'y' self.viewLayerY.Enable(True) self.canvas.viewLayer = float(self.viewLayerY.GetStringSelection()) if self.viewModeLayerZ.GetValue(): self.canvas.viewMode = 'z' self.viewLayerZ.Enable(True) self.canvas.viewLayer = float(self.viewLayerZ.GetStringSelection()) self.canvas.OnDraw() def updateParametersProxy(self, evt): self.updateParameters() def updateParameters(self): layers = self.configBoxLayersCtrl.GetValue() heightReal = self.configBoxHeightCtrl.GetValue() widthPixels = self.grid.getWidth() lengthPixels = self.grid.getLength() widthReal = heightReal * widthPixels / layers lengthReal = heightReal * lengthPixels / layers self.configBoxWidthValue.SetLabel(str('{0:.5f}'.format(widthReal))) self.configBoxLengthValue.SetLabel(str('{0:.5f}'.format(lengthReal))) self.a = a = self.configBoxNetConstantCtrl.GetValue() self.eta = eta = self.configBoxEtaCtrl.GetValue() factor = 1.0 if self.type == "BCC" or self.type == "FCC": factor = 0.5 self.x = (layers * a * factor / heightReal) ** (1/eta) self.configBoxXValue.SetLabel('{0:.5f}'.format(self.x)) # self.configBoxXValue.SetLabel(str(self.x)) def checkParametersTrigger(self, evt): self.checkParameters() self.exportFile() def checkParameters(self): valid = True if not is_number(self.configBoxLayersCtrl.GetValue()): valid = False if not (self.configBoxCellTypeSCRadio.GetValue() or self.configBoxCellTypeBCCRadio.GetValue() or self.configBoxCellTypeFCCRadio.GetValue()): valid = False if not is_number(self.configBoxNetConstantCtrl.GetValue()): valid = False if not is_number(self.configBoxHeightCtrl.GetValue()): valid = False if not valid: wx.MessageBox('You must have valid values for each parameter.', 'Info', wx.OK | wx.ICON_WARNING) else: self.configs['layers'] = self.configBoxLayersCtrl.GetValue() self.configs['cells'] = self.grid.cells if self.type == 'SC': self.cube = SC(self.configs) if self.type == 'BCC': self.cube = BCC(self.configs) if self.type == 'FCC': self.cube = FCC(self.configs) self.cube.calculate() #self.exportFile() # wx.MessageBox('Data exported to export.dat file.', 'Info', wx.OK | wx.ICON_INFORMATION) def exportFile(self): currentPath = None if self.atoms_file: currentPath = os.path.dirname(self.atoms_file) dlg = wx.DirDialog(self, message="Choose a directory", style=wx.OPEN | wx.CHANGE_DIR ) exportDir = None if dlg.ShowModal() == wx.ID_OK: exportDir = dlg.GetPath() dlg.Destroy() if exportDir: os.chdir(exportDir) existingFiles = [] files = ['export.dat'] for f in files: if os.path.isfile(f): existingFiles.append(f) write = True if len(existingFiles): write = False dlg = wx.MessageDialog(self, 'The following files already exists on the directory:\n\n%s' % ('\n'.join(existingFiles)), 'Overwrite files', wx.OK | wx.CANCEL | wx.ICON_WARNING ) if dlg.ShowModal() == wx.ID_OK: write = True dlg.Destroy() if write: f = open("export.dat", "w") number_of_neighbors = 6 if self.type == 'BCC': number_of_neighbors = 8 if self.type == 'FCC': number_of_neighbors = 12 line = [len(self.cube.atoms), 1, number_of_neighbors, '{0:.5f}'.format(self.x)] f.write("\t".join(str(x) for x in line) + "\n") atom_keys = [int(x) for x in self.cube.atoms.keys()] atom_keys.sort() for atom_id in atom_keys: atom = self.cube.atoms[atom_id] neighbors = self.cube.neighborhood[atom_id] line = [atom_id] + ['{0:.5f}'.format(x * self.x) for x in atom] + [len(neighbors)] + neighbors + ([0] * (number_of_neighbors - len(neighbors))) f.write("\t".join(str(x) for x in line) + "\n") f.close() dlg = wx.MessageDialog(self, 'The file was exported succesfully.', 'File exported', wx.OK | wx.ICON_INFORMATION ) dlg.ShowModal() dlg.Destroy() def togglePreview(self, evt): if self.togglePreviewStatus: self.canvas.Hide() self.grid.Show() self.togglePreviewStatus = 0 self.axesD.Show(False) self.axesBoxD.Show(False) self.exportImagesButtonD.Show(False) self.sizeBoxSizer.ShowItems(True) self.figuresBoxSizer.ShowItems(True) self.allowParameterInput(True) else: self.checkParameters() self.canvas.setAtoms(self.cube.atoms, self.cube.atom_type) self.canvas.restartPosition() self.canvas.Show() self.grid.Hide() self.togglePreviewStatus = 1 self.axesD.Show(True) self.axesBoxD.Show(True) self.exportImagesButtonD.Show(True) self.sizeBoxSizer.ShowItems(False) self.figuresBoxSizer.ShowItems(False) self.allowParameterInput(False) self.Layout()
for unit_1, unit_2 in zip(units[:-1], units[1:]): if (unit_1 != unit_2): return NotImplemented return units[0] def multiplication_rule(self, units): non_null = [u for u in units if u] if (len(non_null) > 1): return NotImplemented return non_null[0] op_dict = { '__mul__':multiplication_rule, '__rmul__':multiplication_rule, '__add__':addition_rule, '__radd__':addition_rule, '__sub__':addition_rule, '__rsub__':addition_rule, } def __call__(self, operation, units): if (operation not in self.op_dict): return NotImplemented return self.op_dict[operation](self, units) unit_resolver = UnitResolver() Axes.set_default_unit_to_locator_map(lambda u:u.get_tick_locators()) Axes.set_default_unit_to_formatter_map(lambda u:u.get_tick_formatters())
def __init__(self, image, **kwargs): """ @type image: string/array_like/PIL Image @param image: a filepath or an image in grayscale or RGB @param vmin: @param vmax: @param cmap: @param xmin: @param xmax: @param ymin: @param ymax: @param limits: """ self._cmap = kwargs.get('cmap', 'gray') if isinstance(image, str): self.image = PILImage.open(image) elif isinstance(image, PILImage.Image): self.image = image.copy() else: if isinstance(image, ndarray): # copy array image = array(image) if image.dtype.kind not in ['u', 'i']: self.vmin = kwargs.get('vmin', min(image)) self.vmax = kwargs.get('vmax', max(image)) # rescale image image = (image - self.vmin) / (self.vmax - self.vmin) image = array(image * 256., dtype='int32') image[image < 0] = 0 image[image > 255] = 255 image = array(image, dtype='uint8') if image.ndim < 3: image = repeat(image.reshape(image.shape[0], -1, 1), 3, 2) for i in range(image.shape[0]): for j in range(image.shape[1]): image[i, j, :] = colormaps[self._cmap][image[i, j, 0]] self.image = PILImage.fromarray(image) # specify pixel coordinates self.xmin = kwargs.get('xmin', 0) self.xmax = kwargs.get('xmax', self.image.size[0]) self.ymin = kwargs.get('ymin', 0) self.ymax = kwargs.get('ymax', self.image.size[1]) if 'limits' in kwargs: self.xmin, self.xmax, \ self.ymin, self.ymax = kwargs['limits'] # add image to axis self.axes = kwargs.get('axes', Axes.gca()) self.axes.children.append(self) self.idx = Image._counter Image._counter += 1
def subplot(self, nrows, ncols, plot_number, **kwargs): """ Returen a subplot axes positioned by the given grid definition. :param nrows, nrows: (*int*) Whree *nrows* and *ncols* are used to notionally spli the figure into ``nrows * ncols`` sub-axes. :param plot_number: (*int) Is used to identify the particular subplot that this function is to create within the notional gird. It starts at 1, increments across rows first and has a maximum of ``nrows * ncols`` . :returns: Current axes specified by ``plot_number`` . """ chart = self.getChart() chart.setRowNum(nrows) chart.setColumnNum(ncols) polar = kwargs.pop('polar', False) isnew = True if isnew: polar = kwargs.pop('polar', False) if polar: ax = PolarAxes() else: ax = Axes() ax.axes.isSubPlot = True else: chart.setCurrentPlot(plot_number - 1) position = kwargs.pop('position', None) if position is None: if isnew: if isinstance(plot_number, (list, tuple)): i = 0 for pnum in plot_number: pnum -= 1 rowidx = pnum / ncols colidx = pnum % ncols width = 1. / ncols height = 1. / nrows x = width * colidx y = 1. - height * (rowidx + 1) if i == 0: minx = x miny = y maxx = x + width maxy = y + height else: minx = min(x, minx) miny = min(y, miny) maxx = max(x + width, maxx) maxy = max(y + height, maxy) i += 1 x = minx y = miny width = maxx - minx height = maxy - miny else: plot_number -= 1 rowidx = plot_number / ncols colidx = plot_number % ncols width = 1. / ncols height = 1. / nrows x = width * colidx y = 1. - height * (rowidx + 1) ax.set_position([x, y, width, height]) ax.set_outerposition([x, y, width, height]) ax.active_outerposition(True) else: ax.set_position(position) ax.active_outerposition(False) outerposition = kwargs.pop('outerposition', None) if not outerposition is None: ax.set_outerposition(outerposition) ax.active_outerposition(True) if isinstance(ax, MapAxes): self.__set_axesm(ax, **kwargs) else: self.__set_axes(ax, **kwargs) if isnew: chart.addPlot(ax.axes) chart.setCurrentPlot(chart.getPlots().size() - 1) return ax
def aggregate(arrays, check_overlap=True): """ like a multi-dimensional concatenate input: arrays: sequence of DimArrays check_overlap, optional: if True, check that arrays do not overlap (to avoid data loss) If any two elements overlap, keep the one which is not NaN, if applicable or raise an error if two valid values overlap Default is True to reduce the risk of errors, but this makes the operation less performant since every time a copy of the subarray is extracted and tested for NaNs. Consider setting check_overlap to False for large arrays for a well-tested problems, if the valid-nan selection is not required. Note: Probably a bad idea to have duplicate axis values (not tested) TODO: add support for missing values other than np.nan Examples: --------- >>> a = DimArray([[1.,2,3]],axes=[('line',[0]), ('col',['a','b','c'])]) >>> b = DimArray([[4],[5]], axes=[('line',[1,2]), ('col',['d'])]) >>> c = DimArray([[22]], axes=[('line',[2]), ('col',['b'])]) >>> d = DimArray([-99], axes=[('line',[4])]) >>> aggregate((a,b,c,d)) dimarray: 10 non-null elements (6 null) dimensions: 'line', 'col' 0 / line (4): 0 to 4 1 / col (4): a to d array([[ 1., 2., 3., nan], [ nan, nan, nan, 4.], [ nan, 22., nan, 5.], [-99., -99., -99., -99.]]) But beware of overlapping arrays. The following will raise an error: >>> a = DimArray([[1.,2,3]],axes=[('line',[0]), ('col',['a','b','c'])]) >>> b = DimArray([[4],[5]], axes=[('line',[0,1]), ('col',['b'])]) >>> try: ... aggregate((a,b)) ... except ValueError, msg: ... print msg Overlapping arrays: set check_overlap to False to suppress this error. Can set check_overlap to False to let it happen anyway (the latter array wins) >>> aggregate((a,b), check_overlap=False) dimarray: 4 non-null elements (2 null) dimensions: 'line', 'col' 0 / line (2): 0 to 1 1 / col (3): a to c array([[ 1., 4., 3.], [ nan, 5., nan]]) Note that if NaNs are present on overlapping, the valid data are kept >>> a = DimArray([[1.,2,3]],axes=[('line',[1]), ('col',['a','b','c'])]) >>> b = DimArray([[np.nan],[5]], axes=[('line',[1,2]), ('col',['b'])]) >>> aggregate((a,b)) # does not overwrite `2` at location (1, 'b') dimarray: 4 non-null elements (2 null) dimensions: 'line', 'col' 0 / line (2): 1 to 2 1 / col (3): a to c array([[ 1., 2., 3.], [ nan, 5., nan]]) """ # list of common dimensions dims = get_dims(*arrays) # build a common Axes object axes = Axes() for d in dims: newaxis = concatenate_axes([a.axes[d] for a in arrays if d in a.dims]) newaxis.values = np.unique(newaxis.values) # unique values axes.append(newaxis) # Fill in an array newarray = arrays[0]._constructor(None, axes=axes, dtype=arrays[0].dtype) for a in arrays: indices = {ax.name:ax.values for ax in a.axes} if check_overlap: # look for nans in replaced and replacing arrays subarray = newarray.take(indices, broadcast_arrays=False).values subarray_is_nan = np.isnan(subarray) newvalues_is_nan = np.isnan(a.values) # check overlapping overlap_values = ~subarray_is_nan & ~newvalues_is_nan if np.any(overlap_values): raise ValueError("Overlapping arrays: set check_overlap to False to suppress this error.") # only take new non-nan values newvalues = np.where(newvalues_is_nan, subarray, a.values) else: newvalues = a.values # The actual operation is done by put newarray.put(newvalues, indices=indices, inplace=True, convert=True, broadcast_arrays=False) # That's it ! return newarray
def subplots(self, nrows=1, ncols=1, position=None, sharex=False, sharey=False, \ wspace=None, hspace=None, axestype='Axes', **kwargs): ''' Create a figure and a set of subplots. :param nrows: (*int*) Number of rows. :param ncols: (*int*) Number of cols. :param position: (*list*) All axes' position specified by *position=* [left, bottom, width height] in normalized (0, 1) units. Default is [0,0,1,1]. :param sharex: (*boolean*) If share x axis. :param sharey: (*boolean*) If share y axis. :param subplot_kw: (*dict*) Subplot key words. :param wspace: (*float*) The amount of width reserved for blank space between subplots, expressed as a fraction of the average axis width. :param hspace: (*float*) The amount of height reserved for blank space between subplots, expressed as a fraction of the average axis height. :param axestype: (*string*) Axes type [Axes | Axes3D | MapAxes | PolarAxes]. :returns: The figure and the axes tuple. ''' if position is None: if wspace is None and hspace is None: position = [0, 0, 1, 1] else: position = [0.13, 0.11, 0.775, 0.815] left = float(position[0]) bottom = float(position[1]) width = float(position[2]) height = float(position[3]) chart = self.getChart() chart.setRowNum(nrows) chart.setColumnNum(ncols) axs = [] ax2d = nrows > 1 and ncols > 1 w = width / ncols h = height / nrows iswspace = False ishspace = False if not wspace is None and ncols > 1: w = (width - wspace * (ncols - 1)) / ncols iswspace = True if not hspace is None and nrows > 1: h = (height - hspace * (nrows - 1)) / nrows ishspace = True axestype = axestype.lower() y = bottom + height - h for i in range(nrows): if ax2d: axs2d = [] x = left if ishspace: if i > 0: y -= hspace for j in range(ncols): if axestype == 'axes3d': ax = Axes3D() self.__set_axes3d(ax, **kwarg) elif axestype == 'mapaxes': ax = MapAxes() self.__set_axesm(ax, **kwargs) elif axestype == 'polaraxes': ax = PolarAxes() else: ax = Axes() self.__set_axes(ax, **kwargs) ax.axes.isSubPlot = True if not iswspace and not ishspace: x = left + w * j y = (bottom + height) - h * (i + 1) ax.set_position([x, y, w, h]) ax.set_outerposition([x, y, w, h]) ax.active_outerposition(True) else: if iswspace: if j > 0: x += wspace ax.set_position([x, y, w, h]) ax.active_outerposition(False) x += w if sharex: if i < nrows - 1: ax.axes.getAxis( Location.BOTTOM).setDrawTickLabel(False) if sharey: if j > 0: ax.axes.getAxis(Location.LEFT).setDrawTickLabel(False) chart.addPlot(ax.axes) if ax2d: axs2d.append(ax) else: axs.append(ax) if ax2d: axs.append(tuple(axs2d)) y -= h chart.setCurrentPlot(0) return tuple(axs)
def __init__(self, values=None, axes=None, dims=None, labels=None, copy=False, dtype=None, _indexing=None, _indexing_broadcast=None, **kwargs): """ Initialization. See help on DimArray. """ # check if attached to values (e.g. DimArray object) if hasattr(values, "axes") and axes is None: axes = values.axes # default options if _indexing is None: _indexing = get_option('indexing.by') if _indexing_broadcast is None: _indexing_broadcast = get_option('indexing.broadcast') # # array values # # if masked array, replace mask by NaN if isinstance(values, np.ma.MaskedArray): try: values = values.filled(np.nan) # fill mask with nans # first convert to float except: values = np.ma.asarray(values, dtype=float).filled(np.nan) # fill mask with nans if values is not None: values = np.array(values, copy=copy, dtype=dtype) # # Initialize the axes # if axes is None and labels is None: assert values is not None, "values= or/and axes=, labels= required to determine dimensions" axes = Axes._init(axes, dims=dims, labels=labels, shape=values.shape if values is not None else None) assert type(axes) is Axes # if values not provided, create empty data, filled with NaNs if dtype is float if values is None: values = np.empty([ax.size for ax in axes], dtype=dtype) if dtype in (float, None, np.dtype(float)): values.fill(np.nan) else: warnings.warn("no nan representation for {}, array left empty".format(repr(dtype))) # # store all fields # self.values = values self.axes = axes ## options self._indexing = _indexing self._indexing_broadcast = _indexing_broadcast # # metadata (see Metadata type in metadata.py) # #for k in kwargs: # setncattr(self, k, kwargs[k]) # perform type-checking and store in self._metadata self._metadata = kwargs # Check consistency between axes and values inferred = tuple([ax.size for ax in self.axes]) if inferred != self.values.shape: msg = """\ shape inferred from axes: {} shape inferred from data: {} mismatch between values and axes""".format(inferred, self.values.shape) raise Exception(msg) # If a general ordering relationship of the class is assumed, # always sort the class if self._order is not None and self.dims != tuple(dim for dim in self._order if dim in self.dims): present = filter(lambda x: x in self.dims, self._order) # prescribed missing = filter(lambda x: x not in self._order, self.dims) # not order = missing + present # prepend dimensions not found in ordering relationship obj = self.transpose(order) self.values = obj.values self.axes = obj.axes
def drawSidebar(self): layout = wx.BoxSizer(wx.HORIZONTAL) tabs = wx.Notebook(self) self.designSidebarPanel = scrolled.ScrolledPanel(tabs) self.designSidebar = wx.BoxSizer(wx.VERTICAL) self.content = content = wx.BoxSizer(wx.VERTICAL) self.grid = BitMapGrid(self) self.canvas = AtomsCanvas(self) #Grid size self.sizeBox = wx.StaticBox(self.designSidebarPanel, label='Grid size') self.sizeBoxSizer = wx.StaticBoxSizer(self.sizeBox, wx.VERTICAL) self.sizeBoxGrid = wx.GridSizer(1, 4, 10, 10) self.sizeBoxWidthLabel = wx.StaticText(self.designSidebarPanel, label="Width") self.sizeBoxWidthCtrl = wx.SpinCtrl(self.designSidebarPanel, value=str(self.grid.cols), initial=self.grid.cols, min=0, size=(50, 20)) self.sizeBoxHeightLabel = wx.StaticText(self.designSidebarPanel, label="Height") self.sizeBoxHeightCtrl = wx.SpinCtrl(self.designSidebarPanel, value=str(self.grid.rows), initial=self.grid.rows, min=0, size=(50, 20)) self.sizeBoxGrid.AddMany([ (self.sizeBoxWidthLabel, 0, wx.EXPAND), (self.sizeBoxWidthCtrl, 0, wx.EXPAND), (self.sizeBoxHeightLabel, 0, wx.EXPAND), (self.sizeBoxHeightCtrl, 0, wx.EXPAND) ]) self.sizeBoxWidthCtrl.Bind(wx.EVT_SPINCTRL, self.updateGridSize) self.sizeBoxHeightCtrl.Bind(wx.EVT_SPINCTRL, self.updateGridSize) self.sizeBoxSizer.Add(self.sizeBoxGrid) #Object parameters self.configBox = wx.StaticBox(self.designSidebarPanel, label='Object parameters') self.configBoxSizer = wx.StaticBoxSizer(self.configBox, wx.VERTICAL) self.configBoxGrid = wx.GridSizer(10, 2, 5, 5) # Number of layers self.configBoxLayersLabel = wx.StaticText(self.designSidebarPanel, label="Layers", size=(70,20)) self.configBoxLayersCtrl = wx.SpinCtrl(self.designSidebarPanel, value="3", initial=10, min=1, size=(50, 20)) # Avoid bug on OS X that auto-focus on first field and hides the default value wx.CallAfter(self.configBoxLayersCtrl.SetFocus) self.configBoxLayersCtrl.Bind(wx.EVT_SPINCTRL, self.updateParametersProxy) # Type of structure self.configBoxCellTypeLabel = wx.StaticText(self.designSidebarPanel, label="Structure") self.configBoxCellTypeSCRadio = wx.RadioButton(self.designSidebarPanel, label='SC', style=wx.RB_GROUP) self.configBoxCellTypeBCCRadio = wx.RadioButton(self.designSidebarPanel, label='BCC') self.configBoxCellTypeFCCRadio = wx.RadioButton(self.designSidebarPanel, label='FCC') self.configBoxCellTypeSCRadio.SetValue(True) self.type = "SC" self.configs['type'] = self.type self.configBoxCellTypeSCRadio.Bind(wx.EVT_RADIOBUTTON, self.updateType) self.configBoxCellTypeBCCRadio.Bind(wx.EVT_RADIOBUTTON, self.updateType) self.configBoxCellTypeFCCRadio.Bind(wx.EVT_RADIOBUTTON, self.updateType) # Net constant self.configBoxNetConstantLabel = wx.StaticText(self.designSidebarPanel, label="Lattice constant") self.configBoxNetConstantCtrl = FS.FloatSpin(self.designSidebarPanel, -1, min_val=0, increment=0.1, value=0.28, agwStyle=FS.FS_LEFT) self.configBoxNetConstantCtrl.SetFormat("%f") self.configBoxNetConstantCtrl.SetDigits(5) self.configBoxNetConstantCtrl.Bind(FS.EVT_FLOATSPIN, self.updateParametersProxy) # Size self.configBoxHeightLabel = wx.StaticText(self.designSidebarPanel, label="Height (nm)", size=(70, 20)) self.configBoxHeightCtrl = FS.FloatSpin(self.designSidebarPanel, -1, min_val=0.1, increment=0.1, value=10, agwStyle=FS.FS_LEFT) self.configBoxHeightCtrl.SetFormat("%f") self.configBoxHeightCtrl.SetDigits(2) self.configBoxHeightCtrl.Bind(FS.EVT_FLOATSPIN, self.updateParametersProxy) # Sizes self.configBoxWidthLabel = wx.StaticText(self.designSidebarPanel, label="Width (nm)", size=(70, 20)) self.configBoxWidthValue = wx.StaticText(self.designSidebarPanel, label="--", size=(70, 20)) self.configBoxLengthLabel = wx.StaticText(self.designSidebarPanel, label="Length (nm)", size=(70, 20)) self.configBoxLengthValue = wx.StaticText(self.designSidebarPanel, label="--", size=(70, 20)) # Scaling self.configBoxEtaLabel = wx.StaticText(self.designSidebarPanel, label="Eta", size=(70, 20)) self.configBoxEtaCtrl = FS.FloatSpin(self.designSidebarPanel, -1, min_val=0, increment=0.1, value=0.55, agwStyle=FS.FS_LEFT) self.configBoxEtaCtrl.SetFormat("%f") self.configBoxEtaCtrl.SetDigits(5) self.configBoxEtaCtrl.Bind(FS.EVT_FLOATSPIN, self.updateParametersProxy) self.configBoxXLabel = wx.StaticText(self.designSidebarPanel, label="X", size=(70, 20)) self.configBoxXValue = wx.StaticText(self.designSidebarPanel, label="--", size=(50, 20)) self.configBoxGrid.AddMany([ (self.configBoxLayersLabel, 0, wx.EXPAND), (self.configBoxLayersCtrl, 0, wx.EXPAND), (self.configBoxCellTypeLabel, 0, wx.EXPAND), (self.configBoxCellTypeSCRadio, 0, wx.EXPAND), (wx.StaticText(self, -1, ''), 0, wx.EXPAND), #Blank space (self.configBoxCellTypeBCCRadio, 0, wx.EXPAND), (wx.StaticText(self, -1, ''), 0, wx.EXPAND), #Blank space (self.configBoxCellTypeFCCRadio, 0, wx.EXPAND), (self.configBoxNetConstantLabel, 0, wx.EXPAND), (self.configBoxNetConstantCtrl, 0, wx.EXPAND), (self.configBoxHeightLabel, 0, wx.EXPAND), (self.configBoxHeightCtrl, 0, wx.EXPAND), (self.configBoxWidthLabel, 0, wx.EXPAND), (self.configBoxWidthValue, 0, wx.EXPAND), (self.configBoxLengthLabel, 0, wx.EXPAND), (self.configBoxLengthValue, 0, wx.EXPAND), (self.configBoxEtaLabel, 0, wx.EXPAND), (self.configBoxEtaCtrl, 0, wx.EXPAND), (self.configBoxXLabel, 0, wx.EXPAND), (self.configBoxXValue, 0, wx.EXPAND) ]) self.configBoxSizer.Add(self.configBoxGrid) # Figures self.figuresBox = wx.StaticBox(self.designSidebarPanel, label='Figures') self.figuresBoxSizer = wx.StaticBoxSizer(self.figuresBox, wx.VERTICAL) self.figuresBoxGrid = wx.FlexGridSizer(2, 1, 10, 10) # Quadrilateral self.figuresQuadPane = wx.CollapsiblePane(self.designSidebarPanel, label="Quadrilateral", style=wx.CP_DEFAULT_STYLE|wx.CP_NO_TLW_RESIZE) self.figuresQuadPane.Bind(wx.EVT_COLLAPSIBLEPANE_CHANGED, self.quadToggled) self.figuresQuadSizer = wx.GridSizer(1, 4, 10, 10) self.figuresQuadPaneWin = self.figuresQuadPane.GetPane() self.figuresQuadWidthLabel = wx.StaticText(self.figuresQuadPaneWin, label="Width") self.figuresQuadWidthCtrl = wx.SpinCtrl(self.figuresQuadPaneWin, value="1", initial=1, min=1, size=(50,20)) self.figuresQuadHeightLabel = wx.StaticText(self.figuresQuadPaneWin, label="Height") self.figuresQuadHeightCtrl = wx.SpinCtrl(self.figuresQuadPaneWin, value="1", initial=1, min=1, size=(50,20)) self.figuresQuadSizer.AddMany([ (self.figuresQuadWidthLabel, 0, wx.EXPAND), (self.figuresQuadWidthCtrl, 0, wx.EXPAND), (self.figuresQuadHeightLabel, 0, wx.EXPAND), (self.figuresQuadHeightCtrl, 0, wx.EXPAND) ]) self.figuresQuadPaneWin.SetSizer(self.figuresQuadSizer) # Circle self.figuresCirclePane = wx.CollapsiblePane(self.designSidebarPanel, label="Circle", style=wx.CP_DEFAULT_STYLE|wx.CP_NO_TLW_RESIZE) self.figuresCirclePane.Bind(wx.EVT_COLLAPSIBLEPANE_CHANGED, self.circleToggled) self.figuresCircleSizer = wx.GridSizer(2, 2, 10, 10) self.figuresCirclePaneWin = self.figuresCirclePane.GetPane() self.figuresCircleRadiusLabel = wx.StaticText(self.figuresCirclePaneWin, label="Radius") self.figuresCircleRadiusCtrl = wx.SpinCtrl(self.figuresCirclePaneWin, value="1", initial=1, min=1, size=(50,20)) self.figuresCircleRadiusCtrl.Bind(wx.EVT_SPINCTRL, self.updateCircleWidth) self.figuresCircleWidthLabel = wx.StaticText(self.figuresCirclePaneWin, label="Width (nm)") self.figuresCircleWidthValue = wx.StaticText(self.figuresCirclePaneWin, label="--") self.figuresCircleSizer.AddMany([ (self.figuresCircleRadiusLabel, 0, wx.EXPAND), (self.figuresCircleRadiusCtrl, 0, wx.EXPAND), (self.figuresCircleWidthLabel, 0, wx.EXPAND), (self.figuresCircleWidthValue, 0, wx.EXPAND) ]) self.figuresCirclePaneWin.SetSizer(self.figuresCircleSizer) self.figuresBoxGrid.AddMany([ (self.figuresQuadPane, 0, wx.EXPAND), (self.figuresCirclePane, 0, wx.EXPAND) ]) self.figuresBoxSizer.Add(self.figuresBoxGrid) self.clearButton = wx.Button(self.designSidebarPanel, label="Clear grid") self.clearButton.Bind(wx.EVT_BUTTON, self.clearGrid) self.exportFileButton = wx.Button(self.designSidebarPanel, label="Export Data") self.exportFileButton.Bind(wx.EVT_BUTTON, self.checkParametersTrigger) self.exportImagesButtonD = wx.Button(self.designSidebarPanel, label="Export Images") self.exportImagesButtonD.Bind(wx.EVT_BUTTON, self.exportImagesD) self.exportImagesButtonD.Show(False) self.previewButton = wx.Button(self.designSidebarPanel, label="Show/hide preview") self.previewButton.Bind(wx.EVT_BUTTON, self.togglePreview) self.axesBoxD = wx.StaticBox(self.designSidebarPanel, label='Axes') self.axesBoxSizerD = wx.StaticBoxSizer(self.axesBoxD, wx.VERTICAL) self.axesD = Axes(self.designSidebarPanel) self.axesBoxSizerD.Add(self.axesD) self.designSidebar.Add(self.sizeBoxSizer, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.configBoxSizer, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.figuresBoxSizer, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.clearButton, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.exportFileButton, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.exportImagesButtonD, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.previewButton, 0, wx.EXPAND | wx.ALL, 5) self.designSidebar.Add(self.axesBoxSizerD, 0, wx.EXPAND | wx.ALL, 5) self.designSidebarPanel.SetSizer(self.designSidebar) wx.CallAfter(self.axesBoxD.Show, False) wx.CallAfter(self.axesD.Show, False) self.visualizationSidebarPanel = scrolled.ScrolledPanel(tabs) visualizationSidebar = wx.BoxSizer(wx.VERTICAL) inputDirBtn = wx.Button(self.visualizationSidebarPanel, -1, "Select Atoms file") self.Bind(wx.EVT_BUTTON, self.openFileDialog, inputDirBtn) self.statsBox = wx.StaticBox(self.visualizationSidebarPanel, label='Input Stats') self.statsSizer = wx.StaticBoxSizer(self.statsBox, wx.VERTICAL) self.statsGrid = wx.GridSizer(2, 2, 5, 5) self.statsValidPathLabel = wx.StaticText(self.visualizationSidebarPanel, label="Valid Atom file") self.statsValidPathValue = wx.StaticText(self.visualizationSidebarPanel, label="--") self.statsNumberDataFilesLabel = wx.StaticText(self.visualizationSidebarPanel, label="# of Data files") self.statsNumberDataFilesValue = wx.StaticText(self.visualizationSidebarPanel, label="--") self.statsGrid.AddMany([ (self.statsValidPathLabel, 0, wx.EXPAND), (self.statsValidPathValue, 0, wx.EXPAND), (self.statsNumberDataFilesLabel, 0, wx.EXPAND), (self.statsNumberDataFilesValue, 0, wx.EXPAND) ]) self.statsSizer.Add(self.statsGrid) self.readInputBtn = wx.Button(self.visualizationSidebarPanel, label="Read Input files") # Enable only if we have a valid directory self.readInputBtn.Enable(False) self.readInputBtn.Bind(wx.EVT_BUTTON, self.readInputFiles) viewModeBox = wx.StaticBox(self.visualizationSidebarPanel, label='View layer') self.viewModeSizer = wx.StaticBoxSizer(viewModeBox, wx.VERTICAL) viewModeGrid = wx.FlexGridSizer(2, 4, 5, 5) self.viewModeAllLayers = wx.RadioButton(self.visualizationSidebarPanel, label='All', style=wx.RB_GROUP) self.viewModeLayerX = wx.RadioButton(self.visualizationSidebarPanel, label='X') self.viewLayerX = wx.ComboBox(self.visualizationSidebarPanel, choices=["0.000"], style=wx.CB_DROPDOWN|wx.CB_READONLY, size=(60, 27)) self.viewModeLayerY = wx.RadioButton(self.visualizationSidebarPanel, label='Y') self.viewLayerY = wx.ComboBox(self.visualizationSidebarPanel, choices=["0.000"], style=wx.CB_DROPDOWN|wx.CB_READONLY, size=(60, 27)) self.viewModeLayerZ = wx.RadioButton(self.visualizationSidebarPanel, label='Z') self.viewLayerZ = wx.ComboBox(self.visualizationSidebarPanel, choices=["0.000"], style=wx.CB_DROPDOWN|wx.CB_READONLY, size=(60, 27)) self.viewModeAllLayers.SetValue(True) self.viewModeAllLayers.Enable(False) self.viewModeLayerX.Enable(False) self.viewModeLayerY.Enable(False) self.viewModeLayerZ.Enable(False) self.viewLayerX.Enable(False) self.viewLayerY.Enable(False) self.viewLayerZ.Enable(False) self.viewModeAllLayers.Bind(wx.EVT_RADIOBUTTON, self.updateViewMode) self.viewModeLayerX.Bind(wx.EVT_RADIOBUTTON, self.updateViewMode) self.viewModeLayerY.Bind(wx.EVT_RADIOBUTTON, self.updateViewMode) self.viewModeLayerZ.Bind(wx.EVT_RADIOBUTTON, self.updateViewMode) self.viewLayerX.Bind(wx.EVT_COMBOBOX, self.updateViewMode) self.viewLayerY.Bind(wx.EVT_COMBOBOX, self.updateViewMode) self.viewLayerZ.Bind(wx.EVT_COMBOBOX, self.updateViewMode) viewModeGrid.AddMany([ (self.viewModeAllLayers, 0, wx.EXPAND), (self.viewModeLayerX, 0, wx.EXPAND), (self.viewModeLayerY, 0, wx.EXPAND), (self.viewModeLayerZ, 0, wx.EXPAND), ((1,1)), #Blank space (self.viewLayerX, 0, wx.EXPAND), (self.viewLayerY, 0, wx.EXPAND), (self.viewLayerZ, 0, wx.EXPAND) ]) self.viewModeSizer.Add(viewModeGrid, flag=wx.ALL, border=1) self.exportImagesButtonV = wx.Button(self.visualizationSidebarPanel, label="Export Images") self.exportImagesButtonV.Bind(wx.EVT_BUTTON, self.exportImagesV) self.exportImagesButtonV.Show(False) self.exportVideoButton = wx.Button(self.visualizationSidebarPanel, label="Export Video") self.exportVideoButton.Bind(wx.EVT_BUTTON, self.exportVideo) self.exportVideoButton.Show(False) controlsBox = wx.StaticBox(self.visualizationSidebarPanel, label='Controls') self.controlsSizer = wx.StaticBoxSizer(controlsBox, wx.VERTICAL) controlsGrid = wx.FlexGridSizer(1, 6, 5, 5) self.playBitmap = wx.Bitmap("images/play.png", wx.BITMAP_TYPE_ANY) self.stopBitmap = wx.Bitmap("images/pause.png", wx.BITMAP_TYPE_ANY) self.backBitmap = wx.Bitmap("images/back.png", wx.BITMAP_TYPE_ANY) self.forwardBitmap = wx.Bitmap("images/forward.png", wx.BITMAP_TYPE_ANY) self.previousBitmap = wx.Bitmap("images/previous.png", wx.BITMAP_TYPE_ANY) self.nextBitmap = wx.Bitmap("images/next.png", wx.BITMAP_TYPE_ANY) self.backBtn = wx.BitmapButton(self.visualizationSidebarPanel, -1, self.backBitmap, (0,0), ((30,30))) self.previousBtn = wx.BitmapButton(self.visualizationSidebarPanel, -1, self.previousBitmap, (0,0), ((30,30))) self.playStopBtn = wx.BitmapButton(self.visualizationSidebarPanel, -1, self.playBitmap, (0,0), ((30,30))) self.nextBtn = wx.BitmapButton(self.visualizationSidebarPanel, -1, self.nextBitmap, (0,0), ((30,30))) self.forwardBtn = wx.BitmapButton(self.visualizationSidebarPanel, -1, self.forwardBitmap, (0,0), ((30,30))) self.previousBtn.Bind(wx.EVT_BUTTON, self.previousT) self.backBtn.Bind(wx.EVT_BUTTON, self.backT) self.playStopBtn.Bind(wx.EVT_BUTTON, self.playStop) self.forwardBtn.Bind(wx.EVT_BUTTON, self.forwardT) self.nextBtn.Bind(wx.EVT_BUTTON, self.nextT) self.backBtn.Enable(False) self.previousBtn.Enable(False) self.playStopBtn.Enable(False) self.forwardBtn.Enable(False) self.nextBtn.Enable(False) self.currentTCtrl = wx.TextCtrl(self.visualizationSidebarPanel, value="0", style=wx.TE_CENTRE, size=(70, 10)) font = wx.Font(18, wx.SWISS, wx.NORMAL, wx.NORMAL) self.currentTCtrl.SetFont(font) self.currentTCtrl.Enable(False) self.currentTCtrl.Bind(wx.EVT_TEXT, self.startCurrentTTimer) self.currentTTimer = wx.Timer(self) self.Bind(wx.EVT_TIMER, self.setCurrentT, self.currentTTimer) controlsGrid.AddMany([ (self.backBtn, 0, wx.EXPAND), (self.previousBtn, 0, wx.EXPAND), (self.playStopBtn, 0, wx.EXPAND), (self.nextBtn, 0, wx.EXPAND), (self.forwardBtn, 0, wx.EXPAND), (self.currentTCtrl, 0, wx.EXPAND) ]) self.controlsSizer.Add(controlsGrid) axesBoxV = wx.StaticBox(self.visualizationSidebarPanel, label='Axes') axesBoxSizerV = wx.StaticBoxSizer(axesBoxV, wx.VERTICAL) self.axesV = Axes(self.visualizationSidebarPanel) axesBoxSizerV.Add(self.axesV) self.plotBox = wx.StaticBox(self.visualizationSidebarPanel, label='Plot') plotSizer = wx.StaticBoxSizer(self.plotBox, wx.VERTICAL) self.plotter = plot.PlotCanvas(self.visualizationSidebarPanel) self.plotter.SetInitialSize(size=(220, 220)) plotSizer.Add(self.plotter) self.plotBox.Show(False) self.plotter.Show(False) visualizationSidebar.AddMany([ (inputDirBtn, 0, wx.EXPAND | wx.ALL, 5), (self.statsSizer, 0, wx.EXPAND | wx.ALL, 5), (self.readInputBtn, 0, wx.EXPAND | wx.ALL, 5), (self.controlsSizer, 0, wx.EXPAND | wx.ALL, 5), (self.viewModeSizer, 0, wx.EXPAND | wx.ALL, 5), (self.exportImagesButtonV, 0, wx.EXPAND | wx.ALL, 5), (self.exportVideoButton, 0, wx.EXPAND | wx.ALL, 5), (axesBoxSizerV, 0, wx.EXPAND | wx.ALL, 5), (plotSizer, 0, wx.EXPAND | wx.ALL, 5) ]) self.visualizationSidebarPanel.SetSizer(visualizationSidebar) self.viewModeSizer.ShowItems(False) self.controlsSizer.ShowItems(False) tabs.AddPage(self.designSidebarPanel, "Design") tabs.AddPage(self.visualizationSidebarPanel, "Visualization") tabs.Bind(wx.EVT_NOTEBOOK_PAGE_CHANGED, self.OnPageChanged) content.Add(self.grid, 1, wx.EXPAND) content.Add(self.canvas, 1, wx.EXPAND) self.grid.Show() self.canvas.Hide() self.togglePreviewStatus = 0 layout.Add(tabs, 0, wx.EXPAND) layout.Add(content, 1, wx.EXPAND) self.designSidebarPanel.SetupScrolling(scroll_x=False) self.visualizationSidebarPanel.SetupScrolling(scroll_x=False) self.SetSizer(layout) self.Layout() self.Refresh() self.grid.updateSize() self.updateParameters()
def gca(): """ Returns currently active axis. """ return Axes.gca()
def _take_broadcast(a, indices): """ broadcast array-indices & integers, numpy's classical Examples: --------- >>> a = da.zeros(shape=(3,4,5,6)) >>> a[:,[0, 1],:,2].shape (2, 3, 5) >>> a[:,[0, 1],2,:].shape (3, 2, 6) """ # new values newval = a.values[indices] # if the new values is a scalar, then just return it if np.isscalar(newval): return newval # new axes: broacast indices (should do the same as above, since integers are just broadcast) indices2 = broadcast_indices(indices) # assert np.all(newval == a.values[indices2]) # make a multi-axis with tuples is_array2 = np.array([np.iterable(ix) for ix in indices2]) nb_array2 = is_array2.sum() # If none or one array is present, easy if nb_array2 <= 1: newaxes = [ a.axes[i][ix] for i, ix in enumerate(indices) if not np.isscalar(ix) ] # indices or indices2, does not matter # else, finer check needed else: # same stats but on original indices is_array = np.array([np.iterable(ix) for ix in indices]) array_ix_pos = np.where(is_array)[0] # Determine where the axis will be inserted # - need to consider the integers as well (broadcast as arrays) # - if two indexed dimensions are not contiguous, new axis placed at first position... # a = zeros((3,4,5,6)) # a[:,[1,2],:,0].shape ==> (2, 3, 5) # a[:,[1,2],0,:].shape ==> (3, 2, 6) array_ix_pos2 = np.where(is_array2)[0] if np.any(np.diff(array_ix_pos2) > 1 ): # that mean, if two indexed dimensions are not contiguous insert = 0 else: insert = array_ix_pos2[0] # Now determine axis value # ...if originally only one array was provided, use these values correspondingly if len(array_ix_pos) == 1: i = array_ix_pos[0] values = a.axes[i].values[indices[i]] name = a.axes[i].name # ...else use a list of tuples else: values = zip( *[a.axes[i].values[indices2[i]] for i in array_ix_pos]) name = ",".join([a.axes[i].name for i in array_ix_pos]) broadcastaxis = Axis(values, name) newaxes = Axes() for i, ax in enumerate(a.axes): # axis is already part of the broadcast axis: skip if is_array2[i]: continue else: newaxis = ax[indices2[i]] ## do not append axis if scalar #if np.isscalar(newaxis): # continue newaxes.append(newaxis) # insert the right new axis at the appropriate position newaxes.insert(insert, broadcastaxis) return a._constructor(newval, newaxes, **a._metadata)