UI-Components
DataClass UI
A simple UI for dataclasses, which allows to edit the values of dataclasses by the user within a dialog.
DataClass UI: Controller
This module provides classes to generate simple UI’s for dataclasses, which allow to edit the values of dataclasses in an easy way.
Use these controllers to create and steer the UI’s.
- class omc3_gui.ui_components.dataclass_ui.controller.DataClassTabbedUI(dclass: object | type, layout: QtWidgets.QLayout | None = None, widget: QtWidgets.QTabWidget | None = None)[source]
Controller for the UI representation of a dataclass, containing other dataclasses as fields. It contains a tabbed layout that can be added to any QWidget.
- class omc3_gui.ui_components.dataclass_ui.controller.DataClassUI(field_definitions: Sequence[FieldUIDef], dclass: type | object, layout: QtWidgets.QLayout | None = None)[source]
Controller for the UI representation of a dataclass. It contains a grid-layout that can be added to any QWidget/QLayout.
- reset_labels()[source]
Resets all labels to indicate that the field shows the currently set value in the dataclass.
- update_model()[source]
Updates all dataclass fields from the current edit-widget values.
- update_model_from_widget(name: str)[source]
Updates the dataclass value of the given field from the edit-widget.
- Parameters:
name (str) -- name of the field in the dataclass
- update_ui()[source]
Updates all edit-widgets from the dataclass values.
- update_widget_from_model(name: str)[source]
Updates the edit-widget of the given field from the dataclass values.
- Parameters:
name (str) -- name of the field in the dataclass
- validate(only_modified: bool = False)[source]
Checks all edit-widgets for valid choices.
The validation function NEED to return a truthy value, if the choice is valid. If it is invalid, they can either return a falsy value or raise an exception. In the latter case, this exception will be printed instead of the default message.
- class omc3_gui.ui_components.dataclass_ui.controller.FieldUI(widget: QtWidgets.QWidget, label: QtWidgets.QLabel, get_value: Callable, set_value: Callable, text_color: str | None = '#212121', modified: bool = False)[source]
Controller for a single field in a dataclass, connecting it to a widget.
This class is not meant to be used directly, but is rather automatically generated by and attached to
omc3_gui.utils.dataclass_ui.controller.DataClassUI
.- has_changed()[source]
Triggered when the widget has been modified. Sets then the modified flag and changes label font.
- reset()[source]
Reset the label font to normal and clear the modified flag.
- omc3_gui.ui_components.dataclass_ui.controller.build_getter_setter(widget: QtWidgets.QWidget, field_type: type) tuple[Callable, Callable] [source]
Getter/Setter Factory for widgets.
- Parameters:
widget (QtWidgets.QWidget) -- The widget to get/set the value of.
field_type (type) -- The type of the dataclass field.
- omc3_gui.ui_components.dataclass_ui.controller.get_dataclass_types(dclass: type | object, names: Sequence[str])[source]
Returns a dictionary mapping field names to their associated types.
Why this weird way? First of all, we avoided the cyclic imports of type-hints by using the from __future__ import annotations, but whith this, all type-hints on the dataclasses become ForwardReferences, i.e. strings. So if we get them from the dataclass-fields via field.pytype or field.pytype.__args__, we cannot instanciate them later on.
get_type_hints() from typing solves this problem, but it evaluates the type-hints of all fields in the dataclass. But this can cause again import errors, because the classes were not actually imported (this is why there are no cyclic imports)!
So this function allows using get_type_hints() on the dataclass itself, but only gets the types of the fields that we need, in the hopes that there is no import problem with those.
In the use-case of the DataClass UI here, we should only have very basic types for the fields, so this should be fine.
If you are here because there is, you need to redesign your dataclass/imports. Sorry.
- Parameters:
dclass (type) -- The data class to extract field types from.
names (Sequence[str]) -- The names of the fields to extract types from.
- Returns:
A dictionary mapping field names to their associated types.
- Return type:
Dict[str, type]
- omc3_gui.ui_components.dataclass_ui.controller.run_dialog(dialog: file_dialogs.OpenFilesDialog, get_value: Callable, set_value: Callable)[source]
Asks the user to select a directory/file, using the get_value function o determine the default directory and passing the result to set_value if not None.
- Parameters:
dialog (file_dialogs.OpenFilesDialog) -- The dialog to run.
get_value (Callable) -- The function to get the last value, e.g. from a widget.
set_value (Callable) -- The function to set the value returned from the dialog.
DataClass UI: Model
The backend components that make up the dataclass UI. These are used as inputs to the controllers to define the meta-data and the type of the dataclass fields, so that the controller can find the fitting widgets and provide the user with additional information.
- class omc3_gui.ui_components.dataclass_ui.model.DirectoryPath(*args, **kwargs)[source]
Convenience Class to indicate that the Path should lead to a directory. For the inheritance: https://stackoverflow.com/questions/29850801/subclass-pathlib-path-fails
- class omc3_gui.ui_components.dataclass_ui.model.FieldUIDef(name: str, label: str | None = None, pytype: type | None = None, comment: str | None = None, editable: bool | None = True)[source]
Definition of an FieldUI to be generated by
omc3_gui.utils.dataclass_ui.controller.DataClassUI
. This defines how the label and edit-field widgets should look like for a field in the dataclass to be UI’ed. Missing information is parsed in from the dataclass isetlf if possible, but values given here take precedence.
- class omc3_gui.ui_components.dataclass_ui.model.FilePath(*args, **kwargs)[source]
Convenience Class to indicate that the Path should lead to a file. For the inheritance: https://stackoverflow.com/questions/29850801/subclass-pathlib-path-fails
- class omc3_gui.ui_components.dataclass_ui.model.MetaData(label: str | None = None, comment: str | None = None, validate: Callable | None = None)[source]
Metadata for a dataclass-field.
- omc3_gui.ui_components.dataclass_ui.model.choices_validator(*choices: Any) Callable [source]
Return a validator that checks if a given value is in the choices.
- omc3_gui.ui_components.dataclass_ui.model.metafield(label: str, comment: str, default=<dataclasses._MISSING_TYPE object>, validate: ~collections.abc.Callable | None = None) Field [source]
Convenience function to create a dataclass-field with metadata.
DataClass UI: View
The frontend components that make up the dataclass UI, in particular the dialog windows that can be used to edit dataclasses.
- class omc3_gui.ui_components.dataclass_ui.view.DataClassDialog(*args: Any, **kwargs: Any)[source]
Simple dialog window to display the DataClassUI layout. Adds some convenience functionality like “Ok” and “Cancel” buttons and automatic data-validation on close.
- class omc3_gui.ui_components.dataclass_ui.view.DataClassInterface(*args, **kwargs)[source]
Protocol for the DataClassDialog. Observed by
omc3_gui.utils.dataclass_ui.controller.DataClassUI
andomc3_gui.utils.dataclass_ui.controller.DataClassTabbedUI
, both of which can hence be used with the dialog.
- class omc3_gui.ui_components.dataclass_ui.view.QFullIntSpinBox(*args: Any, **kwargs: Any)[source]
Like a QSpinBox, but overwriting default range(0,100) with maximum integer range.
- class omc3_gui.ui_components.dataclass_ui.view.SettingsDialog(*args: Any, **kwargs: Any)[source]
Slight modification of the DataClassDialog to be used for Tabbed-Settings.
DataClass UI: Tools
Additional tools that can be used with dataclasses.
- omc3_gui.ui_components.dataclass_ui.tools.get_field_inline_comments(dclass: type) dict[str, str] [source]
Returns a dictionary mapping field names to their associated inline code-comments. Has been replaced by the use of the metadata, but I like the function, so I leave it here. (jdilly 2023)
- Parameters:
dclass (type) -- The data class to extract field comments from.
- Returns:
A dictionary mapping field names to their associated comments.
- Return type:
Dict[str, str]
- omc3_gui.ui_components.dataclass_ui.tools.load_dataclass_from_json(dclass: type, json_file: str | Path)[source]
Load a dataclass from a JSON file. Selects only the fields that are in the dataclass. Ignores fields that start with an underscore.
- Parameters:
dclass (type) -- The data class to load from the JSON file.
json_file (str) -- The path to the JSON file to load the data class from.
- Returns:
An instance of the data class loaded from the JSON file.
- Return type:
object
- omc3_gui.ui_components.dataclass_ui.tools.save_dataclass_to_json(data: object, json_file: str | Path)[source]
Save a dataclass to a JSON file. Ignores fields that start with an underscore.
- Parameters:
dclass (object) -- The data class instance to save to the JSON file.
json_file (str) -- The path to the JSON file to save the data class to.
- omc3_gui.ui_components.dataclass_ui.tools.update_dataclass_from_json(data: object, json_file: str | Path)[source]
Update a dataclass with data from a JSON file. Selects only the fields that are in the dataclass and json file. Ignores fields that start with an underscore.
- Parameters:
dclass (object) -- The data class instance to update from to the JSON file.
json_file (str) -- The path to the JSON file to load the data from.
- Returns:
An instance of the data class loaded from the JSON file.
- Return type:
object
UI: Base Classes for CVM
This module contains base classes for UI’s that use the Controller-View-Model pattern.
- class omc3_gui.ui_components.base_classes_cvm.Controller(*args: Any, **kwargs: Any)[source]
Base class for the controller of a UI.
The controller is the glue between the view and the model and also the entry-point for the app.
- class omc3_gui.ui_components.base_classes_cvm.LogConsoleFormatter(*args: Any, **kwargs: Any)[source]
- class omc3_gui.ui_components.base_classes_cvm.View(*args: Any, **kwargs: Any)[source]
Base class for the view of a UI.
Adds a menu bar and a status bar as well as the log-console (if in CERN mode).
- get_action_by_title(title: str, parent: QMenuBar | QMenu | None = None) QAction | QMenu [source]
Retrieve a menu action by its title.
- Parameters:
title (str) -- Action title.
parent (QMenuBar) -- Parent menu bar to search, if None the main menu bar is used.
- showAboutDialog() None
Display an ‘about’ dialog.
- showErrorDialog(title: str, message: str)[source]
Convenience function to displays an error dialog.
- Parameters:
title (str) -- Dialog title.
message (str) -- Dialog message.
UI: Colors
This module contains the color definitions for the application. All colors should be defined here for consistency and the elements will then refer to the main color-constants, e.g. colors.TEXT_DARK (not to the colors themselves). This allows for a unified look and feel.
UI: File Dialogs
Helper functions to open files.
- class omc3_gui.ui_components.file_dialogs.OpenAnyMultiDialog(*args: Any, **kwargs: Any)[source]
Open multiple files/folders.
- accept()[source]
This function is called when the user clicks on “Open”. Normally, when selecting a directories, the first directory is followed/opened inside the dialog, i.e. its content is shown. Overwrite super().accept() to prevent that and close the dialog instead.
- class omc3_gui.ui_components.file_dialogs.OpenAnySingleDialog(*args: Any, **kwargs: Any)[source]
Open a single file/folder.
- class omc3_gui.ui_components.file_dialogs.OpenDirectoriesDialog(*args: Any, **kwargs: Any)[source]
Open multiple directories.
- accept()[source]
This function is called when the user clicks on “Open”. Normally, when selecting a directories, the first directory is followed/opened inside the dialog, i.e. its content is shown. Overwrite super().accept() to prevent that and close the dialog instead.
- class omc3_gui.ui_components.file_dialogs.OpenDirectoryDialog(*args: Any, **kwargs: Any)[source]
Open a single directory.
- class omc3_gui.ui_components.file_dialogs.OpenFileDialog(*args: Any, **kwargs: Any)[source]
Open a single file.
- class omc3_gui.ui_components.file_dialogs.OpenFilesDialog(*args: Any, **kwargs: Any)[source]
Quick dialog to open any kind of file. Modifies QFileDialog, and allows only kwargs to be passed.
UI: Item Models
Classes that makes it easier to handle unique items in UI models.
- class omc3_gui.ui_components.item_models.Item(*args, **kwargs)[source]
Protocol for a class that has an ‘id’-property. As used in
omc3_gui.segment_by_segment.main_model.UniqueItemListModel
, this id defines whether two items are “the same”, i.e. only one of them can be present in the model. Example: For the Segments, this should be the name, as if we have two segements with the same name, running them overwrites each other.
- class omc3_gui.ui_components.item_models.UniqueItemListModel[source]
Mixin-Class for a class that has a dictionary of items. Note: I have considered using QAbstractItemModel/QStandardItemModel, but I do not need all the features it provides, so this should be easier and allows for keeping items unique (jdilly, 2023). All items need to have an ‘id’-property.
- add_item(item: Item, emit: bool = True)[source]
Adds an item to the model, if an item with the same id is not already present.
- add_items(items: Sequence[Item])[source]
Adds all items from a list to the model, for which items with the same id are not already present.
- clear()[source]
Removes all items from the model.
- remove_item(item: Item, emit: bool = True)[source]
Removes an item from the model.
- remove_items(items: Sequence[Item])[source]
Removes all items from a list from the model, if they exist.
- try_emit_change(emit: bool = True)[source]
Emits a dataChanged-signal if the model has changed, and if the class provides such a signal.
UI: Message Boxes
Helper functions to display message boxes.
- omc3_gui.ui_components.message_boxes.show_confirmation_dialog(question: str, title: str = 'Confirmation', parent: qtpy.QtWidgets.QWidget = None) bool [source]
Displays a confirmation dialog.
Could also be done with QMessageBox.question(parent, title, question, QMessageBox.Ok | QMessageBox.Cancel).
- Parameters:
question (str) -- Dialog question.
title (str) -- Dialog title.
parent (QtWidgets.QWidget) -- Parent widget.
- Returns:
True if the user confirmed, False otherwise
- Return type:
bool
- omc3_gui.ui_components.message_boxes.show_error_dialog(message: str, title: str = 'Error', parent: qtpy.QtWidgets.QWidget = None)[source]
Displays an error dialog.
This is a convenience function to displays an error dialog.
- Parameters:
title (str) -- Dialog title.
message (str) -- Dialog message.
parent (QtWidgets.QWidget) -- Parent widget.
UI: Styles
Helper functions to style UI elements and plots.
UI: Text Editor Dialog
This module provides a dialog for editing text files.
- class omc3_gui.ui_components.text_editor.TextEditorDialog(*args: Any, **kwargs: Any)[source]
UI: Threads
Helper functions for threads.
- class omc3_gui.ui_components.threads.BackgroundThread(*args: Any, **kwargs: Any)[source]
Thread that runs a function in the background, providing a post- and exception-hook.
- Parameters:
function (Callable) -- The function to run in the background.
message (str) -- The message to display while the function is running.
on_end_function (Callable) -- A function to call when the function is done.
on_exception_function (Callable) -- A function to call when the function throws an exception.
- run()[source]
Runner for the thread. This function is called automatically when the thread is started.
- start()[source]
Connects the thread to the on_end and on_exception signals and starts the thread. This function is triggered manually to start the thread.
UI: Widgets
Pre-Defined Widgets go here.
- class omc3_gui.ui_components.widgets.ChangeButton(*args: Any, **kwargs: Any)[source]
- class omc3_gui.ui_components.widgets.DefaultButton(*args: Any, **kwargs: Any)[source]
- class omc3_gui.ui_components.widgets.HorizontalSeparator(*args: Any, **kwargs: Any)[source]
- class omc3_gui.ui_components.widgets.OpenButton(*args: Any, **kwargs: Any)[source]
- class omc3_gui.ui_components.widgets.RemoveButton(*args: Any, **kwargs: Any)[source]
- class omc3_gui.ui_components.widgets.RunButton(*args: Any, **kwargs: Any)[source]
- class omc3_gui.ui_components.widgets.RunningSpinner(*args: Any, **kwargs: Any)[source]
- class omc3_gui.ui_components.widgets.VerticalSeparator(*args: Any, **kwargs: Any)[source]