Skip to content

Commit b01009c

Browse files
Merge pull request #5 from SICKAG/grab_numpy_example
Grab numpy example
2 parents 3790513 + b815c33 commit b01009c

File tree

2 files changed

+128
-1
lines changed

2 files changed

+128
-1
lines changed

README.md

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,14 @@
11
## About
22
The purpose of this repository is to give a starting point and some code examples in Python on what can be done using [Harvesters](https://github.com/genicam/harvesters/) during integration with a [Ranger/Ruler device](https://www.sick.com/se/en/catalog/products/machine-vision-and-identification/machine-vision/ranger3/c/g448354).
33

4-
Since our GenIStream API does not have Python support, we recommend Harvesters using for integration using Python and a Ranger/Ruler device.
4+
Since our GenIStream API does not have Python support, we recommend Harvesters using for integration using Python and a Ranger/Ruler device.
55

66
### Version
77
Currently tested with Harvesters 1.4.2 and Python 3.11.1.
88

99
### CTI-file
1010
Get the CTI-file from the SDK, it is located at: `"GenTL producer/x64-release/SICKGigEVisionTL.cti"`. This file is the one you want to load into Harvesters.
11+
12+
## Import an existing icon-image (dat-file)
13+
If you instead want to use existing images saved to disk you can have a look at this article at the support portal (need login):
14+
https://support.sick.com/sick-knowledgebase/article/?code=KA-07788

ranger3_grab_process.py

Lines changed: 123 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,123 @@
1+
from harvesters.core import Harvester
2+
import numpy as np
3+
import matplotlib.pyplot as plt
4+
import os
5+
6+
7+
def reshape_component(component, type=np.uint16):
8+
h, w = component.height, component.width
9+
image = component.data.reshape(h, w)
10+
11+
return np.array(image, dtype=type)
12+
13+
14+
def get_components(buffer):
15+
"""
16+
Extracts the components from the buffer and reshapes them into numpy arrays.
17+
:param buffer: The buffer containing the components.
18+
:return: A dictionary containing the reshaped components.
19+
"""
20+
21+
# The following keys can be used to identify a component:
22+
# 3300: Region ID
23+
# 3301: Component ID
24+
25+
# Region ID:
26+
# 11: Extraction region 1
27+
# 16: Dual Exposure Extraction region
28+
# 12: Extraction region 2
29+
# 13: Extraction region 3
30+
# 14: Extraction region 4
31+
# 15: Extraction region 5
32+
# 17: Extraction White
33+
# 18: Extraction Color
34+
35+
# Component ID:
36+
# 1: Intensity (2D)
37+
# 4: Range
38+
# 5: Reflectance
39+
# 7: Scatter
40+
components = {}
41+
for component in buffer.payload.components:
42+
region_id = component._part.get_info_int64(3300)
43+
component_id = component._part.get_info_int64(3301)
44+
45+
if region_id == 11: # Extraction region 1
46+
if components.get("Scan3dExtraction1") is None:
47+
components["Scan3dExtraction1"] = {}
48+
if component_id == 4: # Ranger
49+
components["Scan3dExtraction1"]["Range"] = reshape_component(component, np.uint16)
50+
elif component_id == 5: # Reflectance
51+
components["Scan3dExtraction1"]["Reflectance"] = reshape_component(component)
52+
elif component_id == 7: # Scatter
53+
components["Scan3dExtraction1"]["Scatter"] = reshape_component(component)
54+
else:
55+
print("Unknown component ID: ", component_id)
56+
else:
57+
print("Unknown region ID: ", region_id)
58+
59+
return components
60+
61+
62+
def main():
63+
# Create the Harvester instance
64+
h = Harvester()
65+
66+
# Load the cti-file
67+
cti_path = os.path.join(os.path.dirname(__file__), "SICKGigEVisionTL.cti")
68+
h.add_file(cti_path, check_existence=True, check_validity=True)
69+
70+
# Update Harvester, this will update the list of devices
71+
h.update()
72+
print("Found devices: ", [(device.user_defined_name, device.serial_number) for device in h.device_info_list])
73+
74+
# The following keys can be used to identify a device:
75+
# - list_index: item index of the list of :class:`DeviceInfo` objects.
76+
# - id_: Index of the device information list.
77+
# - vendor: Vendor name of the target device.
78+
# - model: Model name of the target device.
79+
# - tl_type: Transport layer type of the target device.
80+
# - user_defined_name: User defined name string of the target device.
81+
# - serial_number: Serial number string of the target device.
82+
# - version: Version number string of the target device.
83+
# Note: If list_index is specified that is always used and the other keys
84+
# are not used, otherwise a combination of the others shall be used to
85+
# specify an unique device
86+
with h.create({"user_defined_name": "ZPM03"}) as ia:
87+
88+
node_map = ia.remote_device.node_map
89+
90+
# Set to 3d mode
91+
node_map.DeviceScanType.value = 'Linescan3D'
92+
93+
# Start the acquisition
94+
ia.start()
95+
96+
# Fetch data from the image
97+
print("===== Waiting for image =====")
98+
with ia.fetch() as buffer:
99+
print("===== Image Aquired =====")
100+
components = get_components(buffer)
101+
region1_range = components["Scan3dExtraction1"]["Range"]
102+
region1_reflectance = components["Scan3dExtraction1"]["Reflectance"]
103+
region1_scatter = components["Scan3dExtraction1"]["Scatter"]
104+
105+
ia.stop()
106+
107+
print("===== Camera Stopped =====")
108+
109+
# Save the data to numpy files
110+
np.save("data/region1_range", region1_range)
111+
np.save("data/region1_reflectance", region1_reflectance)
112+
np.save("data/region1_scatter", region1_scatter)
113+
114+
print(region1_reflectance)
115+
plt.subplot(2, 1, 1)
116+
plt.imshow(region1_reflectance, interpolation='none')
117+
plt.subplot(2, 1, 2)
118+
plt.imshow(region1_range, interpolation='none')
119+
plt.show()
120+
121+
122+
if __name__ == "__main__":
123+
main()

0 commit comments

Comments
 (0)