rocketmandrey commited on
Commit
1bb4e73
·
verified ·
1 Parent(s): f8fcbc0

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +171 -38
app.py CHANGED
@@ -1,51 +1,184 @@
1
  import os
2
  import torch
3
  import gradio as gr
4
- from diffusers import DiffusionPipeline
5
- import soundfile as sf
 
 
 
6
 
7
- # 1) Читаем токен из секретов
8
- HF_HUB_TOKEN = os.environ["HF_HUB_TOKEN"]
9
 
10
- # 2) Загружаем pipeline из подпапки GFengG
11
- pipe = DiffusionPipeline.from_pretrained(
12
- "MeiGen-AI/MeiGen-MultiTalk", # первый позиционный аргумент (убрали repo_id=)
13
- subfolder="GFengG", # ← обязательно указываем папку GFengG
14
- token=HF_HUB_TOKEN,
15
- torch_dtype=torch.float16
16
- )
17
- pipe = pipe.to("cuda" if torch.cuda.is_available() else "cpu")
18
 
19
- # 3) Функция генерации
20
- def generate(prompt: str):
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
21
  try:
22
- output = pipe(prompt) # используем дефолтный метод pipeline
23
- # Проверяем структуру output - может быть .audio или .audios
24
- if hasattr(output, 'audios'):
25
- audio = output.audios[0]
26
- elif hasattr(output, 'audio'):
27
- audio = output.audio
28
- else:
29
- # Если output сам является аудио-тензором
30
- audio = output
31
 
32
- # Определяем sample rate
33
- sample_rate = getattr(pipe, 'sample_rate', 22050) # fallback to 22050
34
- if hasattr(pipe, 'unet') and hasattr(pipe.unet, 'config'):
35
- sample_rate = getattr(pipe.unet.config, 'sample_rate', sample_rate)
36
 
37
- sf.write("generated.wav", audio, samplerate=sample_rate)
38
- return "generated.wav"
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
39
  except Exception as e:
40
- return f"Ошибка генерации: {str(e)}"
41
 
42
- # 4) Gradio UI
43
- iface = gr.Interface(
44
- fn=generate,
45
- inputs=gr.Textbox(lines=2, placeholder="Введите текст..."),
46
- outputs=gr.Audio(type="filepath"),
47
- title="MeiGen-MultiTalk Demo"
48
- )
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
49
 
50
  if __name__ == "__main__":
51
- iface.launch()
 
1
  import os
2
  import torch
3
  import gradio as gr
4
+ import numpy as np
5
+ from huggingface_hub import hf_hub_download
6
+ import tempfile
7
+ import subprocess
8
+ from pathlib import Path
9
 
10
+ # Получаем токен из переменных окружения
11
+ HF_HUB_TOKEN = os.environ.get("HF_HUB_TOKEN")
12
 
13
+ # Инициализация модели будет происходить лениво
14
+ model = None
15
+ processor = None
 
 
 
 
 
16
 
17
+ def load_model():
18
+ """Ленивая загрузка модели"""
19
+ global model, processor
20
+ if model is None:
21
+ try:
22
+ # Скачиваем файлы модели
23
+ model_files = [
24
+ "diffusion_pytorch_model.safetensors.index.json",
25
+ "multitalk.safetensors"
26
+ ]
27
+
28
+ local_dir = "./multitalk_weights"
29
+ os.makedirs(local_dir, exist_ok=True)
30
+
31
+ for file in model_files:
32
+ if not os.path.exists(os.path.join(local_dir, file)):
33
+ print(f"Скачиваем {file}...")
34
+ hf_hub_download(
35
+ repo_id="MeiGen-AI/MeiGen-MultiTalk",
36
+ filename=file,
37
+ local_dir=local_dir,
38
+ token=HF_HUB_TOKEN
39
+ )
40
+
41
+ print("Модель загружена!")
42
+ return True
43
+
44
+ except Exception as e:
45
+ print(f"Ошибка загрузки модели: {e}")
46
+ return False
47
+ return True
48
+
49
+ def generate_talking_video(audio_file, reference_image, prompt_text="A person is talking"):
50
+ """
51
+ Генерирует видео с говорящим персонажем
52
+ """
53
  try:
54
+ if not load_model():
55
+ return None, "Ошибка загрузки модели"
 
 
 
 
 
 
 
56
 
57
+ if audio_file is None or reference_image is None:
58
+ return None, "Пожалуйста, загрузите аудио файл и референсное изображение"
 
 
59
 
60
+ # Создаем временные файлы
61
+ with tempfile.TemporaryDirectory() as temp_dir:
62
+ # Сохраняем входные файлы
63
+ audio_path = os.path.join(temp_dir, "input_audio.wav")
64
+ image_path = os.path.join(temp_dir, "reference_image.jpg")
65
+ output_path = os.path.join(temp_dir, "output_video.mp4")
66
+
67
+ # Копируем файлы
68
+ import shutil
69
+ shutil.copy2(audio_file, audio_path)
70
+
71
+ # Сохраняем изображение
72
+ if hasattr(reference_image, 'save'):
73
+ reference_image.save(image_path)
74
+ else:
75
+ from PIL import Image
76
+ Image.fromarray(reference_image).save(image_path)
77
+
78
+ # Здесь должна быть логика inference с моделью
79
+ # Пока что возвращаем заглушку
80
+ return None, f"Модель загружена. Получены файлы:\n- Аудио: {audio_path}\n- Изображение: {image_path}\n- Промпт: {prompt_text}\n\nДля полной реализации нужна интеграция с MultiTalk pipeline."
81
+
82
  except Exception as e:
83
+ return None, f"Ошибка генерации: {str(e)}"
84
 
85
+ def generate_from_text(text, reference_image, voice_type="female"):
86
+ """
87
+ Генерирует видео из текста (сначала TTS, потом lip-sync)
88
+ """
89
+ try:
90
+ if not text.strip():
91
+ return None, "Введите текст для озвучивания"
92
+
93
+ if reference_image is None:
94
+ return None, "Загрузите референсное изображение"
95
+
96
+ # Здесь нужно сначала сгенерировать аудио из текста
97
+ # Затем использовать его для генерации видео
98
+
99
+ return None, f"Функция text-to-video в разработке.\nТекст: {text}\nТип голоса: {voice_type}"
100
+
101
+ except Exception as e:
102
+ return None, f"Ошибка: {str(e)}"
103
+
104
+ # Создаем интерфейс Gradio
105
+ with gr.Blocks(title="MeiGen-MultiTalk Demo") as demo:
106
+ gr.Markdown("# MeiGen-MultiTalk: Audio-Driven Talking Video Generation")
107
+ gr.Markdown("Создавайте видео с говорящими персонажами из аудио и референсных изображений")
108
+
109
+ with gr.Tabs():
110
+ with gr.Tab("Аудио → Видео"):
111
+ gr.Markdown("### Загрузите аудио и референсное изображение для создания говорящего видео")
112
+
113
+ with gr.Row():
114
+ with gr.Column():
115
+ audio_input = gr.Audio(
116
+ label="Аудио файл",
117
+ type="filepath",
118
+ sources=["upload", "microphone"]
119
+ )
120
+ image_input = gr.Image(
121
+ label="Референсное изображение лица",
122
+ type="pil"
123
+ )
124
+ prompt_input = gr.Textbox(
125
+ label="Описание видео (опционально)",
126
+ value="A person is talking naturally",
127
+ lines=2
128
+ )
129
+ generate_btn = gr.Button("Генерировать видео", variant="primary")
130
+
131
+ with gr.Column():
132
+ video_output = gr.Video(label="Результат")
133
+ status_output = gr.Textbox(label="Статус", lines=3)
134
+
135
+ generate_btn.click(
136
+ fn=generate_talking_video,
137
+ inputs=[audio_input, image_input, prompt_input],
138
+ outputs=[video_output, status_output]
139
+ )
140
+
141
+ with gr.Tab("Текст → Видео"):
142
+ gr.Markdown("### Введите текст для создания говорящего видео")
143
+
144
+ with gr.Row():
145
+ with gr.Column():
146
+ text_input = gr.Textbox(
147
+ label="Текст для озвучивания",
148
+ lines=4,
149
+ placeholder="Введите текст, который должен произнести персонаж..."
150
+ )
151
+ image_input2 = gr.Image(
152
+ label="Референсное изображение лица",
153
+ type="pil"
154
+ )
155
+ voice_select = gr.Dropdown(
156
+ choices=["female", "male", "child"],
157
+ value="female",
158
+ label="Тип голоса"
159
+ )
160
+ generate_btn2 = gr.Button("Генерировать видео", variant="primary")
161
+
162
+ with gr.Column():
163
+ video_output2 = gr.Video(label="Результат")
164
+ status_output2 = gr.Textbox(label="Статус", lines=3)
165
+
166
+ generate_btn2.click(
167
+ fn=generate_from_text,
168
+ inputs=[text_input, image_input2, voice_select],
169
+ outputs=[video_output2, status_output2]
170
+ )
171
+
172
+ gr.Markdown("""
173
+ ### Инструкция по использованию:
174
+ 1. **Аудио → Видео**: Загрузите аудио файл и фото лица для создания lip-sync видео
175
+ 2. **Текст → Видео**: Введите текст, выберите тип голоса и загрузите фото
176
+
177
+ ### Требования:
178
+ - Изображение должно содержать четко видимое лицо
179
+ - Аудио должно содержать речь (не музыку)
180
+ - Рекомендуемая длительность аудио: до 15 секунд
181
+ """)
182
 
183
  if __name__ == "__main__":
184
+ demo.launch(server_name="0.0.0.0", server_port=7860)