Skip to content

Commit

Permalink
Merge branch '11-maintenance-ovp8xx-dir-readme' into 'main'
Browse files Browse the repository at this point in the history
Resolve "[Maintenance] OVP8xx dir README"

Closes #11

See merge request syntron/support/csr/ifm3d/ifm3d-examples!14
  • Loading branch information
lola-masson committed Jan 18, 2024
2 parents ad2831e + ff4827d commit e4bd6b9
Show file tree
Hide file tree
Showing 35 changed files with 346 additions and 759 deletions.
10 changes: 3 additions & 7 deletions .gitlab-ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -14,12 +14,8 @@ vale-linting:
before_script:
- apk update && apk add git
script:
- git config --global user.email "[email protected]"
- git config --global user.name "ifm-csr"
- rm -rf /builds/syntron/support/csr/o3r/formatting-tools /builds/syntron/support/csr/o3r/vale
- mkdir -p /builds/syntron/support/csr/o3r/formatting-tools
- git clone https://gitlab-ci-token:${CI_JOB_TOKEN}@gitlab-ee.dev.ifm/syntron/support/csr/formatting-tools.git /builds/syntron/support/csr/o3r/formatting-tools
- cd /builds/syntron/support/csr/o3r/formatting-tools
- vale --minAlertLevel error /builds/syntron/support/csr/ifm3d/ifm3d-examples/.
- git clone https://gitlab-ci-token:${CI_JOB_TOKEN}@gitlab-ee.dev.ifm/syntron/support/csr/formatting-tools.git ${CI_PROJECT_DIR}/formatting-tools
- cd ${CI_PROJECT_DIR}/formatting-tools
- vale --minAlertLevel error ../ovp8xx ../README.md


8 changes: 8 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,14 @@ For the Python library, install using pip: `pip install ifm3dpy`.

For more details refer to [the ifm3d documentation on api.ifm3d.com](https://api.ifm3d.com/stable/index.html).

## Supported languages

Currently, we support the following languages:
| Name | Versions |
| --------- | --------------------- |
| Python | 3.8, 3.9, 3.10, 3.11 |
| C++ | GCC 7.5+, MSVC 2019+ |

## o3d3xx-o3x1xx

This folder contains examples for the O3D3XX and the O3X1XX camera series.
Expand Down
20 changes: 20 additions & 0 deletions ovp8xx/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
# ifm3d examples for OVP8xx

This directory contains example codes in `python3` and `c++` to help you start working with the O3R system. The available example codes are divided into three subdirectories:

1. **Core**
2. **ODS**
3. **Toolbox** (only `Python` examples available atm)

## Core
The core examples, shows you how to use the `ifm3d` API to obtain image data (2D, 3D, distance image, etc.), configure camera parameters, update the embedded firmware, and more.

## ODS
The ODS examples, demonstrates how to work with the Obstacle Detection System (ODS). This includes streaming data, analyzing the data, visualizing results, configuring the ODS, and using diagnostic scripts.

## Toolbox
Within the Toolbox, you find helper scripts, including:
* Angle converter
* Extrinsic calibration
* H5 to ifm3d lib converter
* 2D-3D registration script
2 changes: 1 addition & 1 deletion ovp8xx/cpp/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@

## Build the examples

Follow the instructions below to build the examples. The commands might need to ce updated to run on Windows.
Follow the instructions below to build the examples. The commands might need to be updated to run on Windows.

```bash
$ cd Cpp
Expand Down
2 changes: 1 addition & 1 deletion ovp8xx/cpp/core/2d_data/2d_data.md
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# How to: receive and use the 2D rgb image
# How to: receive and use the 2D RGB image

Receiving RGB data with ifm3d is done similarly as 3D data: the core objects have to be instantiated, and a frame has to be retrieved (see full code below).
The important part is how to access the RGB image and how to decode it for further use.
Expand Down
6 changes: 3 additions & 3 deletions ovp8xx/cpp/core/deserialize/deserialize.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,12 @@ Some of the data provided by the O3R platform needs to be deserialized to be use
- the intrinsic calibration parameters (`ifm3dpy.deserialize.Calibration`), which provides details like which optical model is used (Fisheye, pinhole) and the values for each of the model's parameters,
- the extrinsic calibration (optics to user) parameters (` ifm3dpy.deserialize.ExtrinsicOpticToUser`), which provides the transformations between the optical system and the reference point on the camera housing,
- the ODS zone information (`ifm3dpy.deserialize.ODSInfoV1`), which contains the zone id being used and the occupancy of the zones,
- the ODS occupancy grid information (`ifm3dpy.deserialize.ODSOccupancyGridV1`), which contains occupancy grid data and the transormation matrix,
- the ODS occupancy grid information (`ifm3dpy.deserialize.ODSOccupancyGridV1`), which contains occupancy grid data and the transformation matrix,
- the RGB information (`ifm3dpy.deserialize.RGBInfoV1`), which provides exposure times and calibration parameters for the O3R RGB cameras.

For more information on the data structures of each buffer please refer to the [python API documentation](https://api.ifm3d.com/latest/_autosummary/ifm3dpy.deserialize.html) or the [c++ API documentation].
For more information on the data structures of each buffer please refer to the [Python API documentation](https://api.ifm3d.com/latest/_autosummary/ifm3dpy.deserialize.html) or the [c++ API documentation].

The usage of the deserializer is the same for all the buffers mentioned above: create the object, and call the deserlize function. Follow the example below for an example on deserialializing the `RGBInfoV1` buffer.
The usage of the deserializer is the same for all the buffers mentioned above: create the object, and call the deserialize function. Follow the example below for an example on deserializing the `RGBInfoV1` buffer.

:::::{tabs}
:::: {group-tab} Python
Expand Down
4 changes: 2 additions & 2 deletions ovp8xx/cpp/core/getting_data/getting_data.md
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ auto fg = std::make_shared<ifm3d::FrameGrabber>(o3r, 50012);
::::
:::::

>Note: The example above assumes that an O3R camera head is connected to the VPU at the physical port 2, which has the PCIC TCP port 50012. The PCIC TCP port number can be retrieved via `o3r.get([f"/ports/portX/data/pcicTCPPort"])` with `portX` being a valid port (eg "port0","port1",etc.).
>Note: The example above assumes that an O3R camera head is connected to the VPU at the physical port 2, which has the PCIC TCP port 50012. The PCIC TCP port number can be retrieved via `o3r.get([f"/ports/portX/data/pcicTCPPort"])` with `portX` being a valid port (for example `port0`, `port1`, etc).
The `O3R` class, counter-intuitively, refers to the computing unit (the VPU). It inherits its name from previous ifm 3D devices that only used one camera, with no distinction between sensing and computing units.
You can input:
Expand All @@ -41,7 +41,7 @@ You can input:

The `FrameGrabber` stores a reference to the passed in camera shared pointer and starts a worker thread to stream in pixel data from the device.
Its inputs:
- `o3r`: The o3r instance (the image processing platform) that handles the connection the the camera heads;
- `o3r`: The O3R instance (the image processing platform) that handles the connection to the camera heads;
- `port`: PCIC port number of the camera head to grab data from (not the physical port number);

> Note: instantiating the objects is done the same way for any imager type (2D, 3D, different resolutions, etc).
Expand Down
36 changes: 36 additions & 0 deletions ovp8xx/python/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
# Python Examples
in this Branch you learn how to work with `ifm3dpy` library. The script examples are divided depending on the use case:
1. **Core:** containing general scripts for O3R system.
2. **ODS:** containing ODS example scripts.
3. **Toolbox** containing useful scripts.

## Core
In the Core directory you find multiple general O3R scripts, for instance:
* `2d_data.py`: shows how to receive 2d data.
* `configuration.py`: presents how to configure the O3R parameters
* `deserialize.py`: presents an example on how to deserialize the O3R data.
* `getting_data.py`: presents how to get the data.
* `multi_head.py`: demonstrates how to know the connected heads to the VPU.
* `ifm3dpy_viewer.py`: presents a full demonstration for viewing different images.
* `fw_update_utils.py`: demonstrates how to perform a firmware update for your O3R system.
* `timestamps.py`: demonstrate how to get the timestamps and the effect of `sNTP` on the timestamps.
* `diagnostic.py` contains helper functions for retrieving diagnostics when requested or asynchronously.
* `bootup_monitor.py` checks that the VPU completes it's boot sequence.

## ODS
The ODS directory contains Python scripts including:
* `bootup_monitor.py`: Checks that the VPU completes it's boot sequence before attempting to initialize an application.
* `diagnostic.py`: Contains helper functions for retrieving diagnostics when requested or asynchronously.
* `ods_config.py`: demonstrates how to set JSON configurations to the O3R system following the O3R schema.
* `ods_queue.py` : This script handles the data queues of an ODS application.
* `ods_stream.py` : Provides functions showcasing how to receive data from the O3R platform
* `ods_visualization.py`: is a script used for ODS visualization.
* `ods_demo.py`: is using the described scripts to do a full demonstration of the ODS application.

## Tool box
Within the Toolbox, you find helper scripts, including:
* Angle converter
* Extrinsic calibration:
* `extrinsic_calib_verification.py`: is a script to verify the extrinsic calibration from h5 data.
* H5 to ifm3d lib converter
* 2D-3D registration script
Original file line number Diff line number Diff line change
@@ -1,3 +1,8 @@
#############################################
# Copyright 2023-present ifm electronic, gmbh
# SPDX-License-Identifier: Apache-2.0
#############################################

import time
import cv2
from ifm3dpy.device import O3R
Expand Down
76 changes: 0 additions & 76 deletions ovp8xx/python/core/2d_data/2d_data.md

This file was deleted.

70 changes: 70 additions & 0 deletions ovp8xx/python/core/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
# Core
In this directory you find multiple general O3R scripts that are explained below:

## 2D data
Receiving RGB data with `ifm3dpy` is done similarly as 3D data: the core objects have to be instantiated, and a frame has to be retrieved.
The important part is how to access the RGB image and how to decode it for further use.
Once decoded, the image can be displayed using tools such as OpenCV. The example code in `2d_data.py` illustrates the explained process.


## Configuration

The O3R has multiple parameters that have an influence on the point cloud. Some of them affect the raw measurement and others modify how the data is converted into x,y,z, etc values. These parameters can be changed to better fit your applications and the script `configuration.py` presents how. You can refer to [this page](https://ifm3d.com/latest/Technology/3D/index_3d.html) for a detailed description of each parameter.

The ifm3d API provides functions to read and set the configuration of the device. Note that JSON formatting is used for all the configurations.

## Deserialization

Some of the data provided by the O3R platform needs to be deserialized to be used. This is the case for:
- the intrinsic calibration parameters (`ifm3dpy.deserialize.Calibration`), which provides details like which optical model is used (Fisheye, pinhole) and the values for each of the model's parameters,
- the extrinsic calibration (optics to user) parameters (` ifm3dpy.deserialize.ExtrinsicOpticToUser`), which provides the transformations between the optical system and the reference point on the camera housing,
- the ODS zone information (`ifm3dpy.deserialize.ODSInfoV1`), which contains the zone id being used and the occupancy of the zones,
- the ODS occupancy grid information (`ifm3dpy.deserialize.ODSOccupancyGridV1`), which contains occupancy grid data and the transformation matrix,
- the RGB information (`ifm3dpy.deserialize.RGBInfoV1`), which provides exposure times and calibration parameters for the O3R RGB cameras.

For more information on the data structures of each buffer please refer to the [python3 API documentation](https://api.ifm3d.com/latest/_autosummary/ifm3dpy.deserialize.html).

The usage of the deserializer is the same for all the buffers mentioned above: create the object, and call the deserialize function. Follow the example code, `deserialize.py` for an example on deserializing the `RGBInfoV1` buffer.

## Getting data

The primary objective of `ifm3d` is to make it as simple and performant as possible to acquire pixel data from an ifm 3D camera of the O3xxxx series.
Additionally, the data should be encoded in a useful format for performing computer vision and/or robotics perception tasks.
A typical `ifm3d` client program follows the structure of a control loop whereby images are continuously acquired from the camera and acted upon in some application-specific way.

`ifm3dpy` provides three main classes:
- `O3R` holds the configuration of the camera heads, handles the connection, etc;
- `FrameGrabber` receives frames (images);
- `Frame` stores the image buffers.

The `O3R` class, counter-intuitively, refers to the computing unit (the VPU). It inherits its name from previous ifm 3D devices that only used one camera, with no distinction between sensing and computing units.

The `FrameGrabber` stores a reference to the passed in camera shared pointer and starts a worker thread to stream in pixel data from the device.
Its inputs:
- `o3r`: The O3R instance (the image processing platform) that handles the connection to the camera heads;
- `port`: PCIC port number of the camera head to grab data from (not the physical port number);

Accessing the received data is done through the `Frame`. Different data types are available depending on whether the camera is a 2D or a 3D camera.
Simply access the image by calling `get_buffer` passing the `buffer_id` of the required image as a parameter.

The recommended way to receive a frame is to use the callback function, as shown in the `getting_data_callback.py` script. You can register a callback function that will be executed for every received frame, until the program exits. Alternatively, wait for a frame: you just need to call the `WaitForFrame` function, as shown in the `getting_data.py` script.

## Multi head
The "multi_head.py" script demonstrates how to know the connected heads to the VPU and their types.

## Viewer
In the `ifm3dpy_viewer.py` python3 script a full demonstration of how to view the different images is done.

## Firmware update

The script `fw_update_utils.py` demonstrates how to perform a firmware update for your O3R system. Additionally, the script includes several utility functions that provide information, such as determining the current firmware version.

## Timestamps

The script `timestamps.py` demonstrate how to get the timestamps and the effect of `sNTP` on the timestamps.

## Diagnostic
The script `diagnostic.py` contains helper functions for retrieving diagnostics when requested or asynchronously.

## Bootup monitor:
The script `bootup_monitor.py` checks that the VPU completes it's boot sequence before attempting to initialize an application.
Original file line number Diff line number Diff line change
Expand Up @@ -143,5 +143,3 @@ def main():

if __name__ == "__main__":
main()

# %%
Original file line number Diff line number Diff line change
@@ -1,3 +1,8 @@
#############################################
# Copyright 2021-present ifm electronic, gmbh
# SPDX-License-Identifier: Apache-2.0
#############################################

import json

# Define the ifm3d objects for the communication
Expand Down
Loading

0 comments on commit e4bd6b9

Please sign in to comment.