mustafa2ak commited on
Commit
3c82458
·
verified ·
1 Parent(s): 388e282

Create detection.py

Browse files
Files changed (1) hide show
  1. detection.py +95 -0
detection.py ADDED
@@ -0,0 +1,95 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import cv2
2
+ import numpy as np
3
+ import torch
4
+ from ultralytics import YOLO
5
+ from typing import List, Tuple, Optional
6
+ from dataclasses import dataclass
7
+
8
+ @dataclass
9
+ class Detection:
10
+ """Simple detection data structure"""
11
+ bbox: List[float] # [x1, y1, x2, y2]
12
+ confidence: float
13
+ image_crop: Optional[np.ndarray] = None # Cropped dog image
14
+
15
+ class DogDetector:
16
+ """
17
+ Simplified YOLOv8 detector optimized for dogs
18
+ Uses standard pretrained model - no custom training needed
19
+ """
20
+
21
+ def __init__(self,
22
+ confidence_threshold: float = 0.45,
23
+ device: str = 'cuda'):
24
+ """
25
+ Initialize detector
26
+
27
+ Args:
28
+ confidence_threshold: Min confidence for detections (0.45 works well)
29
+ device: 'cuda' for GPU, 'cpu' for CPU
30
+ """
31
+ self.confidence_threshold = confidence_threshold
32
+ self.device = device if torch.cuda.is_available() else 'cpu'
33
+
34
+ # Load YOLOv8 medium model (good balance of speed/accuracy)
35
+ self.model = YOLO('yolov8m.pt')
36
+ self.model.to(self.device)
37
+
38
+ # COCO class ID for dog
39
+ self.dog_class_id = 16
40
+
41
+ def detect(self, frame: np.ndarray) -> List[Detection]:
42
+ """
43
+ Detect dogs in frame
44
+
45
+ Args:
46
+ frame: BGR image from OpenCV
47
+
48
+ Returns:
49
+ List of Detection objects with bounding boxes and crops
50
+ """
51
+ # Run YOLO inference
52
+ results = self.model(frame,
53
+ conf=self.confidence_threshold,
54
+ classes=[self.dog_class_id], # Only detect dogs
55
+ verbose=False)
56
+
57
+ detections = []
58
+
59
+ if results and len(results) > 0:
60
+ result = results[0]
61
+ if result.boxes is not None:
62
+ boxes = result.boxes
63
+
64
+ for i in range(len(boxes)):
65
+ # Get bbox coordinates
66
+ x1, y1, x2, y2 = boxes.xyxy[i].cpu().numpy()
67
+ x1, y1, x2, y2 = int(x1), int(y1), int(x2), int(y2)
68
+
69
+ # Ensure valid coordinates
70
+ h, w = frame.shape[:2]
71
+ x1 = max(0, x1)
72
+ y1 = max(0, y1)
73
+ x2 = min(w, x2)
74
+ y2 = min(h, y2)
75
+
76
+ # Skip invalid boxes
77
+ if x2 <= x1 or y2 <= y1:
78
+ continue
79
+
80
+ # Crop dog image
81
+ dog_crop = frame[y1:y2, x1:x2].copy()
82
+
83
+ # Create detection
84
+ detection = Detection(
85
+ bbox=[x1, y1, x2, y2],
86
+ confidence=float(boxes.conf[i]),
87
+ image_crop=dog_crop
88
+ )
89
+ detections.append(detection)
90
+
91
+ return detections
92
+
93
+ def set_confidence(self, threshold: float):
94
+ """Update detection confidence threshold"""
95
+ self.confidence_threshold = max(0.1, min(1.0, threshold))