def __evaluate_expression(self) -> float: variables = dict() for key, value in self.__variables.items(): if isinstance(value, Variable): value = value.output_value variables[key] = value try: assert self.__expression res = typing.cast(float, eval(self.__expression, globals(), variables)) except Exception: import traceback traceback.print_exc() return 0 else: return res
def scalar_from_array(array: _ImageDataType, normalize: bool = True) -> _ImageDataType: if numpy.iscomplexobj(array): # type: ignore # numpy.nextafter returns the next possible represented number after 0 in the direction of 1 # this prevents log from generating -inf from 0.0 # quick way to drop out bottom percent: # samples = 2000, fraction=0.10 # numpy.log(numpy.sort(numpy.abs(numpy.random.choice(data.reshape(numpy.product(data.shape)), samples)))[samples*fraction]) # unfortunately, this needs to be integrated into the display calculation, not the conversion here. # the annoying conversion to float64 is to prevent float32 + float64 returning a 0.0. argh. # TODO: consider optimizing log(abs) to 0.5*log(re**2 + im**2) return typing.cast( _ImageDataType, numpy.log( numpy.abs(array).astype(numpy.float64) + numpy.nextafter(0, 1))) return array
def scale_multidimensional(image: _ImageDataType, scaled_size: ShapeType) -> _ImageDataType: """ Return image scaled to scaled_size. scaled_size should be a sequence with the same length as image. """ # we make a list of slice objects like [0:image_x-1:scaled_size_x*1j] # this will give us scaled_size_x equal points between 0 and image_x-1 slices = [ slice(0, x - 1, y * 1j) for x, y in zip(image.shape, scaled_size) ] # we pass slices into ogrid, to gives us vectors for each dimension # ogrid returns a list of floating numbers if we use complex so we have # to convert to int. np.rint rounds to nearest for us, but doesn't cast to int! coords = [numpy.rint(x).astype(int) for x in numpy.ogrid[slices]] # coords is now, for an array image of dimension n, a list of n 1d arrays we the # coords we want to take from image: return typing.cast(_ImageDataType, image[coords])
def test_accessing_control_in_non_native_axis_works(self) -> None: instrument = InstrumentDevice.Instrument("usim_stem_controller") success = instrument.SetVal("C12.x", 1e-5) self.assertTrue(success) success = instrument.SetVal("C12.y", 2e-5) self.assertTrue(success) success, value = instrument.TryGetVal("C12.px") self.assertTrue(success) assert value is not None self.assertAlmostEqual(value, 1e-5) success, value = instrument.TryGetVal("C12.py") self.assertTrue(success) assert value is not None self.assertAlmostEqual(value, 2e-5) self.assertTrue( isinstance( typing.cast(InstrumentDevice.Control2D, instrument.get_control("C12")).px, InstrumentDevice.ConvertedControl))
def rebin_1d( src: _ImageDataType, len: int, retained: typing.Optional[typing.Dict[str, typing.Any]] = None ) -> _ImageDataType: src_len = src.shape[0] if len < src_len: if retained is not None and (retained.get("src_len") != src_len or retained.get("len") != len): retained.clear() if retained is not None and "w" in retained: w = retained["w"] else: ix, iy = numpy.meshgrid(numpy.linspace(0, src_len - 1, src_len), numpy.linspace(0, len - 1, len)) # type: ignore # # create linear bins # ss = numpy.linspace(0, float(src_len), len+1) # # create some useful row and column values using meshgrid # ix = ix.astype(numpy.int32) # iy = iy.astype(numpy.int32) # # basic idea here is to multiply low window by high window to get the window for each bin; then sum the transpose to do the actual binning # # result is scaled to keep amplitude the same. # w = numpy.maximum(numpy.minimum(ss[iy+1] - ix, 1.0), 0.0) * numpy.minimum(numpy.maximum(ix+1 - ss[iy], 0), 1.0) # below is a faster version (which releases the GIL). s1 = (iy + 1) * float(src_len) / len - ix s2 = s1[::-1, ::-1] w = numpy.clip(s1, 0.0, 1.0) * numpy.clip(s2, 0.0, 1.0) if retained is not None: retained["src_len"] = src_len retained["len"] = len retained["w"] = w weighted_src = w * src # This ensures that nans are handled properly: Only propagate nans that fall within a bin (i.e. where weight != 0) weighted_src[w == 0] = 0 return typing.cast(_ImageDataType, numpy.sum(weighted_src, axis=1) * len / src_len) else: # linear result = numpy.empty((len, ), dtype=numpy.double) index = (numpy.arange(len) * src_len / len).astype(numpy.int32) result[:] = src[index] return result
def test_eels_data_is_consistent_when_energy_offset_changes_with_negative_zlp_offset( self) -> None: instrument = InstrumentDevice.Instrument("usim_stem_controller") instrument.get_scan_data( scan_base.ScanFrameParameters({ "size": (256, 256), "pixel_time_us": 1, "fov_nm": 10 }), 0) instrument.validate_probe_position() camera = typing.cast(EELSCameraSimulator.EELSCameraSimulator, instrument._get_camera_simulator("eels")) camera_size = camera._camera_shape camera.noise.enabled = False readout_area = Geometry.IntRect(origin=Geometry.IntPoint(), size=camera_size) binning_shape = Geometry.IntSize(1, 1) # get the value at 200eV and ZLP offset of 0 instrument.SetVal("ZLPoffset", -20) instrument.get_camera_data("eels", readout_area, binning_shape, 0.01)
def close(self) -> None: self.__cancel = True self.__thread_event.set() self.__thread.join() self.__thread = typing.cast(typing.Any, None)
def close(self) -> None: self.__property_changed_event_listener.close() self.__property_changed_event_listener = typing.cast(typing.Any, None) self.__probe_state_changed_event_listener.close() self.__probe_state_changed_event_listener = typing.cast( typing.Any, None)
def rectangle_from_center_size( center: Core.NormPointType, size: Core.NormSizeType) -> Core.NormRectangleType: return typing.cast( Core.NormRectangleType, tuple(Geometry.FloatRect.from_center_and_size(center, size)))
def rectangle_from_origin_size( origin: Core.NormPointType, size: Core.NormSizeType) -> Core.NormRectangleType: return typing.cast(Core.NormRectangleType, tuple(Geometry.FloatRect(origin, size)))
def __init__(self) -> None: self.__amorphous = typing.cast( _NDArray, numpy.random.RandomState(1).randn(2048, 2048)) * 2 + 1
def close(self) -> None: self.__drift_changed_event_listener.close() self.__drift_changed_event_listener = typing.cast(typing.Any, None)
def create_rgba_image_from_array( array: _ImageDataType, normalize: bool = True, data_range: typing.Optional[typing.Tuple[float, float]] = None, display_limits: typing.Optional[typing.Tuple[float, float]] = None, underlimit: typing.Optional[float] = None, overlimit: typing.Optional[float] = None, lookup: typing.Optional[_RGBAImageDataType] = None ) -> _RGBAImageDataType: assert numpy.ndim(array) in (1, 2, 3) assert numpy.can_cast(array.dtype, numpy.double) # type: ignore if numpy.ndim(array) == 1: # temporary hack to display 1-d images array = array.reshape((1, ) + array.shape) if numpy.ndim(array) == 2: rgba_image = numpy.empty(array.shape, numpy.uint32) if normalize: if display_limits and len(display_limits) == 2: nmin_new = display_limits[0] nmax_new = display_limits[1] # scalar data assigned to each component of rgb view m = 255.0 / (nmax_new - nmin_new) if nmax_new != nmin_new else 1 if lookup is not None: get_rgb_view(rgba_image)[:] = lookup[numpy.clip( typing.cast(_ImageDataType, m * (array - nmin_new)).astype(int), 0, 255)] else: # slower by 5ms # get_rgb_view(rgba_image)[:] = numpy.clip(numpy.multiply(m, numpy.subtract(array[..., numpy.newaxis], nmin_new)), 0, 255) # slowest by 15ms # clipped_array = numpy.clip(array, nmin_new, nmax_new) # get_rgb_view(rgba_image)[:] = m * (clipped_array[..., numpy.newaxis] - nmin_new) # best (in place) clipped_array = numpy.clip(array, nmin_new, nmax_new) # 12ms if clipped_array.dtype in (numpy.float32, numpy.float64): # 12ms numpy.subtract(clipped_array, nmin_new, out=clipped_array) numpy.multiply(clipped_array, m, out=clipped_array) else: clipped_array = (clipped_array - nmin_new) * m # 16ms get_red_view(rgba_image)[:] = clipped_array get_green_view(rgba_image)[:] = clipped_array get_blue_view(rgba_image)[:] = clipped_array if overlimit: rgba_image = numpy.where( numpy.less(array - nmin_new, nmax_new - nmin_new * overlimit), rgba_image, 0xFFFF0000) if underlimit: rgba_image = numpy.where( numpy.greater(array - nmin_new, nmax_new - nmin_new * underlimit), rgba_image, 0xFF0000FF) elif array.size: nmin = data_range[0] if data_range else numpy.amin(array) nmax = data_range[1] if data_range else numpy.amax(array) # scalar data assigned to each component of rgb view m = 255.0 / (nmax - nmin) if nmax != nmin else 1.0 if lookup is not None: get_rgb_view(rgba_image)[:] = lookup[numpy.clip( (m * (array - nmin)).astype(int), 0, 255)] else: # get_rgb_view(rgba_image)[:] = m * (array[..., numpy.newaxis] - nmin) # optimized version below r0 = numpy.empty(array.shape, numpy.uint8) r0[:] = (m * (array - nmin)) rgb_view = get_dtype_view( rgba_image, numpy.uint8).reshape(rgba_image.shape + (-1, ))[..., :3] rgb_view[..., 0] = rgb_view[..., 1] = rgb_view[..., 2] = r0 if overlimit: rgba_image = numpy.where( numpy.less(array - nmin, (nmax - nmin) * overlimit), rgba_image, 0xFFFF0000) if underlimit: rgba_image = numpy.where( numpy.greater(array - nmin, (nmax - nmin) * underlimit), rgba_image, 0xFF0000FF) else: get_rgb_view(rgba_image)[:] = array[ ..., numpy. newaxis] # scalar data assigned to each component of rgb view if rgba_image.size: # 3ms get_alpha_view(rgba_image)[:] = 255 return rgba_image elif numpy.ndim(array) == 3: assert array.shape[2] in (3, 4) # rgb, rgba if array.shape[2] == 4: return get_dtype_view(array, numpy.uint32).reshape( array.shape[:-1]) # squash the color into uint32 else: assert array.shape[2] == 3 rgba_image = numpy.empty(array.shape[:-1] + (4, ), numpy.uint8) rgba_image[:, :, 0:3] = array rgba_image[:, :, 3] = 255 return get_dtype_view(rgba_image, numpy.uint32).reshape( rgba_image.shape[:-1]) # squash the color into uint32 raise Exception("Could not create RGBA from data.")
def __init__(self) -> None: super().__init__() self.icon1 = make_icon(12, 12) self.icon2 = make_icon(48, 36) self.image_model = Model.PropertyModel(make_icon(16, 16), typing.cast(typing.Callable[[typing.Optional[IconType], typing.Optional[IconType]], bool], numpy.array_equal)) self.property_changed_event = Event.Event()