mirror of
https://github.com/bec-project/bec_widgets.git
synced 2025-07-14 11:41:49 +02:00
139 lines
7.9 KiB
Markdown
139 lines
7.9 KiB
Markdown
(developer.widget_development.bec_dispatcher)=
|
|
|
|
# BECDispatcher
|
|
|
|
## Overview
|
|
|
|
The [`BECDispatcher`](https://bec.readthedocs.io/projects/bec-widgets/en/latest/api_reference/_autosummary/bec_widgets.utils.bec_dispatcher.BECDispatcher.html#bec_widgets.utils.bec_dispatcher.BECDispatcher)
|
|
is a powerful tool that simplifies the process of connecting [Qt slots](https://doc.qt.io/qt-6/signalsandslots.html) to message updates from the BEC server. It enables real-time communication between your widget and the BEC server by listening to specific message channels and triggering callbacks when new data is received.
|
|
|
|
This tool is especially useful for creating widgets that need to respond to dynamic data, such as device readbacks or
|
|
scan updates. By
|
|
using [`BECDispatcher`](https://bec.readthedocs.io/projects/bec-widgets/en/latest/api_reference/_autosummary/bec_widgets.utils.bec_dispatcher.BECDispatcher.html#bec_widgets.utils.bec_dispatcher.BECDispatcher),
|
|
you
|
|
can create callback functions that react to incoming messages and update your widget's state or perform other tasks
|
|
based on the data received.
|
|
|
|
## How It Works
|
|
|
|
When you create a widget that needs to respond to updates from the BEC server, you can use
|
|
the [`BECDispatcher`](https://bec.readthedocs.io/projects/bec-widgets/en/latest/api_reference/_autosummary/bec_widgets.utils.bec_dispatcher.BECDispatcher.html#bec_widgets.utils.bec_dispatcher.BECDispatcher)
|
|
to
|
|
connect specific Qt slots (callback functions) to message endpoints. These endpoints are defined within the BEC system
|
|
and represent specific channels of information (
|
|
e.g., [`device readback`](https://beamline-experiment-control.readthedocs.io/en/latest/api_reference/_autosummary/bec_lib.endpoints.MessageEndpoints.html#bec_lib.endpoints.MessageEndpoints.device_readback),
|
|
[`scan_segment`](https://beamline-experiment-control.readthedocs.io/en/latest/api_reference/_autosummary/bec_lib.endpoints.MessageEndpoints.html#bec_lib.endpoints.MessageEndpoints.scan_segment),
|
|
etc.).
|
|
|
|
### Step-by-Step Guide
|
|
|
|
1. **Create a Callback Function**: Define a function within your widget that will handle the data received from the BEC
|
|
server. This function must accept two parameters: `msg_content` (the message content) and `metadata` (
|
|
additional
|
|
information about the message).
|
|
|
|
```python
|
|
# Example for a callback function that updates a widget display based on motor readback data
|
|
from qtpy.QtCore import Slot
|
|
|
|
@Slot(dict, dict)
|
|
def on_device_readback(self, msg_content:dict, metadata:dict):
|
|
# Process the incoming data
|
|
new_value = msg_content["signals"]['motor_x']["value"]
|
|
# Update the widget's display or perform another action
|
|
self.update_display(new_value)
|
|
```
|
|
|
|
2. **Connect the Slot to an Endpoint**: Use
|
|
the [`BECDispatcher`](https://bec.readthedocs.io/projects/bec-widgets/en/latest/api_reference/_autosummary/bec_widgets.utils.bec_dispatcher.BECDispatcher.html#bec_widgets.utils.bec_dispatcher.BECDispatcher)
|
|
to connect your callback function to a specific
|
|
endpoint. The endpoint represents the type of data or message you're interested in.
|
|
|
|
```python
|
|
from bec_lib.endpoints import MessageEndpoints
|
|
|
|
self.bec_dispatcher.connect_slot(self.on_device_readback, MessageEndpoints.device_readback("motor_x"))
|
|
```
|
|
|
|
3. **Handle Incoming Data**: Your callback function will be triggered automatically whenever a new message is received
|
|
on the connected endpoint. Use the data in `msg_content` to update your widget or perform other actions.
|
|
|
|
4. **Clean Up Connections**: If your widget is being destroyed or you no longer need to listen for updates, make sure to
|
|
disconnect your slots from
|
|
the [`BECDispatcher`](https://bec.readthedocs.io/projects/bec-widgets/en/latest/api_reference/_autosummary/bec_widgets.utils.bec_dispatcher.BECDispatcher.html#bec_widgets.utils.bec_dispatcher.BECDispatcher)
|
|
to avoid memory or thread leaks.
|
|
|
|
```python
|
|
self.bec_dispatcher.disconnect_slot(self.on_device_readback, MessageEndpoints.device_readback("motor_x"))
|
|
```
|
|
|
|
### Example: Motor Map Widget
|
|
|
|
The [`BECMotorMap`](https://bec.readthedocs.io/projects/bec-widgets/en/latest/api_reference/_autosummary/bec_widgets.widgets.figure.plots.motor_map.motor_map.BECMotorMap.html#bec-widgets-widgets-figure-plots-motor-map-motor-map-becmotormap)
|
|
widget is a great example of
|
|
how [`BECDispatcher`](https://bec.readthedocs.io/projects/bec-widgets/en/latest/api_reference/_autosummary/bec_widgets.utils.bec_dispatcher.BECDispatcher.html#bec_widgets.utils.bec_dispatcher.BECDispatcher)
|
|
can be used to handle real-time data updates. This
|
|
widget listens for updates on specific motor positions and dynamically updates the motor map display.
|
|
|
|
Here's a breakdown of
|
|
how [`BECDispatcher`](https://bec.readthedocs.io/projects/bec-widgets/en/latest/api_reference/_autosummary/bec_widgets.utils.bec_dispatcher.BECDispatcher.html#bec_widgets.utils.bec_dispatcher.BECDispatcher)
|
|
is used in
|
|
the [`BECMotorMap`](https://bec.readthedocs.io/projects/bec-widgets/en/latest/api_reference/_autosummary/bec_widgets.widgets.figure.plots.motor_map.motor_map.BECMotorMap.html#bec-widgets-widgets-figure-plots-motor-map-motor-map-becmotormap)
|
|
widget:
|
|
|
|
1. **Connecting to Motor Readbacks**:
|
|
The widget connects to
|
|
the [`device readback`](https://beamline-experiment-control.readthedocs.io/en/latest/api_reference/_autosummary/bec_lib.endpoints.MessageEndpoints.html#bec_lib.endpoints.MessageEndpoints.device_readback)
|
|
endpoints using
|
|
the [`connect_slot`](https://bec.readthedocs.io/projects/bec-widgets/en/latest/api_reference/_autosummary/bec_widgets.utils.bec_dispatcher.BECDispatcher.html#bec_widgets.utils.bec_dispatcher.BECDispatcher.connect_slot)
|
|
method
|
|
of [`BECDispatcher`](https://bec.readthedocs.io/projects/bec-widgets/en/latest/api_reference/_autosummary/bec_widgets.utils.bec_dispatcher.BECDispatcher.html#bec_widgets.utils.bec_dispatcher.BECDispatcher).
|
|
This allows
|
|
the widget to receive real-time updates about the motor positions.
|
|
|
|
```{literalinclude} ../../../bec_widgets/widgets/figure/plots/motor_map/motor_map.py
|
|
:language: python
|
|
:pyobject: BECMotorMap._connect_motor_to_slots
|
|
:dedent: 4
|
|
```
|
|
|
|
2. **Handling Readback Data**:
|
|
The `on_device_readback` slot is called whenever new data is received from the motor readback. This slot processes
|
|
the data and updates the motor map plot accordingly.
|
|
|
|
```{literalinclude} ../../../bec_widgets/widgets/figure/plots/motor_map/motor_map.py
|
|
:language: python
|
|
:pyobject: BECMotorMap.on_device_readback
|
|
:dedent: 4
|
|
```
|
|
|
|
3. **Updating the Plot**:
|
|
The motor map plot is updated in response to the new data, providing a real-time visualization of the motor's
|
|
position.
|
|
|
|
```{literalinclude} ../../../bec_widgets/widgets/figure/plots/motor_map/motor_map.py
|
|
:language: python
|
|
:pyobject: BECMotorMap._update_plot
|
|
:dedent: 4
|
|
```
|
|
|
|
4. **Disconnecting When No Longer Needed**:
|
|
The widget ensures that connections are properly cleaned up when no longer needed.
|
|
|
|
```{literalinclude} ../../../bec_widgets/widgets/figure/plots/motor_map/motor_map.py
|
|
:language: python
|
|
:pyobject: BECMotorMap._update_plot
|
|
:dedent: 4
|
|
```
|
|
|
|
## Conclusion
|
|
|
|
The [`BECDispatcher`](https://bec.readthedocs.io/projects/bec-widgets/en/latest/api_reference/_autosummary/bec_widgets.utils.bec_dispatcher.BECDispatcher.html#bec_widgets.utils.bec_dispatcher.BECDispatcher)
|
|
is a key tool for developing interactive and responsive widgets within the BEC framework. By leveraging this tool, you can create widgets that automatically respond to real-time data updates from the BEC server,
|
|
enhancing the interactivity and functionality of your user interface.
|
|
|
|
In next tutorials we will cover how to create a custom widget using the BECDispatcher and BECWidget base class.
|
|
|
|
```{note}
|
|
For more details on specific messages and endpoints, please refer to the [Message Endpoints Documentation](https://beamline-experiment-control.readthedocs.io/en/latest/api_reference/_autosummary/bec_lib.endpoints.MessageEndpoints.html#bec-lib-endpoints-messageendpoints).
|
|
``` |