mx-bluesky 0.0.2__py3-none-any.whl → 0.3.1__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.
- mx_bluesky/__main__.py +1 -2
- mx_bluesky/_version.py +14 -2
- mx_bluesky/example.py +4 -4
- mx_bluesky/i04/__init__.py +3 -0
- mx_bluesky/i04/callbacks/murko_callback.py +45 -0
- mx_bluesky/i04/thawing_plan.py +84 -0
- mx_bluesky/i24/serial/__init__.py +49 -0
- mx_bluesky/i24/serial/blueapi_config.yaml +12 -0
- mx_bluesky/{I24 → i24}/serial/dcid.py +53 -41
- mx_bluesky/{I24 → i24}/serial/extruder/EX-gui-edm/DetStage.edl +1 -2
- mx_bluesky/{I24 → i24}/serial/extruder/EX-gui-edm/DiamondExtruder-I24-py3v1.edl +28 -32
- mx_bluesky/{I24 → i24}/serial/extruder/EX-gui-edm/microdrop_alignment.edl +0 -1
- mx_bluesky/i24/serial/extruder/i24ssx_Extruder_Collect_py3v2.py +513 -0
- mx_bluesky/{I24 → i24}/serial/fixed_target/FT-gui-edm/CustomChip_py3v1.edl +1 -2
- mx_bluesky/{I24 → i24}/serial/fixed_target/FT-gui-edm/DetStage.edl +1 -2
- mx_bluesky/{I24 → i24}/serial/fixed_target/FT-gui-edm/DiamondChipI24-py3v1.edl +46 -41
- mx_bluesky/{I24 → i24}/serial/fixed_target/FT-gui-edm/ME14E-GeneralPurpose.edl +0 -1
- mx_bluesky/{I24 → i24}/serial/fixed_target/FT-gui-edm/MappingLite-oxford_py3v1.edl +10 -11
- mx_bluesky/{I24 → i24}/serial/fixed_target/FT-gui-edm/PMAC_Command.edl +0 -1
- mx_bluesky/{I24 → i24}/serial/fixed_target/FT-gui-edm/Shutter_Control.edl +0 -1
- mx_bluesky/{I24 → i24}/serial/fixed_target/FT-gui-edm/microdrop_alignment.edl +0 -1
- mx_bluesky/{I24 → i24}/serial/fixed_target/FT-gui-edm/nudgechip.edl +0 -1
- mx_bluesky/{I24 → i24}/serial/fixed_target/FT-gui-edm/pumpprobe-py3v1.edl +273 -143
- mx_bluesky/i24/serial/fixed_target/FT-gui-edm/short1-laser.png +0 -0
- mx_bluesky/i24/serial/fixed_target/FT-gui-edm/short2-laser.png +0 -0
- mx_bluesky/{I24 → i24}/serial/fixed_target/ft_utils.py +24 -1
- mx_bluesky/i24/serial/fixed_target/i24ssx_Chip_Collect_py3v1.py +798 -0
- mx_bluesky/{I24 → i24}/serial/fixed_target/i24ssx_Chip_Manager_py3v1.py +374 -412
- mx_bluesky/{I24 → i24}/serial/fixed_target/i24ssx_Chip_Mapping_py3v1.py +34 -40
- mx_bluesky/i24/serial/fixed_target/i24ssx_Chip_StartUp_py3v1.py +325 -0
- mx_bluesky/{I24 → i24}/serial/fixed_target/i24ssx_moveonclick.py +39 -41
- mx_bluesky/i24/serial/log.py +156 -0
- mx_bluesky/i24/serial/parameters/__init__.py +15 -0
- mx_bluesky/i24/serial/parameters/constants.py +47 -0
- mx_bluesky/i24/serial/parameters/experiment_parameters.py +124 -0
- mx_bluesky/i24/serial/parameters/fixed_target/cs/cs_maker.json +9 -0
- mx_bluesky/{I24 → i24}/serial/parameters/fixed_target/cs/motor_direction.txt +1 -1
- mx_bluesky/{I24 → i24}/serial/parameters/fixed_target/pvar_files/minichip-oxford.pvar +1 -1
- mx_bluesky/i24/serial/parameters/utils.py +40 -0
- mx_bluesky/i24/serial/run_extruder.sh +19 -0
- mx_bluesky/i24/serial/run_fixed_target.sh +22 -0
- mx_bluesky/i24/serial/run_serial.py +36 -0
- mx_bluesky/{I24 → i24}/serial/set_visit_directory.sh +6 -1
- mx_bluesky/{I24 → i24}/serial/setup_beamline/pv.py +1 -62
- mx_bluesky/{I24 → i24}/serial/setup_beamline/pv_abstract.py +6 -7
- mx_bluesky/{I24 → i24}/serial/setup_beamline/setup_beamline.py +90 -269
- mx_bluesky/{I24 → i24}/serial/setup_beamline/setup_detector.py +47 -40
- mx_bluesky/i24/serial/setup_beamline/setup_zebra_plans.py +459 -0
- mx_bluesky/i24/serial/start_blueapi.sh +28 -0
- mx_bluesky/i24/serial/write_nexus.py +102 -0
- mx_bluesky/parameters/__init__.py +31 -0
- mx_bluesky/parameters/components.py +200 -0
- {mx_bluesky-0.0.2.dist-info → mx_bluesky-0.3.1.dist-info}/METADATA +33 -27
- mx_bluesky-0.3.1.dist-info/RECORD +67 -0
- {mx_bluesky-0.0.2.dist-info → mx_bluesky-0.3.1.dist-info}/WHEEL +1 -1
- mx_bluesky-0.3.1.dist-info/entry_points.txt +4 -0
- mx_bluesky/I24/serial/extruder/i24ssx_Extruder_Collect_py3v2.py +0 -476
- mx_bluesky/I24/serial/fixed_target/FT-gui-edm/ME14E-motors.edl +0 -1874
- mx_bluesky/I24/serial/fixed_target/__init__.py +0 -0
- mx_bluesky/I24/serial/fixed_target/i24ssx_Chip_Collect_py3v1.py +0 -706
- mx_bluesky/I24/serial/fixed_target/i24ssx_Chip_StartUp_py3v1.py +0 -463
- mx_bluesky/I24/serial/log.py +0 -101
- mx_bluesky/I24/serial/parameters/__init__.py +0 -5
- mx_bluesky/I24/serial/parameters/constants.py +0 -39
- mx_bluesky/I24/serial/parameters/fixed_target/cs/cs_maker.json +0 -9
- mx_bluesky/I24/serial/parameters/fixed_target/cs/fiducial_1.txt +0 -4
- mx_bluesky/I24/serial/parameters/fixed_target/cs/fiducial_2.txt +0 -4
- mx_bluesky/I24/serial/parameters/fixed_target/litemaps/currentchip.map +0 -81
- mx_bluesky/I24/serial/parameters/fixed_target/parameters.txt +0 -13
- mx_bluesky/I24/serial/run_serial.py +0 -52
- mx_bluesky/I24/serial/write_nexus.py +0 -113
- mx_bluesky-0.0.2.dist-info/RECORD +0 -58
- mx_bluesky-0.0.2.dist-info/entry_points.txt +0 -4
- /mx_bluesky/{I24 → i24}/__init__.py +0 -0
- /mx_bluesky/{I24/serial → i24/serial/extruder}/__init__.py +0 -0
- /mx_bluesky/{I24/serial/extruder → i24/serial/fixed_target}/__init__.py +0 -0
- /mx_bluesky/{I24 → i24}/serial/parameters/fixed_target/pvar_files/oxford.pvar +0 -0
- /mx_bluesky/{I24 → i24}/serial/run_ssx.sh +0 -0
- /mx_bluesky/{I24 → i24}/serial/setup_beamline/__init__.py +0 -0
- /mx_bluesky/{I24 → i24}/serial/setup_beamline/ca.py +0 -0
- {mx_bluesky-0.0.2.dist-info → mx_bluesky-0.3.1.dist-info}/LICENSE +0 -0
- {mx_bluesky-0.0.2.dist-info → mx_bluesky-0.3.1.dist-info}/top_level.txt +0 -0
|
@@ -3,23 +3,24 @@ Chip mapping utilities for fixed target
|
|
|
3
3
|
|
|
4
4
|
This version changed to python3 March2020 by RLO
|
|
5
5
|
"""
|
|
6
|
+
|
|
6
7
|
import logging
|
|
7
8
|
import time
|
|
8
9
|
|
|
9
10
|
import numpy as np
|
|
10
11
|
from matplotlib import pyplot as plt
|
|
11
12
|
|
|
12
|
-
from mx_bluesky.
|
|
13
|
-
from mx_bluesky.
|
|
14
|
-
from mx_bluesky.
|
|
13
|
+
from mx_bluesky.i24.serial import log
|
|
14
|
+
from mx_bluesky.i24.serial.fixed_target.ft_utils import ChipType
|
|
15
|
+
from mx_bluesky.i24.serial.fixed_target.i24ssx_Chip_StartUp_py3v1 import (
|
|
15
16
|
check_files,
|
|
16
|
-
get_format,
|
|
17
17
|
get_shot_order,
|
|
18
18
|
get_xy,
|
|
19
|
-
|
|
19
|
+
read_parameter_file,
|
|
20
20
|
write_file,
|
|
21
21
|
)
|
|
22
|
-
from mx_bluesky.
|
|
22
|
+
from mx_bluesky.i24.serial.parameters import get_chip_format
|
|
23
|
+
from mx_bluesky.i24.serial.parameters.constants import PARAM_FILE_PATH_FT
|
|
23
24
|
|
|
24
25
|
logger = logging.getLogger("I24ssx.chip_mapping")
|
|
25
26
|
|
|
@@ -34,7 +35,7 @@ def setup_logging():
|
|
|
34
35
|
def read_file_make_dict(fid, chip_type, switch=False):
|
|
35
36
|
a_dict = {}
|
|
36
37
|
b_dict = {}
|
|
37
|
-
with open(fid
|
|
38
|
+
with open(fid) as f:
|
|
38
39
|
for line in f.readlines():
|
|
39
40
|
if line.startswith("#"):
|
|
40
41
|
continue
|
|
@@ -78,36 +79,36 @@ def plot_file(fid, chip_type):
|
|
|
78
79
|
ax1.set_xlim(-1, 26)
|
|
79
80
|
ax1.set_ylim(-1, 26)
|
|
80
81
|
ax1.invert_yaxis()
|
|
81
|
-
check_files(["
|
|
82
|
-
plt.savefig("
|
|
82
|
+
check_files("i24", [f"{chip_type}.png"])
|
|
83
|
+
plt.savefig(f"{fid[:-5]}.png", dpi=200, bbox_inches="tight", pad_inches=0.05)
|
|
83
84
|
return 1
|
|
84
85
|
|
|
85
86
|
|
|
86
87
|
@log.log_on_entry
|
|
87
88
|
def convert_chip_to_hex(fid, chip_type):
|
|
88
89
|
chip_dict = read_file_make_dict(fid, chip_type, True)
|
|
89
|
-
chip_format =
|
|
90
|
-
check_files(["
|
|
91
|
-
with open("
|
|
90
|
+
chip_format = get_chip_format(ChipType(chip_type))
|
|
91
|
+
check_files("i24", [f"{chip_type}.full"])
|
|
92
|
+
with open(f"{fid[:-5]}.full", "w") as g:
|
|
92
93
|
# Normal
|
|
93
94
|
if chip_type in [ChipType.Oxford, ChipType.OxfordInner]:
|
|
94
95
|
shot_order_list = get_shot_order(chip_type)
|
|
95
96
|
logger.info("Shot Order List: \n")
|
|
96
|
-
logger.info("
|
|
97
|
-
logger.info("
|
|
97
|
+
logger.info(f"{shot_order_list[:14]}")
|
|
98
|
+
logger.info(f"{shot_order_list[-14:]}")
|
|
98
99
|
for i, k in enumerate(shot_order_list):
|
|
99
100
|
if i % 20 == 0:
|
|
100
101
|
logger.info("\n")
|
|
101
102
|
else:
|
|
102
|
-
logger.info("
|
|
103
|
+
logger.info(f"{k}")
|
|
103
104
|
sorted_pres_list = []
|
|
104
105
|
for addr in shot_order_list:
|
|
105
106
|
sorted_pres_list.append(chip_dict[addr])
|
|
106
107
|
|
|
107
|
-
windows_per_block = chip_format
|
|
108
|
-
number_of_lines = len(sorted_pres_list) / windows_per_block
|
|
108
|
+
windows_per_block = chip_format.x_num_steps
|
|
109
|
+
number_of_lines = int(len(sorted_pres_list) / windows_per_block)
|
|
109
110
|
hex_length = windows_per_block / 4
|
|
110
|
-
pad = 7 - hex_length
|
|
111
|
+
pad = int(7 - hex_length)
|
|
111
112
|
for i in range(number_of_lines):
|
|
112
113
|
sublist = sorted_pres_list[
|
|
113
114
|
i * windows_per_block : (i * windows_per_block) + windows_per_block
|
|
@@ -116,24 +117,24 @@ def convert_chip_to_hex(fid, chip_type):
|
|
|
116
117
|
right_list = sublist
|
|
117
118
|
else:
|
|
118
119
|
right_list = sublist[::-1]
|
|
119
|
-
hex_string = ("{0:0
|
|
120
|
+
hex_string = (f"{{0:0>{hex_length}X}}").format(
|
|
120
121
|
int("".join(str(x) for x in right_list), 2)
|
|
121
122
|
)
|
|
122
|
-
hex_string = hex_string + pad * "0"
|
|
123
|
+
hex_string = hex_string + (pad * "0")
|
|
123
124
|
pvar = 5001 + i
|
|
124
|
-
line = "P
|
|
125
|
+
line = f"P{pvar}=${hex_string}"
|
|
125
126
|
g.write(line + "\n")
|
|
126
127
|
logger.info("hex string: %s" % (hex_string + 4 * "0"))
|
|
127
|
-
logger.info("line number=
|
|
128
|
+
logger.info(f"line number= {i}")
|
|
128
129
|
logger.info(
|
|
129
|
-
"right_list: \n
|
|
130
|
+
"right_list: \n{}\n".format("".join(str(x) for x in right_list))
|
|
130
131
|
)
|
|
131
|
-
logger.info("PVAR:
|
|
132
|
+
logger.info(f"PVAR: {line}")
|
|
132
133
|
if (i + 1) % windows_per_block == 0:
|
|
133
134
|
logger.info(
|
|
134
135
|
"\n %s" % (40 * (" %i" % ((i / windows_per_block) + 2)))
|
|
135
136
|
)
|
|
136
|
-
logger.info("hex_length:
|
|
137
|
+
logger.info(f"hex_length: {hex_length}")
|
|
137
138
|
else:
|
|
138
139
|
logger.warning("Chip type unknown, no conversion done.")
|
|
139
140
|
return 0
|
|
@@ -141,24 +142,17 @@ def convert_chip_to_hex(fid, chip_type):
|
|
|
141
142
|
|
|
142
143
|
def main():
|
|
143
144
|
setup_logging()
|
|
144
|
-
(
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
sub_dir,
|
|
148
|
-
n_exposures,
|
|
149
|
-
chip_type,
|
|
150
|
-
map_type,
|
|
151
|
-
) = scrape_parameter_file()
|
|
152
|
-
|
|
153
|
-
check_files([".spec"])
|
|
145
|
+
params = read_parameter_file()
|
|
146
|
+
|
|
147
|
+
check_files("i24", [".spec"])
|
|
154
148
|
write_file(suffix=".spec", order="shot")
|
|
155
149
|
|
|
156
|
-
logger.info("PARAMETER PATH =
|
|
157
|
-
fid = PARAM_FILE_PATH_FT / f"{
|
|
158
|
-
logger.info("FID =
|
|
150
|
+
logger.info(f"PARAMETER PATH = {PARAM_FILE_PATH_FT}")
|
|
151
|
+
fid = PARAM_FILE_PATH_FT / f"{params.filename}.spec"
|
|
152
|
+
logger.info(f"FID = {fid}")
|
|
159
153
|
|
|
160
|
-
plot_file(fid, chip_type)
|
|
161
|
-
convert_chip_to_hex(fid, chip_type)
|
|
154
|
+
plot_file(fid, params.chip.chip_type.value)
|
|
155
|
+
convert_chip_to_hex(fid, params.chip.chip_type.value)
|
|
162
156
|
|
|
163
157
|
|
|
164
158
|
if __name__ == "__main__":
|
|
@@ -0,0 +1,325 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Startup utilities for chip
|
|
3
|
+
"""
|
|
4
|
+
|
|
5
|
+
import logging
|
|
6
|
+
import os
|
|
7
|
+
import string
|
|
8
|
+
import time
|
|
9
|
+
from pathlib import Path
|
|
10
|
+
|
|
11
|
+
import numpy as np
|
|
12
|
+
|
|
13
|
+
from mx_bluesky.i24.serial import log
|
|
14
|
+
from mx_bluesky.i24.serial.fixed_target.ft_utils import ChipType
|
|
15
|
+
from mx_bluesky.i24.serial.parameters import FixedTargetParameters, get_chip_format
|
|
16
|
+
from mx_bluesky.i24.serial.parameters.constants import (
|
|
17
|
+
HEADER_FILES_PATH,
|
|
18
|
+
PARAM_FILE_NAME,
|
|
19
|
+
PARAM_FILE_PATH_FT,
|
|
20
|
+
)
|
|
21
|
+
|
|
22
|
+
logger = logging.getLogger("I24ssx.chip_startup")
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
def setup_logging():
|
|
26
|
+
# Log should now change name daily.
|
|
27
|
+
logfile = time.strftime("i24fixedtarget_%d%B%y.log").lower()
|
|
28
|
+
log.config(logfile)
|
|
29
|
+
|
|
30
|
+
|
|
31
|
+
def read_parameter_file(
|
|
32
|
+
param_path: Path | str = PARAM_FILE_PATH_FT,
|
|
33
|
+
) -> FixedTargetParameters:
|
|
34
|
+
if not isinstance(param_path, Path):
|
|
35
|
+
param_path = Path(param_path)
|
|
36
|
+
params_file = param_path / PARAM_FILE_NAME
|
|
37
|
+
params = FixedTargetParameters.from_file(params_file)
|
|
38
|
+
return params
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
@log.log_on_entry
|
|
42
|
+
def fiducials(chip_type: int):
|
|
43
|
+
fiducial_list: list | None = None
|
|
44
|
+
if chip_type in [ChipType.Oxford, ChipType.OxfordInner, ChipType.Minichip]:
|
|
45
|
+
fiducial_list = []
|
|
46
|
+
elif chip_type == ChipType.Custom:
|
|
47
|
+
# No fiducial for custom
|
|
48
|
+
logger.warning("No fiducials for custom chip")
|
|
49
|
+
else:
|
|
50
|
+
logger.warning(f"Unknown chip_type, {chip_type}, in fiducials")
|
|
51
|
+
return fiducial_list
|
|
52
|
+
|
|
53
|
+
|
|
54
|
+
def get_xy(addr: str, chip_type: ChipType):
|
|
55
|
+
entry = addr.split("_")[-2:]
|
|
56
|
+
R, C = entry[0][0], entry[0][1]
|
|
57
|
+
r2, c2 = entry[1][0], entry[1][1]
|
|
58
|
+
blockR = string.ascii_uppercase.index(R)
|
|
59
|
+
blockC = int(C) - 1
|
|
60
|
+
lowercase_list = list(string.ascii_lowercase + string.ascii_uppercase + "0")
|
|
61
|
+
windowR = lowercase_list.index(r2)
|
|
62
|
+
windowC = lowercase_list.index(c2)
|
|
63
|
+
|
|
64
|
+
chip_params = get_chip_format(chip_type)
|
|
65
|
+
|
|
66
|
+
x = (
|
|
67
|
+
(blockC * chip_params.b2b_horz)
|
|
68
|
+
+ (blockC * (chip_params.x_num_steps - 1) * chip_params.x_step_size)
|
|
69
|
+
+ (windowC * chip_params.x_step_size)
|
|
70
|
+
)
|
|
71
|
+
y = (
|
|
72
|
+
(blockR * chip_params.b2b_vert)
|
|
73
|
+
+ (blockR * (chip_params.y_num_steps - 1) * chip_params.y_step_size)
|
|
74
|
+
+ (windowR * chip_params.y_step_size)
|
|
75
|
+
)
|
|
76
|
+
return x, y
|
|
77
|
+
|
|
78
|
+
|
|
79
|
+
def pathli(l_in=None, way="typewriter", reverse=False):
|
|
80
|
+
if l_in is None:
|
|
81
|
+
l_in = []
|
|
82
|
+
if reverse is True:
|
|
83
|
+
li = list(reversed(l_in))
|
|
84
|
+
else:
|
|
85
|
+
li = list(l_in)
|
|
86
|
+
long_list = []
|
|
87
|
+
if li:
|
|
88
|
+
if way == "typewriter":
|
|
89
|
+
for i in range(len(li) ** 2):
|
|
90
|
+
long_list.append(li[i % len(li)])
|
|
91
|
+
elif way == "snake":
|
|
92
|
+
lr = list(reversed(li))
|
|
93
|
+
for rep in range(len(li)):
|
|
94
|
+
if rep % 2 == 0:
|
|
95
|
+
long_list += li
|
|
96
|
+
else:
|
|
97
|
+
long_list += lr
|
|
98
|
+
elif way == "snake53":
|
|
99
|
+
lr = list(reversed(li))
|
|
100
|
+
for rep in range(53):
|
|
101
|
+
if rep % 2 == 0:
|
|
102
|
+
long_list += li
|
|
103
|
+
else:
|
|
104
|
+
long_list += lr
|
|
105
|
+
elif way == "expand":
|
|
106
|
+
for entry in li:
|
|
107
|
+
for _ in range(len(li)):
|
|
108
|
+
long_list.append(entry)
|
|
109
|
+
elif way == "expand28":
|
|
110
|
+
for entry in li:
|
|
111
|
+
for _ in range(28):
|
|
112
|
+
long_list.append(entry)
|
|
113
|
+
elif way == "expand25":
|
|
114
|
+
for entry in li:
|
|
115
|
+
for _ in range(25):
|
|
116
|
+
long_list.append(entry)
|
|
117
|
+
else:
|
|
118
|
+
logger.warning(f"No known path, way = {way}")
|
|
119
|
+
else:
|
|
120
|
+
logger.warning("No list written")
|
|
121
|
+
return long_list
|
|
122
|
+
|
|
123
|
+
|
|
124
|
+
def zippum(list_1_args, list_2_args):
|
|
125
|
+
list_1, type_1, reverse_1 = list_1_args
|
|
126
|
+
list_2, type_2, reverse_2 = list_2_args
|
|
127
|
+
A_path = pathli(list_1, type_1, reverse_1)
|
|
128
|
+
B_path = pathli(list_2, type_2, reverse_2)
|
|
129
|
+
zipped_list = []
|
|
130
|
+
for a, b in zip(A_path, B_path, strict=False):
|
|
131
|
+
zipped_list.append(a + b)
|
|
132
|
+
return zipped_list
|
|
133
|
+
|
|
134
|
+
|
|
135
|
+
def get_alphanumeric(chip_type: ChipType):
|
|
136
|
+
cell_format = get_chip_format(chip_type)
|
|
137
|
+
blk_num = cell_format.x_blocks
|
|
138
|
+
wnd_num = cell_format.x_num_steps
|
|
139
|
+
uppercase_list = list(string.ascii_uppercase)[:blk_num]
|
|
140
|
+
lowercase_list = list(string.ascii_lowercase + string.ascii_uppercase + "0")[
|
|
141
|
+
:wnd_num
|
|
142
|
+
]
|
|
143
|
+
number_list = [str(x) for x in range(1, blk_num + 1)]
|
|
144
|
+
|
|
145
|
+
block_list = zippum([uppercase_list, "expand", 0], [number_list, "typewriter", 0])
|
|
146
|
+
window_list = zippum(
|
|
147
|
+
[lowercase_list, "expand", 0], [lowercase_list, "typewriter", 0]
|
|
148
|
+
)
|
|
149
|
+
|
|
150
|
+
alphanumeric_list = []
|
|
151
|
+
for block in block_list:
|
|
152
|
+
for window in window_list:
|
|
153
|
+
alphanumeric_list.append(block + "_" + window)
|
|
154
|
+
logger.info(f"Length of alphanumeric list = {len(alphanumeric_list)}")
|
|
155
|
+
return alphanumeric_list
|
|
156
|
+
|
|
157
|
+
|
|
158
|
+
@log.log_on_entry
|
|
159
|
+
def get_shot_order(chip_type: ChipType):
|
|
160
|
+
cell_format = get_chip_format(chip_type)
|
|
161
|
+
blk_num = cell_format.x_blocks
|
|
162
|
+
wnd_num = cell_format.x_num_steps
|
|
163
|
+
uppercase_list = list(string.ascii_uppercase)[:blk_num]
|
|
164
|
+
number_list = [str(x) for x in range(1, blk_num + 1)]
|
|
165
|
+
lowercase_list = list(string.ascii_lowercase + string.ascii_uppercase + "0")[
|
|
166
|
+
:wnd_num
|
|
167
|
+
]
|
|
168
|
+
|
|
169
|
+
block_list = zippum([uppercase_list, "snake", 0], [number_list, "expand", 0])
|
|
170
|
+
window_dn = zippum([lowercase_list, "expand", 0], [lowercase_list, "snake", 0])
|
|
171
|
+
window_up = zippum([lowercase_list, "expand", 1], [lowercase_list, "snake", 0])
|
|
172
|
+
|
|
173
|
+
switch = 0
|
|
174
|
+
count = 0
|
|
175
|
+
collect_list = []
|
|
176
|
+
for block in block_list:
|
|
177
|
+
if switch == 0:
|
|
178
|
+
for window in window_dn:
|
|
179
|
+
collect_list.append(block + "_" + window)
|
|
180
|
+
count += 1
|
|
181
|
+
if count == blk_num:
|
|
182
|
+
count = 0
|
|
183
|
+
switch = 1
|
|
184
|
+
else:
|
|
185
|
+
for window in window_up:
|
|
186
|
+
collect_list.append(block + "_" + window)
|
|
187
|
+
count += 1
|
|
188
|
+
if count == blk_num:
|
|
189
|
+
count = 0
|
|
190
|
+
switch = 0
|
|
191
|
+
|
|
192
|
+
logger.info(f"Length of collect list = {len(collect_list)}")
|
|
193
|
+
return collect_list
|
|
194
|
+
|
|
195
|
+
|
|
196
|
+
@log.log_on_entry
|
|
197
|
+
def write_file(
|
|
198
|
+
location: str = "i24",
|
|
199
|
+
suffix: str = ".addr",
|
|
200
|
+
order: str = "alphanumeric",
|
|
201
|
+
param_file_path: Path = PARAM_FILE_PATH_FT,
|
|
202
|
+
save_path: Path = HEADER_FILES_PATH,
|
|
203
|
+
):
|
|
204
|
+
if location == "i24":
|
|
205
|
+
params = read_parameter_file(param_file_path)
|
|
206
|
+
else:
|
|
207
|
+
msg = f"Unknown location, {location}"
|
|
208
|
+
logger.error(msg)
|
|
209
|
+
raise ValueError(msg)
|
|
210
|
+
chip_file_path = save_path / f"chips/{params.directory}/{params.filename}{suffix}"
|
|
211
|
+
|
|
212
|
+
fiducial_list = fiducials(params.chip.chip_type.value)
|
|
213
|
+
|
|
214
|
+
if order == "alphanumeric":
|
|
215
|
+
addr_list = get_alphanumeric(params.chip.chip_type)
|
|
216
|
+
elif order == "shot":
|
|
217
|
+
addr_list = get_shot_order(params.chip.chip_type)
|
|
218
|
+
else:
|
|
219
|
+
raise ValueError(f"{order=} unrecognised")
|
|
220
|
+
|
|
221
|
+
with open(chip_file_path, "a") as g:
|
|
222
|
+
for addr in addr_list:
|
|
223
|
+
xtal_name = "_".join([params.filename, addr])
|
|
224
|
+
(x, y) = get_xy(xtal_name, params.chip.chip_type)
|
|
225
|
+
if addr in fiducial_list:
|
|
226
|
+
pres = "0"
|
|
227
|
+
else:
|
|
228
|
+
if "rand" in suffix:
|
|
229
|
+
pres = str(np.random.randint(2))
|
|
230
|
+
else:
|
|
231
|
+
pres = "-1"
|
|
232
|
+
line = "\t".join([xtal_name, str(x), str(y), "0.0", pres]) + "\n"
|
|
233
|
+
g.write(line)
|
|
234
|
+
|
|
235
|
+
logger.info(f"Write {chip_file_path} completed")
|
|
236
|
+
|
|
237
|
+
|
|
238
|
+
@log.log_on_entry
|
|
239
|
+
def check_files(
|
|
240
|
+
location: str,
|
|
241
|
+
suffix_list: list[str],
|
|
242
|
+
param_file_path: Path | str = PARAM_FILE_PATH_FT,
|
|
243
|
+
save_path: Path = HEADER_FILES_PATH,
|
|
244
|
+
):
|
|
245
|
+
if location == "i24":
|
|
246
|
+
params = read_parameter_file(param_file_path)
|
|
247
|
+
else:
|
|
248
|
+
msg = f"Unknown location, {location}"
|
|
249
|
+
logger.error(msg)
|
|
250
|
+
raise ValueError(msg)
|
|
251
|
+
chip_file_path = save_path / f"chips/{params.directory}/{params.filename}"
|
|
252
|
+
|
|
253
|
+
try:
|
|
254
|
+
os.stat(chip_file_path)
|
|
255
|
+
except Exception:
|
|
256
|
+
os.makedirs(chip_file_path)
|
|
257
|
+
for suffix in suffix_list:
|
|
258
|
+
full_fid = chip_file_path.with_suffix(suffix)
|
|
259
|
+
if full_fid.is_file():
|
|
260
|
+
time_str = time.strftime("%Y%m%d_%H%M%S_")
|
|
261
|
+
timestamp_fid = ( # noqa: F841
|
|
262
|
+
full_fid.parent / f"{time_str}_{params.filename}{full_fid.suffix}"
|
|
263
|
+
)
|
|
264
|
+
# FIXME hack / fix. Actually move the file
|
|
265
|
+
logger.info(f"File {full_fid} Already Exists")
|
|
266
|
+
logger.debug("Check files done")
|
|
267
|
+
return 1
|
|
268
|
+
|
|
269
|
+
|
|
270
|
+
@log.log_on_entry
|
|
271
|
+
def write_headers(
|
|
272
|
+
location: str,
|
|
273
|
+
suffix_list: list[str],
|
|
274
|
+
param_file_path: Path = PARAM_FILE_PATH_FT,
|
|
275
|
+
save_path: Path = HEADER_FILES_PATH,
|
|
276
|
+
):
|
|
277
|
+
if location == "i24":
|
|
278
|
+
params = read_parameter_file(param_file_path)
|
|
279
|
+
chip_file_path = save_path / f"chips/{params.directory}/{params.filename}"
|
|
280
|
+
|
|
281
|
+
for suffix in suffix_list:
|
|
282
|
+
full_fid = chip_file_path.with_suffix(suffix)
|
|
283
|
+
with open(full_fid, "w") as g:
|
|
284
|
+
g.write(
|
|
285
|
+
"#23456789012345678901234567890123456789012345678901234567890123456789012345678901234567890\n#\n"
|
|
286
|
+
)
|
|
287
|
+
g.write(f"#&i24\tchip_name = {params.filename}\n")
|
|
288
|
+
g.write(f"#&i24\tvisit = {params.visit}\n")
|
|
289
|
+
g.write(f"#&i24\tsub_dir = {params.directory}\n")
|
|
290
|
+
g.write(f"#&i24\tn_exposures = {params.num_exposures}\n")
|
|
291
|
+
g.write(f"#&i24\tchip_type = {params.chip.chip_type.value}\n")
|
|
292
|
+
g.write(f"#&i24\tmap_type = {params.map_type.value}\n")
|
|
293
|
+
g.write(f"#&i24\tpump_repeat = {params.pump_repeat.value}\n")
|
|
294
|
+
g.write(f"#&i24\tpumpexptime = {params.laser_dwell_s}\n")
|
|
295
|
+
g.write(f"#&i24\texptime = {params.laser_delay_s}\n")
|
|
296
|
+
g.write(f"#&i24\tdcdetdist = {params.detector_distance_mm}\n")
|
|
297
|
+
g.write(f"#&i24\tprepumpexptime = {params.pre_pump_exposure_s}\n")
|
|
298
|
+
g.write(f"#&i24\tdet_Type = {params.detector_name}\n")
|
|
299
|
+
g.write("#\n")
|
|
300
|
+
g.write(
|
|
301
|
+
"#XtalAddr XCoord YCoord ZCoord Present Shot Spare04 Spare03 Spare02 Spare01\n"
|
|
302
|
+
)
|
|
303
|
+
else:
|
|
304
|
+
msg = f"Unknown location, {location}"
|
|
305
|
+
logger.error(msg)
|
|
306
|
+
raise ValueError(msg)
|
|
307
|
+
logger.debug("Write headers done")
|
|
308
|
+
|
|
309
|
+
|
|
310
|
+
def run():
|
|
311
|
+
logger.debug("Run Startup")
|
|
312
|
+
check_files("i24", [".addr", ".shot"])
|
|
313
|
+
logger.info("Checked Files")
|
|
314
|
+
write_headers("i24", [".addr", ".shot"])
|
|
315
|
+
logger.info("Written Headers")
|
|
316
|
+
logger.info("Writing to Files has been disabled. Headers Only")
|
|
317
|
+
# Makes a file with random crystal positions
|
|
318
|
+
check_files("i24", ["rando.spec"])
|
|
319
|
+
write_headers("i24", ["rando.spec"])
|
|
320
|
+
logger.debug("StartUp Done")
|
|
321
|
+
|
|
322
|
+
|
|
323
|
+
if __name__ == "__main__":
|
|
324
|
+
setup_logging()
|
|
325
|
+
run()
|
|
@@ -2,14 +2,19 @@
|
|
|
2
2
|
Move on click gui for fixed targets at I24
|
|
3
3
|
Robin Owen 12 Jan 2021
|
|
4
4
|
"""
|
|
5
|
+
|
|
5
6
|
import logging
|
|
6
7
|
|
|
8
|
+
import bluesky.plan_stubs as bps
|
|
7
9
|
import cv2 as cv
|
|
10
|
+
from bluesky.run_engine import RunEngine
|
|
8
11
|
from dodal.beamlines import i24
|
|
12
|
+
from dodal.devices.i24.pmac import PMAC
|
|
9
13
|
from dodal.devices.oav.oav_detector import OAV
|
|
10
14
|
|
|
11
|
-
from mx_bluesky.
|
|
12
|
-
from mx_bluesky.
|
|
15
|
+
from mx_bluesky.i24.serial.fixed_target import i24ssx_Chip_Manager_py3v1 as manager
|
|
16
|
+
from mx_bluesky.i24.serial.fixed_target.ft_utils import Fiducials
|
|
17
|
+
from mx_bluesky.i24.serial.parameters.constants import OAV1_CAM
|
|
13
18
|
|
|
14
19
|
logger = logging.getLogger("I24ssx.moveonclick")
|
|
15
20
|
|
|
@@ -27,34 +32,25 @@ def _get_beam_centre(oav: OAV):
|
|
|
27
32
|
return oav.parameters.beam_centre_i, oav.parameters.beam_centre_j
|
|
28
33
|
|
|
29
34
|
|
|
30
|
-
# TODO In the future, this should be done automatically in the OAV device
|
|
31
|
-
# See https://github.com/DiamondLightSource/dodal/issues/224
|
|
32
|
-
def get_beam_centre():
|
|
33
|
-
# Get I24 oav device from dodal
|
|
34
|
-
oav = i24.oav()
|
|
35
|
-
|
|
36
|
-
beamX, beamY = _get_beam_centre(oav)
|
|
37
|
-
return beamX, beamY
|
|
38
|
-
|
|
39
|
-
|
|
40
35
|
# Register clicks and move chip stages
|
|
41
36
|
def onMouse(event, x, y, flags, param):
|
|
42
|
-
pmac = param
|
|
43
|
-
beamX, beamY = get_beam_centre()
|
|
44
37
|
if event == cv.EVENT_LBUTTONUP:
|
|
45
|
-
|
|
38
|
+
pmac = param[0]
|
|
39
|
+
oav = param[1]
|
|
40
|
+
beamX, beamY = _get_beam_centre(oav)
|
|
41
|
+
logger.info(f"Clicked X and Y {x} {y}")
|
|
46
42
|
xmove = -1 * (beamX - x) * zoomcalibrator
|
|
47
43
|
ymove = -1 * (beamY - y) * zoomcalibrator
|
|
48
|
-
logger.info("Moving X and Y
|
|
44
|
+
logger.info(f"Moving X and Y {xmove} {ymove}")
|
|
49
45
|
xmovepmacstring = "#1J:" + str(xmove)
|
|
50
46
|
ymovepmacstring = "#2J:" + str(ymove)
|
|
51
|
-
pmac.pmac_string
|
|
52
|
-
pmac.pmac_string
|
|
47
|
+
yield from bps.abs_set(pmac.pmac_string, xmovepmacstring, wait=True)
|
|
48
|
+
yield from bps.abs_set(pmac.pmac_string, ymovepmacstring, wait=True)
|
|
53
49
|
|
|
54
50
|
|
|
55
|
-
def update_ui(frame):
|
|
51
|
+
def update_ui(oav, frame):
|
|
56
52
|
# Get beam x and y values
|
|
57
|
-
beamX, beamY =
|
|
53
|
+
beamX, beamY = _get_beam_centre(oav)
|
|
58
54
|
|
|
59
55
|
# Overlay text and beam centre
|
|
60
56
|
cv.ellipse(
|
|
@@ -135,14 +131,15 @@ def update_ui(frame):
|
|
|
135
131
|
|
|
136
132
|
|
|
137
133
|
def start_viewer(oav1: str = OAV1_CAM):
|
|
138
|
-
# Get
|
|
139
|
-
|
|
134
|
+
# Get devices out of dodal
|
|
135
|
+
oav: OAV = i24.oav()
|
|
136
|
+
pmac: PMAC = i24.pmac()
|
|
140
137
|
# Create a video caputure from OAV1
|
|
141
138
|
cap = cv.VideoCapture(oav1)
|
|
142
139
|
|
|
143
140
|
# Create window named OAV1view and set onmouse to this
|
|
144
141
|
cv.namedWindow("OAV1view")
|
|
145
|
-
cv.setMouseCallback("OAV1view", onMouse, param=pmac) # type: ignore
|
|
142
|
+
cv.setMouseCallback("OAV1view", onMouse, param=[pmac, oav]) # type: ignore
|
|
146
143
|
|
|
147
144
|
logger.info("Showing camera feed. Press escape to close")
|
|
148
145
|
# Read captured video and store them in success and frame
|
|
@@ -152,42 +149,42 @@ def start_viewer(oav1: str = OAV1_CAM):
|
|
|
152
149
|
while success:
|
|
153
150
|
success, frame = cap.read()
|
|
154
151
|
|
|
155
|
-
update_ui(frame)
|
|
152
|
+
update_ui(oav, frame)
|
|
156
153
|
|
|
157
154
|
k = cv.waitKey(1)
|
|
158
155
|
if k == 113: # Q
|
|
159
|
-
manager.moveto(
|
|
156
|
+
yield from manager.moveto(Fiducials.zero, pmac)
|
|
160
157
|
if k == 119: # W
|
|
161
|
-
manager.moveto(
|
|
158
|
+
yield from manager.moveto(Fiducials.fid1, pmac)
|
|
162
159
|
if k == 101: # E
|
|
163
|
-
manager.moveto(
|
|
160
|
+
yield from manager.moveto(Fiducials.fid2, pmac)
|
|
164
161
|
if k == 97: # A
|
|
165
|
-
pmac.
|
|
162
|
+
yield from bps.trigger(pmac.home, wait=True)
|
|
166
163
|
print("Current position set as origin")
|
|
167
164
|
if k == 115: # S
|
|
168
|
-
manager.fiducial(1)
|
|
165
|
+
yield from manager.fiducial(1)
|
|
169
166
|
if k == 100: # D
|
|
170
|
-
manager.fiducial(2)
|
|
167
|
+
yield from manager.fiducial(2)
|
|
171
168
|
if k == 99: # C
|
|
172
|
-
manager.cs_maker()
|
|
169
|
+
yield from manager.cs_maker(pmac)
|
|
173
170
|
if k == 98: # B
|
|
174
|
-
manager.block_check() # doesn't work well for blockcheck as image doesn't update
|
|
171
|
+
yield from manager.block_check() # doesn't work well for blockcheck as image doesn't update
|
|
175
172
|
if k == 104: # H
|
|
176
|
-
pmac.pmac_string
|
|
173
|
+
yield from bps.abs_set(pmac.pmac_string, "#2J:-10", wait=True)
|
|
177
174
|
if k == 110: # N
|
|
178
|
-
pmac.pmac_string
|
|
175
|
+
yield from bps.abs_set(pmac.pmac_string, "#2J:10", wait=True)
|
|
179
176
|
if k == 109: # M
|
|
180
|
-
pmac.pmac_string
|
|
177
|
+
yield from bps.abs_set(pmac.pmac_string, "#1J:-10", wait=True)
|
|
181
178
|
if k == 98: # B
|
|
182
|
-
pmac.pmac_string
|
|
179
|
+
yield from bps.abs_set(pmac.pmac_string, "#1J:10", wait=True)
|
|
183
180
|
if k == 105: # I
|
|
184
|
-
pmac.pmac_string
|
|
181
|
+
yield from bps.abs_set(pmac.pmac_string, "#3J:-150", wait=True)
|
|
185
182
|
if k == 111: # O
|
|
186
|
-
pmac.pmac_string
|
|
183
|
+
yield from bps.abs_set(pmac.pmac_string, "#3J:150", wait=True)
|
|
187
184
|
if k == 117: # U
|
|
188
|
-
pmac.pmac_string
|
|
185
|
+
yield from bps.abs_set(pmac.pmac_string, "#3J:-1000", wait=True)
|
|
189
186
|
if k == 112: # P
|
|
190
|
-
pmac.pmac_string
|
|
187
|
+
yield from bps.abs_set(pmac.pmac_string, "#3J:1000", wait=True)
|
|
191
188
|
if k == 0x1B: # esc
|
|
192
189
|
cv.destroyWindow("OAV1view")
|
|
193
190
|
print("Pressed escape. Closing window")
|
|
@@ -198,4 +195,5 @@ def start_viewer(oav1: str = OAV1_CAM):
|
|
|
198
195
|
|
|
199
196
|
|
|
200
197
|
if __name__ == "__main__":
|
|
201
|
-
|
|
198
|
+
RE = RunEngine()
|
|
199
|
+
RE(start_viewer())
|