class DataX(HasTraits): # Rewritten and simplified description = String('') uuid = String() values = Array() unit = String() label = String() def __init__(self, x, label = '', unit = '', description = ''): self.uuid = uuid.uuid4().hex self.description = description if isinstance(x, DataX): self.values = x.values.copy() self.label = x.label self.unit = x.unit elif isinstance(x, np.ndarray): self.values = x elif isinstance(x, int): self.values = np.empty(x) self.values[:] = np.nan if label: self.label = label if unit: self.unit = unit def write_h5(self, h5_base): dset = h5_base.create_dataset(self.uuid, data=self.values) dset.attrs["unit"] = self.unit dset.attrs["label"] = self.label dset.attrs["description"] = self.description dset.attrs["uuid"] = self.uuid
class DataValue(HasStrictTraits): """Contains in-transit data between the various components (MCO/DS/KPI). Each DataValue instance holds information about the CUBA type it contains, the name as assigned by the user, and the value (which can be anything. """ #: The CUBA type associated to the value. type = String() #: The user-defined name associated to the value. name = String() #: The value. value = Any() # The numerical accuracy of the value. accuracy = Any() #: A flag for the quality of the data. quality = Enum("AVERAGE", "POOR", "GOOD") def __str__(self): s = "{} {} = {}".format( str(self.type), str(self.name), str(self.value)) if self.accuracy is not None: s += " +/- {}".format(str(self.accuracy)) s += " ({})".format(str(self.quality)) return s def __getstate__(self): return pop_dunder_recursive(super().__getstate__())
class UVLaserOpticsClient(LaserOpticsClient): mask = Property(String(enter_set=True, auto_set=False), depends_on='_mask') _mask = Either(Str, Float) masks = Property attenuator = String(enter_set=True, auto_set=False) #attenuators = Property zoom = Range(0.0, 100.0) @on_trait_change('mask, attenuator, zoom') def _motor_changed(self, name, new): if new is not None: t = Thread(target=self.parent.set_motor, args=(name, new)) t.start() def _set_mask(self, m): self._mask = m def _get_mask(self): return self._mask def _validate_mask(self, m): if m in self.masks: return m else: try: return float(m) except ValueError: pass def traits_view(self): v = View( HGroup(Item('mask', editor=EnumEditor(name='masks')), UItem('mask')), Item('attenuator'), ) return v @cached_property def _get_masks(self): return self._get_motor_values('mask_names') #@cached_property #def _get_attenuators(self): # return self._get_motor_values('attenuators') def _get_motor_values(self, name): p = os.path.join(paths.device_dir, 'fusions_uv', '{}.txt'.format(name)) values = [] if os.path.isfile(p): with open(p, 'r') as fp: for lin in fp: lin = lin.strip() if not lin or lin.startswith('#'): continue values.append(lin) return values
class LogDisplay(HasTraits): history = String() string = String() view = View(Item('string', show_label=False, springy=True, style='custom')) def update(self, str): self.string = str + '----------------------------------------\n' + self.history self.history = str + self.history
class Axes(AxesLikeModuleFactory): """ Creates axes for the current (or given) object.""" xlabel = String(None, adapts='axes.x_label', help='the label of the x axis') ylabel = String(None, adapts='axes.y_label', help='the label of the y axis') zlabel = String(None, adapts='axes.z_label', help='the label of the z axis') nb_labels = Range(0, 50, 2, adapts='axes.number_of_labels', desc='The number of labels along each direction') ranges = Trait( None, None, CArray(shape=(6, )), help="""[xmin, xmax, ymin, ymax, zmin, zmax] Ranges of the labels displayed on the axes. Default is the object's extents.""", ) x_axis_visibility = true( adapts='axes.x_axis_visibility', help="Whether or not the x axis is visible (boolean)") y_axis_visibility = true( adapts='axes.y_axis_visibility', help="Whether or not the y axis is visible (boolean)") z_axis_visibility = true( adapts='axes.z_axis_visibility', help="Whether or not the z axis is visible (boolean)") _target = Instance(modules.Axes, ()) def _extent_changed(self): """ Code to modify the extents for """ axes = self._target axes.axes.use_data_bounds = False axes.axes.bounds = self.extent if self.ranges is None: axes.axes.ranges = \ axes.module_manager.source.outputs[0].bounds def _ranges_changed(self): if self.ranges is not None: self._target.axes.ranges = self.ranges self._target.axes.use_ranges = True
class TraitsTableOption(HasTraits): fr = Int() to = Int() re = String() identifier = String() leads_to = String() traits_view = View( HGroup(Item('fr', width=2), Item('to', width=2), Item('re', width=400), Item('identifier', width=20), Item('leads_to')))
class CustomEquation(HasTraits): example = 'p[0]+p[1]*cos(p[2]*x)' equation = String('p[0]+x**2+p[1]*cos(2*x)+p[2]*sin(2*x)') initial_guess = String('1,1,1') v = View(Item('example', style='readonly'), Item('equation', label='Y ='), Item('initial_guess'), resizable=True, kind='modal', buttons=['OK', 'Cancel'])
class DataXY(HasTraits): # Rewritten and simplified label = String() description = String('') uuid = String() values = Array() unit = String() x = Instance(DataX) full = Bool(False) index = Int(-1) def __init__(self, x, y = None, label = '', unit = '', description = ''): self.uuid = uuid.uuid4().hex self.label = label self.description = description self.unit = unit self.x = x if isinstance(y, DataX): self.values = x.values.copy() self.label = x.label self.unit = x.unit elif isinstance(x, np.ndarray): self.values = x elif not y: self.values = np.empty(len(x.values)) self.values[:] = np.nan def add_point(self, newpoint, x=None): if self.full: raise DataError('The data container is already full') self.index = self.index + 1 if isinstance(newpoint, Number): self.values[:,self.index] = newpoint if x is not None: self.x.value[self.idx] = x elif isinstance(newline, tuple): self.x.values[:,self.index] = newpoint[0] self.values[:,self.index] = newpoint[1] else: raise DataError('Unsupported data') if self.idx >= self.values.shape[0]-1: self.full = True self.changed = True def write_h5(self, h5_base): dset = h5_base.create_dataset(self.uuid, data=self.values) dset.attrs["unit"] = self.unit dset.attrs["label"] = self.label dset.attrs["description"] = self.description dset.attrs["uuid"] = self.uuid
class DataXYZ(HasTraits): # Rewritten and simplified. Does not contain the x- and y-arrays description = String('') uuid = String() x = Instance(DataX) y = Instance(DataX) values = Array() label = String('z') unit = String('') full = Bool(False) index = Int(-1) changed = Event() def __init__(self, x, y, label = '', unit = '', description = ''): self.uuid = uuid.uuid4().hex self.label = label self.description = description self.unit = unit self.x = x self.y = y self.values = np.empty(len(x.values),len(y.values)) self.values[:] = np.nan def add_line(self, newline, x=None): if self.full: raise DataError('The data container is already full') self.index = self.index + 1 if isinstance(newline, DataX): self.values[:,self.index] = newline.values elif isinstance(newline, np.ndarray): self.values[:,self.index] = newline elif isinstance(newline, DataXY): self.values[:,self.index] = newline.values else: raise DataError('Unsupported data') if x is not None: self.x.value[self.idx] = x if self.idx >= self.values.shape[0]-1: self.full = True self.changed = True def write_h5(self, h5_base): dset = h5_base.create_dataset(self.uuid, data=self.values) dset.attrs["label"] = self.label dset.attrs["unit"] = self.unit dset.attrs["description"] = self.description dset.attrs["uuid"] = self.uuid dset.attrs["x"] = self.x.uuid dset.attrs["y"] = self.y.uuid dset.attrs["class"] = self.__class__.__name__
class IntelHexFileDialog(HasTraits): file_wildcard = String("Intel HEX File (*.hex)|*.hex|All files|*") status = String('Please choose a file') choose_fw = Button(label='Choose Firmware File') view = View( UItem('status'), UItem('choose_fw') ) def __init__(self, flash_type): if not flash_type=='M25' and not flash_type=='STM': raise ValueError("flash_type must be 'M25' or 'STM'") self._flash_type = flash_type self.ihx = None def set_status(self, status): self.ihx = None self.status = status def load_ihx(self, filepath): try: self.ihx = IntelHex(filepath) self.status = os.path.split(filepath)[1] except HexRecordError: self.set_status('Error: File is not a valid Intel HEX File') # Check that address ranges are valid for self._flash_type. ihx_addrs = flash.ihx_ranges(self.ihx) if self._flash_type == "M25": try: sectors = flash.sectors_used(ihx_addrs, flash.m25_addr_sector_map) except IndexError: self.set_status('Error: HEX File contains restricted address ' + \ '(STM Firmware File Chosen?)') elif self._flash_type == "STM": try: sectors = flash.sectors_used(ihx_addrs, flash.stm_addr_sector_map) except: self.set_status('Error: HEX File contains restricted address ' + \ '(NAP Firmware File Chosen?)') def _choose_fw_fired(self): dialog = FileDialog(label='Choose Firmware File', action='open', wildcard=self.file_wildcard) dialog.open() if dialog.return_code == OK: filepath = os.path.join(dialog.directory, dialog.filename) self.load_ihx(filepath) else: self.set_status('Error while selecting file')
class OrientationAxesFactory(SingletonModuleFactory): """Applies the OrientationAxes mayavi module to the given VTK data object. """ xlabel = String(None, adapts='axes.x_axis_label_text', help='the label of the x axis') ylabel = String(None, adapts='axes.y_axis_label_text', help='the label of the y axis') zlabel = String(None, adapts='axes.z_axis_label_text', help='the label of the z axis') _target = Instance(modules.OrientationAxes, ())
class FirmwareFileDialog(HasTraits): file_wildcard = String("Binary image set (*.bin)|*.bin|All files|*") status = String('Please choose a file') choose_fw = Button(label='...', padding=-1) view = View( HGroup(UItem('status', resizable=True), UItem('choose_fw', width=-0.1)), ) def __init__(self, default_dir): """ Pop-up file dialog to choose an IntelHex file, with status and button to display in traitsui window. """ self.ihx = None self.blob = None self.default_dir = default_dir def clear(self, status): """ Set text of status box and clear IntelHex file. Parameters ---------- status : string Error text to replace status box text with. """ self.ihx = None self.blob = None self.status = status def load_bin(self, filepath): try: self.blob = open(filepath, 'rb').read() self.status = os.path.split(filepath)[1] except: # noqa self.clear('Error: Failed to read binary file') def _choose_fw_fired(self): """ Activate file dialog window to choose IntelHex firmware file. """ dialog = FileDialog(label='Choose Firmware File', action='open', default_directory=self.default_dir, wildcard=self.file_wildcard) dialog.open() if dialog.return_code == OK: filepath = os.path.join(dialog.directory, dialog.filename) self.load_bin(filepath) else: self.clear('Error while selecting file')
class Signature(HasTraits): color = String(desc='color signature name') dimmest = Color(desc='dimmest allowable RGB intensities') brightest = Color(desc='brightest allowable RGB intensities') def __eq__(self, other): return self.dimmest == other.dimmest or self.brightest == other.brightest def __ne__(self, other): return self.dimmest != other.dimmest and self.brightest != other.brightest def __hash__(self): return hash( (hash(self.dimmest), hash(self.brightest)) ) # color signature is all that matters for identification purposes def __setattr__(self, attribute, setting): if attribute == 'dimmest' and hasattr(self, 'brightest'): assert self.brightest != setting, '{} `dimmest` and `brightest` attributes are equal ({})'.format( self.__class__.__name__, setting) elif attribute == 'brightest' and hasattr(self, 'dimmest'): assert self.dimmest != setting, '{} `dimmest` and `brightest` attributes are equal ({})'.format( self.__class__.__name__, setting) HasTraits.__setattr__(self, attribute, setting) def __str__(self): return '{}(color:{}, dimmest:{}, brightest:{})'.format( self.__class__.__name__, self.color, self.dimmest, self.brightest)
class ReferenceHole(ReferencePoint): hole = Property _hole = Str help_tag = String(HELP_TAG_HOLE) valid_holes = List def _get_hole(self): return self._hole def _set_hole(self, v): self._hole = v def _validate_hole(self, v): if v in self.valid_holes: return v def traits_view(self): v = View( CustomLabel('help_tag', top_padding=10, left_padding=10, color='maroon'), Item('hole'), buttons=['OK', 'Cancel'], kind='modal', title='Reference Hole') return v
class FSLConfig(Controller): config = File(Undefined, output=False, desc='Parameter to specify the fsl.sh path') prefix = String(Undefined, desc='Prefix to add to FSL commands') use = Bool(Undefined, desc='Parameter to tell that FSL must be configured')
class CameraParameter(HasTraits): value = Property(Float(np.NaN)) name = String() def __init__(self, videoCapture, parameter_name): self._cap = videoCapture self.name = parameter_name.title().replace('_', ' ') try: self._parameter_ID = getattr( cv2.cv, 'CV_CAP_PROP_' + parameter_name.upper().replace(' ', '_')) except AttributeError: raise AttributeError( "%s is not a valid capture property, try CameraParameter.list_names()" ) def _get_value(self): return self._cap.get(self._parameter_ID) def _set_value(self, value): return self._cap.set(self._parameter_ID, value) def default_traits_view(self): return View(Item(name="value", label=self.name), kind="live") @classmethod def list_names(cls): return [ name.replace("CV_CAP_PROP_", "") for name in dir(cv2.cv) if "CV_CAP_PROP_" in name ]
class HasTraitsPersistent(HasTraits): "custom Traits class with methods for loading/saving state" settings_id = String('state', transient=True) def load_settings(self): try: sfilename = 'config/%s.pkl' % self.settings_id sfilename = os.path.join(os.path.split(__file__)[0], sfilename) with open(sfilename, 'rb') as sfile: state = pickle.load(sfile) state.pop('__traits_version__') print("load settings", self.settings_id) self.trait_set(trait_change_notify=True, **state) except Exception as e: print("error loading settings", end=' ') exc_type, exc_value, exc_tb = sys.exc_info() info = str(e) log = '\n'.join( traceback.format_exception(exc_type, exc_value, exc_tb)[2:]) print(log) print(str(self.__class__)) print(e) print() def dump_settings(self): sfilename = 'config/%s.pkl' % self.settings_id sfilename = os.path.join(os.path.split(__file__)[0], sfilename) with open(sfilename, 'wb') as sfile: state = self.__getstate__() for key in list(state): if key.startswith('_') and key is not '__traits_version__': state.pop(key) pickle.dump(state, sfile) print("saved settings", self.settings_id)
class Loader(HasTraits): table_to_load = Enum(all_table_names) txt_file = File() new_from_txt_file = Button() name = String() def _new_from_txt_file_fired(self): file_name = self.txt_file print(file_name) f = open(file_name, 'r') tt = TraitsTable() n = 1 ide_n = 0 for line in f: string = line[:-1] ide = self.name + str(ide_n) tt.options.append( TraitsTableOption(fr=n, to=n, re=string, identifier=ide)) n += 1 ide_n += 1 tt.configure_traits() f.close() view = View( Item('table_to_load'), HGroup(Item('txt_file'), Item('name'), Item('new_from_txt_file', show_label=False)))
class NotesView(HasTraits): notes = String('') save = Button() def selected_update(self, obj, name, old, new): if not isinstance(new, ModelDataDirectory): try: new = new[0] except (IndexError, TypeError): return try: if os.path.isdir(new.path): # p = os.path.join(new.path, 'notes.txt') if os.path.isfile(p): with open(p, 'r') as f: self.notes = f.read() self.path = p else: self.path = p self.notes = '' except AttributeError: pass def _save_fired(self): if self.path is not None: with open(self.path, 'w') as f: f.write(self.notes) def traits_view(self): v = View(Item('notes', style='custom', show_label=False), HGroup(spring, Item('save', show_label=False))) return v
class IndexSelector(HasTraits): name = String('Weight') names = ['Volume', 'Weight'] def traits_view(self): v = View(Item('name', editor=EnumEditor(name='names'))) return v
class ConstraintsPlotContainer(ConstraintsContainer): """ A Plot container that supports constraints-based layout """ # !! Bits copied from BasePlotContainer !! container_under_layers = Tuple("background", "image", "underlay", "plot") draw_order = Instance(list, args=(DEFAULT_DRAWING_ORDER,)) draw_layer = String('plot')
class Client(HasTraits): command = Property(String('GetData', enter_set=True, auto_set=False), depends_on='_command') _command = Str resend = Button receive_data_stream = Button response = String port = Int(1069) # port = Int(8080) # host = Str('192.168.0.65') # host = Str('129.138.12.145') host = 'localhost' path = None kind = Enum('IPC', 'UDP', 'TCP') period = Float(100) periodic = Event periodic_label = Property(depends_on='_alive') periods_completed = Int time_remain = Float n_periods = Int(100) _alive = Bool(False) calculated_duration = Property(depends_on=['n_periods', 'period']) ask_id = 'A' sent_commands = List pcommand = Str test_command = '' test_response = '' _sock = None def _get_calculated_duration(self): return self.period / 1000. * self.n_periods / 3600. def _periodic_fired(self): self._alive = not self._alive self.periods_completed = 0 if self._alive: t = Thread(target=self._loop) t.start() def _loop(self): self.time_remain = self.calculated_duration # sock = self.get_connection() while self._alive and self.periods_completed <= self.n_periods: t = time.time() try: self._send(sock=None) self.time_remain = self.calculated_duration - self.periods_completed * self.period / 1000.0 / 3600. self.periods_completed += 1 time.sleep(max(0, self.period / 1000.0 - (time.time() - t))) except Exception, e: print 'exception', e print 'looping complete' self._alive = False
class TextDisplay(HasTraits): string = String('Choose a model name.\n') view = View(Item('string', show_label=False, height=25, springy=False, style='custom'), handler=TextDisplayHandler())
class TestClass(HasTraits): b = Bool(True) b_str = String("teststring") traits_view = View(Item(name = 'b', label = "boooool", show_label = False, editor = ToggleButtonEditor(label_value = "b_str")))
class AuxPlotOptions(HasTraits): use = Bool name = Str(NULL_STR) plot_name = Property(Str, depends_on='name') names = List([ NULL_STR, 'Analysis Number Stacked', 'Analysis Number', 'Radiogenic 40Ar', 'K/Ca', 'K/Cl', 'Mol K39', 'Ideogram' ]) _plot_names = List([ '', 'analysis_number_stacked', 'analysis_number', 'radiogenic_yield', 'kca', 'kcl', 'moles_k39', 'relative_probability' ]) scale = Enum('linear', 'log') height = Int(100, enter_set=True, auto_set=False) x_error = Bool(False) y_error = Bool(False) show_labels = Bool(False) filter_str = String(enter_set=True, auto_set=False) normalize = None use_time_axis = False initialized = False ylimits = Tuple(Float, Float, transient=True) overlay_positions = Dict(transient=True) _has_ylimits = Bool(False) def set_overlay_position(self, k, v): self.overlay_positions[k] = v def has_ylimits(self): return self._has_ylimits def dump_yaml(self): d = dict() attrs = ('use', 'name', 'scale', 'height', 'x_error', 'y_error', 'show_labels', 'filter_str') for attr in attrs: d[attr] = getattr(self, attr) d['ylimits'] = map(float, self.ylimits) d['overlay_positions'] = dict(self.overlay_positions) return d def _name_changed(self): if self.initialized: if self.name != NULL_STR: self.use = True print 'setting use true', self.name def _get_plot_name(self): if self.name in self.names: return self._plot_names[self.names.index(self.name)] else: return self.name
class ControlPanel(HasTraits): """ This object is the core of the traitsUI interface. Its view is the right panel of the application, and it hosts the method for interaction between the objects and the GUI. """ experiment = Instance(Experiment, ()) camera = Instance(Camera, ()) figure = Instance(Figure) results = Instance(Results, ()) start_stop_acquisition = Button("Start/Stop acquisition") results_string = String() acquisition_thread = Instance(AcquisitionThread) data_changed = Event view = View(Group( Group( Item('start_stop_acquisition', show_label=False ), Item('results_string',show_label=False, springy=True, style='custom' ), label="Control", dock='tab',), Group( Group( Item('experiment', style='custom', show_label=False), label="Input",), Group( Item('results', style='custom', show_label=False), label="Results",), label='Experiment', dock="tab"), Item('camera', style='custom', show_label=False, dock="tab"), layout='tabbed'), ) def _start_stop_acquisition_fired(self): """ Callback of the "start stop acquisition" button. This starts the acquisition thread, or kills it. """ if self.acquisition_thread and self.acquisition_thread.isAlive(): self.acquisition_thread.wants_abort = True else: self.acquisition_thread = AcquisitionThread() self.acquisition_thread.display = self.add_line self.acquisition_thread.acquire = self.camera.acquire self.acquisition_thread.experiment = self.experiment self.acquisition_thread.image_show = self.image_show self.acquisition_thread.results = self.results self.acquisition_thread.start() def add_line(self, string): """ Adds a line to the textbox display. """ self.results_string = (string + "\n" + self.results_string)[0:1000] def image_show(self, image): """ Plots an image on the canvas in a thread safe way. """ self.figure.axes[0].images=[] self.figure.axes[0].imshow(image, aspect='auto') self.data_changed = True
class RemoteSource(Source): host = String('localhost', enter_set=True, auto_set=False) port = Int(1084, enter_set=True, auto_set=False) def traits_view(self): return View(Item('host'), Item('port')) def url(self): return 'pvs://{}:{}'.format(self.host, self.port)
def __init__(self, subDict): """ Args: subDict (dict): Dictionary of [Component] sub-keywords/params. """ # Super-class initialization is ABSOLUTELY NECESSARY, in order # to get all the Traits/UI machinery setup correctly. super(Component, self).__init__() # Stash the sub-keywords/parameters. self._subDict = subDict # Fetch available keyword/parameter definitions. def maybe(name): return subDict[name] if name in subDict else None self._mfr = maybe('manufacturer') self._pkg = maybe('package') self._pins = maybe('pin') self._diffs = maybe('diff_pin') # Check for the required keywords. if not self._mfr: raise LookupError("Missing [Manufacturer]!") if not self._pkg: print(self._mfr) raise LookupError("Missing [Package]!") if not self._pins: raise LookupError("Missing [Pin]!") # Set up the GUI. self.add_trait('manufacturer', String(self._mfr)) self.add_trait('package', String(self._pkg)) self.add_trait('_pin', Trait(list(self._pins)[0], self._pins)) self._content = [ Group( Item('manufacturer', label='Manufacturer', style='readonly'), Item('package', label='Package', style='readonly'), Item('_pin', label='Pin'), label='Component', show_border=True, ), ]
class DummyCopyProcess(FileCopyProcess): """ Dummy file copy. """ f = Float(output=False, optional=False, desc="a float") i = File(output=False, optional=False, desc="a file") l = List(File(), output=False, optional=False, desc="a list of file") s = String(output=True, optional=False, desc="the output file copy map") def _run_process(self): self.s = repr(self.copied_inputs)
class TraitsTable(HasTraits): name = String() description = String() options = List(Instance(TraitsTableOption, ())) upload = Button() def load(self, tablename): self.name = tablename print(tablename) db_mgr = DBManager() if db_mgr.fuzion_tables.count_options(tablename) > 0: pass else: t = utilities.get_aws_table(tablename) utilities.save_table_to_db(t) t = db_mgr.fuzion_tables.get_table(tablename) for row in t: option = TraitsTableOption() option.fr = int(row.fr) option.to = int(row.to) option.re = str(row.re) option.identifier = str(row.identifier) leads_to = "" if row.leads_to_table is not None: leads_to = row.leads_to_table option.leads_to = leads_to self.options.append(option) def _upload_fired(self): for option in self.options: utilities.export_to_aws(name=self.name, identifier=option.identifier, fr=option.fr, to=option.to, re=option.re, leads_to=option.leads_to) view = View(Item('name'), Item('description'), Item('options', editor=ListEditor(style='custom')), Item('upload', show_label=False))