| import cv2 |
| import numpy as np |
|
|
| class Visualizer: |
| def __init__(self): |
| self.colors = { |
| "person": (0, 255, 0), |
| "keypoint": (255, 255, 0), |
| "connection": (0, 255, 255) |
| } |
|
|
| def rescale_coords(self, x, y, scale_info): |
| """Convert model coordinates back to original video dimensions""" |
| scale = scale_info['scale'] |
| pad_w = scale_info['pad_w'] |
| pad_h = scale_info['pad_h'] |
| original_h, original_w = scale_info['original_size'] |
|
|
| |
| x_orig = int((x - pad_w) / scale) |
| y_orig = int((y - pad_h) / scale) |
|
|
| |
| x_orig = max(0, min(x_orig, original_w - 1)) |
| y_orig = max(0, min(y_orig, original_h - 1)) |
|
|
| return (x_orig, y_orig) |
|
|
| def draw_detections(self, frame, det_results, pose_results, scale_info, tracked_persons): |
| """Draw detections and poses on the frame.""" |
| try: |
| display_frame = frame.copy() |
|
|
| |
| for person_id, box in tracked_persons.items(): |
| try: |
| if len(box) != 4: |
| continue |
|
|
| x1, y1, x2, y2 = map(float, box) |
| x1, y1 = self.rescale_coords(x1, y1, scale_info) |
| x2, y2 = self.rescale_coords(x2, y2, scale_info) |
|
|
| |
| if any(coord < 0 for coord in [x1, y1, x2, y2]): |
| continue |
|
|
| |
| cv2.rectangle(display_frame, |
| (int(x1), int(y1)), |
| (int(x2), int(y2)), |
| self.colors["person"], |
| 2) |
|
|
| |
| id_text = f"ID:{person_id}" |
| (text_w, text_h), _ = cv2.getTextSize( |
| id_text, cv2.FONT_HERSHEY_SIMPLEX, 0.5, 2 |
| ) |
| cv2.rectangle( |
| display_frame, |
| (int(x2 - text_w - 5), int(y1)), |
| (int(x2), int(y1 + text_h + 5)), |
| self.colors["person"], |
| -1, |
| ) |
| cv2.putText( |
| display_frame, |
| id_text, |
| (int(x2 - text_w - 2), int(y1 + text_h + 2)), |
| cv2.FONT_HERSHEY_SIMPLEX, |
| 0.5, |
| (0, 0, 255), |
| 1, |
| ) |
| except Exception as e: |
| print(f"Error drawing person ID {person_id}: {e}") |
| continue |
|
|
| |
| if pose_results: |
| for result in pose_results: |
| if result.keypoints: |
| for kpts in result.keypoints: |
| try: |
| keypoints = kpts.data[0].cpu().numpy() |
| for kp in keypoints: |
| x, y, conf = kp |
| if conf > 0.5: |
| x, y = self.rescale_coords(x, y, scale_info) |
| cv2.circle(display_frame, (int(x), int(y)), 3, self.colors["keypoint"], -1) |
| except Exception as e: |
| print(f"Error drawing keypoints: {e}") |
| continue |
|
|
| return display_frame |
|
|
| except Exception as e: |
| print(f"Error in draw_detections: {e}") |
| return frame |