Python程式設計人員指南#
Basler pylon 的官方 Python 語言繫結為 pypylon 專案。pypylon 是託管於 GitHub 上的開源專案。若要使用 Basler 3D 相機,必須使用 4.0 或更高版本。
作為官方 Python 包裝函式的替代方案,您可以透過 Python Harvester 函式庫來操作相機。Harvesters 是一個 Python 函式庫,旨在簡化電腦視覺應用程式中的影像擷取程序。它可透過 GenTL Producer 進行影像擷取。
資訊
本主題中的所有資訊均適用於所有 blaze 和 Smart blaze 相機型號。為求簡潔,文中以「blaze」統稱所有型號。
pypylon#
安裝 pypylon#
- 安裝 pylon(7.5 或以上版本)與 pylon Supplementary Package for blaze(1.7 或以上版本)
- 安裝 pypylon:
pip3 install pypylon
Python 程式設計範例#
pylon Supplementary Package for blaze 包含一些 Python 編程式範,說明如何使用 Python 和 pypylon 存取 blaze 相機。
To open the folder containing the programming samples for blaze cameras, press the Win key, go to the Basler folder, and choose blaze Samples. A File Explorer window opens. The Python programming samples are located in the Python folder.
The Python samples are located in the /opt/pylon/share/pylon/Samples/blaze/Python/pypylon folder.
資訊
在建置範例之前,請將包含範例的資料夾複製到您具有寫入權限的任意位置。
每個範例都附有一個 README.md 檔案,提供有關範例功能以及執行範例所需條件的資訊。
使用 pypylon 存取 blaze 相機#
請參閱 SimpleGrab/simple_grab.py 或使用以下程式碼片段:
from pypylon import pylon
dc = pylon.DeviceInfo()
dc.SetDeviceClass("BaslerGTC/Basler/GenTL_Producer_for_Basler_blaze_101_cameras")
camera = pylon.InstantCamera(pylon.TlFactory.GetInstance().CreateFirstDevice(dc))
camera.Open()
camera.StartGrabbing(pylon.GrabStrategy_LatestImageOnly)
while camera.IsGrabbing():
grabResult = camera.RetrieveResult(1000, pylon.TimeoutHandling_ThrowException)
if grabResult.GrabSucceeded():
pylonDataContainer = grabResult.GetDataContainer()
for componentIndex in range(pylonDataContainer.DataComponentCount):
pylonDataComponent = pylonDataContainer.GetDataComponent(componentIndex)
if pylonDataComponent.ComponentType == pylon.ComponentType_Intensity:
intensity = pylonDataComponent.Array
_2d_intensity = intensity.reshape(pylonDataComponent.Height, pylonDataComponent.Width)
pylonDataComponent.Release()
grabResult.Release()
camera.StopGrabbing()
Harvester#
安裝 Harvester#
在命令列中執行以下指令:
Python Harvester 編程式範#
pylon Supplementary Package for blaze 包含一些 Python 編程式範,說明如何使用 Python 和 Harvester 存取 blaze 相機。
To open the folder containing the programming samples for blaze cameras, press the Win key, go to the Basler folder, and choose blaze Samples. A File Explorer window opens. The Python programming samples are located in the Python folder.
The Python Harvester samples are located in the /opt/pylon/share/pylon/Samples/blaze/Python/Harvester folder.
資訊
在建置範例之前,請將包含範例的資料夾複製到您具有寫入權限的任意位置。
每個範例都附有一個 README.md 檔案,提供有關範例功能以及執行範例所需條件的資訊。
Linux
如果您將 pylon Software Suite 和 pylon Supplementary Package for blaze 安裝在 /opt/pylon 以外的位置,則必須調整 Harvester 載入 blaze 相機 GenTL Producer 的路徑。
在範例程式碼中搜尋以下內容: /opt/pylon/lib/gentlproducer/gtl 並調整路徑。
使用 Harvester 存取 blaze 相機#
執行下列步驟,透過 Harvester 尋找所有可用的 blaze 相機:
- 匯入 Harvester 模組。
- 將 Harvester 物件執行個체化。
-
載入適用於 blaze 相機的 GenTL Producer。
-
更新可用裝置清單。
- 取得可用裝置的相關資訊。
若要連線至相機,請使用 h.create() 函式搭配使用。
下列敘述會連線至第一個可用的 blaze 相機:
若要開啟特定的相機,您可以使用透過以下方式提供的 Property 來指定: device_info_list Harvester 類別物件的 Property。
範例:
請注意,指定名稱必須能唯一識別您要開啟的裝置。如果有多部相機符合條件,將無法開啟任何裝置。
若要中斷與相機的連線,請發出下列指令:
存取相機 Property#
相機參數可透過影像擷取器的 remote_device Property 來存取。遠端裝置的 node_map Property 提供對所有相機參數的存取權。
範例:
# Get a parameter.
operatingMode = ia.remote_device.node_map.OperatingMode.value
# Set a parameter.
ia.remote_device.node_map.OperatingMode.value = 'ShortRange'
若要取得所有可用相機參數的清單,請使用下列指令:
如需有關如何設定和取得 blaze 相機參數的更多範例,請參閱 SimpleGrab sample。
擷取資料#
資訊
由於 Harvester 不支援 GenICam GenDC 串流格式,因此在擷取資料之前,您必須一律停用 GenDC 串流格式。若要停用 GenDC 串流格式,請使用下列指令:
從 blaze 相機擷取的 Buffer 可能包含多個元件。其中包含 Range、Intensity 和 Confidence 元件。
下列程式碼片段會啟用所有可用的元件,並設定 Range 元件的 Pixel Format,以便將深度資料提供為點雲(point cloud)。在點雲中,每個感測器像素都會被指派一組 x、y、z 座標三元組。
ia.remote_device.node_map.ComponentSelector.value = "Range"
ia.remote_device.node_map.ComponentEnable.value = True
ia.remote_device.node_map.PixelFormat.value = "Coord3D_ABC32f"
ia.remote_device.node_map.ComponentSelector.value = "Intensity"
ia.remote_device.node_map.ComponentEnable.value = True
ia.remote_device.node_map.PixelFormat.value = "Mono16"
ia.remote_device.node_map.ComponentSelector.value = "Confidence"
ia.remote_device.node_map.ComponentEnable.value = True
ia.remote_device.node_map.PixelFormat.value = "Confidence16"
如果您想要使用深度圖(depth map)而非點雲,請依下列方式設定 Range 元件:
ia.remote_device.node_map.ComponentSelector.value = "Range"
ia.remote_device.node_map.ComponentEnable.value = True
ia.remote_device.node_map.PixelFormat.value = "Coord3D_C16"
若要開始擷取,請呼叫影像擷取器的 start() 函式:
典型的擷取迴圈如下所示:
資訊
Buffer 僅在 with 敘述內有效,並將在您離開範圍時被摧毀。如果您想要在外部使用 Buffer with 範圍,你必須使用 np.copy() 以進行深拷貝。
下列程式碼片段說明如何存取緩衝區的元件:
with ia.fetch() as buffer:
depth = buffer.payload.components[0]
intensity = buffer.payload.components[1]
confidence = buffer.payload.components[2]
Harvester 會將這些元件傳回為一維 NumPy 陣列。
為了便於後續處理,將一維陣列重新塑造(reshape)為二維或三維陣列可能會很方便:
depth_arr = depth.data.reshape(pointcloud.height, pointcloud.width,
int(pointcloud.num_components_per_pixel))
intenstiy_arr = intensity.data.reshape(intensity.height, intensity.width)
confidence_arr = confidence.data.reshape(confidence.height, confidence.width)
num_components_per_pixel 取決於 Range 元件的 Pixel Format。如果 Pixel Format 等於 Coord3D_ABC32f,Range 元件會表示為點雲,亦即每個像素有 3 個浮點數值。其結果是一個儲存每個像素之 x、y 和 z 座標的三維陣列。
如果 Pixel Format 等於 Coord3D_C16,Range 元件會表示為 16 位元灰階影像,亦即每個像素有一個 16 位元整數值。
如需關於如何將深度圖的灰階值轉換為公釐(mm)的更多詳細資訊,請參閱Processing Measurement Results主題。
完成資料擷取後,請呼叫 stop() 函式:
作為實作如上所示擷取迴圈的替代方案,Harvester 可以提供一個背景執行緒來實作擷取迴圈,並透過發出回呼(callback)來通知應用程式。SimpleGrab_Callbacksample中說明了這種方法。
偵錯應用程式與控制GigE Vision心跳訊號#
諸如 blaze 相機等 GigE Vision 相機要求應用程式透過定期傳送特殊的網路封包給相機,來定期存取相機。如果相機未收到這些心跳信號(heartbeats),它將認為連線已中斷,並不再接受來自應用程式的任何命令。
當你執行應用程式時,用於 blaze 相機的 GenTL Producer 通常會產生這些心跳信號。如果你在應用程式中設定了中斷點(breakpoint)且觸發了該中斷點,偵錯工具將暫停所有執行緒,包括負責傳送心跳信號的執行緒。因此,當你在對應用程式進行偵錯並在程式碼中進行單步執行時,將不會有心跳信號傳送給相機。結果,相機偵測到心跳逾時並關閉連線。心跳逾時的預設值為 3000 毫秒。
為了迴避此問題,你必須在開發期間增加心跳逾時時間。你可以透過設定名為 GEV_HEARTBEAT_TIMEOUT 的環境變數,並指定所需的逾時時間(以毫秒為單位)來做到這一點。
或者,你可以在應用程式中這樣設定心跳逾時時間:
資訊
如果你將心跳逾時時間增加到一個很大的數值,並在未正確關閉裝置的情況下停止應用程式,你將無法再次開啟相機,並且會收到一則指出該裝置目前正在使用的錯誤訊息。如果你使用偵錯工具停止應用程式,或者你的應用程式非預期終止,就可能會發生這種情況。若要再次開啟相機,你必須等待逾時時間過期,或者拔除相機的網路線。