Spaces:
Sleeping
Sleeping
File size: 4,938 Bytes
3881be4 d68547b 691e51a 6d83718 691e51a 6d83718 691e51a 6d83718 691e51a 6d83718 691e51a 6d83718 691e51a 2c0a9f6 691e51a 2c0a9f6 691e51a 72e0b27 691e51a 6d83718 691e51a 40709e4 691e51a 3881be4 691e51a | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 | import gradio as gr
import cv2
import numpy as np
import insightface
from insightface.app import FaceAnalysis
from insightface.model_zoo import get_model
import urllib.request
import os
import tempfile
# Download model if not exists
MODEL_URL = "https://huggingface.co/ezioruan/inswapper_128.onnx/resolve/main/inswapper_128.onnx"
MODEL_PATH = "inswapper_128.onnx"
if not os.path.exists(MODEL_PATH):
print("📥 Downloading face swap model...")
urllib.request.urlretrieve(MODEL_URL, MODEL_PATH)
# Initialize face analysis
print("🔄 Loading face analysis models...")
face_app = FaceAnalysis(name="buffalo_l", providers=["CPUExecutionProvider"])
face_app.prepare(ctx_id=0, det_size=(640, 640))
face_swapper = get_model(MODEL_PATH, providers=["CPUExecutionProvider"])
print("✅ Models ready!")
def process_video(source_img, target_video, quality_choice):
try:
# Quality settings map
quality_map = {
"320p (Fastest)": {"width": 320, "fps_reduction": 3, "bitrate": "300k"},
"480p (Balanced)": {"width": 480, "fps_reduction": 2, "bitrate": "500k"},
"720p (Good)": {"width": 720, "fps_reduction": 1, "bitrate": "1000k"},
"1080p (Original)": {"width": None, "fps_reduction": 1, "bitrate": "2000k"}
}
settings = quality_map[quality_choice]
# Open video
cap = cv2.VideoCapture(target_video)
original_fps = cap.get(cv2.CAP_PROP_FPS)
original_width = int(cap.get(cv2.CAP_PROP_FRAME_WIDTH))
original_height = int(cap.get(cv2.CAP_PROP_FRAME_HEIGHT))
# Calculate new dimensions
if settings["width"]:
new_width = settings["width"]
aspect = original_height / original_width
new_height = int(new_width * aspect)
else:
new_width = original_width
new_height = original_height
# Calculate new fps
new_fps = original_fps // settings["fps_reduction"]
# Setup output
temp_output = tempfile.NamedTemporaryFile(suffix=".mp4", delete=False).name
fourcc = cv2.VideoWriter_fourcc(*"mp4v")
out = cv2.VideoWriter(temp_output, fourcc, new_fps, (new_width, new_height))
# Get source face
source_rgb = cv2.cvtColor(source_img, cv2.COLOR_BGR2RGB)
source_faces = face_app.get(source_rgb)
if len(source_faces) == 0:
return None, "❌ No face detected in source image"
source_face = source_faces[0]
# Process video
frame_count = 0
while True:
ret, frame = cap.read()
if not ret:
break
# Resize frame
if settings["width"]:
frame = cv2.resize(frame, (new_width, new_height))
# Convert and swap face
frame_rgb = cv2.cvtColor(frame, cv2.COLOR_BGR2RGB)
target_faces = face_app.get(frame_rgb)
if len(target_faces) > 0:
result = face_swapper.get(frame_rgb, target_faces[0], source_face, paste_back=True)
frame_rgb = result
# Convert back and write
frame_bgr = cv2.cvtColor(frame_rgb, cv2.COLOR_RGB2BGR)
out.write(frame_bgr)
frame_count += 1
cap.release()
out.release()
return temp_output, f"✅ Video processed at {quality_choice} - {frame_count} frames"
except Exception as e:
return None, f"❌ Error: {str(e)}"
# Create UI
with gr.Blocks(theme=gr.themes.Soft(), title="FaceSwapAll") as demo:
gr.Markdown("# FaceSwapAll with Quality Control")
with gr.Row():
with gr.Column():
source = gr.Image(label="Source Face", type="numpy", height=300)
with gr.Column():
target = gr.Video(label="Target Video", height=300)
# Quality dropdown
quality = gr.Dropdown(
label="Video Output Quality",
choices=["320p (Fastest)", "480p (Balanced)", "720p (Good)", "1080p (Original)"],
value="480p (Balanced)",
info="Lower quality = faster processing on free CPU"
)
swap_btn = gr.Button("Swap Face in Video", variant="primary", size="lg")
with gr.Row():
result = gr.Video(label="Result Video")
status = gr.Textbox(label="Status", lines=3)
swap_btn.click(
fn=process_video,
inputs=[source, target, quality],
outputs=[result, status]
)
gr.Markdown("""
### ⚡ Speed Tips:
- **320p**: Fastest (8-10x speedup) - Best for testing
- **480p**: Balanced (4-5x speedup) - Good quality/speed tradeoff
- **720p**: Good quality (2x speedup)
- **1080p**: Original quality - Slowest on free CPU
""")
if __name__ == "__main__":
demo.launch()
|