import gradio as gr import numpy as np import cv2 import os # Load Haar cascade for face detection face_cascade = cv2.CascadeClassifier(cv2.data.haarcascades + "haarcascade_frontalface_default.xml") # Load precomputed model data mean = np.load("mean.npy") eigenfaces = np.load("eigenfaces.npy") projected_faces = np.load("projected_faces.npy") labels = np.load("labels.npy") # Preprocess the image: detect face, crop, grayscale, resize, flatten def preprocess(img): try: gray = cv2.cvtColor(img, cv2.COLOR_RGB2GRAY) gray = cv2.equalizeHist(gray) # Improve lighting except Exception as e: raise ValueError(f"Failed to convert to grayscale: {e}") # Detect face faces = face_cascade.detectMultiScale(gray, scaleFactor=1.1, minNeighbors=5) if len(faces) == 0: raise ValueError("❌ No face detected in the image.") # Crop the first face found x, y, w, h = faces[0] face_roi = gray[y:y+h, x:x+w] resized_face = cv2.resize(face_roi, (100, 100)) return resized_face.flatten() # Predict function def predict(img): if img is None: return "❌ No image provided." try: img_vector = preprocess(img) img_centered = img_vector - mean img_projected = np.dot(eigenfaces.T, img_centered) # Calculate Euclidean distances distances = np.linalg.norm(projected_faces - img_projected, axis=1) min_index = np.argmin(distances) predicted_label = labels[min_index] confidence = distances[min_index] return f"✅ Match: Person {predicted_label} (distance = {confidence:.2f})" except Exception as e: return f"⚠️ Error: {str(e)}" # Gradio interface iface = gr.Interface( fn=predict, inputs=gr.Image(type="numpy", label="Upload or Capture a Face"), outputs=gr.Textbox(label="Prediction Result"), title="Enhanced Eigenfaces Face Recognition", description="Improved with face detection and lighting normalization. Upload a clear frontal face image." ) iface.launch()