assile commited on
Commit
495a7a7
·
verified ·
1 Parent(s): 4b45c99

Update run.py

Browse files
Files changed (1) hide show
  1. run.py +48 -49
run.py CHANGED
@@ -3,19 +3,18 @@ import cv2
3
  import numpy as np
4
  from insightface.app import FaceAnalysis
5
  import tempfile
 
6
  import os
7
 
8
- # Initialisation du modèle
9
- face_swapper = FaceAnalysis(name="buffalo_l")
10
- face_swapper.prepare(ctx_id=0, det_size=(640, 640))
11
 
12
- def swap_face(source_face, target_face, frame, blend_factor=0.7):
13
- """Échange le visage avec possibilité de régler l'intensité du mélange"""
14
  src_emb = source_face.normed_embedding
15
  tgt_bbox = target_face.bbox.astype(int)
16
 
17
- # Obtenir le visage source (de la cible pour garder la taille)
18
- h, w = frame.shape[:2]
19
  src_face_img = source_face.img
20
  resized_face = cv2.resize(src_face_img, (tgt_bbox[2]-tgt_bbox[0], tgt_bbox[3]-tgt_bbox[1]))
21
 
@@ -29,27 +28,27 @@ def swap_face(source_face, target_face, frame, blend_factor=0.7):
29
  # Positionner le visage
30
  center = ((tgt_bbox[0]+tgt_bbox[2])//2, (tgt_bbox[1]+tgt_bbox[3])//2)
31
 
32
- # Appliquer seamlessClone
33
- result = cv2.seamlessClone(
34
- resized_face, frame, mask, center, cv2.NORMAL_CLONE
35
- )
36
 
37
- # Mélanger avec l'original selon blend_factor
38
- blended = cv2.addWeighted(frame, 1-blend_factor, result, blend_factor, 0)
39
-
40
- return blended
41
 
42
-
43
- def process_video(source_img, target_video, face_index_source=0, face_index_target=0, blend_factor=0.8):
44
  try:
45
- temp_output = tempfile.NamedTemporaryFile(suffix=".mp4", delete=False)
46
-
 
 
47
  # Charger le visage source
48
- source_faces = face_swapper.get(np.array(source_img))
49
  if not source_faces:
50
- raise ValueError("Aucun visage trouvé sur l'image source.")
51
- source_face = source_faces[face_index_source]
 
 
 
52
 
 
53
  cap = cv2.VideoCapture(target_video)
54
  fps = cap.get(cv2.CAP_PROP_FPS)
55
  frame_width = int(cap.get(cv2.CAP_PROP_FRAME_WIDTH))
@@ -58,48 +57,48 @@ def process_video(source_img, target_video, face_index_source=0, face_index_targ
58
  fourcc = cv2.VideoWriter_fourcc(*'mp4v')
59
  out = cv2.VideoWriter(temp_output.name, fourcc, fps, (frame_width, frame_height))
60
 
61
- while cap.isOpened():
62
  ret, frame = cap.read()
63
  if not ret:
64
  break
65
 
66
- target_faces = face_swapper.get(frame)
67
- if target_faces and len(target_faces) > face_index_target:
68
- frame = swap_face(source_face, target_faces[face_index_target], frame, blend_factor)
 
69
 
70
  out.write(frame)
71
 
72
  cap.release()
73
  out.release()
74
 
75
- return temp_output.name
 
 
 
 
 
76
 
77
  except Exception as e:
78
- print(f"ERREUR: {str(e)}")
79
  return None
80
 
81
 
82
  # Interface Gradio
83
- with gr.Blocks() as app:
84
- gr.Markdown("## 🎬 VideoFaceSwap Pro - Échangez des visages en vidéo avec précision")
85
-
86
- with gr.Row():
87
- src_img = gr.Image(label="Visage Source", type="numpy")
88
- tgt_video = gr.Video(label="Vidéo Cible")
89
-
90
- with gr.Row():
91
- face_index_source = gr.Slider(0, 5, value=0, step=1, label="Index Visage Source")
92
- face_index_target = gr.Slider(0, 5, value=0, step=1, label="Index Visage à Remplacer")
93
- blend_factor = gr.Slider(0.0, 1.0, value=0.8, label="Intensité du mélange")
94
-
95
- btn = gr.Button("🔁 Traiter la Vidéo", variant="primary")
96
- output_video = gr.Video(label="Vidéo Résultat")
97
-
98
- btn.click(
99
- fn=process_video,
100
- inputs=[src_img, tgt_video, face_index_source, face_index_target, blend_factor],
101
- outputs=output_video
102
- )
103
 
104
  if __name__ == "__main__":
105
- app.launch(server_name="0.0.0.0", server_port=7860)
 
3
  import numpy as np
4
  from insightface.app import FaceAnalysis
5
  import tempfile
6
+ from moviepy.editor import VideoFileClip
7
  import os
8
 
9
+ # Forcer InsightFace à utiliser un répertoire avec des permissions
10
+ os.environ['INSIGHTFACE_ROOT'] = '/tmp/.insightface'
 
11
 
12
+ def swap_face(source_face, target_face, frame):
13
+ """Remplace le visage cible par le visage source"""
14
  src_emb = source_face.normed_embedding
15
  tgt_bbox = target_face.bbox.astype(int)
16
 
17
+ # Obtenir le visage redimensionné
 
18
  src_face_img = source_face.img
19
  resized_face = cv2.resize(src_face_img, (tgt_bbox[2]-tgt_bbox[0], tgt_bbox[3]-tgt_bbox[1]))
20
 
 
28
  # Positionner le visage
29
  center = ((tgt_bbox[0]+tgt_bbox[2])//2, (tgt_bbox[1]+tgt_bbox[3])//2)
30
 
31
+ # Échange réaliste
32
+ result = cv2.seamlessClone(resized_face, frame, mask, center, cv2.NORMAL_CLONE)
33
+ return result
 
34
 
 
 
 
 
35
 
36
+ def process_video(source_img, target_video):
 
37
  try:
38
+ # Initialiser le modèle INSIDE la fonction pour éviter les problèmes de chargement
39
+ face_app = FaceAnalysis(name="buffalo_l", root="/tmp/.insightface")
40
+ face_app.prepare(ctx_id=0, det_size=(640, 640))
41
+
42
  # Charger le visage source
43
+ source_faces = face_app.get(source_img)
44
  if not source_faces:
45
+ raise ValueError("Aucun visage trouvé dans l'image source.")
46
+ source_face = source_faces[0]
47
+
48
+ # Fichier temporaire pour sauvegarder la sortie
49
+ temp_output = tempfile.NamedTemporaryFile(suffix=".mp4", delete=False)
50
 
51
+ # Ouvrir la vidéo cible
52
  cap = cv2.VideoCapture(target_video)
53
  fps = cap.get(cv2.CAP_PROP_FPS)
54
  frame_width = int(cap.get(cv2.CAP_PROP_FRAME_WIDTH))
 
57
  fourcc = cv2.VideoWriter_fourcc(*'mp4v')
58
  out = cv2.VideoWriter(temp_output.name, fourcc, fps, (frame_width, frame_height))
59
 
60
+ while True:
61
  ret, frame = cap.read()
62
  if not ret:
63
  break
64
 
65
+ # Détecter les visages dans la frame
66
+ target_faces = face_app.get(frame)
67
+ for face in target_faces:
68
+ frame = swap_face(source_face, face, frame)
69
 
70
  out.write(frame)
71
 
72
  cap.release()
73
  out.release()
74
 
75
+ # Réencodage pour compatibilité Gradio/HF
76
+ clip = VideoFileClip(temp_output.name)
77
+ final_path = temp_output.name.replace(".mp4", "_final.mp4")
78
+ clip.write_videofile(final_path, codec="libx264", audio_codec="aac")
79
+
80
+ return final_path
81
 
82
  except Exception as e:
83
+ print(f"Erreur lors du traitement : {str(e)}")
84
  return None
85
 
86
 
87
  # Interface Gradio
88
+ title = "🎬 FaceSwap Pro - Swap Video"
89
+ description = "Télécharge une image avec un visage et une vidéo. Le visage sera remplacé automatiquement."
90
+
91
+ demo = gr.Interface(
92
+ fn=process_video,
93
+ inputs=[
94
+ gr.Image(label="Visage Source", type="numpy"),
95
+ gr.Video(label="Vidéo Cible"),
96
+ ],
97
+ outputs=gr.Video(label="Vidéo Résultat"),
98
+ title=title,
99
+ description=description,
100
+ allow_flagging="never"
101
+ )
 
 
 
 
 
 
102
 
103
  if __name__ == "__main__":
104
+ demo.launch()