HackOdisha / face_model.py
Shreyas
Upload 9 files
c20196f verified
Raw
History Blame Contribute Delete
3.25 kB
import cv2
from ultralytics import YOLO
import supervision as sv
import numpy as np
import os
from typing import Union, Tuple
class FacialEmotionDetector:
"""
Detect facial emotions from an image or video frame using a YOLO model.
"""
def __init__(self, model_path: str = "best.pt"):
"""
Initialize the detector.
Args:
model_path (str): Path to YOLO model weights (.pt).
"""
if not os.path.exists(model_path):
raise FileNotFoundError(
f"❌ Model file not found at '{model_path}'. "
f"Please ensure 'best.pt' is available in the project directory."
)
# Load YOLO model
self.model = YOLO(model_path)
# Supervision annotators for boxes + labels
self.box_annotator = sv.BoxAnnotator(thickness=2)
self.label_annotator = sv.LabelAnnotator(text_scale=0.5, text_thickness=1)
print("βœ… FacialEmotionDetector initialized successfully.")
def detect_emotion(self, frame: np.ndarray) -> Tuple[np.ndarray, Union[str, None]]:
"""
Detect emotions in a single frame.
Args:
frame (np.ndarray): BGR image (OpenCV).
Returns:
Tuple[np.ndarray, str|None]:
- Annotated frame (with boxes + labels).
- Most confident emotion label (or None if no detection).
"""
# YOLO inference
result = self.model(frame, agnostic_nms=True)[0]
# Convert YOLO results β†’ Supervision detections
detections = sv.Detections.from_ultralytics(result)
# Find dominant (highest confidence) detection
dominant_emotion = None
if len(detections) > 0:
most_confident_idx = np.argmax(detections.confidence)
dominant_emotion = detections.data["class_name"][most_confident_idx]
# Build label strings
labels = [
f"{self.model.model.names[class_id]} {confidence:.2f}"
for _, _, confidence, class_id, _, _ in detections
]
# Annotate boxes
annotated = self.box_annotator.annotate(scene=frame.copy(), detections=detections)
# Annotate labels
annotated = self.label_annotator.annotate(scene=annotated, detections=detections, labels=labels)
return annotated, dominant_emotion
if __name__ == "__main__":
# Quick webcam test
try:
detector = FacialEmotionDetector(model_path="best.pt")
cap = cv2.VideoCapture(0)
if not cap.isOpened():
print("❌ Could not open webcam.")
else:
while True:
ret, frame = cap.read()
if not ret:
break
annotated_frame, emotion = detector.detect_emotion(frame)
cv2.imshow("Facial Emotion Detection", annotated_frame)
if emotion:
print(f"Detected Emotion: {emotion}")
if cv2.waitKey(1) & 0xFF == ord("q"):
break
cap.release()
cv2.destroyAllWindows()
except FileNotFoundError as e:
print(e)
except Exception as e:
print(f"⚠️ Unexpected error: {e}")