37from dataclasses
import dataclass
38from pathlib
import Path
39from typing
import List, Optional
45from visp.core
import XmlParserCamera, CameraParameters, ColVector, HomogeneousMatrix, Display, ImageConvert
46from visp.core
import ImageGray, ImageUInt16
47from visp.io
import ImageIo
48from visp.mbt
import MbGenericTracker, MbTracker
50from visp.core
import Color
51from visp.core
import PixelMeterConversion
56 print(
'Could not import opencv python! make sure that it is installed as it is required')
60import matplotlib.pyplot
as plt
65 model_path = data_root /
'model' /
'teabox'
66 assert model_path.exists()
75 data_path = data_root /
'data' /
'teabox'
76 assert data_path.exists()
96 I_depth: Optional[ImageUInt16]
97 point_cloud: Optional[np.ndarray]
98 cMo_ground_truth: HomogeneousMatrix
100def read_data(exp_config: MBTConfig, cam_depth: CameraParameters |
None, I: ImageGray):
101 color_format =
'{:04d}_L.jpg'
102 depth_format =
'Image{:04d}_R.exr'
103 use_depth = cam_depth
is not None
106 start_parse_time = time.time()
107 color_filepath = exp_config.color_images_dir / color_format.format(iteration)
108 if not color_filepath.exists():
109 print(f
'Could not find image {color_filepath}, is the sequence finished?')
111 ImageIo.read(I,
str(color_filepath), ImageIo.IO_DEFAULT_BACKEND)
118 depth_filepath = exp_config.depth_images_dir / depth_format.format(iteration)
119 if not depth_filepath.exists():
120 print(f
'Could not find image {depth_filepath}')
122 I_depth_np = cv2.imread(
str(depth_filepath), cv2.IMREAD_ANYCOLOR | cv2.IMREAD_ANYDEPTH)
123 I_depth_np = I_depth_np[..., 0]
124 print(f
'\tDepth load took {(time.time() - t) * 1000}ms')
125 I_depth_raw = ImageUInt16(I_depth_np * 32767.5)
126 if I_depth_np.size == 0:
127 print(
'Could not successfully read the depth image')
131 Z = I_depth_np.copy()
134 vs, us = np.meshgrid(range(I_depth_np.shape[0]), range(I_depth_np.shape[1]), indexing=
'ij')
135 xs, ys = PixelMeterConversion.convertPoints(cam_depth, us, vs)
136 point_cloud = np.stack((xs * Z, ys * Z, Z), axis=-1)
138 print(f
'\tPoint_cloud took {(time.time() - t) * 1000}ms')
141 cMo_ground_truth = HomogeneousMatrix()
142 ground_truth_file = exp_config.ground_truth_dir / (exp_config.color_camera_name +
'_{:04d}.txt'.format(iteration))
143 cMo_ground_truth.load(
str(ground_truth_file))
145 end_parse_time = time.time()
146 print(f
'Data parsing took: {(end_parse_time - start_parse_time) * 1000}ms')
147 yield FrameData(I, I_depth_raw, point_cloud, cMo_ground_truth)
150 cam = CameraParameters()
151 xml_parser = XmlParserCamera()
153 camera_name, file_path = exp_config.color_camera_name, exp_config.color_intrinsics_file
155 camera_name, file_path = exp_config.depth_camera_name, exp_config.depth_intrinsics_file
156 parse_res = xml_parser.parse(cam,
str(file_path), camera_name,
157 CameraParameters.perspectiveProjWithoutDistortion, 0, 0,
True)
158 assert parse_res == XmlParserCamera.SEQUENCE_OK
161if __name__ ==
'__main__':
162 parser = argparse.ArgumentParser()
163 parser.add_argument(
'--data-root', type=str, required=
True,
164 help=
'Path to the folder containing all the data for the synthetic MBT example')
165 parser.add_argument(
'--disable-klt', action=
'store_true', help=
'Disable KLT features for tracking.')
166 parser.add_argument(
'--disable-depth', action=
'store_true', help=
'Do not use depth to perform tracking.')
167 parser.add_argument(
'--step-by-step', action=
'store_true', help=
'Perform tracking frame by frame. Go to the next frame by clicking.')
168 parser.add_argument(
'--init-ground-truth', action=
'store_true')
170 args = parser.parse_args()
171 data_root = Path(args.data_root)
176 assert data_root.exists()
and data_root.is_dir()
178 rgb_tracker: int = MbGenericTracker.EDGE_TRACKER | (MbGenericTracker.KLT_TRACKER
if not args.disable_klt
else 0)
179 tracker_types: List[int] = [rgb_tracker]
180 if not args.disable_depth:
181 depth_tracker = MbGenericTracker.DEPTH_DENSE_TRACKER
182 tracker_types.append(depth_tracker)
184 tracker = MbGenericTracker(tracker_types)
186 if args.disable_depth:
187 tracker.loadConfigFile(
str(mbt_model.config_color))
189 tracker.loadConfigFile(
str(mbt_model.config_color),
str(mbt_model.config_depth))
190 tracker.loadModel(
str(mbt_model.cad_file))
196 tracker.setCameraParameters(*((cam_color,)
if args.disable_depth
else (cam_color, cam_depth)))
197 tracker.setDisplayFeatures(
True)
199 print(
'Color intrinsics:', cam_color)
200 print(
'Depth intrinsics:', cam_depth)
203 frame_data = next(data_generator)
205 depth_M_color = HomogeneousMatrix()
206 if not args.disable_depth:
207 depth_M_color.load(exp_config.extrinsic_file)
208 tracker.setCameraTransformationMatrix(
'Camera2', depth_M_color)
212 dI.init(I, 0, 0,
'Color image')
214 I_depth =
None if args.disable_depth
else ImageGray()
215 dDepth = get_display()
216 if not args.disable_depth:
217 ImageConvert.createDepthHistogram(frame_data.I_depth, I_depth)
218 dDepth.init(I_depth, I.getWidth(), 0,
'Depth')
220 if args.init_ground_truth:
221 tracker.initFromPose(I, frame_data.cMo_ground_truth)
223 tracker.initClick(I,
str(mbt_model.init_file))
225 start_time = time.time()
226 for frame_data
in data_generator:
227 if frame_data.I_depth
is not None:
228 ImageConvert.createDepthHistogram(frame_data.I_depth, I_depth)
231 if not args.disable_depth:
232 Display.display(I_depth)
234 if args.disable_depth:
237 pc = frame_data.point_cloud
242 tracker.track(image_dict, {
'Camera2': pc})
243 print(f
'Tracking took {(time.time() - t) * 1000}ms')
244 cMo = HomogeneousMatrix()
247 Display.displayFrame(I, cMo, cam_color, 0.05, Color.none, 2)
248 tracker.display(I, cMo, cam_color, Color.red, 2)
250 if not args.disable_depth:
251 Display.flush(I_depth)
252 if args.step_by_step:
253 Display.getKeyboardEvent(I, blocking=
True)
254 end_time = time.time()
255 print(f
'total time = {end_time - start_time}s')
str depth_intrinsics_file
str color_intrinsics_file
__init__(self, Path data_root)
__init__(self, Path data_root)
CameraParameters parse_camera_file(MBTConfig exp_config, bool is_color)
read_data(MBTConfig exp_config, CameraParameters|None cam_depth, ImageGray I)