Utilities¶
Dialogs, progress indicators, configuration, and infrastructure classes.
Dialog¶
- class mytk.dialog.Dialog(title, buttons_labels=None, geometry=None, auto_position=None, auto_click=(None, None), *args, **kwargs)[source]¶
Bases:
BaseA modal dialog window with configurable buttons and content.
- classmethod showinfo(message, title='Info', auto_click=(None, None), auto_position='center')[source]¶
Show an informational dialog with the given message.
- classmethod showwarning(message, title='Warning', auto_click=(None, None), auto_position='center')[source]¶
Show a warning dialog with the given message.
- classmethod showerror(message, title='Error', auto_click=(None, None), auto_position='center')[source]¶
Show an error dialog with the given message.
- classmethod showprogress(message, title='Info', auto_click=(None, None))[source]¶
Show a progress dialog with the given message.
- property is_disabled¶
Whether the dialog and its children are disabled.
- create_widget(master, **kwargs)[source]¶
Create the Toplevel dialog window and populate its contents.
- create_behavior_buttons()[source]¶
Create Ok and Cancel buttons based on the configured button labels.
ProgressBar¶
- class mytk.progressbar.ProgressBarNotification(*values)[source]¶
Bases:
EnumNotification types for controlling a ProgressBar via NotificationCenter.
- class mytk.progressbar.ProgressBar(maximum=100, mode='determinate')[source]¶
Bases:
BaseA determinate or indeterminate progress bar widget.
- property value¶
The current progress value.
Configurable¶
Configurable — easy settings management with automatic dialog generation.
Scientific instruments and applications almost always have parameters that need to be adjusted by the user: exposure time, gain, wavelength, threshold values, file paths, and so on. Managing those parameters by hand is tedious: you have to store each value somewhere, write code to check that the user has not entered something impossible (a negative exposure time, a wavelength outside the detector range), and build a dialog box so the user can change the settings interactively.
This module takes care of all of that for you.
The basic idea¶
You describe each parameter once — its name, its type, its allowed range, and a sensible default — and the framework handles validation, correction of bad values, and the dialog window automatically.
There are two ways to use it. The simple, recommended way is to inherit
from Configurable and declare parameters as class attributes:
from mytk import App, Configurable, ConfigurableNumericProperty
- class Microscope(Configurable):
- exposure_time = ConfigurableNumericProperty(
default_value = 100, min_value = 1, max_value = 10000, displayed_name = “Exposure time (ms)”)
- gain = ConfigurableNumericProperty(
default_value = 1.0, min_value = 0.1, max_value = 16.0, displayed_name = “Gain”)
scope = Microscope()
# Read and write parameters like ordinary Python attributes. scope.exposure_time = 500 print(scope.exposure_time) # 500
# Show a settings dialog. The user edits the values and clicks Ok; # the new values are applied to the object automatically. scope.show_config_dialog(title=”Microscope settings”)
# Get all current values at once as a plain dict. print(scope.values) # {‘exposure_time’: 500, ‘gain’: 1.0}
Values are always kept valid. If you accidentally assign a value outside the allowed range it is silently clamped to the nearest boundary:
scope.exposure_time = 99999 # stored as 10000 (the maximum) scope.exposure_time = -5 # stored as 1 (the minimum)
The second way — ConfigModel — is for situations where you need to
build the list of parameters programmatically rather than at class
definition time. Both approaches use the same ConfigurableProperty
building blocks and produce the same dialog.
Available property types¶
ConfigurableNumericPropertyFor numbers (integers or floats). You can set a minimum, maximum, a display multiplier, and a format string for the dialog.
ConfigurableStringPropertyFor text values. You can restrict accepted values with a regular expression or a fixed set of allowed strings.
ConfigurablePropertyThe base class. Use this when the built-in types do not fit; you can supply any validation function you like via
validate_fct.
- class mytk.configurable.ConfigurableProperty(name=None, default_value=None, displayed_name=None, validate_fct=None, valid_set=None, value_type=None)[source]¶
Bases:
objectDescriptor that defines a single configurable parameter with validation.
Instances can be declared as class attributes on a
Configurablesubclass (descriptor-based approach) or collected into aConfigModelfor dynamic schema construction.
- class mytk.configurable.ConfigurableStringProperty(valid_regex=None, name=None, default_value=None, displayed_name=None, validate_fct=None, valid_set=None)[source]¶
Bases:
ConfigurablePropertyString-typed configurable property with optional regex validation.
- class mytk.configurable.ConfigurableNumericProperty(min_value=-inf, max_value=inf, multiplier=1, format_string=None, name=None, default_value=None, displayed_name=None, validate_fct=None, valid_set=None, value_type=None)[source]¶
Bases:
ConfigurablePropertyNumeric configurable property with range clamping and optional formatting.
- is_valid_type(value: Any) bool[source]¶
Return True if value is numeric or matches the explicit type.
- class mytk.configurable.Configurable[source]¶
Bases:
objectMixin that turns declared ConfigurableProperty attributes into a managed configuration.
- update_values(new_values: dict)[source]¶
Apply a possibly partial dict of new values.
Each value is sanitized by its property descriptor on assignment.
- is_valid(values: dict) dict[source]¶
Return a per-key dict of booleans indicating validity per property schema.
- all_valid(values: dict) bool[source]¶
Return True only if every value in the dict passes its schema.
- show_config_dialog(title='Configuration', **kwargs)[source]¶
Show a modal configuration dialog built from declared properties.
If the user clicks Ok the values are applied back to self via
update_values(). Extra keyword arguments are forwarded toConfigurationDialog(e.g. buttons_labels, auto_click, geometry).
- class mytk.configurable.ConfigModel(properties: list[ConfigurableProperty] = None, values: dict = None)[source]¶
Bases:
objectExplicit-list configuration model for dynamically built property schemas.
- property values¶
Return the current configuration values as a dict.
- class mytk.configurable.ConfigurationDialog(properties=None, values=None, populate_body_fct=None, *args, **kwargs)[source]¶
Bases:
Dialog,ConfigModelModal dialog that presents configurable properties as editable fields.
NotificationCenter¶
One-to-many notification system for decoupled observer communication.
This implements a notification system where one class can notify many other objects that something has happened. You use this strategy when the notifier does not need to know who does what, but it knows that other objects may need to adjust in response to a change.
At the center of this mechanism is the NotificationCenter: a singleton class that manages the observers and posts the notifications. Notification names must be defined as Enum subclasses.
Example:
class DeviceNotification(Enum):
will_move = "will_move"
did_move = "did_move"
NotificationCenter().post_notification(
DeviceNotification.did_move, self, user_info={"position": (x, y, z)}
)
The NotificationCenter is thread-safe.
- class mytk.notificationcenter.Notification(name, object=None, user_info=None)[source]¶
Bases:
objectA notification object carrying a name, source object, and optional user info.
- class mytk.notificationcenter.ObserverInfo(observer, method=None, notification_name=None, observed_object=None)[source]¶
Bases:
objectRecord describing an observer registration in the NotificationCenter.
- class mytk.notificationcenter.NotificationCenter(*args, **kwargs)[source]¶
Bases:
objectSingleton notification center for one-to-many observer communication.
All notification names must be Enum members. The center is thread-safe.
- add_observer(observer, method, notification_name=None, observed_object=None)[source]¶
Register an observer to be notified when a notification is posted.
- Parameters:
observer – The object that wants to receive notifications.
method – Callable to invoke with the Notification as its argument.
notification_name – Enum member identifying the notification to observe.
observed_object – If provided, only notifications from this object will be forwarded.
- Raises:
ValueError – If notification_name is not None and not an Enum member.
- remove_observer(observer, notification_name=None, observed_object=None)[source]¶
Unregister an observer so it no longer receives notifications.
- Parameters:
observer – The observer object to remove.
notification_name – If provided, remove only for this notification.
observed_object – If provided, remove only for this observed object.
- Raises:
ValueError – If notification_name is not None and not an Enum member.
- post_notification(notification_name, notifying_object, user_info=None)[source]¶
Post a notification, invoking all matching observer callbacks.
- Parameters:
notification_name – Enum member identifying the notification.
notifying_object – The object posting the notification.
user_info – Optional dict of additional data for observers.
- Raises:
ValueError – If notification_name is not an Enum member.
EventCapable¶
Event mixin class for widget behavior.
Provides the EventCapable class, a mixin designed to add event-related capabilities to GUI widgets that expose a widget attribute compatible with tk.Widget. This includes scheduling timed callbacks, cancelling them, and binding or generating Tkinter events.
It is used for Base and App, which handle their widgets differently.
Also includes the HasWidget protocol to allow static checking of widget presence for type-checkers.
- class mytk.eventcapable.HasWidget(*args, **kwargs)[source]¶
Bases:
ProtocolProtocol for objects that expose a widget attribute of type tk.Widget.
This can be used with isinstance(obj, HasWidget) to check interface compliance.
- class mytk.eventcapable.EventCapable(*args, **kwargs)[source]¶
Bases:
objectMixin class providing event-related methods for classes exposing a widget attribute.
Designed to be used alongside other base classes that define self.widget as a tk.Widget. This class should not be used on its own.
Responsibilities: - Scheduling and cancelling timed callbacks (after, after_cancel, etc.) - Event binding and generation via widget.bind and widget.event_generate - Lifecycle cleanup via __del__
- after(delay: int, function: Callable) int[source]¶
Schedules a function to be called after a given time delay.
- after_cancel(task_id: int)[source]¶
Cancels a previously scheduled task by its ID.
- Parameters:
task_id (int) – ID of the task returned by after().
- after_cancel_many(task_ids: Sequence[int])[source]¶
Cancels multiple tasks given a sequence of IDs.
- Parameters:
task_ids (Sequence[int]) – List or tuple of task IDs to cancel.
ModulesManager¶
- class mytk.modulesmanager.ModulesManager[source]¶
Bases:
objectUtility for checking, installing, and importing Python modules at runtime.
- classmethod validate_environment(pip_modules, ask_for_confirmation=True)[source]¶
Ensure all required pip modules are installed and imported.
- classmethod is_imported(module_name)[source]¶
Check whether a module has already been imported into sys.modules.
Vectors¶
- mytk.vectors.is_standard_basis(basis)[source]¶
Return True if the basis is None or is the standard (identity) basis.
- class mytk.vectors.PointDefault(basis=None)[source]¶
Bases:
objectContext manager to temporarily override the default basis for Points.
- class mytk.vectors.Vector(*args, basis=None)[source]¶
Bases:
objectTwo-dimensional vector with optional basis for coordinate transformations.
- property c0¶
Return the first component of the vector.
- property c1¶
Return the second component of the vector.
- property length¶
Return the Euclidean length of the vector in standard coordinates.
- property is_unitary¶
Return True if the vector has unit length within floating-point tolerance.
- class mytk.vectors.Point(*args, basis: Basis = None, reference_point: Point = None)[source]¶
Bases:
objectTwo-dimensional point with basis and optional reference point for coordinate transforms.
- property x¶
Return the x (first) coordinate.
- property y¶
Return the y (second) coordinate.
- property c0¶
Return the first component of the point.
- property c1¶
Return the second component of the point.
- class mytk.vectors.Basis(e0: Vector = None, e1: Vector = None)[source]¶
Bases:
objectOrthogonal 2D basis defined by two vectors, defaulting to the standard basis.
- property e0¶
Return the first basis vector.
- property e1¶
Return the second basis vector.
- property is_standard_basis¶
Return True if this is the standard Cartesian basis.
- property is_orthogonal¶
Return True if the two basis vectors are perpendicular.
- property is_orthonormal¶
Return True if the basis is orthogonal and both vectors are unitary.
- class mytk.vectors.DynamicBasis(source, basis_name)[source]¶
Bases:
BasisBasis that reads its vectors dynamically from an attribute on a source object.
- property e0¶
Return the first basis vector resolved from the source at access time.
- property e1¶
Return the second basis vector resolved from the source at access time.
- class mytk.vectors.Doublet(*args)[source]¶
Bases:
tupleImmutable two-element tuple with arithmetic operations for 2D math.
- property x¶
Return the first element.
- property y¶
Return the second element.
- property length¶
Return the Euclidean length.
- class mytk.vectors.ReferenceFrame(basis=None, scale=None, reference_point: Point = None)[source]¶
Bases:
objectCoordinate reference frame defined by a basis, scale, and origin point.
- property scale¶
Return the scale factors as a tuple of basis vector lengths.
- convert_to_local(point: Point)[source]¶
Convert a point from standard coordinates to local frame coordinates.
- convert_to_canvas(local_point)[source]¶
Convert a local-frame point to canvas (standard) coordinates.
- property unit_vectors_scaled¶
Return the unit vectors multiplied by their respective scale factors.
- property unit_vectors¶
Return the unit vectors of the frame.
- class mytk.vectors.TestCase(methodName='runTest')[source]¶
Bases:
TestCaseUnit tests for Vector, Point, and Basis coordinate operations.
- test_point_reference_frame_same_origin()[source]¶
Test reference frame conversions with the origin at (0, 0).
- test_point_reference_frame_new_origin()[source]¶
Test reference frame conversions with a shifted origin.
- test_point_reference_frame_new_origin_not_standard_coordinates()[source]¶
Test reference frame with a non-standard-basis origin point.
- test_define_default_reference()[source]¶
Test that PointDefault context manager sets a default reference point.
Utilities¶
- mytk.utils.parse_geometry(geometry)[source]¶
Parse a Tkinter geometry string into its size and offset components.
- Parameters:
geometry (str | None) – A geometry string such as “800x600”, “+100+200”, “800x600+100+200”, or None.
- Returns:
(size_str, offset_str) where either element may be None.
- Return type:
Examples
“800x600+100+200” -> (“800x600”, “+100+200”) “800x600” -> (“800x600”, None) “+100+200” -> (None, “+100+200”) None -> (None, None)
- mytk.utils.apply_window_position(widget, position, size_str=None)[source]¶
Set only the +X+Y offset of a Tk or Toplevel window.
The window size is never modified. When size_str is provided the offset is computed and applied immediately; otherwise the call is deferred to the first idle tick (after the event loop has laid out all content) and the window is briefly withdrawn to avoid a visible jump.
- Parameters:
- Raises:
ValueError – If position is not a recognised name.