用SOVITS炼制AI人声

基于项目 https://github.com/svc-develop-team/so-vits-svc 完成
本文主要是解释 BV1sx4y1P7xd 这部AI作品的制作,是纯粹经验性的,内含的理论知识如同up的大脑一样空空如也。
1.解包游戏文件
首先需要从游戏中提取所需角色的音频文件,无论是用古朴的CRASS、独特的exkizpak、还是强大的GARbro。
白色相簿2游戏文件中对应的音频的主要是SE.pak和VOICE.pak。
2.筛选并简单处理音频
解包游戏文件后一般会获得所有音频,这时筛选显然是必要的。SE.pak中较短的都是声效,可以在时长数十秒的文件中找出雪菜清唱的歌声。VOICE.pak中文件名以02结尾的是雪菜的声音(逾5000条),但其中有部分有电话或回声效果,需要手动筛去。这一步的内容需要全部手动完成,工作量极大,是货真价实的劳动密集型。(up最后选出了约600条58分钟音频,50min口语+5min歌声+3min角川)这个数据集确实啊,音质好、数量足、声线正,10句才有1句入选;跑起来效果确实好,我们那个SOVITS,不吃它不行
此外为了避免在训练的预处理中爆显存,还需要剪切音频到合适的长度。up在这里使用的是Audio Slicer (https://github.com/openvpi/audio-slicer),来去除音频的无声部分并剪切之(只需要处理数分钟的音频)。不要有超过1分钟的音频就行。
另外SOVITS训练用的数据集必须完全是人声,如果你想保留SE.pak中解包出来的有伴奏的歌声或者采用别处下载的米泽圆的歌曲,那么你需要用别的工具单独分离出人声,再进行剪切等操作。
最后还需要把这一步获得的音频全部转换为wav格式,因为up目前见到的SOVITS全都要求数据集是wav格式。建议使用FFmpeg (https://github.com/FFmpeg/FFmpeg)。
3.找到合适的SOVITS
可以直接下载so-vits-svc项目自己配置(需要自己找适应的底模D_0.pth和G_0.pth),也可以在网上找懒人包,还可以在一些服务器平台上找镜像。up选择的是在服务器平台租用显卡、使用线上的镜像;个人感觉训练很耗时间,如果没有很好的显卡和条件的话可以考虑租用。特别要注意的是不同环境训练出来的模型不能通用,最好哪里训练就在哪里推理(训练用的底模也不能通用)。
4.放入音频并进行训练前预处理
在/so-vits-svc/dataset_raw下创建新文件夹,并把先前得到的音频放入文件夹中;这个文件夹的名字将被默认为说话人的名字。如果使用线上服务器的话还需要打包上传、网盘转存等,按具体情况考虑。
然后运行resample.py,会自动重采样音频并保存到/so-vits-svc/dataset中。理论上这一步后就可以删除/so-vits-svc/dataset_raw下的文件了。
运行preprocess_flist_config.py,会自动划分数据集并生成配置文件。在/so-vits-svc/configs中会生成一个config.json,注意调整batch_size和learning_rate(根据显存调整batch_size,一定要比显存上限小,再等比例调整learning_rate),还可以设置训练次数上限epochs(意义不大,大多数时候你都会中途打断训练)。
运行preprocess_hubert_f0.py,生成hubert与f0文件,这需要开始占用显存并花上一些时间。爆显存的话只好重新剪切出错的那个音频并把预处理全部重来一遍。
5.训练
在terminal中运行python train.py -c configs/config.json -m 44k
(最后这个某某k根据你的sovits决定),并进入漫长的等待。每过1000步会保存一对模型到/so-vits-svc/logs/某某k,底模D_0.pth和G_0.pth也在这个文件夹里;如果没有自动清除的话可以在训练过程中手动删掉一些模型。训练结束(或被打断)后数字最大的模型就是最后的结果(如D_40000.pth和G_40000.pth)。爆显存的话调整config.json并重新运行preprocess_hubert_f0.py再重新训练。
这一步需要漫长的等待,不过好在不需要你自己劳作了。
6.处理推理的目标音频
找一份你希望推理的目标音频。sovits训练时只有人声,推理时自然也只能有人声,所以想合成歌曲就需要先单独分离出人声。这里up使用的是Ultimate Vocal Remover (https://github.com/Anjok07/ultimatevocalremovergui)。分离之后伴奏文件也要保留下来,因为后面重新合成为歌曲时要用。另外注意格式应为wav。
有时你可能觉得分离出来的Vocal仍不够干净?那么……对Vocal文件再做一次分离会好一些(这次只保留Vocal即可)。
为了避免在推理时爆显存,这份音频也需要合理剪切,不过不需要过于细,一分钟之内即可;由于是人声的推理,尽量在无人声处分割。
不可以再使用Audio Slicer,而应该用音频处理软件手动分割(Au肯定是最好的选择,这里up用了很低级的软件);这是过程中第2个工作量大的地方。
7.推理
把推理的目标音频放到/so-vits-svc/raw中。在terminal中运行python inference_main.py -m "logs/某某k/模型名" -c "configs/config.json" -n "目标音频名" -t 0 -s "说话人名"
(具体看你的文档或readme,模型名应是G开头的那个)。稍微等一会儿,这比训练快得多。然后逐个调整目标音频名来推理所有音频。推理完后结果出现在/so-vits-svc/results中。如果爆显存了,就重新剪切出错的音频,再来一次。
8.收尾
这样你就得到了具有你所期待的音色的人声了。可以用音频处理软件把这些截断的成果再合并回一首完整的人声;再和伴奏混合到一起,就得到了完整的歌曲。
之后你可以找来视频素材、歌词等做成一份视频,也可以就留着一份音频,这自然由你自己决定。
如果对成果不满意:1.步数较少时,可以继续训练,看看能否得到更好的结果;2.步数很多时,可能有过拟合,看看较早的模型怎么样。如果实在不好,考虑一下重新准备数据集吧。
(完)
PS. up在几个月前还尝试用Vocaloid绁星灯(声源也是米泽圆)调制歌曲,在没有基础又不努力的情况下调出来的声音不堪入耳。而sovits仅仅输入人声的音频就可以以很高的质量产出结果,对比之下绁星灯不如AI雪菜一根。想到Vocaloid这种计算机合成歌声的技术在不久的过去还科幻感十足,这实在是让人不由得感叹AI技术的强大和科技进步的迅捷。