Spaces:
Running
on
Zero
Running
on
Zero
Upload 2 files
Browse files- app.py +76 -0
- requirements.txt +8 -0
app.py
ADDED
@@ -0,0 +1,76 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
import gradio as gr
|
2 |
+
import whisper
|
3 |
+
import moviepy.editor as mp
|
4 |
+
from googletrans import Translator
|
5 |
+
from pydub import AudioSegment
|
6 |
+
import os
|
7 |
+
import tempfile
|
8 |
+
|
9 |
+
def extract_audio(video_path):
|
10 |
+
video = mp.VideoFileClip(video_path)
|
11 |
+
audio = video.audio
|
12 |
+
audio_path = tempfile.mktemp(suffix=".wav")
|
13 |
+
audio.write_audiofile(audio_path)
|
14 |
+
return audio_path
|
15 |
+
|
16 |
+
def generate_subtitles(audio_path):
|
17 |
+
model = whisper.load_model("base")
|
18 |
+
result = model.transcribe(audio_path)
|
19 |
+
return result["segments"]
|
20 |
+
|
21 |
+
def translate_subtitles(subtitles, target_language):
|
22 |
+
translator = Translator()
|
23 |
+
translated_subtitles = []
|
24 |
+
for segment in subtitles:
|
25 |
+
translated_text = translator.translate(segment["text"], dest=target_language).text
|
26 |
+
translated_subtitles.append({
|
27 |
+
"start": segment["start"],
|
28 |
+
"end": segment["end"],
|
29 |
+
"text": translated_text
|
30 |
+
})
|
31 |
+
return translated_subtitles
|
32 |
+
|
33 |
+
def add_subtitles_to_video(video_path, subtitles, output_path):
|
34 |
+
video = mp.VideoFileClip(video_path)
|
35 |
+
subtitles_clips = [
|
36 |
+
mp.TextClip(txt=subtitle["text"], fontsize=24, color='white', bg_color='black', font='Arial')
|
37 |
+
.set_position(('center', 'bottom'))
|
38 |
+
.set_duration(subtitle["end"] - subtitle["start"])
|
39 |
+
.set_start(subtitle["start"])
|
40 |
+
for subtitle in subtitles
|
41 |
+
]
|
42 |
+
final_video = mp.CompositeVideoClip([video] + subtitles_clips)
|
43 |
+
final_video.write_videofile(output_path, codec="libx264", audio_codec="aac")
|
44 |
+
|
45 |
+
def process_video(video_path, target_language):
|
46 |
+
# Extract audio from video
|
47 |
+
audio_path = extract_audio(video_path)
|
48 |
+
|
49 |
+
# Generate subtitles using Whisper
|
50 |
+
subtitles = generate_subtitles(audio_path)
|
51 |
+
|
52 |
+
# Translate subtitles
|
53 |
+
translated_subtitles = translate_subtitles(subtitles, target_language)
|
54 |
+
|
55 |
+
# Add translated subtitles to video
|
56 |
+
output_path = tempfile.mktemp(suffix=".mp4")
|
57 |
+
add_subtitles_to_video(video_path, translated_subtitles, output_path)
|
58 |
+
|
59 |
+
return output_path
|
60 |
+
|
61 |
+
def gradio_interface(video, target_language):
|
62 |
+
output_video = process_video(video.name, target_language)
|
63 |
+
return output_video
|
64 |
+
|
65 |
+
iface = gr.Interface(
|
66 |
+
fn=gradio_interface,
|
67 |
+
inputs=[
|
68 |
+
gr.Video(label="Upload Video"),
|
69 |
+
gr.Dropdown(choices=["es", "fr", "de", "it", "ja", "ko", "zh-cn"], label="Target Language")
|
70 |
+
],
|
71 |
+
outputs=gr.Video(label="Processed Video"),
|
72 |
+
title="Video Subtitle Translator",
|
73 |
+
description="Upload a video, and get it back with translated subtitles!"
|
74 |
+
)
|
75 |
+
|
76 |
+
iface.launch()
|
requirements.txt
ADDED
@@ -0,0 +1,8 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
gradio==3.50.2
|
2 |
+
whisper==1.1.10
|
3 |
+
moviepy==1.0.3
|
4 |
+
googletrans==3.1.0a0
|
5 |
+
pydub==0.25.1
|
6 |
+
torch==2.0.1
|
7 |
+
numpy==1.24.3
|
8 |
+
ffmpeg-python==0.2.0
|