bec-widgets 0.99.8__py3-none-any.whl → 0.99.9__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (155) hide show
  1. CHANGELOG.md +6 -6
  2. PKG-INFO +1 -1
  3. {bec_widgets-0.99.8.dist-info → bec_widgets-0.99.9.dist-info}/METADATA +1 -1
  4. {bec_widgets-0.99.8.dist-info → bec_widgets-0.99.9.dist-info}/RECORD +8 -155
  5. pyproject.toml +6 -1
  6. docs/Makefile +0 -20
  7. docs/_static/custom.css +0 -170
  8. docs/_templates/custom-class-template.rst +0 -34
  9. docs/_templates/custom-module-template.rst +0 -66
  10. docs/api_reference/api_reference.md +0 -12
  11. docs/assets/apps_48dp.svg +0 -1
  12. docs/assets/display_settings_48dp.svg +0 -1
  13. docs/assets/index_api.svg +0 -97
  14. docs/assets/index_contribute.svg +0 -76
  15. docs/assets/index_getting_started.svg +0 -66
  16. docs/assets/index_user_guide.svg +0 -67
  17. docs/assets/rocket_launch_48dp.svg +0 -1
  18. docs/assets/widget_screenshots/buttons.png +0 -0
  19. docs/assets/widget_screenshots/device_box.png +0 -0
  20. docs/assets/widget_screenshots/device_browser.png +0 -0
  21. docs/assets/widget_screenshots/device_inputs.png +0 -0
  22. docs/assets/widget_screenshots/dock_area.png +0 -0
  23. docs/assets/widget_screenshots/figure.png +0 -0
  24. docs/assets/widget_screenshots/image_widget.png +0 -0
  25. docs/assets/widget_screenshots/motor_map_widget.png +0 -0
  26. docs/assets/widget_screenshots/position_indicator.png +0 -0
  27. docs/assets/widget_screenshots/queue.png +0 -0
  28. docs/assets/widget_screenshots/ring_progress_bar.png +0 -0
  29. docs/assets/widget_screenshots/scan_controller.png +0 -0
  30. docs/assets/widget_screenshots/spinner.gif +0 -0
  31. docs/assets/widget_screenshots/status_box.png +0 -0
  32. docs/assets/widget_screenshots/text_box.png +0 -0
  33. docs/assets/widget_screenshots/toggle.png +0 -0
  34. docs/assets/widget_screenshots/waveform_widget.png +0 -0
  35. docs/assets/widget_screenshots/website.png +0 -0
  36. docs/conf.py +0 -82
  37. docs/developer/developer.md +0 -52
  38. docs/developer/introduction/concepts.md +0 -14
  39. docs/developer/introduction/contributing.md +0 -28
  40. docs/developer/introduction/introduction.md +0 -16
  41. docs/developer/introduction/useful_links.md +0 -23
  42. docs/developer/widget_development/bec_dispatcher.md +0 -143
  43. docs/developer/widget_development/widget_base_class.md +0 -171
  44. docs/developer/widget_development/widget_development.md +0 -14
  45. docs/index.md +0 -74
  46. docs/introduction/introduction.md +0 -18
  47. docs/make.bat +0 -35
  48. docs/requirements.txt +0 -12
  49. docs/user/api_reference/api_reference.md +0 -11
  50. docs/user/applications/applications.md +0 -10
  51. docs/user/customisation.md +0 -123
  52. docs/user/getting_started/BECDockArea.png +0 -0
  53. docs/user/getting_started/auto_updates.md +0 -82
  54. docs/user/getting_started/getting_started.md +0 -15
  55. docs/user/getting_started/gui_complex_gui.gif +0 -0
  56. docs/user/getting_started/installation.md +0 -33
  57. docs/user/getting_started/quick_start.md +0 -110
  58. docs/user/getting_started/video_tutorials.md +0 -17
  59. docs/user/user.md +0 -71
  60. docs/user/widgets/bec_figure/BECFigure.png +0 -0
  61. docs/user/widgets/bec_figure/bec_figure.md +0 -105
  62. docs/user/widgets/bec_status_box/bec_status_box.gif +0 -0
  63. docs/user/widgets/bec_status_box/bec_status_box.md +0 -38
  64. docs/user/widgets/buttons/buttons.md +0 -90
  65. docs/user/widgets/buttons/dark_mode_disabled.png +0 -0
  66. docs/user/widgets/buttons/dark_mode_enabled.png +0 -0
  67. docs/user/widgets/device_browser/device_browser.md +0 -36
  68. docs/user/widgets/device_browser/device_browser.png +0 -0
  69. docs/user/widgets/device_input/device_input.md +0 -100
  70. docs/user/widgets/dock_area/BECDockArea.png +0 -0
  71. docs/user/widgets/dock_area/bec_dock_area.md +0 -109
  72. docs/user/widgets/image/image_plot.gif +0 -0
  73. docs/user/widgets/image/image_widget.md +0 -84
  74. docs/user/widgets/motor_map/motor.gif +0 -0
  75. docs/user/widgets/motor_map/motor_map.md +0 -80
  76. docs/user/widgets/position_indicator/position_indicator.md +0 -69
  77. docs/user/widgets/positioner_box/positioner_box.md +0 -63
  78. docs/user/widgets/progress_bar/progress_bar.gif +0 -0
  79. docs/user/widgets/progress_bar/ring_progress_bar.md +0 -103
  80. docs/user/widgets/queue/queue.md +0 -41
  81. docs/user/widgets/scan_control/hide_scan_control.png +0 -0
  82. docs/user/widgets/scan_control/scan_control.gif +0 -0
  83. docs/user/widgets/scan_control/scan_control.md +0 -54
  84. docs/user/widgets/spinner/spinner.md +0 -68
  85. docs/user/widgets/text_box/text_box.md +0 -74
  86. docs/user/widgets/toggle/toggle.md +0 -66
  87. docs/user/widgets/waveform/bec_figure_dap.gif +0 -0
  88. docs/user/widgets/waveform/scatter_2D.gif +0 -0
  89. docs/user/widgets/waveform/w1D.gif +0 -0
  90. docs/user/widgets/waveform/waveform_widget.md +0 -132
  91. docs/user/widgets/website/website.md +0 -69
  92. docs/user/widgets/widgets.md +0 -220
  93. tests/__init__.py +0 -0
  94. tests/end-2-end/__init__.py +0 -0
  95. tests/end-2-end/conftest.py +0 -53
  96. tests/end-2-end/test_bec_dock_rpc_e2e.py +0 -298
  97. tests/end-2-end/test_bec_figure_rpc_e2e.py +0 -212
  98. tests/end-2-end/test_rpc_register_e2e.py +0 -40
  99. tests/end-2-end/test_scan_control_e2e.py +0 -71
  100. tests/references/SpinnerWidget/SpinnerWidget_darwin.png +0 -0
  101. tests/references/SpinnerWidget/SpinnerWidget_linux.png +0 -0
  102. tests/references/SpinnerWidget/SpinnerWidget_started_darwin.png +0 -0
  103. tests/references/SpinnerWidget/SpinnerWidget_started_linux.png +0 -0
  104. tests/unit_tests/__init__.py +0 -0
  105. tests/unit_tests/client_mocks.py +0 -189
  106. tests/unit_tests/conftest.py +0 -64
  107. tests/unit_tests/test_bec_connector.py +0 -80
  108. tests/unit_tests/test_bec_dispatcher.py +0 -119
  109. tests/unit_tests/test_bec_dock.py +0 -155
  110. tests/unit_tests/test_bec_figure.py +0 -270
  111. tests/unit_tests/test_bec_image.py +0 -63
  112. tests/unit_tests/test_bec_image_widget.py +0 -217
  113. tests/unit_tests/test_bec_motor_map.py +0 -282
  114. tests/unit_tests/test_bec_queue.py +0 -111
  115. tests/unit_tests/test_bec_status_box.py +0 -123
  116. tests/unit_tests/test_client_utils.py +0 -76
  117. tests/unit_tests/test_color_map_selector.py +0 -42
  118. tests/unit_tests/test_color_validation.py +0 -75
  119. tests/unit_tests/test_configs/config_device.yaml +0 -33
  120. tests/unit_tests/test_configs/config_device_no_entry.yaml +0 -27
  121. tests/unit_tests/test_configs/config_scan.yaml +0 -82
  122. tests/unit_tests/test_crosshair.py +0 -143
  123. tests/unit_tests/test_dark_mode_button.py +0 -70
  124. tests/unit_tests/test_device_browser.py +0 -83
  125. tests/unit_tests/test_device_input_base.py +0 -76
  126. tests/unit_tests/test_device_input_widgets.py +0 -178
  127. tests/unit_tests/test_error_utils.py +0 -63
  128. tests/unit_tests/test_generate_cli_client.py +0 -123
  129. tests/unit_tests/test_generate_plugin.py +0 -155
  130. tests/unit_tests/test_motor_map_widget.py +0 -194
  131. tests/unit_tests/test_msgs/__init__.py +0 -0
  132. tests/unit_tests/test_msgs/available_scans_message.py +0 -989
  133. tests/unit_tests/test_plot_base.py +0 -95
  134. tests/unit_tests/test_plugin_utils.py +0 -13
  135. tests/unit_tests/test_positioner_box.py +0 -130
  136. tests/unit_tests/test_ring_progress_bar.py +0 -337
  137. tests/unit_tests/test_rpc_register.py +0 -52
  138. tests/unit_tests/test_rpc_server.py +0 -42
  139. tests/unit_tests/test_rpc_widget_handler.py +0 -7
  140. tests/unit_tests/test_scan_control.py +0 -324
  141. tests/unit_tests/test_scan_control_group_box.py +0 -160
  142. tests/unit_tests/test_setting_dialog.py +0 -96
  143. tests/unit_tests/test_spinner.py +0 -31
  144. tests/unit_tests/test_stop_button.py +0 -27
  145. tests/unit_tests/test_text_box_widget.py +0 -54
  146. tests/unit_tests/test_toggle.py +0 -38
  147. tests/unit_tests/test_vscode_widget.py +0 -75
  148. tests/unit_tests/test_waveform1d.py +0 -712
  149. tests/unit_tests/test_waveform_widget.py +0 -462
  150. tests/unit_tests/test_website_widget.py +0 -25
  151. tests/unit_tests/test_widget_io.py +0 -90
  152. tests/unit_tests/test_yaml_dialog.py +0 -163
  153. {bec_widgets-0.99.8.dist-info → bec_widgets-0.99.9.dist-info}/WHEEL +0 -0
  154. {bec_widgets-0.99.8.dist-info → bec_widgets-0.99.9.dist-info}/entry_points.txt +0 -0
  155. {bec_widgets-0.99.8.dist-info → bec_widgets-0.99.9.dist-info}/licenses/LICENSE +0 -0
File without changes
@@ -1,53 +0,0 @@
1
- import random
2
- import time
3
- from contextlib import contextmanager
4
-
5
- import pytest
6
- from bec_lib.endpoints import MessageEndpoints
7
-
8
- from bec_widgets.cli.client_utils import _start_plot_process
9
- from bec_widgets.cli.rpc_register import RPCRegister
10
- from bec_widgets.utils import BECDispatcher
11
- from bec_widgets.widgets.dock import BECDockArea
12
- from bec_widgets.widgets.figure import BECFigure
13
-
14
-
15
- # make threads check in autouse, **will be executed at the end**; better than
16
- # having it in fixtures for each test, since it prevents from needing to
17
- # 'manually' shutdown bec_client_lib (for example) to make it happy, whereas
18
- # whereas in fact bec_client_lib makes its on cleanup
19
- @pytest.fixture(autouse=True)
20
- def threads_check_fixture(threads_check):
21
- return
22
-
23
-
24
- @pytest.fixture
25
- def gui_id():
26
- return f"figure_{random.randint(0,100)}" # make a new gui id each time, to ensure no 'gui is alive' zombie key can perturbate
27
-
28
-
29
- @contextmanager
30
- def plot_server(gui_id, klass, client_lib):
31
- dispatcher = BECDispatcher(client=client_lib) # Has to init singleton with fixture client
32
- process, _ = _start_plot_process(gui_id, klass, client_lib._client._service_config.config_path)
33
- try:
34
- while client_lib._client.connector.get(MessageEndpoints.gui_heartbeat(gui_id)) is None:
35
- time.sleep(0.3)
36
- yield gui_id
37
- finally:
38
- process.terminate()
39
- process.wait()
40
- dispatcher.disconnect_all()
41
- dispatcher.reset_singleton()
42
-
43
-
44
- @pytest.fixture
45
- def rpc_server_figure(gui_id, bec_client_lib):
46
- with plot_server(gui_id, BECFigure, bec_client_lib) as server:
47
- yield server
48
-
49
-
50
- @pytest.fixture
51
- def rpc_server_dock(gui_id, bec_client_lib):
52
- with plot_server(gui_id, BECDockArea, bec_client_lib) as server:
53
- yield server
@@ -1,298 +0,0 @@
1
- import time
2
-
3
- import numpy as np
4
- import pytest
5
- from bec_lib.client import BECClient
6
- from bec_lib.endpoints import MessageEndpoints
7
-
8
- from bec_widgets.cli.auto_updates import AutoUpdates
9
- from bec_widgets.cli.client import BECDockArea, BECFigure, BECImageShow, BECMotorMap, BECWaveform
10
- from bec_widgets.utils import Colors
11
-
12
- # pylint: disable=unused-argument
13
- # pylint: disable=redefined-outer-name
14
- # pylint: disable=too-many-locals
15
-
16
-
17
- def test_rpc_add_dock_with_figure_e2e(bec_client_lib, rpc_server_dock):
18
- # BEC client shortcuts
19
- dock = BECDockArea(rpc_server_dock)
20
- client = bec_client_lib
21
- dev = client.device_manager.devices
22
- scans = client.scans
23
- queue = client.queue
24
-
25
- # Create 3 docks
26
- d0 = dock.add_dock("dock_0")
27
- d1 = dock.add_dock("dock_1")
28
- d2 = dock.add_dock("dock_2")
29
-
30
- dock_config = dock._config_dict
31
- assert len(dock_config["docks"]) == 3
32
- # Add 3 figures with some widgets
33
- fig0 = d0.add_widget("BECFigure")
34
- fig1 = d1.add_widget("BECFigure")
35
- fig2 = d2.add_widget("BECFigure")
36
-
37
- dock_config = dock._config_dict
38
- assert len(dock_config["docks"]) == 3
39
- assert len(dock_config["docks"]["dock_0"]["widgets"]) == 1
40
- assert len(dock_config["docks"]["dock_1"]["widgets"]) == 1
41
- assert len(dock_config["docks"]["dock_2"]["widgets"]) == 1
42
-
43
- assert fig1.__class__.__name__ == "BECFigure"
44
- assert fig1.__class__ == BECFigure
45
- assert fig2.__class__.__name__ == "BECFigure"
46
- assert fig2.__class__ == BECFigure
47
-
48
- mm = fig0.motor_map("samx", "samy")
49
- plt = fig1.plot(x_name="samx", y_name="bpm4i")
50
- im = fig2.image("eiger")
51
-
52
- assert mm.__class__.__name__ == "BECMotorMap"
53
- assert mm.__class__ == BECMotorMap
54
- assert plt.__class__.__name__ == "BECWaveform"
55
- assert plt.__class__ == BECWaveform
56
- assert im.__class__.__name__ == "BECImageShow"
57
- assert im.__class__ == BECImageShow
58
-
59
- assert mm._config_dict["signals"] == {
60
- "dap": None,
61
- "source": "device_readback",
62
- "x": {
63
- "name": "samx",
64
- "entry": "samx",
65
- "unit": None,
66
- "modifier": None,
67
- "limits": [-50.0, 50.0],
68
- },
69
- "y": {
70
- "name": "samy",
71
- "entry": "samy",
72
- "unit": None,
73
- "modifier": None,
74
- "limits": [-50.0, 50.0],
75
- },
76
- "z": None,
77
- }
78
- assert plt._config_dict["curves"]["bpm4i-bpm4i"]["signals"] == {
79
- "dap": None,
80
- "source": "scan_segment",
81
- "x": {"name": "samx", "entry": "samx", "unit": None, "modifier": None, "limits": None},
82
- "y": {"name": "bpm4i", "entry": "bpm4i", "unit": None, "modifier": None, "limits": None},
83
- "z": None,
84
- }
85
- assert im._config_dict["images"]["eiger"]["monitor"] == "eiger"
86
-
87
- # check initial position of motor map
88
- initial_pos_x = dev.samx.read()["samx"]["value"]
89
- initial_pos_y = dev.samy.read()["samy"]["value"]
90
-
91
- # Try to make a scan
92
- status = scans.line_scan(dev.samx, -5, 5, steps=10, exp_time=0.05, relative=False)
93
-
94
- # wait for scan to finish
95
- while not status.status == "COMPLETED":
96
- time.sleep(0.2)
97
-
98
- # plot
99
- plt_last_scan_data = queue.scan_storage.storage[-1].data
100
- plt_data = plt.get_all_data()
101
- assert plt_data["bpm4i-bpm4i"]["x"] == plt_last_scan_data["samx"]["samx"].val
102
- assert plt_data["bpm4i-bpm4i"]["y"] == plt_last_scan_data["bpm4i"]["bpm4i"].val
103
-
104
- # image
105
- last_image_device = client.connector.get_last(MessageEndpoints.device_monitor_2d("eiger"))[
106
- "data"
107
- ].data
108
- time.sleep(0.5)
109
- last_image_plot = im.images[0].get_data()
110
- np.testing.assert_equal(last_image_device, last_image_plot)
111
-
112
- # motor map
113
- final_pos_x = dev.samx.read()["samx"]["value"]
114
- final_pos_y = dev.samy.read()["samy"]["value"]
115
-
116
- # check final coordinates of motor map
117
- motor_map_data = mm.get_data()
118
-
119
- np.testing.assert_equal(
120
- [motor_map_data["x"][0], motor_map_data["y"][0]], [initial_pos_x, initial_pos_y]
121
- )
122
- np.testing.assert_equal(
123
- [motor_map_data["x"][-1], motor_map_data["y"][-1]], [final_pos_x, final_pos_y]
124
- )
125
-
126
-
127
- def test_dock_manipulations_e2e(rpc_server_dock):
128
- dock = BECDockArea(rpc_server_dock)
129
-
130
- d0 = dock.add_dock("dock_0")
131
- d1 = dock.add_dock("dock_1")
132
- d2 = dock.add_dock("dock_2")
133
- dock_config = dock._config_dict
134
- assert len(dock_config["docks"]) == 3
135
-
136
- d0.detach()
137
- dock.detach_dock("dock_2")
138
- dock_config = dock._config_dict
139
- assert len(dock_config["docks"]) == 3
140
- assert len(dock.temp_areas) == 2
141
-
142
- d0.attach()
143
- dock_config = dock._config_dict
144
- assert len(dock_config["docks"]) == 3
145
- assert len(dock.temp_areas) == 1
146
-
147
- d2.remove()
148
- dock_config = dock._config_dict
149
- assert len(dock_config["docks"]) == 2
150
-
151
- assert ["dock_0", "dock_1"] == list(dock_config["docks"])
152
-
153
- dock.clear_all()
154
-
155
- dock_config = dock._config_dict
156
- assert len(dock_config["docks"]) == 0
157
- assert len(dock.temp_areas) == 0
158
-
159
-
160
- def test_ring_bar(rpc_server_dock):
161
- dock = BECDockArea(rpc_server_dock)
162
-
163
- d0 = dock.add_dock(name="dock_0")
164
-
165
- bar = d0.add_widget("RingProgressBar")
166
- assert bar.__class__.__name__ == "RingProgressBar"
167
-
168
- bar.set_number_of_bars(5)
169
- bar.set_colors_from_map("viridis")
170
- bar.set_value([10, 20, 30, 40, 50])
171
-
172
- bar_config = bar._config_dict
173
-
174
- expected_colors = [list(color) for color in Colors.golden_angle_color("viridis", 5, "RGB")]
175
- bar_colors = [ring._config_dict["color"] for ring in bar.rings]
176
- bar_values = [ring._config_dict["value"] for ring in bar.rings]
177
- assert bar_config["num_bars"] == 5
178
- assert bar_values == [10, 20, 30, 40, 50]
179
- assert bar_colors == expected_colors
180
-
181
-
182
- def test_ring_bar_scan_update(bec_client_lib, rpc_server_dock):
183
- dock = BECDockArea(rpc_server_dock)
184
-
185
- d0 = dock.add_dock("dock_0")
186
-
187
- bar = d0.add_widget("RingProgressBar")
188
-
189
- client = bec_client_lib
190
- dev = client.device_manager.devices
191
- dev.samx.tolerance.set(0)
192
- dev.samy.tolerance.set(0)
193
- scans = client.scans
194
-
195
- status = scans.line_scan(dev.samx, -5, 5, steps=10, exp_time=0.05, relative=False)
196
- status.wait()
197
-
198
- bar_config = bar._config_dict
199
- assert bar_config["num_bars"] == 1
200
- assert bar_config["rings"][0]["value"] == 10
201
- assert bar_config["rings"][0]["min_value"] == 0
202
- assert bar_config["rings"][0]["max_value"] == 10
203
-
204
- status = scans.grid_scan(dev.samx, -5, 5, 4, dev.samy, -10, 10, 4, relative=True, exp_time=0.1)
205
- status.wait()
206
-
207
- bar_config = bar._config_dict
208
- assert bar_config["num_bars"] == 1
209
- assert bar_config["rings"][0]["value"] == 16
210
- assert bar_config["rings"][0]["min_value"] == 0
211
- assert bar_config["rings"][0]["max_value"] == 16
212
-
213
- init_samx = dev.samx.read()["samx"]["value"]
214
- init_samy = dev.samy.read()["samy"]["value"]
215
- final_samx = init_samx + 5
216
- final_samy = init_samy + 10
217
-
218
- dev.samx.velocity.put(5)
219
- dev.samy.velocity.put(5)
220
-
221
- status = scans.umv(dev.samx, 5, dev.samy, 10, relative=True)
222
- status.wait()
223
-
224
- bar_config = bar._config_dict
225
- assert bar_config["num_bars"] == 2
226
- assert bar_config["rings"][0]["value"] == final_samx
227
- assert bar_config["rings"][1]["value"] == final_samy
228
- assert bar_config["rings"][0]["min_value"] == init_samx
229
- assert bar_config["rings"][0]["max_value"] == final_samx
230
- assert bar_config["rings"][1]["min_value"] == init_samy
231
- assert bar_config["rings"][1]["max_value"] == final_samy
232
-
233
-
234
- def test_auto_update(bec_client_lib, rpc_server_dock, qtbot):
235
- dock = BECDockArea(rpc_server_dock)
236
-
237
- AutoUpdates.enabled = True
238
- AutoUpdates.create_default_dock = True
239
- dock.auto_updates = AutoUpdates(gui=dock)
240
- dock.auto_updates.start_default_dock()
241
-
242
- def get_default_figure():
243
- return dock.auto_updates.get_default_figure()
244
-
245
- qtbot.waitUntil(lambda: get_default_figure() is not None, timeout=10000)
246
- plt = get_default_figure()
247
-
248
- dock.selected_device = "bpm4i"
249
-
250
- # we need to start the update script manually; normally this is done when the GUI is started
251
- dock._start_update_script()
252
-
253
- client = bec_client_lib
254
- dev = client.device_manager.devices
255
- scans = client.scans
256
- queue = client.queue
257
-
258
- status = scans.line_scan(dev.samx, -5, 5, steps=10, exp_time=0.05, relative=False)
259
- status.wait()
260
-
261
- last_scan_data = queue.scan_storage.storage[-1].data
262
-
263
- # get data from curves
264
- widgets = plt.widget_list
265
- plt_data = widgets[0].get_all_data()
266
-
267
- # check plotted data
268
- assert (
269
- plt_data[f"Scan {status.scan.scan_number} - bpm4i"]["x"]
270
- == last_scan_data["samx"]["samx"].val
271
- )
272
- assert (
273
- plt_data[f"Scan {status.scan.scan_number} - bpm4i"]["y"]
274
- == last_scan_data["bpm4i"]["bpm4i"].val
275
- )
276
-
277
- status = scans.grid_scan(
278
- dev.samx, -10, 10, 5, dev.samy, -5, 5, 5, exp_time=0.05, relative=False
279
- )
280
- status.wait()
281
-
282
- plt = dock.auto_updates.get_default_figure()
283
- widgets = plt.widget_list
284
- qtbot.waitUntil(lambda: len(plt.widget_list) > 0, timeout=5000)
285
- plt_data = widgets[0].get_all_data()
286
-
287
- last_scan_data = queue.scan_storage.storage[-1].data
288
-
289
- # check plotted data
290
- assert (
291
- plt_data[f"Scan {status.scan.scan_number} - {dock.selected_device}"]["x"]
292
- == last_scan_data["samx"]["samx"].val
293
- )
294
- assert (
295
- plt_data[f"Scan {status.scan.scan_number} - {dock.selected_device}"]["y"]
296
- == last_scan_data["samy"]["samy"].val
297
- )
298
- dock.auto_updates.shutdown()
@@ -1,212 +0,0 @@
1
- import time
2
-
3
- import numpy as np
4
- import pytest
5
- from bec_lib.endpoints import MessageEndpoints
6
-
7
- from bec_widgets.cli.client import BECFigure, BECImageShow, BECMotorMap, BECWaveform
8
-
9
-
10
- def test_rpc_waveform1d_custom_curve(rpc_server_figure):
11
- fig = BECFigure(rpc_server_figure)
12
-
13
- ax = fig.plot()
14
- curve = ax.plot(x=[1, 2, 3], y=[1, 2, 3])
15
- curve.set_color("red")
16
- curve = ax.curves[0]
17
- curve.set_color("blue")
18
-
19
- assert len(fig.widgets) == 1
20
- assert len(fig.widgets[ax._rpc_id].curves) == 1
21
-
22
-
23
- def test_rpc_plotting_shortcuts_init_configs(rpc_server_figure, qtbot):
24
- fig = BECFigure(rpc_server_figure)
25
-
26
- plt = fig.plot(x_name="samx", y_name="bpm4i")
27
- im = fig.image("eiger")
28
- motor_map = fig.motor_map("samx", "samy")
29
- plt_z = fig.plot(x_name="samx", y_name="samy", z_name="bpm4i", new=True)
30
-
31
- # Checking if classes are correctly initialised
32
- assert len(fig.widgets) == 4
33
- assert plt.__class__.__name__ == "BECWaveform"
34
- assert plt.__class__ == BECWaveform
35
- assert im.__class__.__name__ == "BECImageShow"
36
- assert im.__class__ == BECImageShow
37
- assert motor_map.__class__.__name__ == "BECMotorMap"
38
- assert motor_map.__class__ == BECMotorMap
39
-
40
- # check if the correct devices are set
41
- # plot
42
- assert plt._config_dict["curves"]["bpm4i-bpm4i"]["signals"] == {
43
- "dap": None,
44
- "source": "scan_segment",
45
- "x": {"name": "samx", "entry": "samx", "unit": None, "modifier": None, "limits": None},
46
- "y": {"name": "bpm4i", "entry": "bpm4i", "unit": None, "modifier": None, "limits": None},
47
- "z": None,
48
- }
49
- # image
50
- assert im._config_dict["images"]["eiger"]["monitor"] == "eiger"
51
- # motor map
52
- assert motor_map._config_dict["signals"] == {
53
- "dap": None,
54
- "source": "device_readback",
55
- "x": {
56
- "name": "samx",
57
- "entry": "samx",
58
- "unit": None,
59
- "modifier": None,
60
- "limits": [-50.0, 50.0],
61
- },
62
- "y": {
63
- "name": "samy",
64
- "entry": "samy",
65
- "unit": None,
66
- "modifier": None,
67
- "limits": [-50.0, 50.0],
68
- },
69
- "z": None,
70
- }
71
- # plot with z scatter
72
- assert plt_z._config_dict["curves"]["bpm4i-bpm4i"]["signals"] == {
73
- "dap": None,
74
- "source": "scan_segment",
75
- "x": {"name": "samx", "entry": "samx", "unit": None, "modifier": None, "limits": None},
76
- "y": {"name": "samy", "entry": "samy", "unit": None, "modifier": None, "limits": None},
77
- "z": {"name": "bpm4i", "entry": "bpm4i", "unit": None, "modifier": None, "limits": None},
78
- }
79
-
80
-
81
- def test_rpc_waveform_scan(rpc_server_figure, bec_client_lib):
82
- fig = BECFigure(rpc_server_figure)
83
-
84
- # add 3 different curves to track
85
- plt = fig.plot(x_name="samx", y_name="bpm4i")
86
- fig.plot(x_name="samx", y_name="bpm3a")
87
- fig.plot(x_name="samx", y_name="bpm4d")
88
-
89
- client = bec_client_lib
90
- dev = client.device_manager.devices
91
- scans = client.scans
92
- queue = client.queue
93
-
94
- status = scans.line_scan(dev.samx, -5, 5, steps=10, exp_time=0.05, relative=False)
95
- status.wait()
96
-
97
- last_scan_data = queue.scan_storage.storage[-1].data
98
-
99
- # get data from curves
100
- plt_data = plt.get_all_data()
101
-
102
- # check plotted data
103
- assert plt_data["bpm4i-bpm4i"]["x"] == last_scan_data["samx"]["samx"].val
104
- assert plt_data["bpm4i-bpm4i"]["y"] == last_scan_data["bpm4i"]["bpm4i"].val
105
- assert plt_data["bpm3a-bpm3a"]["x"] == last_scan_data["samx"]["samx"].val
106
- assert plt_data["bpm3a-bpm3a"]["y"] == last_scan_data["bpm3a"]["bpm3a"].val
107
- assert plt_data["bpm4d-bpm4d"]["x"] == last_scan_data["samx"]["samx"].val
108
- assert plt_data["bpm4d-bpm4d"]["y"] == last_scan_data["bpm4d"]["bpm4d"].val
109
-
110
-
111
- def test_rpc_image(rpc_server_figure, bec_client_lib):
112
- fig = BECFigure(rpc_server_figure)
113
-
114
- im = fig.image("eiger")
115
-
116
- client = bec_client_lib
117
- dev = client.device_manager.devices
118
- scans = client.scans
119
-
120
- status = scans.line_scan(dev.samx, -5, 5, steps=10, exp_time=0.05, relative=False)
121
- status.wait()
122
-
123
- last_image_device = client.connector.get_last(MessageEndpoints.device_monitor_2d("eiger"))[
124
- "data"
125
- ].data
126
- last_image_plot = im.images[0].get_data()
127
-
128
- # check plotted data
129
- np.testing.assert_equal(last_image_device, last_image_plot)
130
-
131
-
132
- def test_rpc_motor_map(rpc_server_figure, bec_client_lib):
133
- fig = BECFigure(rpc_server_figure)
134
-
135
- motor_map = fig.motor_map("samx", "samy")
136
-
137
- client = bec_client_lib
138
- dev = client.device_manager.devices
139
- scans = client.scans
140
-
141
- initial_pos_x = dev.samx.read()["samx"]["value"]
142
- initial_pos_y = dev.samy.read()["samy"]["value"]
143
-
144
- status = scans.mv(dev.samx, 1, dev.samy, 2, relative=True)
145
- status.wait()
146
-
147
- final_pos_x = dev.samx.read()["samx"]["value"]
148
- final_pos_y = dev.samy.read()["samy"]["value"]
149
-
150
- # check plotted data
151
- motor_map_data = motor_map.get_data()
152
-
153
- np.testing.assert_equal(
154
- [motor_map_data["x"][0], motor_map_data["y"][0]], [initial_pos_x, initial_pos_y]
155
- )
156
- np.testing.assert_equal(
157
- [motor_map_data["x"][-1], motor_map_data["y"][-1]], [final_pos_x, final_pos_y]
158
- )
159
-
160
-
161
- def test_dap_rpc(rpc_server_figure, bec_client_lib, qtbot):
162
-
163
- fig = BECFigure(rpc_server_figure)
164
- plt = fig.plot(x_name="samx", y_name="bpm4i", dap="GaussianModel")
165
-
166
- client = bec_client_lib
167
- dev = client.device_manager.devices
168
- scans = client.scans
169
-
170
- dev.bpm4i.sim.sim_select_model("GaussianModel")
171
- params = dev.bpm4i.sim.sim_params
172
- params.update(
173
- {"noise": "uniform", "noise_multiplier": 10, "center": 5, "sigma": 1, "amplitude": 200}
174
- )
175
- dev.bpm4i.sim.sim_params = params
176
- time.sleep(1)
177
-
178
- res = scans.line_scan(dev.samx, 0, 8, steps=50, relative=False)
179
- res.wait()
180
-
181
- # especially on slow machines, the fit might not be done yet
182
- # so we wait until the fit reaches the expected value
183
- def wait_for_fit():
184
- dap_curve = plt.get_curve("bpm4i-bpm4i-GaussianModel")
185
- fit_params = dap_curve.dap_params
186
- print(fit_params)
187
- return np.isclose(fit_params["center"], 5, atol=0.5)
188
-
189
- qtbot.waitUntil(wait_for_fit, timeout=10000)
190
-
191
-
192
- def test_removing_subplots(rpc_server_figure, bec_client_lib):
193
- fig = BECFigure(rpc_server_figure)
194
- plt = fig.plot(x_name="samx", y_name="bpm4i", dap="GaussianModel")
195
- im = fig.image(monitor="eiger")
196
- mm = fig.motor_map(motor_x="samx", motor_y="samy")
197
-
198
- assert len(fig.widget_list) == 3
199
-
200
- # removing curves
201
- assert len(plt.curves) == 2
202
- plt.curves[0].remove()
203
- assert len(plt.curves) == 1
204
- plt.remove_curve("bpm4i-bpm4i")
205
- assert len(plt.curves) == 0
206
-
207
- # removing all subplots from figure
208
- plt.remove()
209
- im.remove()
210
- mm.remove()
211
-
212
- assert len(fig.widget_list) == 0
@@ -1,40 +0,0 @@
1
- import pytest
2
-
3
- from bec_widgets.cli.client import BECFigure, BECImageShow, BECMotorMap, BECWaveform
4
-
5
-
6
- def test_rpc_register_list_connections(rpc_server_figure):
7
- fig = BECFigure(rpc_server_figure)
8
-
9
- plt = fig.plot(x_name="samx", y_name="bpm4i")
10
- im = fig.image("eiger")
11
- motor_map = fig.motor_map("samx", "samy")
12
- plt_z = fig.plot(x_name="samx", y_name="samy", z_name="bpm4i", new=True)
13
-
14
- # keep only class names from objects, since objects on server and client are different
15
- # so the best we can do is to compare types (rpc register is unit-tested elsewhere)
16
- all_connections = {obj_id: type(obj).__name__ for obj_id, obj in fig._get_all_rpc().items()}
17
-
18
- all_subwidgets_expected = {wid: type(widget).__name__ for wid, widget in fig.widgets.items()}
19
- curve_1D = fig.widgets[plt._rpc_id]
20
- curve_2D = fig.widgets[plt_z._rpc_id]
21
- curves_expected = {
22
- curve_1D._rpc_id: type(curve_1D).__name__,
23
- curve_2D._rpc_id: type(curve_2D).__name__,
24
- }
25
- curves_expected.update({curve._gui_id: type(curve).__name__ for curve in curve_1D.curves})
26
- curves_expected.update({curve._gui_id: type(curve).__name__ for curve in curve_2D.curves})
27
- fig_expected = {fig._rpc_id: type(fig).__name__}
28
- image_item_expected = {
29
- fig.widgets[im._rpc_id].images[0]._rpc_id: type(fig.widgets[im._rpc_id].images[0]).__name__
30
- }
31
-
32
- all_connections_expected = {
33
- **all_subwidgets_expected,
34
- **curves_expected,
35
- **fig_expected,
36
- **image_item_expected,
37
- }
38
-
39
- assert len(all_connections) == 8
40
- assert all_connections == all_connections_expected
@@ -1,71 +0,0 @@
1
- import time
2
-
3
- import pytest
4
-
5
- from bec_widgets.utils.widget_io import WidgetIO
6
- from bec_widgets.widgets.scan_control import ScanControl
7
-
8
-
9
- @pytest.fixture(scope="function")
10
- def scan_control(qtbot, bec_client_lib): # , mock_dev):
11
- widget = ScanControl(client=bec_client_lib)
12
- qtbot.addWidget(widget)
13
- qtbot.waitExposed(widget)
14
- yield widget
15
-
16
-
17
- def test_scan_control_populate_scans_e2e(scan_control):
18
- expected_scans = [
19
- "grid_scan",
20
- "fermat_scan",
21
- "round_scan",
22
- "cont_line_scan",
23
- "cont_line_fly_scan",
24
- "round_scan_fly",
25
- "round_roi_scan",
26
- "time_scan",
27
- "monitor_scan",
28
- "acquire",
29
- "line_scan",
30
- ]
31
- items = [
32
- scan_control.comboBox_scan_selection.itemText(i)
33
- for i in range(scan_control.comboBox_scan_selection.count())
34
- ]
35
- assert scan_control.comboBox_scan_selection.count() == len(expected_scans)
36
- assert sorted(items) == sorted(expected_scans)
37
-
38
-
39
- def test_run_line_scan_with_parameters_e2e(scan_control, bec_client_lib, qtbot):
40
- client = bec_client_lib
41
- queue = client.queue
42
-
43
- scan_name = "line_scan"
44
- kwargs = {"exp_time": 0.01, "steps": 10, "relative": True, "burst_at_each_point": 1}
45
- args = {"device": "samx", "start": -5, "stop": 5}
46
-
47
- scan_control.comboBox_scan_selection.setCurrentText(scan_name)
48
-
49
- # Set kwargs in the UI
50
- for kwarg_box in scan_control.kwarg_boxes:
51
- for widget in kwarg_box.widgets:
52
- for key, value in kwargs.items():
53
- if widget.arg_name == key:
54
- WidgetIO.set_value(widget, value)
55
- break
56
- # Set args in the UI
57
- for widget in scan_control.arg_box.widgets:
58
- for key, value in args.items():
59
- if widget.arg_name == key:
60
- WidgetIO.set_value(widget, value)
61
- break
62
-
63
- # Run the scan
64
- scan_control.button_run_scan.click()
65
- time.sleep(2)
66
-
67
- last_scan = queue.scan_storage.storage[-1]
68
- assert last_scan.status_message.info["scan_name"] == scan_name
69
- assert last_scan.status_message.info["exp_time"] == kwargs["exp_time"]
70
- assert last_scan.status_message.info["scan_motors"] == [args["device"]]
71
- assert last_scan.status_message.info["num_points"] == kwargs["steps"]
File without changes