## 成果圖 ![](https://hackmd.io/_uploads/ryXJb9unn.png) ## 使用到的函式庫 ![](https://hackmd.io/_uploads/rJhV-5O32.png) ## 實作影片 https://youtu.be/l4bwW-TMbR8 ## 參考網址 https://www.youtube.com/watch?v=O3b8lVF93jU ## 完整程式碼(都有附上註解) ``` import cv2 from tracker import * tracker = EuclideanDistTracker() # 創建追蹤器物件 cap = cv2.VideoCapture("white_plastic_2.mp4") # 讀取影片 object_detector = cv2.createBackgroundSubtractorMOG2(history=100, varThreshold=40) # 創建背景消除物件,以便進行物體檢測 while True: ret, frame = cap.read() # 讀取影片中的一幀 height, width, _ = frame.shape # 獲取影片幀的高度和寬度 roi = frame[350:500,250:650] # 從原始影像中提取出感興趣區域 # 1. 物體檢測 mask = object_detector.apply(roi) # 將背景消除應用於感興趣區域,生成遮罩 _, mask = cv2.threshold(mask, 254, 255, cv2.THRESH_BINARY) # 將遮罩二值化,使檢測物體更為明顯 contours, _ = cv2.findContours(mask, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE) # 找到遮罩中的輪廓 detections = [] # 創建一個空的列表,用於儲存檢測到的物體 for cnt in contours: # 遍歷所有的輪廓 # 計算面積並移除小元素 area = cv2.contourArea(cnt) # 計算輪廓的面積 if area > 100: # 如果面積大於100,則認為該輪廓是一個物體 x, y, w, h = cv2.boundingRect(cnt) # 獲取該物體的邊界框座標 detections.append([x, y, w, h]) # 將物體的座標添加到檢測列表中 # 2. 物體追蹤 boxes_ids = tracker.update(detections) # 更新追蹤器,得到帶有ID的邊界框 for box_id in boxes_ids: # 遍歷所有的邊界框 x, y, w, h, id = box_id # 獲取邊界框和ID cv2.putText(roi, str(id), (x, y - 15), cv2.FONT_HERSHEY_PLAIN, 2, (255, 0, 0), 2) # 在物體上方顯示ID cv2.rectangle(roi, (x, y), (x + w, y + h), (0, 255, 0), 3) # 畫出物體的邊界框 cv2.imshow("roi", roi) # 顯示感興趣區域 cv2.imshow("Frame", frame) # 顯示原始影像 cv2.imshow("Mask", mask) # 顯示遮罩 key = cv2.waitKey(30) # 每30毫秒檢查一次鍵盤,並將鍵盤的輸入儲存到key中 if key == 27: # 如果按下ESC(其ASCII值為27),則結束循環 break cap.release() # 釋放影片 cv2.destroyAllWindows() # 關閉所有OpenCV視窗 ```