diff --git a/gui/guimain.py b/gui/guimain.py
index c0b27cc..cc1d785 100644
--- a/gui/guimain.py
+++ b/gui/guimain.py
@@ -419,7 +419,9 @@ def get_widget_all_items(wid: QListWidget):
widget: QListWidget = getattr(self.ui, f"listWidget_mx_{i}")
args0 += [int(i.text()) for i in get_widget_all_items(widget)]
ex = self.get_live_extractor()
- save_names = ex.mix_live_song_all_sing(music_id, list(set(args0)), float(self.ui.lineEdit_chara_vol.text()))
+ chara_vol_str = self.ui.lineEdit_chara_vol.text().strip()
+ chara_vol_str = chara_vol_str or "-2"
+ save_names = ex.mix_live_song_all_sing(music_id, list(set(args0)), float(chara_vol_str))
voiceex.log.logger(f"Extract success: {save_names}")
else:
args = []
@@ -427,7 +429,9 @@ def get_widget_all_items(wid: QListWidget):
widget: QListWidget = getattr(self.ui, f"listWidget_mx_{i}")
args.append([int(i.text()) for i in get_widget_all_items(widget)])
ex = self.get_live_extractor()
- save_names = ex.mix_live_song_by_parts(music_id, *args, volume=float(self.ui.lineEdit_chara_vol.text()))
+ chara_vol_str = self.ui.lineEdit_chara_vol.text().strip()
+ chara_vol_str = chara_vol_str or "-2"
+ save_names = ex.mix_live_song_by_parts(music_id, *args, volume=float(chara_vol_str))
voiceex.log.logger(f"Extract success: {save_names}")
finally:
self.set_start_btn_stat_signal.emit(True)
diff --git a/gui/qtui/main_ui.py b/gui/qtui/main_ui.py
index c447621..978fb71 100644
--- a/gui/qtui/main_ui.py
+++ b/gui/qtui/main_ui.py
@@ -471,6 +471,7 @@ def setupUi(self, MainWindow):
self.label_15.setObjectName("label_15")
self.gridLayout_5.addWidget(self.label_15, 1, 0, 1, 1)
self.lineEdit_chara_vol = QtWidgets.QLineEdit(self.groupBox_9)
+ self.lineEdit_chara_vol.setInputMask("")
self.lineEdit_chara_vol.setObjectName("lineEdit_chara_vol")
self.gridLayout_5.addWidget(self.lineEdit_chara_vol, 1, 1, 1, 1)
self.pushButton_start_mix = QtWidgets.QPushButton(self.groupBox_9)
@@ -530,7 +531,7 @@ def setupUi(self, MainWindow):
self.tabWidget.setCurrentIndex(0)
self.tabWidget_4.setCurrentIndex(0)
self.tabWidget_music_type.setCurrentIndex(0)
- self.tabWidget_2.setCurrentIndex(0)
+ self.tabWidget_2.setCurrentIndex(1)
self.tabWidget_parts.setCurrentIndex(0)
QtCore.QMetaObject.connectSlotsByName(MainWindow)
@@ -607,7 +608,9 @@ def retranslateUi(self, MainWindow):
self.pushButton_me_clear.setText(_translate("MainWindow", "Clear"))
self.groupBox_9.setTitle(_translate("MainWindow", "Mix Config"))
self.label_15.setText(_translate("MainWindow", "Character Volume"))
- self.lineEdit_chara_vol.setText(_translate("MainWindow", "0.85"))
+ self.lineEdit_chara_vol.setToolTip(_translate("MainWindow", "Leave blank to automatically balance the loudness. -1 will not change volume. 1.0 is the full volume."))
+ self.lineEdit_chara_vol.setText(_translate("MainWindow", "-1"))
+ self.lineEdit_chara_vol.setPlaceholderText(_translate("MainWindow", "Leave blank to automatically balance the loudness. -1 will not change volume. 1.0 is the full volume."))
self.pushButton_start_mix.setText(_translate("MainWindow", "Start Mix"))
self.checkBox_all_singing.setText(_translate("MainWindow", "Force All Singing"))
self.tabWidget_2.setTabText(self.tabWidget_2.indexOf(self.tab_4), _translate("MainWindow", "Mixer"))
diff --git a/gui/qtui/main_ui.qm b/gui/qtui/main_ui.qm
index bbd96b6..b16c0cb 100644
Binary files a/gui/qtui/main_ui.qm and b/gui/qtui/main_ui.qm differ
diff --git a/gui/qtui/main_ui.ts b/gui/qtui/main_ui.ts
index d78088c..b25d3d2 100644
--- a/gui/qtui/main_ui.ts
+++ b/gui/qtui/main_ui.ts
@@ -4,257 +4,257 @@
MainWindow
-
+
-
+
角色列表
-
+
配置
-
+
-
+
选择
-
+
保存路径
-
+
代理设置
-
+
-
+
使用代理
-
+
Wave参数
-
+
-
+
-
+
-
+
-
+
-
+
-
+
从所有故事中提取对应角色的语音
-
+
下载缺失的语音文件
-
+
使用缓存
-
+
角色ID
-
+
开始提取
-
+
单角色提取模式
-
+
角色ID
-
+
保存ID
-
+
移除选择
-
+
多角色提取模式
-
+
角色语音提取
-
+
音乐列表
-
+
歌唱角色
-
+
下载缺失的文件
-
+
音乐ID
-
+
角色ID
-
+
提取BGM
-
+
提取角色清唱
-
+
提取角色清唱并根据歌词分割
-
+
删除音频首尾空白
-
+
提取器
-
+
位置设定
-
+
歌唱角色位置数:
-
+
-
+
-
+
-
+
-
+
-
+
-
+
-
+
清除
-
+
音频混合设置
-
+
强制全部歌唱
-
+
开始混合
-
+
混合器
@@ -264,52 +264,47 @@
Live 音乐提取
-
+
角色音量
-
-
-
-
-
-
+
Live 音乐
-
+
点唱机音乐
-
+
-
+
音乐提取
-
+
提取音量
-
+
-
+
关于
-
+
-
+
更多设置
-
+
全局设置
+
+
+
+ 留空自动平衡响度。-1不改变音量。满音量为 1.0。
+
diff --git a/gui/qtui/main_ui.ui b/gui/qtui/main_ui.ui
index 3deafb5..47dbc64 100644
--- a/gui/qtui/main_ui.ui
+++ b/gui/qtui/main_ui.ui
@@ -542,7 +542,7 @@
-
- 0
+ 1
@@ -932,8 +932,17 @@
-
+
+ Leave blank to automatically balance the loudness. -1 will not change volume. 1.0 is the full volume.
+
+
+
+
- 0.85
+ -1
+
+
+ Leave blank to automatically balance the loudness. -1 will not change volume. 1.0 is the full volume.
diff --git a/gui/qtui/msrc_rc.py b/gui/qtui/msrc_rc.py
index 16a4a96..4ed52cd 100644
--- a/gui/qtui/msrc_rc.py
+++ b/gui/qtui/msrc_rc.py
@@ -9,98 +9,110 @@
from PyQt5 import QtCore
qt_resource_data = b"\
-\x00\x00\x0a\x99\
+\x00\x00\x0b\x59\
\x3c\
\xb8\x64\x18\xca\xef\x9c\x95\xcd\x21\x1c\xbf\x60\xa1\xbd\xdd\xa7\
-\x00\x00\x00\x05\x7a\x68\x5f\x43\x4e\x42\x00\x00\x01\x58\x00\x47\
+\x00\x00\x00\x05\x7a\x68\x5f\x43\x4e\x42\x00\x00\x01\x60\x00\x47\
\x96\xc4\x00\x00\x00\x00\x00\x4a\x2b\x82\x00\x00\x01\x24\x00\x54\
-\x0e\xc2\x00\x00\x04\x9d\x00\x57\x96\xf9\x00\x00\x06\x06\x00\x5a\
-\xa8\x94\x00\x00\x07\xc8\x00\xe1\xab\xc3\x00\x00\x03\x70\x02\x72\
-\xb3\x52\x00\x00\x05\x3c\x02\xcd\x6e\x94\x00\x00\x00\xb8\x03\x6f\
-\x96\x03\x00\x00\x05\xd2\x03\xbc\xe8\x94\x00\x00\x02\x8c\x04\x10\
-\xbc\xc2\x00\x00\x08\x84\x04\x29\x20\xf4\x00\x00\x06\x69\x04\x78\
-\x7a\x47\x00\x00\x06\x32\x04\xa1\x0c\x57\x00\x00\x04\x68\x04\xa6\
-\x4c\xf7\x00\x00\x01\x4c\x04\xab\x1f\xf4\x00\x00\x08\xbe\x05\x98\
-\xc9\xd4\x00\x00\x06\xdb\x05\xb3\x9d\x2a\x00\x00\x07\x45\x06\x2f\
-\x71\x95\x00\x00\x07\x86\x07\x51\xf9\x33\x00\x00\x04\x31\x07\x57\
-\xea\x69\x00\x00\x08\x24\x07\x69\x25\x75\x00\x00\x08\x54\x07\x9c\
-\x2b\xa4\x00\x00\x08\xf4\x07\xea\xbd\x3d\x00\x00\x02\x05\x08\x96\
-\x2a\xa8\x00\x00\x07\xf4\x08\xd2\x91\x23\x00\x00\x04\xc7\x09\x24\
-\xdd\x83\x00\x00\x01\xb8\x09\xe8\x85\x94\x00\x00\x00\x57\x0a\x5b\
-\x21\x73\x00\x00\x02\x39\x0a\xb1\xcb\x57\x00\x00\x03\xc7\x0b\x87\
-\xe7\x92\x00\x00\x03\x06\x0b\x95\x70\xc3\x00\x00\x03\xfb\x0c\x77\
-\x31\x28\x00\x00\x06\xab\x0c\x9f\x51\x94\x00\x00\x05\x72\x0c\xce\
-\x7e\xd4\x00\x00\x07\x08\x0d\xcc\x0a\xf5\x00\x00\x00\xed\x0d\xcc\
-\x60\xe5\x00\x00\x02\xcf\x0e\x32\xcc\xa4\x00\x00\x00\x85\x0e\x57\
-\xa2\x13\x00\x00\x01\x75\x0e\x88\x30\x44\x00\x00\x00\x28\x0e\xf8\
-\x0e\xd5\x00\x00\x04\xfb\x0f\x0f\x9a\x87\x00\x00\x03\x34\x0f\x52\
-\x7c\x34\x00\x00\x05\xa1\x69\x00\x00\x09\x1d\x03\x00\x00\x00\x04\
-\x51\x73\x4e\x8e\x08\x00\x00\x00\x00\x06\x00\x00\x00\x05\x41\x62\
-\x6f\x75\x74\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\
-\x6f\x77\x01\x03\x00\x00\x00\x08\x89\xd2\x82\x72\x00\x49\x00\x44\
-\x08\x00\x00\x00\x00\x06\x00\x00\x00\x08\x43\x68\x61\x72\x61\x20\
-\x49\x44\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\
-\x77\x01\x03\x00\x00\x00\x08\x89\xd2\x82\x72\x00\x49\x00\x44\x08\
-\x00\x00\x00\x00\x06\x00\x00\x00\x07\x43\x68\x61\x72\x61\x49\x44\
-\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\
-\x03\x00\x00\x00\x08\x89\xd2\x82\x72\x00\x49\x00\x44\x08\x00\x00\
-\x00\x00\x06\x00\x00\x00\x0c\x43\x68\x61\x72\x61\x63\x74\x65\x72\
-\x20\x49\x44\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\
-\x6f\x77\x01\x03\x00\x00\x00\x08\x89\xd2\x82\x72\x52\x17\x88\x68\
-\x08\x00\x00\x00\x00\x06\x00\x00\x00\x0e\x43\x68\x61\x72\x61\x63\
-\x74\x65\x72\x20\x4c\x69\x73\x74\x07\x00\x00\x00\x0a\x4d\x61\x69\
+\x0e\xc2\x00\x00\x05\x55\x00\x57\x96\xf9\x00\x00\x06\xbe\x00\x5a\
+\xa8\x94\x00\x00\x08\x80\x00\xe1\xab\xc3\x00\x00\x03\x70\x02\x72\
+\xb3\x52\x00\x00\x05\xf4\x02\xcd\x6e\x94\x00\x00\x00\xb8\x03\x6f\
+\x96\x03\x00\x00\x06\x8a\x03\xbc\xe8\x94\x00\x00\x02\x8c\x04\x10\
+\xbc\xc2\x00\x00\x09\x3c\x04\x29\x20\xf4\x00\x00\x07\x21\x04\x78\
+\x7a\x47\x00\x00\x06\xea\x04\xa1\x0c\x57\x00\x00\x05\x20\x04\xa6\
+\x4c\xf7\x00\x00\x01\x4c\x04\xab\x1f\xf4\x00\x00\x09\x76\x05\x98\
+\xc9\xd4\x00\x00\x07\x93\x05\xb3\x9d\x2a\x00\x00\x07\xfd\x06\x2f\
+\x71\x95\x00\x00\x08\x3e\x07\x51\xf9\x33\x00\x00\x04\xe9\x07\x57\
+\xea\x69\x00\x00\x08\xdc\x07\x69\x25\x75\x00\x00\x09\x0c\x07\x9c\
+\x2b\xa4\x00\x00\x09\xac\x07\xea\xbd\x3d\x00\x00\x02\x05\x07\xf3\
+\xb2\x2e\x00\x00\x04\x31\x08\x96\x2a\xa8\x00\x00\x08\xac\x08\xd2\
+\x91\x23\x00\x00\x05\x7f\x09\x24\xdd\x83\x00\x00\x01\xb8\x09\xe8\
+\x85\x94\x00\x00\x00\x57\x0a\x5b\x21\x73\x00\x00\x02\x39\x0a\xb1\
+\xcb\x57\x00\x00\x03\xc7\x0b\x87\xe7\x92\x00\x00\x03\x06\x0b\x95\
+\x70\xc3\x00\x00\x03\xfb\x0c\x77\x31\x28\x00\x00\x07\x63\x0c\x9f\
+\x51\x94\x00\x00\x06\x2a\x0c\xce\x7e\xd4\x00\x00\x07\xc0\x0d\xcc\
+\x0a\xf5\x00\x00\x00\xed\x0d\xcc\x60\xe5\x00\x00\x02\xcf\x0e\x32\
+\xcc\xa4\x00\x00\x00\x85\x0e\x57\xa2\x13\x00\x00\x01\x75\x0e\x88\
+\x30\x44\x00\x00\x00\x28\x0e\xf8\x0e\xd5\x00\x00\x05\xb3\x0f\x0f\
+\x9a\x87\x00\x00\x03\x34\x0f\x52\x7c\x34\x00\x00\x06\x59\x69\x00\
+\x00\x09\xd5\x03\x00\x00\x00\x04\x51\x73\x4e\x8e\x08\x00\x00\x00\
+\x00\x06\x00\x00\x00\x05\x41\x62\x6f\x75\x74\x07\x00\x00\x00\x0a\
+\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x08\
+\x89\xd2\x82\x72\x00\x49\x00\x44\x08\x00\x00\x00\x00\x06\x00\x00\
+\x00\x08\x43\x68\x61\x72\x61\x20\x49\x44\x07\x00\x00\x00\x0a\x4d\
+\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x08\x89\
+\xd2\x82\x72\x00\x49\x00\x44\x08\x00\x00\x00\x00\x06\x00\x00\x00\
+\x07\x43\x68\x61\x72\x61\x49\x44\x07\x00\x00\x00\x0a\x4d\x61\x69\
\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x08\x89\xd2\x82\
-\x72\x97\xf3\x91\xcf\x08\x00\x00\x00\x00\x06\x00\x00\x00\x10\x43\
-\x68\x61\x72\x61\x63\x74\x65\x72\x20\x56\x6f\x6c\x75\x6d\x65\x07\
-\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\
-\x00\x00\x00\x04\x6e\x05\x96\x64\x08\x00\x00\x00\x00\x06\x00\x00\
-\x00\x05\x43\x6c\x65\x61\x72\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\
-\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x04\x91\x4d\x7f\x6e\
-\x08\x00\x00\x00\x00\x06\x00\x00\x00\x06\x43\x6f\x6e\x66\x69\x67\
-\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\
-\x03\x00\x00\x00\x0e\x4e\x0b\x8f\x7d\x7f\x3a\x59\x31\x76\x84\x65\
-\x87\x4e\xf6\x08\x00\x00\x00\x00\x06\x00\x00\x00\x16\x44\x6f\x77\
-\x6e\x6c\x6f\x61\x64\x20\x6d\x69\x73\x73\x69\x6e\x67\x20\x66\x69\
-\x6c\x65\x73\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\
-\x6f\x77\x01\x03\x00\x00\x00\x12\x4e\x0b\x8f\x7d\x7f\x3a\x59\x31\
-\x76\x84\x8b\xed\x97\xf3\x65\x87\x4e\xf6\x08\x00\x00\x00\x00\x06\
-\x00\x00\x00\x1c\x44\x6f\x77\x6e\x6c\x6f\x61\x64\x20\x6d\x69\x73\
-\x73\x69\x6e\x67\x20\x76\x6f\x69\x63\x65\x20\x66\x69\x6c\x65\x73\
+\x72\x00\x49\x00\x44\x08\x00\x00\x00\x00\x06\x00\x00\x00\x0c\x43\
+\x68\x61\x72\x61\x63\x74\x65\x72\x20\x49\x44\x07\x00\x00\x00\x0a\
+\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x08\
+\x89\xd2\x82\x72\x52\x17\x88\x68\x08\x00\x00\x00\x00\x06\x00\x00\
+\x00\x0e\x43\x68\x61\x72\x61\x63\x74\x65\x72\x20\x4c\x69\x73\x74\
\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\
-\x03\x00\x00\x00\x0a\x63\xd0\x53\xd6\x00\x42\x00\x47\x00\x4d\x08\
-\x00\x00\x00\x00\x06\x00\x00\x00\x0b\x45\x78\x74\x72\x61\x63\x74\
-\x20\x42\x47\x4d\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\
-\x64\x6f\x77\x01\x03\x00\x00\x00\x1a\x63\xd0\x53\xd6\x89\xd2\x82\
-\x72\x6e\x05\x55\x31\x5e\x76\x68\x39\x63\x6e\x6b\x4c\x8b\xcd\x52\
-\x06\x52\x72\x08\x00\x00\x00\x00\x06\x00\x00\x00\x1a\x45\x78\x74\
-\x72\x61\x63\x74\x20\x43\x68\x61\x72\x61\x20\x53\x6f\x75\x6e\x64\
-\x20\x42\x79\x20\x4c\x72\x63\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\
-\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x0c\x63\xd0\x53\xd6\
-\x89\xd2\x82\x72\x6e\x05\x55\x31\x08\x00\x00\x00\x00\x06\x00\x00\
-\x00\x18\x45\x78\x74\x72\x61\x63\x74\x20\x46\x75\x6c\x6c\x20\x43\
-\x68\x61\x72\x61\x20\x53\x6f\x75\x6e\x64\x07\x00\x00\x00\x0a\x4d\
-\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x08\x63\
-\xd0\x53\xd6\x97\xf3\x91\xcf\x08\x00\x00\x00\x00\x06\x00\x00\x00\
-\x10\x45\x78\x74\x72\x61\x63\x74\x65\x64\x20\x56\x6f\x6c\x75\x6d\
-\x65\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\
-\x01\x03\x00\x00\x00\x06\x63\xd0\x53\xd6\x56\x68\x08\x00\x00\x00\
-\x00\x06\x00\x00\x00\x09\x45\x78\x74\x72\x61\x63\x74\x6f\x72\x07\
+\x03\x00\x00\x00\x08\x89\xd2\x82\x72\x97\xf3\x91\xcf\x08\x00\x00\
+\x00\x00\x06\x00\x00\x00\x10\x43\x68\x61\x72\x61\x63\x74\x65\x72\
+\x20\x56\x6f\x6c\x75\x6d\x65\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\
+\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x04\x6e\x05\x96\x64\
+\x08\x00\x00\x00\x00\x06\x00\x00\x00\x05\x43\x6c\x65\x61\x72\x07\
+\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\
+\x00\x00\x00\x04\x91\x4d\x7f\x6e\x08\x00\x00\x00\x00\x06\x00\x00\
+\x00\x06\x43\x6f\x6e\x66\x69\x67\x07\x00\x00\x00\x0a\x4d\x61\x69\
+\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x0e\x4e\x0b\x8f\
+\x7d\x7f\x3a\x59\x31\x76\x84\x65\x87\x4e\xf6\x08\x00\x00\x00\x00\
+\x06\x00\x00\x00\x16\x44\x6f\x77\x6e\x6c\x6f\x61\x64\x20\x6d\x69\
+\x73\x73\x69\x6e\x67\x20\x66\x69\x6c\x65\x73\x07\x00\x00\x00\x0a\
+\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x12\
+\x4e\x0b\x8f\x7d\x7f\x3a\x59\x31\x76\x84\x8b\xed\x97\xf3\x65\x87\
+\x4e\xf6\x08\x00\x00\x00\x00\x06\x00\x00\x00\x1c\x44\x6f\x77\x6e\
+\x6c\x6f\x61\x64\x20\x6d\x69\x73\x73\x69\x6e\x67\x20\x76\x6f\x69\
+\x63\x65\x20\x66\x69\x6c\x65\x73\x07\x00\x00\x00\x0a\x4d\x61\x69\
+\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x0a\x63\xd0\x53\
+\xd6\x00\x42\x00\x47\x00\x4d\x08\x00\x00\x00\x00\x06\x00\x00\x00\
+\x0b\x45\x78\x74\x72\x61\x63\x74\x20\x42\x47\x4d\x07\x00\x00\x00\
+\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\
+\x1a\x63\xd0\x53\xd6\x89\xd2\x82\x72\x6e\x05\x55\x31\x5e\x76\x68\
+\x39\x63\x6e\x6b\x4c\x8b\xcd\x52\x06\x52\x72\x08\x00\x00\x00\x00\
+\x06\x00\x00\x00\x1a\x45\x78\x74\x72\x61\x63\x74\x20\x43\x68\x61\
+\x72\x61\x20\x53\x6f\x75\x6e\x64\x20\x42\x79\x20\x4c\x72\x63\x07\
\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\
-\x00\x00\x00\x0c\x5f\x3a\x52\x36\x51\x68\x90\xe8\x6b\x4c\x55\x31\
-\x08\x00\x00\x00\x00\x06\x00\x00\x00\x11\x46\x6f\x72\x63\x65\x20\
-\x41\x6c\x6c\x20\x53\x69\x6e\x67\x69\x6e\x67\x07\x00\x00\x00\x0a\
-\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x1e\
-\x4e\xce\x62\x40\x67\x09\x65\x45\x4e\x8b\x4e\x2d\x63\xd0\x53\xd6\
-\x5b\xf9\x5e\x94\x89\xd2\x82\x72\x76\x84\x8b\xed\x97\xf3\x08\x00\
-\x00\x00\x00\x06\x00\x00\x00\x1a\x47\x65\x74\x20\x76\x6f\x69\x63\
-\x65\x20\x66\x72\x6f\x6d\x20\x61\x6c\x6c\x20\x73\x74\x6f\x72\x69\
-\x65\x73\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\
-\x77\x01\x03\x00\x00\x00\x08\x51\x68\x5c\x40\x8b\xbe\x7f\x6e\x08\
-\x00\x00\x00\x00\x06\x00\x00\x00\x0d\x47\x6c\x6f\x62\x61\x6c\x20\
-\x43\x6f\x6e\x66\x69\x67\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\
-\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x0a\x70\xb9\x55\x31\x67\
-\x3a\x97\xf3\x4e\x50\x08\x00\x00\x00\x00\x06\x00\x00\x00\x0d\x4a\
-\x75\x6b\x65\x62\x6f\x78\x20\x4d\x75\x73\x69\x63\x07\x00\x00\x00\
+\x00\x00\x00\x0c\x63\xd0\x53\xd6\x89\xd2\x82\x72\x6e\x05\x55\x31\
+\x08\x00\x00\x00\x00\x06\x00\x00\x00\x18\x45\x78\x74\x72\x61\x63\
+\x74\x20\x46\x75\x6c\x6c\x20\x43\x68\x61\x72\x61\x20\x53\x6f\x75\
+\x6e\x64\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\
+\x77\x01\x03\x00\x00\x00\x08\x63\xd0\x53\xd6\x97\xf3\x91\xcf\x08\
+\x00\x00\x00\x00\x06\x00\x00\x00\x10\x45\x78\x74\x72\x61\x63\x74\
+\x65\x64\x20\x56\x6f\x6c\x75\x6d\x65\x07\x00\x00\x00\x0a\x4d\x61\
+\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x06\x63\xd0\
+\x53\xd6\x56\x68\x08\x00\x00\x00\x00\x06\x00\x00\x00\x09\x45\x78\
+\x74\x72\x61\x63\x74\x6f\x72\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\
+\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x0c\x5f\x3a\x52\x36\
+\x51\x68\x90\xe8\x6b\x4c\x55\x31\x08\x00\x00\x00\x00\x06\x00\x00\
+\x00\x11\x46\x6f\x72\x63\x65\x20\x41\x6c\x6c\x20\x53\x69\x6e\x67\
+\x69\x6e\x67\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\
+\x6f\x77\x01\x03\x00\x00\x00\x1e\x4e\xce\x62\x40\x67\x09\x65\x45\
+\x4e\x8b\x4e\x2d\x63\xd0\x53\xd6\x5b\xf9\x5e\x94\x89\xd2\x82\x72\
+\x76\x84\x8b\xed\x97\xf3\x08\x00\x00\x00\x00\x06\x00\x00\x00\x1a\
+\x47\x65\x74\x20\x76\x6f\x69\x63\x65\x20\x66\x72\x6f\x6d\x20\x61\
+\x6c\x6c\x20\x73\x74\x6f\x72\x69\x65\x73\x07\x00\x00\x00\x0a\x4d\
+\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\x08\x51\
+\x68\x5c\x40\x8b\xbe\x7f\x6e\x08\x00\x00\x00\x00\x06\x00\x00\x00\
+\x0d\x47\x6c\x6f\x62\x61\x6c\x20\x43\x6f\x6e\x66\x69\x67\x07\x00\
+\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\
+\x00\x00\x0a\x70\xb9\x55\x31\x67\x3a\x97\xf3\x4e\x50\x08\x00\x00\
+\x00\x00\x06\x00\x00\x00\x0d\x4a\x75\x6b\x65\x62\x6f\x78\x20\x4d\
+\x75\x73\x69\x63\x07\x00\x00\x00\x0a\x4d\x61\x69\x6e\x57\x69\x6e\
+\x64\x6f\x77\x01\x03\x00\x00\x00\x34\x75\x59\x7a\x7a\x81\xea\x52\
+\xa8\x5e\x73\x88\x61\x54\xcd\x5e\xa6\x30\x02\x00\x2d\x00\x31\x4e\
+\x0d\x65\x39\x53\xd8\x97\xf3\x91\xcf\x30\x02\x6e\xe1\x97\xf3\x91\
+\xcf\x4e\x3a\x00\x20\x00\x31\x00\x2e\x00\x30\x30\x02\x08\x00\x00\
+\x00\x00\x06\x00\x00\x00\x65\x4c\x65\x61\x76\x65\x20\x62\x6c\x61\
+\x6e\x6b\x20\x74\x6f\x20\x61\x75\x74\x6f\x6d\x61\x74\x69\x63\x61\
+\x6c\x6c\x79\x20\x62\x61\x6c\x61\x6e\x63\x65\x20\x74\x68\x65\x20\
+\x6c\x6f\x75\x64\x6e\x65\x73\x73\x2e\x20\x2d\x31\x20\x77\x69\x6c\
+\x6c\x20\x6e\x6f\x74\x20\x63\x68\x61\x6e\x67\x65\x20\x76\x6f\x6c\
+\x75\x6d\x65\x2e\x20\x31\x2e\x30\x20\x69\x73\x20\x74\x68\x65\x20\
+\x66\x75\x6c\x6c\x20\x76\x6f\x6c\x75\x6d\x65\x2e\x07\x00\x00\x00\
\x0a\x4d\x61\x69\x6e\x57\x69\x6e\x64\x6f\x77\x01\x03\x00\x00\x00\
\x0e\x00\x4c\x00\x69\x00\x76\x00\x65\x00\x20\x97\xf3\x4e\x50\x08\
\x00\x00\x00\x00\x06\x00\x00\x00\x0a\x4c\x69\x76\x65\x20\x4d\x75\
@@ -17110,7 +17122,7 @@
\x00\x00\x00\x00\x00\x02\x00\x00\x00\x01\x00\x00\x00\x04\
\x00\x00\x00\x0c\x00\x02\x00\x00\x00\x01\x00\x00\x00\x03\
\x00\x00\x00\x1c\x00\x00\x00\x00\x00\x01\x00\x00\x00\x00\
-\x00\x00\x00\x36\x00\x00\x00\x00\x00\x01\x00\x00\x0a\x9d\
+\x00\x00\x00\x36\x00\x00\x00\x00\x00\x01\x00\x00\x0b\x5d\
"
qt_resource_struct_v2 = b"\
@@ -17121,8 +17133,8 @@
\x00\x00\x00\x0c\x00\x02\x00\x00\x00\x01\x00\x00\x00\x03\
\x00\x00\x00\x00\x00\x00\x00\x00\
\x00\x00\x00\x1c\x00\x00\x00\x00\x00\x01\x00\x00\x00\x00\
-\x00\x00\x01\x8a\x22\x60\x83\x56\
-\x00\x00\x00\x36\x00\x00\x00\x00\x00\x01\x00\x00\x0a\x9d\
+\x00\x00\x01\x8a\x30\xc5\x08\xb5\
+\x00\x00\x00\x36\x00\x00\x00\x00\x00\x01\x00\x00\x0b\x5d\
\x00\x00\x01\x86\x12\x11\x04\xf2\
"
diff --git a/voiceex/live_music/live_music_ex.py b/voiceex/live_music/live_music_ex.py
index 5000d13..fcbb2e8 100644
--- a/voiceex/live_music/live_music_ex.py
+++ b/voiceex/live_music/live_music_ex.py
@@ -1,3 +1,4 @@
+import math
import os
import shutil
from .. import resource as umares
@@ -86,11 +87,13 @@ def extract_live_music_bgm(self, music_id, oke_index="01", raise_notfound_error=
acb_path = self.bundle_hash_to_path(acb_hash)
awb_path = self.bundle_hash_to_path(awb_hash)
exactor = self.get_extractor(awb_path, acb_path)
- if self.wav_format is not None:
- exactor.SetWaveFormat(*self.wav_format)
- ret = exactor.ExtractAudioFromWaveId(f"{self.save_path}/{'jukebox' if is_jukebox else 'music'}/{music_id}",
- f"bgm_{oke_index}_", 0)
- exactor.Close()
+ try:
+ if self.wav_format is not None:
+ exactor.SetWaveFormat(*self.wav_format)
+ ret = exactor.ExtractAudioFromWaveId(f"{self.save_path}/{'jukebox' if is_jukebox else 'music'}/{music_id}",
+ f"bgm_{oke_index}_", 0)
+ finally:
+ exactor.Close()
return ret
@staticmethod
@@ -193,22 +196,53 @@ def get_charas_singing_data(self, music_id, chara_list: t.Optional[t.List[int]],
def mix_live_song_all_sing(self, music_id: int, chara_list: t.Optional[t.List[int]], volume: float):
save_names = []
+
+ save_singing_file_names = self.get_charas_singing_data(music_id, chara_list)
+ temp_singing_name = f"temp/live/{music_id}/mix_all_no_bgm.wav"
+ save_singing_name = f"{self.save_path}/music/{music_id}/mix_all_no_bgm.wav"
+ file_list = []
+ for chara_id in save_singing_file_names:
+ for wave_id in save_singing_file_names[chara_id]:
+ file_list.append(save_singing_file_names[chara_id][wave_id])
+ self.mix_wavs(file_list, temp_singing_name, -1)
+ self.AdjustVolume(temp_singing_name,
+ [{"start": 0, "end": 600000, "db": -10 * math.log10(len(save_singing_file_names))}],
+ save_singing_name)
+ os.remove(temp_singing_name)
+
for oke in ["01", "02"]:
music_bgm = self.extract_live_music_bgm(music_id, oke_index=oke, raise_notfound_error=False)
if not music_bgm:
continue
- save_file_names = self.get_charas_singing_data(music_id, chara_list)
save_name = f"{self.save_path}/music/{music_id}/mix_all_oke_{oke}.wav"
- file_list = [music_bgm]
- for chara_id in save_file_names:
- for wave_id in save_file_names[chara_id]:
- file_list.append(save_file_names[chara_id][wave_id])
- self.mix_wavs(file_list, save_name, volume)
+ self.mix_wavs([music_bgm, save_singing_name], save_name, volume)
save_names.append(save_name)
return save_names
+ @staticmethod
+ def get_overlap_times(dictionary):
+ overlap_times = []
+ time_counts = {}
+
+ for file, times in dictionary.items():
+ for time in times:
+ start = time[0]
+ end = time[1]
+
+ # 更新时间段的文件数量
+ if (start, end) not in time_counts:
+ time_counts[(start, end)] = 1
+ else:
+ time_counts[(start, end)] += 1
+
+ # 遍历时间数量字典,找到重叠时间段并添加到重叠时间列表中
+ for time, count in time_counts.items():
+ if count >= 1:
+ overlap_times.append({"start": time[0], "end": time[1], "count": count})
+ return overlap_times
+
def mix_live_song_by_parts(self, music_id: int, *charas: t.List[int], volume: float):
- charas = charas[:7]
+ # charas = charas[:7]
save_file_names = [self.get_charas_singing_data(music_id, i) for i in charas]
singing_data = self.get_parts(music_id)
singing_data_keys = list(singing_data.keys())
@@ -236,12 +270,22 @@ def mix_live_song_by_parts(self, music_id: int, *charas: t.List[int], volume: fl
save_name_p = f"{file_name}_sl.wav"
target_files.append(save_name_p)
self.SilenceWavPartsByActivePos(file_name, save_name_p, ftimes)
+
+ silence_mixed_temp_name = f"temp/live/{music_id}/mix_by_parts_no_bgm.wav"
+ silence_mixed_save_name = f"{self.save_path}/music/{music_id}/mix_by_parts_no_bgm.wav"
+ self.mix_wavs(target_files, silence_mixed_temp_name, -1)
+ overlap_times = self.get_overlap_times(file_on_times)
+ for n, overlap in enumerate(overlap_times):
+ overlap_times[n]["db"] = -10 * math.log10(overlap["count"])
+ self.AdjustVolume(silence_mixed_temp_name, overlap_times, silence_mixed_save_name)
+ os.remove(silence_mixed_temp_name)
+
save_names = []
for oke in ["01", "02"]:
music_bgm = self.extract_live_music_bgm(music_id, oke_index=oke, raise_notfound_error=False)
if music_bgm:
save_name = f"{self.save_path}/music/{music_id}/mix_by_parts_oke_{oke}.wav"
- self.mix_wavs([music_bgm] + target_files, save_name, volume)
+ self.mix_wavs([music_bgm, silence_mixed_save_name], save_name, volume)
save_names.append(save_name)
for i in target_files:
os.remove(i)
diff --git a/voiceex/resource.py b/voiceex/resource.py
index 25a0054..8493fd8 100644
--- a/voiceex/resource.py
+++ b/voiceex/resource.py
@@ -15,7 +15,8 @@
# clr.FindAssembly("voice_extractor.dll")
clr.AddReference("./voice extractor/voice extractor/bin/Release/net6.0/voice extractor")
from System.Collections.Generic import List as CsList
-from System import UInt64, String
+from System.Collections.Generic import Dictionary as CsDict
+from System import UInt64, String, Object
from System.IO import InvalidDataException
import voice_extractor
@@ -82,6 +83,13 @@ def cut_wav_batch(file_name: str, save_name_prefix: str, time_ms_list: List[List
@staticmethod
def mix_wavs(files: List[str], save_name: str, volume: float):
+ """
+ mix wav files
+ :param files: file list
+ :param save_name: save name
+ :param volume: volume, 1.0 is full. -1: dont' change volume. -2: automatic balance of loudness
+ :return: None
+ """
lst_param = CsList[String]()
for i in files:
lst_param.Add(i)
@@ -106,3 +114,13 @@ def SilenceWavPartsByActivePos(file_name: str, save_name: str, active_ms: List[L
add_p.Add(j)
lst_param.Add(add_p)
voice_extractor.UmaVoiceEx.SilenceWavPartsByActivePos(file_name, save_name, lst_param)
+
+ @staticmethod
+ def AdjustVolume(file_name: str, volume_changes: List[dict], output_path):
+ lst_param = CsList[CsDict[String, Object]]()
+ for i in volume_changes:
+ add_p = CsDict[String, Object]()
+ for k in i:
+ add_p.Add(k, i[k])
+ lst_param.Add(add_p)
+ return voice_extractor.UmaVoiceEx.AdjustVolume(file_name, lst_param, output_path)