Script the pipeline =================== All ArUco marker pipeline objects are accessible from a Python script. This could be particularly useful for real-time AR interaction applications. ## Load ArUcoCamera configuration from dictionary An [ArUcoCamera](../../../argaze.md/#argaze.ArUcoMarker.ArUcoCamera) configuration can be loaded from a Python dictionary. ```python from argaze import DataFeatures from argaze.ArUcoMarker import ArUcoCamera # Set working directory to enable relative file path loading DataFeatures.set_working_directory('path/to/folder') # Edit a dict with ArUcoCamera configuration configuration = { "name": "My FullHD camera", "size": (1920, 1080), ... "aruco_detector": { ... }, "scenes": { "MyScene" : { "aruco_markers_group": { ... }, "layers": { "MyLayer": { "aoi_scene": { ... } }, ... } }, ... } "layers": { "MyLayer": { ... }, ... }, "image_parameters": { ... } } # Load ArUcoCamera with ArUcoCamera.ArUcoCamera(**configuration) as aruco_camera: # Do something with ArUcoCamera ... ``` ## Access to ArUcoCamera and ArScenes attributes Then, once the configuration is loaded, it is possible to access to its attributes: [read ArUcoCamera code reference](../../../argaze.md/#argaze.ArUcoMarker.ArUcoCamera) to get a complete list of what is available. Thus, the [ArUcoCamera.scenes](../../../argaze.md/#argaze.ArFeatures.ArCamera) attribute allows to access each loaded ArUcoScene and so, access to their attributes: [read ArUcoScene code reference](../../../argaze.md/#argaze.ArUcoMarker.ArUcoScene) to get a complete list of what is available. ```python from argaze import ArFeatures # Assuming the ArUcoCamera is loaded ... # Iterate over each ArUcoCamera scene for name, aruco_scene in aruco_camera.scenes.items(): ... ``` ## Pipeline execution ### Detect ArUco markers, estimate scene pose and project 3D AOI Pass each camera image with timestamp information to the [ArUcoCamera.watch](../../../argaze.md/#argaze.ArFeatures.ArCamera.watch) method to execute the whole pipeline dedicated to ArUco marker detection, scene pose estimation and 3D AOI projection. !!! warning "Mandatory" The [ArUcoCamera.watch](../../../argaze.md/#argaze.ArFeatures.ArCamera.watch) method must be called from a *try* block to catch pipeline exceptions. ```python # Assuming that Full HD (1920x1080) images are available with timestamp values ...: # Edit timestamped image timestamped_image = DataFeatures.TimestampedImage(image, timestamp=timestamp) try: # Detect ArUco markers, estimate scene pose then, project 3D AOI into camera frame aruco_camera.watch(timestamped_image) # Do something with pipeline exception except Exception as e: ... # Display ArUcoCamera frame image to display detected ArUco markers, scene pose, 2D AOI projection and ArFrame visualization. ... aruco_camera.image() ``` ### Detection outputs The [ArUcoCamera.watch](../../../argaze.md/#argaze.ArFeatures.ArCamera.watch) method returns data about pipeline execution. ```python # Assuming that watch method has been called # Do something with detected_markers ... aruco_camera.aruco_detector.detected_markers() ``` Let's understand the meaning of each returned data. #### *aruco_camera.aruco_detector.detected_markers()* A dictionary containing all detected markers is provided by [ArUcoDetector](../../../argaze.md/#argaze.ArUcoMarker.ArUcoDetector) class. ### Analyse timestamped gaze positions into the camera frame As mentioned above, [ArUcoCamera](../../../argaze.md/#argaze.ArUcoMarker.ArUcoCamera) inherits from [ArFrame](../../../argaze.md/#argaze.ArFeatures.ArFrame) and, so, benefits from all the services described in the [gaze analysis pipeline section](../../gaze_analysis_pipeline/introduction.md). Particularly, timestamped gaze positions can be passed one by one to the [ArUcoCamera.look](../../../argaze.md/#argaze.ArFeatures.ArFrame.look) method to execute the whole pipeline dedicated to gaze analysis. !!! warning "Mandatory" The [ArUcoCamera.look](../../../argaze.md/#argaze.ArFeatures.ArFrame.look) method must be called from a *try* block to catch pipeline exceptions. ```python # Assuming that timestamped gaze positions are available ... try: # Look ArUcoCamera frame at a timestamped gaze position aruco_camera.look(timestamped_gaze_position) # Do something with pipeline exception except Exception as e: ... ``` ## Setup ArUcoCamera image parameters Specific [ArUcoCamera.image](../../../argaze.md/#argaze.ArFeatures.ArFrame.image) method parameters can be configured with a Python dictionary. ```python # Assuming ArUcoCamera is loaded ... # Edit a dict with ArUcoCamera image parameters image_parameters = { "draw_detected_markers": { ... }, "draw_scenes": { ... }, "draw_optic_parameters_grid": { ... }, ... } # Pass image parameters to ArUcoCamera aruco_camera_image = aruco_camera.image(**image_parameters) # Do something with ArUcoCamera image ... ``` !!! note [ArUcoCamera](../../../argaze.md/#argaze.ArUcoMarker.ArUcoCamera) inherits from [ArFrame](../../../argaze.md/#argaze.ArFeatures.ArFrame) and, so, benefits from all image parameters described in [gaze analysis pipeline visualization section](../../gaze_analysis_pipeline/visualization.md). ## Display ArUcoScene frames All [ArUcoScene](../../../argaze.md/#argaze.ArUcoMarker.ArUcoScene) frames image can be displayed as any [ArFrame](../../../argaze.md/#argaze.ArFeatures.ArFrame). ```python ... # Display all ArUcoScene frames for frame in aruco_camera.scene_frames(): ... frame.image() ```