comparison track_objects.py @ 2:972d2c365739 draft default tip

planemo upload for repository https://github.com/bgruening/galaxytools/tree/master/tools commit 57a0433defa3cbc37ab34fbb0ebcfaeb680db8d5
author bgruening
date Sun, 05 Nov 2023 09:31:44 +0000
parents 1fd453cd757b
children
comparison
equal deleted inserted replaced
1:1fd453cd757b 2:972d2c365739
1 #!/usr/bin/env python 1 #!/usr/bin/env python
2 2
3 import argparse 3 import argparse
4 import json 4 import json
5 5
6 from cp_common_functions import get_json_value 6 from cp_common_functions import (get_json_value,
7 from cp_common_functions import get_pipeline_lines 7 get_pipeline_lines,
8 from cp_common_functions import get_total_number_of_modules 8 get_total_number_of_modules,
9 from cp_common_functions import INDENTATION 9 INDENTATION, update_module_count,
10 from cp_common_functions import update_module_count 10 write_pipeline)
11 from cp_common_functions import write_pipeline
12 11
13 MODULE_NAME = "TrackObjects" 12 MODULE_NAME = "TrackObjects"
14 OUTPUT_FILENAME = "output.cppipe" 13 OUTPUT_FILENAME = "output.cppipe"
15 14
16 15
17 def build_header(module_name, module_number): 16 def build_header(module_name, module_number):
18 result = "|".join([f"{module_name}:[module_num:{module_number}", 17 result = "|".join(
19 "svn_version:\\'Unknown\\'", 18 [
20 "variable_revision_number:7", 19 f"{module_name}:[module_num:{module_number}",
21 "show_window:True", 20 "svn_version:\\'Unknown\\'",
22 "notes:\\x5B\\'Track the embryos across images using the Overlap method\\x3A tracked objects are identified by the amount of frame-to-frame overlap. Save an image of embryos labeled with a unique number across time.\\'\\x5D", 21 "variable_revision_number:7",
23 "batch_state:array(\\x5B\\x5D, dtype=uint8)", 22 "show_window:True",
24 "enabled:True", 23 "notes:\\x5B\\'Track the embryos across images using the Overlap method\\x3A tracked objects are identified by the amount of frame-to-frame overlap. Save an image of embryos labeled with a unique number across time.\\'\\x5D",
25 "wants_pause:False]\n"]) 24 "batch_state:array(\\x5B\\x5D, dtype=uint8)",
25 "enabled:True",
26 "wants_pause:False]\n",
27 ]
28 )
26 return result 29 return result
27 30
28 31
29 def build_main_block(input_params): 32 def build_main_block(input_params):
30 result = INDENTATION.join([f"{INDENTATION}Choose a tracking method:{get_json_value(input_params,'con_tracking_method.tracking_method')}\n", 33 result = INDENTATION.join(
31 f"Select the objects to track:{get_json_value(input_params,'object_to_track')}\n" 34 [
32 ]) 35 f"{INDENTATION}Choose a tracking method:{get_json_value(input_params,'con_tracking_method.tracking_method')}\n",
33 36 f"Select the objects to track:{get_json_value(input_params,'object_to_track')}\n",
34 tracking_method = get_json_value(input_params, 'con_tracking_method.tracking_method') 37 ]
38 )
39
40 tracking_method = get_json_value(
41 input_params, "con_tracking_method.tracking_method"
42 )
35 43
36 obj_measurement = "None" # default value 44 obj_measurement = "None" # default value
37 if tracking_method == "Measurements": 45 if tracking_method == "Measurements":
38 measurement_category = get_json_value(input_params, 'con_tracking_method.con_measurement_category.measurement_category') 46 measurement_category = get_json_value(
39 measurement = get_json_value(input_params, 'con_tracking_method.con_measurement_category.measurement') 47 input_params,
48 "con_tracking_method.con_measurement_category.measurement_category",
49 )
50 measurement = get_json_value(
51 input_params, "con_tracking_method.con_measurement_category.measurement"
52 )
40 53
41 if measurement_category == "Intensity" or measurement_category == "Location": 54 if measurement_category == "Intensity" or measurement_category == "Location":
42 img_measure = get_json_value(input_params, 'con_tracking_method.con_measurement_category.img_measure') 55 img_measure = get_json_value(
56 input_params, "con_tracking_method.con_measurement_category.img_measure"
57 )
43 obj_measurement = f"{measurement_category}_{measurement}_{img_measure}" 58 obj_measurement = f"{measurement_category}_{measurement}_{img_measure}"
44 else: 59 else:
45 obj_measurement = f"{measurement_category}_{measurement}" 60 obj_measurement = f"{measurement_category}_{measurement}"
46 61
47 result += INDENTATION.join([f"{INDENTATION}Select object measurement to use for tracking:{obj_measurement}\n"]) 62 result += INDENTATION.join(
63 [
64 f"{INDENTATION}Select object measurement to use for tracking:{obj_measurement}\n"
65 ]
66 )
48 67
49 if tracking_method == "LAP": # no max distance required, set default for pipeline 68 if tracking_method == "LAP": # no max distance required, set default for pipeline
50 max_distance = 50 69 max_distance = 50
51 else: 70 else:
52 max_distance = get_json_value(input_params, 'con_tracking_method.max_distance') 71 max_distance = get_json_value(input_params, "con_tracking_method.max_distance")
53 72
54 result += INDENTATION.join([f"{INDENTATION}Maximum pixel distance to consider matches:{max_distance}\n"]) 73 result += INDENTATION.join(
55 74 [f"{INDENTATION}Maximum pixel distance to consider matches:{max_distance}\n"]
56 display_option = get_json_value(input_params, 'con_tracking_method.display_option') 75 )
76
77 display_option = get_json_value(input_params, "con_tracking_method.display_option")
57 78
58 output_img_name = "TrackedCells" # default value, required by cppipe regardless of its presence in UI 79 output_img_name = "TrackedCells" # default value, required by cppipe regardless of its presence in UI
59 save = get_json_value(input_params, 'con_tracking_method.con_save_coded_img.save_coded_img') 80 save = get_json_value(
81 input_params, "con_tracking_method.con_save_coded_img.save_coded_img"
82 )
60 if save == "Yes": 83 if save == "Yes":
61 output_img_name = get_json_value(input_params, 'con_tracking_method.con_save_coded_img.name_output_img') 84 output_img_name = get_json_value(
62 85 input_params, "con_tracking_method.con_save_coded_img.name_output_img"
63 result += INDENTATION.join( 86 )
64 [f"{INDENTATION}Select display option:{display_option}\n", 87
65 f"Save color-coded image?:{save}\n", 88 result += INDENTATION.join(
66 f"Name the output image:{output_img_name}\n" 89 [
67 ]) 90 f"{INDENTATION}Select display option:{display_option}\n",
91 f"Save color-coded image?:{save}\n",
92 f"Name the output image:{output_img_name}\n",
93 ]
94 )
68 95
69 # LAP method default values 96 # LAP method default values
70 movement_model = "Both" 97 movement_model = "Both"
71 no_std = 3.0 98 no_std = 3.0
72 radius_limit_max = 10.0 99 radius_limit_max = 10.0
83 max_mitosis_dist = 40 110 max_mitosis_dist = 40
84 mitosis_alt = 80 111 mitosis_alt = 80
85 112
86 # LAP method 113 # LAP method
87 if tracking_method == "LAP": 114 if tracking_method == "LAP":
88 movement_model = get_json_value(input_params, 'con_tracking_method.movement_method') 115 movement_model = get_json_value(
89 no_std = get_json_value(input_params, 'con_tracking_method.no_std_radius') 116 input_params, "con_tracking_method.movement_method"
90 radius_limit_max = get_json_value(input_params, 'con_tracking_method.max_radius') 117 )
91 radius_limit_min = get_json_value(input_params, 'con_tracking_method.min_radius') 118 no_std = get_json_value(input_params, "con_tracking_method.no_std_radius")
119 radius_limit_max = get_json_value(
120 input_params, "con_tracking_method.max_radius"
121 )
122 radius_limit_min = get_json_value(
123 input_params, "con_tracking_method.min_radius"
124 )
92 radius = f"{radius_limit_min},{radius_limit_max}" 125 radius = f"{radius_limit_min},{radius_limit_max}"
93 126
94 run_second = get_json_value(input_params, 'con_tracking_method.con_second_lap.second_lap') 127 run_second = get_json_value(
128 input_params, "con_tracking_method.con_second_lap.second_lap"
129 )
95 if run_second == "Yes": 130 if run_second == "Yes":
96 gap_closing = get_json_value(input_params, 'con_tracking_method.con_second_lap.gap_closing') 131 gap_closing = get_json_value(
97 split_alt = get_json_value(input_params, 'con_tracking_method.con_second_lap.split_alt') 132 input_params, "con_tracking_method.con_second_lap.gap_closing"
98 merge_alt = get_json_value(input_params, 'con_tracking_method.con_second_lap.merge_alt') 133 )
99 max_gap_displacement = get_json_value(input_params, 'con_tracking_method.con_second_lap.max_gap_displacement') 134 split_alt = get_json_value(
100 max_split = get_json_value(input_params, 'con_tracking_method.con_second_lap.max_split') 135 input_params, "con_tracking_method.con_second_lap.split_alt"
101 max_merge = get_json_value(input_params, 'con_tracking_method.con_second_lap.max_merge') 136 )
102 max_temporal = get_json_value(input_params, 'con_tracking_method.con_second_lap.max_temporal') 137 merge_alt = get_json_value(
103 max_mitosis_dist = get_json_value(input_params, 'con_tracking_method.con_second_lap.max_mitosis_distance') 138 input_params, "con_tracking_method.con_second_lap.merge_alt"
104 mitosis_alt = get_json_value(input_params, 'con_tracking_method.con_second_lap.mitosis_alt') 139 )
105 140 max_gap_displacement = get_json_value(
106 result += INDENTATION.join( 141 input_params, "con_tracking_method.con_second_lap.max_gap_displacement"
107 [f"{INDENTATION}Select the movement model:{movement_model}\n", 142 )
108 f"Number of standard deviations for search radius:{no_std}\n", 143 max_split = get_json_value(
109 f"Search radius limit, in pixel units (Min,Max):{radius}\n", 144 input_params, "con_tracking_method.con_second_lap.max_split"
110 f"Run the second phase of the LAP algorithm?:{run_second}\n", 145 )
111 f"Gap closing cost:{gap_closing}\n", 146 max_merge = get_json_value(
112 f"Split alternative cost:{split_alt}\n", 147 input_params, "con_tracking_method.con_second_lap.max_merge"
113 f"Merge alternative cost:{merge_alt}\n", 148 )
114 f"Maximum gap displacement, in pixel units:{max_gap_displacement}\n", 149 max_temporal = get_json_value(
115 f"Maximum split score:{max_split}\n", 150 input_params, "con_tracking_method.con_second_lap.max_temporal"
116 f"Maximum merge score:{max_merge}\n", 151 )
117 f"Maximum temporal gap, in frames:{max_temporal}\n" 152 max_mitosis_dist = get_json_value(
118 ]) 153 input_params, "con_tracking_method.con_second_lap.max_mitosis_distance"
154 )
155 mitosis_alt = get_json_value(
156 input_params, "con_tracking_method.con_second_lap.mitosis_alt"
157 )
158
159 result += INDENTATION.join(
160 [
161 f"{INDENTATION}Select the movement model:{movement_model}\n",
162 f"Number of standard deviations for search radius:{no_std}\n",
163 f"Search radius limit, in pixel units (Min,Max):{radius}\n",
164 f"Run the second phase of the LAP algorithm?:{run_second}\n",
165 f"Gap closing cost:{gap_closing}\n",
166 f"Split alternative cost:{split_alt}\n",
167 f"Merge alternative cost:{merge_alt}\n",
168 f"Maximum gap displacement, in pixel units:{max_gap_displacement}\n",
169 f"Maximum split score:{max_split}\n",
170 f"Maximum merge score:{max_merge}\n",
171 f"Maximum temporal gap, in frames:{max_temporal}\n",
172 ]
173 )
119 174
120 # common section 175 # common section
121 filter_by_lifetime = get_json_value(input_params, 'con_tracking_method.con_filter_by_lifetime.filter_by_lifetime') 176 filter_by_lifetime = get_json_value(
177 input_params, "con_tracking_method.con_filter_by_lifetime.filter_by_lifetime"
178 )
122 use_min = "Yes" # default 179 use_min = "Yes" # default
123 min_life = 1 # default 180 min_life = 1 # default
124 use_max = "No" # default 181 use_max = "No" # default
125 max_life = 100 # default 182 max_life = 100 # default
126 183
127 if filter_by_lifetime == "Yes": 184 if filter_by_lifetime == "Yes":
128 use_min = get_json_value(input_params, 'con_tracking_method.con_filter_by_lifetime.con_use_min.use_min') 185 use_min = get_json_value(
186 input_params,
187 "con_tracking_method.con_filter_by_lifetime.con_use_min.use_min",
188 )
129 if use_min == "Yes": 189 if use_min == "Yes":
130 min_life = get_json_value(input_params, 'con_tracking_method.con_filter_by_lifetime.con_use_min.min_lifetime') 190 min_life = get_json_value(
131 191 input_params,
132 use_max = get_json_value(input_params, 'con_tracking_method.con_filter_by_lifetime.con_use_max.use_max') 192 "con_tracking_method.con_filter_by_lifetime.con_use_min.min_lifetime",
193 )
194
195 use_max = get_json_value(
196 input_params,
197 "con_tracking_method.con_filter_by_lifetime.con_use_max.use_max",
198 )
133 if use_max == "Yes": 199 if use_max == "Yes":
134 max_life = get_json_value(input_params, 'con_tracking_method.con_filter_by_lifetime.con_use_max.max_lifetime') 200 max_life = get_json_value(
135 201 input_params,
136 result += INDENTATION.join( 202 "con_tracking_method.con_filter_by_lifetime.con_use_max.max_lifetime",
137 [f"{INDENTATION}Filter objects by lifetime?:{filter_by_lifetime}\n", 203 )
138 f"Filter using a minimum lifetime?:{use_min}\n", 204
139 f"Minimum lifetime:{min_life}\n", 205 result += INDENTATION.join(
140 f"Filter using a maximum lifetime?:{use_max}\n", 206 [
141 f"Maximum lifetime:{max_life}\n" 207 f"{INDENTATION}Filter objects by lifetime?:{filter_by_lifetime}\n",
142 ]) 208 f"Filter using a minimum lifetime?:{use_min}\n",
209 f"Minimum lifetime:{min_life}\n",
210 f"Filter using a maximum lifetime?:{use_max}\n",
211 f"Maximum lifetime:{max_life}\n",
212 ]
213 )
143 214
144 # print 2 leftover from LAP 215 # print 2 leftover from LAP
145 result += INDENTATION.join( 216 result += INDENTATION.join(
146 [f"{INDENTATION}Mitosis alternative cost:{mitosis_alt}\n", 217 [
147 f"Maximum mitosis distance, in pixel units:{max_mitosis_dist}\n" 218 f"{INDENTATION}Mitosis alternative cost:{mitosis_alt}\n",
148 ]) 219 f"Maximum mitosis distance, in pixel units:{max_mitosis_dist}\n",
220 ]
221 )
149 222
150 # Follow Neighbors 223 # Follow Neighbors
151 # defaults 224 # defaults
152 avg_cell_diameter = 35.0 225 avg_cell_diameter = 35.0
153 use_adv = "No" 226 use_adv = "No"
154 cost_of_cell = 15.0 227 cost_of_cell = 15.0
155 weight_of_area_diff = 25.0 228 weight_of_area_diff = 25.0
156 229
157 if tracking_method == "Follow Neighbors": 230 if tracking_method == "Follow Neighbors":
158 avg_cell_diameter = get_json_value(input_params, 'con_tracking_method.avg_diameter') 231 avg_cell_diameter = get_json_value(
159 use_adv = get_json_value(input_params, 'con_tracking_method.con_adv_parameter.adv_parameter') 232 input_params, "con_tracking_method.avg_diameter"
233 )
234 use_adv = get_json_value(
235 input_params, "con_tracking_method.con_adv_parameter.adv_parameter"
236 )
160 if use_adv == "Yes": 237 if use_adv == "Yes":
161 cost_of_cell = get_json_value(input_params, 'con_tracking_method.con_adv_parameter.cost') 238 cost_of_cell = get_json_value(
162 weight_of_area_diff = get_json_value(input_params, 'con_tracking_method.con_adv_parameter.weight') 239 input_params, "con_tracking_method.con_adv_parameter.cost"
163 240 )
164 result += INDENTATION.join( 241 weight_of_area_diff = get_json_value(
165 [f"{INDENTATION}Average cell diameter in pixels:{avg_cell_diameter}\n", 242 input_params, "con_tracking_method.con_adv_parameter.weight"
166 f"Use advanced configuration parameters:{use_adv}\n", 243 )
167 f"Cost of cell to empty matching:{cost_of_cell}\n", 244
168 f"Weight of area difference in function matching cost:{weight_of_area_diff}\n" 245 result += INDENTATION.join(
169 ]) 246 [
247 f"{INDENTATION}Average cell diameter in pixels:{avg_cell_diameter}\n",
248 f"Use advanced configuration parameters:{use_adv}\n",
249 f"Cost of cell to empty matching:{cost_of_cell}\n",
250 f"Weight of area difference in function matching cost:{weight_of_area_diff}\n",
251 ]
252 )
170 result = result.rstrip("\n") 253 result = result.rstrip("\n")
171 return result 254 return result
172 255
173 256
174 if __name__ == "__main__": 257 if __name__ == "__main__":
175 parser = argparse.ArgumentParser() 258 parser = argparse.ArgumentParser()
176 parser.add_argument( 259 parser.add_argument("-p", "--pipeline", help="CellProfiler pipeline")
177 '-p', '--pipeline', 260 parser.add_argument("-i", "--inputs", help="JSON inputs from Galaxy")
178 help='CellProfiler pipeline'
179 )
180 parser.add_argument(
181 '-i', '--inputs',
182 help='JSON inputs from Galaxy'
183 )
184 args = parser.parse_args() 261 args = parser.parse_args()
185 262
186 pipeline_lines = get_pipeline_lines(args.pipeline) 263 pipeline_lines = get_pipeline_lines(args.pipeline)
187 inputs_galaxy = json.load(open(args.inputs, "r")) 264 inputs_galaxy = json.load(open(args.inputs, "r"))
188 265