|
|
import os |
|
|
import gradio as gr |
|
|
import json |
|
|
import numpy as np |
|
|
from datetime import datetime |
|
|
import os |
|
|
import sys |
|
|
import librosa |
|
|
import os.path as op |
|
|
APP_DIR = op.dirname(op.abspath(__file__)) |
|
|
|
|
|
from download import download_model |
|
|
|
|
|
download_model(APP_DIR) |
|
|
print("Successful downloaded model.") |
|
|
|
|
|
from levo_inference import LeVoInference |
|
|
|
|
|
model = LeVoInference(op.join(APP_DIR, "conf/infer.yaml")) |
|
|
|
|
|
EXAMPLE_DESC = """female, dark, pop, sad, piano and drums, the bpm is 125.""" |
|
|
EXAMPLE_LYRICS = """ |
|
|
[intro-short] |
|
|
|
|
|
[verse] |
|
|
夜晚的街灯闪烁. |
|
|
我漫步在熟悉的角落. |
|
|
回忆像潮水般涌来. |
|
|
你的笑容如此清晰. |
|
|
在心头无法抹去. |
|
|
那些曾经的甜蜜. |
|
|
如今只剩我独自回忆. |
|
|
|
|
|
[bridge] |
|
|
手机屏幕亮起. |
|
|
是你发来的消息. |
|
|
简单的几个字. |
|
|
却让我泪流满面. |
|
|
曾经的拥抱温暖. |
|
|
如今却变得遥远. |
|
|
我多想回到从前. |
|
|
重新拥有你的陪伴. |
|
|
|
|
|
[chorus] |
|
|
回忆的温度还在. |
|
|
你却已不在. |
|
|
我的心被爱填满. |
|
|
却又被思念刺痛. |
|
|
R&B的节奏奏响. |
|
|
我的心却在流浪. |
|
|
没有你的日子. |
|
|
我该如何继续向前. |
|
|
|
|
|
[outro-short] |
|
|
""".strip() |
|
|
|
|
|
|
|
|
|
|
|
def generate_song(description, lyric, prompt_audio=None): |
|
|
global model |
|
|
|
|
|
print(f"Generating song with description: {description}") |
|
|
print(f"Lyrics provided: {lyric}") |
|
|
if prompt_audio is not None: |
|
|
print("Using prompt audio for generation") |
|
|
|
|
|
|
|
|
audio_path = os.path.join(os.path.dirname(__file__), "sample/example.mp3") |
|
|
audio_data, sample_rate = librosa.load(audio_path, sr=None) |
|
|
|
|
|
|
|
|
|
|
|
input_config = { |
|
|
"description": description, |
|
|
"lyric": lyric, |
|
|
"has_prompt_audio": prompt_audio is not None, |
|
|
"timestamp": datetime.now().isoformat(), |
|
|
"model": str(model), |
|
|
} |
|
|
|
|
|
return (sample_rate, audio_data), json.dumps(input_config, indent=2) |
|
|
|
|
|
|
|
|
with gr.Blocks(title="LeVo Demo Space") as demo: |
|
|
gr.Markdown("# 🎵 LeVo Demo Space") |
|
|
gr.Markdown("Demo interface for the LeVo song generation model. Provide a description, lyrics, and optionally an audio prompt to generate a custom song.") |
|
|
|
|
|
with gr.Row(): |
|
|
with gr.Column(): |
|
|
description = gr.Textbox( |
|
|
label="Song Description", |
|
|
placeholder="Describe the style, mood, and characteristics of the song...", |
|
|
lines=1, |
|
|
max_lines=2, |
|
|
value=EXAMPLE_DESC, |
|
|
) |
|
|
lyric = gr.Textbox( |
|
|
label="Lyrics", |
|
|
placeholder="Enter the lyrics for the song...", |
|
|
lines=5, |
|
|
max_lines=8, |
|
|
value=EXAMPLE_LYRICS, |
|
|
) |
|
|
|
|
|
with gr.Tabs(elem_id="extra-tabs"): |
|
|
with gr.Tab("Audio Prompt"): |
|
|
prompt_audio = gr.Audio( |
|
|
label="Prompt Audio (Optional)", |
|
|
type="filepath", |
|
|
elem_id="audio-prompt" |
|
|
) |
|
|
with gr.Tab("Advanced Config"): |
|
|
text_prompt = gr.Textbox( |
|
|
label="Text Prompt", |
|
|
placeholder="Enter the Text Prompt, eg: emotional piano pop", |
|
|
) |
|
|
|
|
|
generate_btn = gr.Button("Generate Song", variant="primary") |
|
|
|
|
|
with gr.Column(): |
|
|
output_audio = gr.Audio(label="Generated Song", type="numpy") |
|
|
output_json = gr.JSON(label="Input Configuration") |
|
|
|
|
|
|
|
|
examples = gr.Examples( |
|
|
examples=[ |
|
|
["An uplifting pop song with catchy melodies"], |
|
|
["Melancholic piano ballad"], |
|
|
], |
|
|
inputs=[description], |
|
|
label="Description examples" |
|
|
) |
|
|
|
|
|
examples = gr.Examples( |
|
|
examples=[ |
|
|
["Shine bright like the stars above\nYou're the one that I'm dreaming of"], |
|
|
["The rain keeps falling on my window pane\nReminding me of love that's gone away"], |
|
|
], |
|
|
inputs=[lyric], |
|
|
label="Lyrics examples" |
|
|
) |
|
|
|
|
|
|
|
|
generate_btn.click( |
|
|
fn=generate_song, |
|
|
inputs=[description, lyric, prompt_audio], |
|
|
outputs=[output_audio, output_json] |
|
|
) |
|
|
|
|
|
|
|
|
|
|
|
if __name__ == "__main__": |
|
|
demo.launch(server_name="0.0.0.0", server_port=7860) |