metadata
license: apache-2.0
ReSpark TTS 模型
本仓库包含 ReSpark 文本转语音 (TTS) 模型,这是一个强大而高效的模型,可以从文本生成高质量的语音。它基于 RWKV 架构,并利用 BiCodec-Tokenizer 进行音频处理。
安装
首先,请安装所需的依赖库:
pip install transformers rwkv-fla torch torchaudio torchvision transformers soundfile numpy librosa omegaconf soxr soundfile einx librosa
使用方法
tts.py
脚本提供了一个完整的使用该模型进行文本转语音合成(带声音克隆功能)的示例。
运行测试脚本
要生成语音,只需运行以下脚本:
python tts.py
工作原理
该脚本执行以下步骤:
- 从当前目录加载预训练的
AutoModelForCausalLM
和AutoTokenizer
。 - 初始化用于音频编码和解码的
BiCodecTokenizer
。 - 加载一个参考音频文件 (
kafka.wav
) 及其对应的文本 (prompt_text
) 以提供声音提示(voice prompt)。 - 如果需要,将参考音频重采样以匹配模型期望的采样率 (24000 Hz)。
- 指定一个需要被合成的目标文本 (
text
)。 - 调用
generate_speech
函数,该函数会根据目标文本和参考音频中的声音生成音频。 - 将生成的音频保存到
output.wav
。
您可以修改 tts.py
文件中的 prompt_text
、prompt_audio_file
和 text
变量,以使用不同的声音合成不同的文本。
示例代码 (tts.py
)
import os
import sys
current_dir = os.path.dirname(os.path.abspath(__file__))
print('add current dir to sys.path', current_dir)
sys.path.append(current_dir)
from sparktts.models.audio_tokenizer import BiCodecTokenizer
from transformers import AutoTokenizer, AutoModelForCausalLM
import soundfile as sf
import numpy as np
import torch
from utilities import generate_embeddings
def generate_speech(model, tokenizer, text, bicodec, prompt_text=None, prompt_audio=None,
max_new_tokens=3000, do_sample=True, top_k=50, top_p=0.95,
temperature=1.0, device="cuda:0"):
"""
生成语音的函数
"""
eos_token_id = model.config.vocab_size - 1
embeddings = generate_embeddings(
model=model,
tokenizer=tokenizer,
text=text,
bicodec=bicodec,
prompt_text=prompt_text,
prompt_audio=prompt_audio
)
global_tokens = embeddings['global_tokens'].unsqueeze(0)
model.eval()
with torch.no_grad():
generated_outputs = model.generate(
inputs_embeds=embeddings['input_embs'],
attention_mask=torch.ones((1, embeddings['input_embs'].shape[1]),dtype=torch.long,device=device),
max_new_tokens=max_new_tokens,
do_sample=do_sample,
top_k=top_k,
top_p=top_p,
temperature=temperature,
eos_token_id=eos_token_id,
pad_token_id=tokenizer.pad_token_id if hasattr(tokenizer, 'pad_token_id') else tokenizer.eos_token_id,
use_cache=True
)
semantic_tokens_tensor = generated_outputs[:,:-1]
with torch.no_grad():
wav = bicodec.detokenize(global_tokens, semantic_tokens_tensor)
return wav
# --- 主程序 ---
device = 'cuda:0'
# 初始化分词器和模型
audio_tokenizer = BiCodecTokenizer(model_dir=current_dir, device=device)
tokenizer = AutoTokenizer.from_pretrained(current_dir, trust_remote_code=True)
model = AutoModelForCausalLM.from_pretrained(current_dir, trust_remote_code=True)
model = model.bfloat16().to(device)
model.eval()
# 准备用于声音克隆的提示音频和文本
prompt_text = "我们并不是通过物理移动手段找到星河的。"
prompt_audio_file = os.path.join(current_dir, 'kafka.wav')
prompt_audio, sampling_rate = sf.read(prompt_audio_file)
# 如果需要,重采样音频
target_sample_rate = audio_tokenizer.config['sample_rate']
if sampling_rate != target_sample_rate:
from librosa import resample
prompt_audio = resample(prompt_audio, orig_sr=sampling_rate, target_sr=target_sample_rate)
prompt_audio = np.array(prompt_audio, dtype=np.float32)
# 要合成的文本
text = "科学技术是第一生产力,最近 AI的迅猛发展让我们看到了迈向星辰大海的希望。"
# 生成语音
wav = generate_speech(model, tokenizer, text, audio_tokenizer, prompt_audio=prompt_audio, device=device)
# 保存输出
sf.write('output.wav', wav, target_sample_rate)
print("生成的音频已保存到 output.wav")