import threading from typing import Any, Optional, List import insightface import numpy import roop.globals from roop.typing import Frame, Face FACE_ANALYSER = None THREAD_LOCK = threading.Lock() def get_face_analyser() -> Any: global FACE_ANALYSER with THREAD_LOCK: if FACE_ANALYSER is None: FACE_ANALYSER = insightface.app.FaceAnalysis(name='buffalo_l', providers=roop.globals.execution_providers) FACE_ANALYSER.prepare(ctx_id=0) return FACE_ANALYSER def clear_face_analyser() -> Any: global FACE_ANALYSER FACE_ANALYSER = None def get_one_face(frame: Frame) -> Any: face = get_face_analyser().get(frame) try: return min(face, key=lambda x: x.bbox[0]) except ValueError: return None def get_many_faces(frame: Frame) -> Optional[List[Face]]: try: return get_face_analyser().get(frame) except ValueError: return None def find_similar_face(frame: Frame, reference_face: Face) -> Optional[Face]: many_faces = get_many_faces(frame) if many_faces: for face in many_faces: if hasattr(face, 'normed_embedding') and hasattr(reference_face, 'normed_embedding'): distance = numpy.sum(numpy.square(face.normed_embedding - reference_face.normed_embedding)) if distance < roop.globals.similar_face_distance: return face return None