From ab61b46d78bd48ebab0487c7e8ca5b61fb1144bc Mon Sep 17 00:00:00 2001 From: Tseng Woody Date: Wed, 3 Feb 2021 09:08:49 +0800 Subject: [PATCH] WorldVoice v1.6 --- addon/doc/zh_CN/readme.md | 16 +++- addon/doc/zh_HK/readme.md | 16 +++- addon/doc/zh_TW/readme.md | 16 +++- .../globalPlugins/WorldVoiceXVED2/__init__.py | 4 +- addon/locale/zh_CN/LC_MESSAGES/nvda.po | 81 ++++++++++------- addon/locale/zh_HK/LC_MESSAGES/nvda.po | 77 +++++++++------- addon/locale/zh_TW/LC_MESSAGES/nvda.po | 77 +++++++++------- .../synthDrivers/WorldVoiceXVED2/__init__.py | 91 +++++++++---------- .../WorldVoiceXVED2/_vocalizer.py | 6 +- .../languageDetection/__init__.py | 12 +-- .../WorldVoiceXVED2/speechcommand.py | 23 +++++ buildVars.py | 2 +- readme.md | 16 +++- 13 files changed, 267 insertions(+), 170 deletions(-) create mode 100644 addon/synthDrivers/WorldVoiceXVED2/speechcommand.py diff --git a/addon/doc/zh_CN/readme.md b/addon/doc/zh_CN/readme.md index 80bb396..f739e29 100644 --- a/addon/doc/zh_CN/readme.md +++ b/addon/doc/zh_CN/readme.md @@ -1,6 +1,6 @@ # WorldVoice -WorldVoice 是依据 VE driver 为基础开发而成的 addon。运行于 NVDA 2019.3 以上。 +WorldVoice 是依据 VE driver 为基础开发而成的 addon。运行于 NVDA 2019.3 以上版本。 主要包括有多国语音自动切换、各别语音速度设定、朗读行为客制(数字读法、中文空格间隔)、自定义文字地区等功能。 @@ -11,7 +11,7 @@ WorldVoice 是依据 VE driver 为基础开发而成的 addon。运行于 NVDA 2 * 核心包可透过 WorldVoice -> 档案汇入将 zip 压缩包汇入语音组件工作区。 * 语音包安装方式 * 基本:使用兼容于 Vocalizer for NVDA 的语音包addon,[官方下载点](https://vocalizer-nvda.com/downloads)。 - * 进阶:可透过各种语音包内直接复制其内的地区文件夹(ex: en, mnc, mnt)等并将其压成 zip 压缩包后透过 WorldVoice 接口的档案汇入功能汇入addon内,与核心包相同需留意汇入之工作区,如无特殊需求建议使用 addon 版本安装,因 addon 版本可共享同时提供第 1 驱动与第 2 驱动使用。 + * 进阶:可透过各种语音包内直接复制其内的地区文件夹(ex: en, mnc, mnt)等并将其压成 zip 压缩包后透过 WorldVoice 接口的档案汇入功能汇入 addon 内,如无特殊需求建议使用 addon 版本安装,因当 WorldVoice 升级版本时 addon 版本语音包不会被删除亦无需重新安装。 ## 相依性套件 @@ -22,7 +22,9 @@ WorldVoice 是依据 VE driver 为基础开发而成的 addon。运行于 NVDA 2 * NVDA+ctrl+S 选择 WorldVoice 语音合成器。 * NVDA+ctrl+V 有基本语音速度、音调、音量等基本设定,其中数字模式、中文空白间隔为 WorldVoice 多的客制设定。 * 数字读法:分为 2 个维度设定选项「数字语言」与「数字模式」,数字语言设定数字朗读时使用的地区语音、数字模式分为数值与数字两种 - * 中文空白间隔:可设定中文间有空白时,欲停顿长度,数字愈小停顿愈短, 0 为不停顿。 + * 「当遇到中文与中文间的空白时暂停长度」:可设定中文间有空白时,欲停顿长度,数字愈小停顿愈短, 0 为不停顿。 + * 「忽略在数字间的逗号」选项勾选时,可让数字位数的逗号标错位置仍能正常朗读数值。 + * 「启用 WorldVoice 设定规则来侦测文字语言」勾选时,会使用语音设定内的规则来侦测文字语言并切换语音朗读。 * WorldVoice -> 语音设定:可设定不同地区所使用的语音角色、各别语音角色速度、音调、音量、自动语音切换设定。 * 先选择地区后语音列表会列出该地区可用的语音角色,选择后即完成该地区与语音角色的对应纪录。 * 当语音角色有选择时,下方速度、音调、音量滑杆会变为该语音角色的设定值。 @@ -80,3 +82,11 @@ WorldVoice 是依据 VE driver 为基础开发而成的 addon。运行于 NVDA 2 * 将自动语言切换设定与语音设定窗口合并 * 地区与语音对应加入 no-select 用来取消对应 * 支持快捷键弹出语音设定与 Unicode 设定 + +### v1.6 + +* 修正数字模式下小数点不朗读问题 +* 更新 VE 核心包工作目录,未来更新时可无需重新汇入 +* 将「使用 WorldVoice 设定规则针测语言」的开关与「自动切换语言」的开关分开,避免部份情境两者不兼容问题。 +* 修正启用 unicode 自动语言针测时,默认语音与 NVDA 语言地区不相同但同语系时无法切换的问题 +* 修正自动切换语言无勾选时 WorldVoice 变更语音语言命令被滤掉的问题 diff --git a/addon/doc/zh_HK/readme.md b/addon/doc/zh_HK/readme.md index 2dca7a9..7307de1 100644 --- a/addon/doc/zh_HK/readme.md +++ b/addon/doc/zh_HK/readme.md @@ -1,6 +1,6 @@ # WorldVoice -WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2019.3 以上。 +WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2019.3 以上版本。 主要包括有多國語音自動切換、各別語音速度設定、朗讀行為客製(數字讀法、中文空格間隔)、自訂文字地區等功能。 @@ -11,7 +11,7 @@ WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2 * 核心包可透過 WorldVoice -> 檔案匯入將 zip 壓縮包匯入語音元件工作區。 * 語音包安裝方式 * 基本:使用兼容於 Vocalizer for NVDA 的語音包addon,[官方下載點](https://vocalizer-nvda.com/downloads)。 - * 進階:可透過各種語音包內直接複製其內的地區資料夾(ex: en, mnc, mnt)等並將其壓成 zip 壓縮包後透過 WorldVoice 介面的檔案匯入功能匯入addon內,與核心包相同需留意匯入之工作區,如無特殊需求建議使用 addon 版本安裝,因 addon 版本可共享同時提供第 1 驅動與第 2 驅動使用。 + * 進階:可透過各種語音包內直接複製其內的地區資料夾(ex: en, mnc, mnt)等並將其壓成 zip 壓縮包後透過 WorldVoice 介面的檔案匯入功能匯入 addon 內,如無特殊需求建議使用 addon 版本安裝,因當 WorldVoice 升級版本時 addon 版本語音包不會被刪除亦無需重新安裝。 ## 相依性套件 @@ -22,7 +22,9 @@ WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2 * NVDA+ctrl+S 選擇 WorldVoice 語音合成器。 * NVDA+ctrl+V 有基本語音速度、音調、音量等基本設定,其中數字模式、中文空白間隔為 WorldVoice 多的客製設定。 * 數字讀法:分為 2 個維度設定選項「數字語言」與「數字模式」,數字語言設定數字朗讀時使用的地區語音、數字模式分為數值與數字兩種 - * 中文空白間隔:可設定中文間有空白時,欲停頓長度,數字愈小停頓愈短, 0 為不停頓。 + * 「當遇到中文與中文間的空白時暫停長度」:可設定中文間有空白時,欲停頓長度,數字愈小停頓愈短, 0 為不停頓。 + * 「忽略在數字間的逗號」選項勾選時,可讓數字位數的逗號標錯位置仍能正常朗讀數值。 + * 「啟用 WorldVoice 設定規則來偵測文字語言」勾選時,會使用語音設定內的規則來偵測文字語言並切換語音朗讀。 * WorldVoice -> 語音設定:可設定不同地區所使用的語音角色、各別語音角色速度、音調、音量、自動語音切換設定。 * 先選擇地區後語音列表會列出該地區可用的語音角色,選擇後即完成該地區與語音角色的對應紀錄。 * 當語音角色有選擇時,下方速度、音調、音量滑桿會變為該語音角色的設定值。 @@ -80,3 +82,11 @@ WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2 * 將自動語言切換設定與語音設定視窗合併 * 地區與語音對應加入 no-select 用來取消對應 * 支援快速鍵彈出語音設定與 Unicode 設定 + +### v1.6 + +* 修正數字模式下小數點不朗讀問題 +* 更新 VE 核心包工作目錄,未來更新時可無需重新匯入 +* 將「使用 WorldVoice 設定規則針測語言」的開關與「自動切換語言」的開關分開,避免部份情境兩者不相容問題。 +* 修正啟用 unicode 自動語言針測時,預設語音與 NVDA 語言地區不相同但同語系時無法切換的問題 +* 修正自動切換語言無勾選時 WorldVoice 變更語音語言命令被濾掉的問題 diff --git a/addon/doc/zh_TW/readme.md b/addon/doc/zh_TW/readme.md index 2dca7a9..7307de1 100644 --- a/addon/doc/zh_TW/readme.md +++ b/addon/doc/zh_TW/readme.md @@ -1,6 +1,6 @@ # WorldVoice -WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2019.3 以上。 +WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2019.3 以上版本。 主要包括有多國語音自動切換、各別語音速度設定、朗讀行為客製(數字讀法、中文空格間隔)、自訂文字地區等功能。 @@ -11,7 +11,7 @@ WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2 * 核心包可透過 WorldVoice -> 檔案匯入將 zip 壓縮包匯入語音元件工作區。 * 語音包安裝方式 * 基本:使用兼容於 Vocalizer for NVDA 的語音包addon,[官方下載點](https://vocalizer-nvda.com/downloads)。 - * 進階:可透過各種語音包內直接複製其內的地區資料夾(ex: en, mnc, mnt)等並將其壓成 zip 壓縮包後透過 WorldVoice 介面的檔案匯入功能匯入addon內,與核心包相同需留意匯入之工作區,如無特殊需求建議使用 addon 版本安裝,因 addon 版本可共享同時提供第 1 驅動與第 2 驅動使用。 + * 進階:可透過各種語音包內直接複製其內的地區資料夾(ex: en, mnc, mnt)等並將其壓成 zip 壓縮包後透過 WorldVoice 介面的檔案匯入功能匯入 addon 內,如無特殊需求建議使用 addon 版本安裝,因當 WorldVoice 升級版本時 addon 版本語音包不會被刪除亦無需重新安裝。 ## 相依性套件 @@ -22,7 +22,9 @@ WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2 * NVDA+ctrl+S 選擇 WorldVoice 語音合成器。 * NVDA+ctrl+V 有基本語音速度、音調、音量等基本設定,其中數字模式、中文空白間隔為 WorldVoice 多的客製設定。 * 數字讀法:分為 2 個維度設定選項「數字語言」與「數字模式」,數字語言設定數字朗讀時使用的地區語音、數字模式分為數值與數字兩種 - * 中文空白間隔:可設定中文間有空白時,欲停頓長度,數字愈小停頓愈短, 0 為不停頓。 + * 「當遇到中文與中文間的空白時暫停長度」:可設定中文間有空白時,欲停頓長度,數字愈小停頓愈短, 0 為不停頓。 + * 「忽略在數字間的逗號」選項勾選時,可讓數字位數的逗號標錯位置仍能正常朗讀數值。 + * 「啟用 WorldVoice 設定規則來偵測文字語言」勾選時,會使用語音設定內的規則來偵測文字語言並切換語音朗讀。 * WorldVoice -> 語音設定:可設定不同地區所使用的語音角色、各別語音角色速度、音調、音量、自動語音切換設定。 * 先選擇地區後語音列表會列出該地區可用的語音角色,選擇後即完成該地區與語音角色的對應紀錄。 * 當語音角色有選擇時,下方速度、音調、音量滑桿會變為該語音角色的設定值。 @@ -80,3 +82,11 @@ WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2 * 將自動語言切換設定與語音設定視窗合併 * 地區與語音對應加入 no-select 用來取消對應 * 支援快速鍵彈出語音設定與 Unicode 設定 + +### v1.6 + +* 修正數字模式下小數點不朗讀問題 +* 更新 VE 核心包工作目錄,未來更新時可無需重新匯入 +* 將「使用 WorldVoice 設定規則針測語言」的開關與「自動切換語言」的開關分開,避免部份情境兩者不相容問題。 +* 修正啟用 unicode 自動語言針測時,預設語音與 NVDA 語言地區不相同但同語系時無法切換的問題 +* 修正自動切換語言無勾選時 WorldVoice 變更語音語言命令被濾掉的問題 diff --git a/addon/globalPlugins/WorldVoiceXVED2/__init__.py b/addon/globalPlugins/WorldVoiceXVED2/__init__.py index 2a1f33f..da84872 100644 --- a/addon/globalPlugins/WorldVoiceXVED2/__init__.py +++ b/addon/globalPlugins/WorldVoiceXVED2/__init__.py @@ -23,6 +23,7 @@ from .speechSettingsDialog import SpeechSettingsDialog from generics.views import SpeechSymbolsDialog +workspace_path = os.path.join(globalVars.appArgs.configPath, "WorldVoice-workspace") ADDON_SUMMARY = addonHandler.getCodeAddon().manifest["summary"] SpeechSettingsDialog = SpeechSettingsDialog() @@ -35,7 +36,7 @@ def __init__(self): def initialize(self): if globalVars.appArgs.secure: return - if not os.path.isdir(os.path.join(synth_drivers_path, 'common')): + if (not os.path.isdir(os.path.join(workspace_path, 'common'))) and (not os.path.isdir(os.path.join(synth_drivers_path, 'common'))): self.createMenu() wx.CallLater(2000, self.onNoCoreInstalled) return @@ -74,6 +75,7 @@ def onFileImport(self, event): from zipfile import ZipFile with ZipFile(path, 'r') as core_file: core_file.testzip() + core_file.extractall(workspace_path) core_file.extractall(synth_drivers_path) except: gui.messageBox( diff --git a/addon/locale/zh_CN/LC_MESSAGES/nvda.po b/addon/locale/zh_CN/LC_MESSAGES/nvda.po index f015b7d..4df30ff 100644 --- a/addon/locale/zh_CN/LC_MESSAGES/nvda.po +++ b/addon/locale/zh_CN/LC_MESSAGES/nvda.po @@ -5,10 +5,10 @@ # msgid "" msgstr "" -"Project-Id-Version: 'WorldVoiceXVE' '1.5'\n" +"Project-Id-Version: 'WorldVoiceXVE' '1.6'\n" "Report-Msgid-Bugs-To: 'nvda-translations@groups.io'\n" -"POT-Creation-Date: 2020-12-28 20:55+0800\n" -"PO-Revision-Date: 2020-12-28 21:02+0800\n" +"POT-Creation-Date: 2021-02-03 08:50+0800\n" +"PO-Revision-Date: 2021-02-03 08:52+0800\n" "Last-Translator: \n" "Language-Team: \n" "Language: zh_CN\n" @@ -111,54 +111,54 @@ msgstr "为了让已编辑的 Unicode 生效,必须重新启动 NVDA,您要 msgid "unicode rule edited" msgstr "unicode 规则已编辑" -#: globalPlugins/WorldVoiceXVED2/__init__.py:51 +#: globalPlugins/WorldVoiceXVED2/__init__.py:52 msgid "&Speech Settings" msgstr "语音设置(&S)" -#: globalPlugins/WorldVoiceXVED2/__init__.py:51 +#: globalPlugins/WorldVoiceXVED2/__init__.py:52 msgid "Speech Settings." msgstr "语音设置(&S)" -#: globalPlugins/WorldVoiceXVED2/__init__.py:53 +#: globalPlugins/WorldVoiceXVED2/__init__.py:54 msgid "&Unicode Settings" msgstr "Unicode 设置(&U)" -#: globalPlugins/WorldVoiceXVED2/__init__.py:53 +#: globalPlugins/WorldVoiceXVED2/__init__.py:54 msgid "Unicode Settings." msgstr "Unicode 设置" -#: globalPlugins/WorldVoiceXVED2/__init__.py:55 +#: globalPlugins/WorldVoiceXVED2/__init__.py:56 msgid "&File Import" msgstr "导入文件(&F)" -#: globalPlugins/WorldVoiceXVED2/__init__.py:55 +#: globalPlugins/WorldVoiceXVED2/__init__.py:56 msgid "Import File." msgstr "导入文件" -#: globalPlugins/WorldVoiceXVED2/__init__.py:57 +#: globalPlugins/WorldVoiceXVED2/__init__.py:58 msgid "WorldVoice(VE)" msgstr "WorldVoice(VE)" -#: globalPlugins/WorldVoiceXVED2/__init__.py:68 +#: globalPlugins/WorldVoiceXVED2/__init__.py:69 msgid "Import file..." msgstr "导入文件" -#: globalPlugins/WorldVoiceXVED2/__init__.py:80 +#: globalPlugins/WorldVoiceXVED2/__init__.py:82 msgid "Import fail" msgstr "导入失败" -#: globalPlugins/WorldVoiceXVED2/__init__.py:81 -#: globalPlugins/WorldVoiceXVED2/__init__.py:86 +#: globalPlugins/WorldVoiceXVED2/__init__.py:83 +#: globalPlugins/WorldVoiceXVED2/__init__.py:88 msgid "Import File" msgstr "导入文件" -#: globalPlugins/WorldVoiceXVED2/__init__.py:85 +#: globalPlugins/WorldVoiceXVED2/__init__.py:87 msgid "" "For the new file to import, NVDA must be restarted. Are you want to restart " "NVDA now ?" msgstr "为了使导入的文件生效, NVDA 必需重新启动。您要立即重新启动吗?" -#: globalPlugins/WorldVoiceXVED2/__init__.py:93 +#: globalPlugins/WorldVoiceXVED2/__init__.py:95 msgid "" "You have no core(driver 2) installed.\n" "Do you want to install the core(driver 2) now?" @@ -166,23 +166,23 @@ msgstr "" "您尚未安装(driver 2)核心。\n" "您是否要现在安装?" -#: globalPlugins/WorldVoiceXVED2/__init__.py:95 +#: globalPlugins/WorldVoiceXVED2/__init__.py:97 msgid "No core installed." msgstr "尚未安装核心" -#: globalPlugins/WorldVoiceXVED2/__init__.py:108 +#: globalPlugins/WorldVoiceXVED2/__init__.py:110 msgid "SpeechSettingsDialog have already been opened" -msgstr "语音设置(&S)對話框已開啟" +msgstr "语音设置對話框已開啟" -#: globalPlugins/WorldVoiceXVED2/__init__.py:114 +#: globalPlugins/WorldVoiceXVED2/__init__.py:116 msgid "SpeechSymbolsDialog have already been opened" -msgstr "Unicode 設定對話框已開啟" +msgstr "Unicode 设置對話框已開啟" -#: globalPlugins/WorldVoiceXVED2/__init__.py:118 +#: globalPlugins/WorldVoiceXVED2/__init__.py:120 msgid "popup SpeechSettingsDialog" msgstr "弹出语音设置对话框(&S)" -#: globalPlugins/WorldVoiceXVED2/__init__.py:126 +#: globalPlugins/WorldVoiceXVED2/__init__.py:128 msgid "popup SpeechSymbolsDialog" msgstr "弹出 标点符号读音对话框" @@ -242,40 +242,51 @@ msgstr "拉丁字符对应的语言" msgid "Language assumed for CJK characters:" msgstr "中日韩字符对应的语言:" -#: synthDrivers/WorldVoiceXVED2/__init__.py:71 +#: synthDrivers/WorldVoiceXVED2/__init__.py:44 msgid "Number &Language" msgstr "数字语言(&M)" -#: synthDrivers/WorldVoiceXVED2/__init__.py:75 -#: synthDrivers/WorldVoiceXVED2/__init__.py:84 -msgid "Number Mode" -msgstr "数字模式" +#: synthDrivers/WorldVoiceXVED2/__init__.py:48 +msgid "Number Language" +msgstr "数字语言" -#: synthDrivers/WorldVoiceXVED2/__init__.py:80 +#: synthDrivers/WorldVoiceXVED2/__init__.py:53 msgid "Number &Mode" msgstr "数字模式(&M)" -#: synthDrivers/WorldVoiceXVED2/__init__.py:89 +#: synthDrivers/WorldVoiceXVED2/__init__.py:57 +msgid "Number Mode" +msgstr "数字模式" + +#: synthDrivers/WorldVoiceXVED2/__init__.py:62 msgid "Pause time when encountering spaces between Chinese" msgstr "中文空格暂停时间" -#: synthDrivers/WorldVoiceXVED2/__init__.py:95 +#: synthDrivers/WorldVoiceXVED2/__init__.py:68 msgid "Ignore comma between number" msgstr "忽略数字中的逗号" -#: synthDrivers/WorldVoiceXVED2/__init__.py:100 +#: synthDrivers/WorldVoiceXVED2/__init__.py:73 msgid "Ignore language information of document" msgstr "忽略文档中的语言信息" -#: synthDrivers/WorldVoiceXVED2/__init__.py:354 +#: synthDrivers/WorldVoiceXVED2/__init__.py:78 +msgid "Enable WorldVoice setting rules to detect text language" +msgstr "启用 WorldVoice 设定规则来检测文本语言" + +#: synthDrivers/WorldVoiceXVED2/__init__.py:81 +msgid "Enable WorldVoice rules" +msgstr "启用 WorldVoice 规则" + +#: synthDrivers/WorldVoiceXVED2/__init__.py:338 msgid "default" msgstr "默认" -#: synthDrivers/WorldVoiceXVED2/__init__.py:370 +#: synthDrivers/WorldVoiceXVED2/__init__.py:351 msgid "value" msgstr "数值" -#: synthDrivers/WorldVoiceXVED2/__init__.py:371 +#: synthDrivers/WorldVoiceXVED2/__init__.py:352 msgid "number" msgstr "数字" diff --git a/addon/locale/zh_HK/LC_MESSAGES/nvda.po b/addon/locale/zh_HK/LC_MESSAGES/nvda.po index 44301b2..26f01b6 100644 --- a/addon/locale/zh_HK/LC_MESSAGES/nvda.po +++ b/addon/locale/zh_HK/LC_MESSAGES/nvda.po @@ -5,10 +5,10 @@ # msgid "" msgstr "" -"Project-Id-Version: 'WorldVoice' '1.5'\n" +"Project-Id-Version: 'WorldVoice' '1.6'\n" "Report-Msgid-Bugs-To: 'nvda-translations@groups.io'\n" -"POT-Creation-Date: 2020-12-28 20:55+0800\n" -"PO-Revision-Date: 2020-12-28 21:00+0800\n" +"POT-Creation-Date: 2021-02-03 08:50+0800\n" +"PO-Revision-Date: 2021-02-03 08:51+0800\n" "Last-Translator: \n" "Language-Team: \n" "Language: zh_HK\n" @@ -112,54 +112,54 @@ msgstr "" msgid "unicode rule edited" msgstr "unicode 規則已編輯" -#: globalPlugins/WorldVoiceXVED2/__init__.py:51 +#: globalPlugins/WorldVoiceXVED2/__init__.py:52 msgid "&Speech Settings" msgstr "語音設定(&S)" -#: globalPlugins/WorldVoiceXVED2/__init__.py:51 +#: globalPlugins/WorldVoiceXVED2/__init__.py:52 msgid "Speech Settings." msgstr "語音設定。" -#: globalPlugins/WorldVoiceXVED2/__init__.py:53 +#: globalPlugins/WorldVoiceXVED2/__init__.py:54 msgid "&Unicode Settings" msgstr "&Unicode 設定" -#: globalPlugins/WorldVoiceXVED2/__init__.py:53 +#: globalPlugins/WorldVoiceXVED2/__init__.py:54 msgid "Unicode Settings." msgstr "Unicode 設定。" -#: globalPlugins/WorldVoiceXVED2/__init__.py:55 +#: globalPlugins/WorldVoiceXVED2/__init__.py:56 msgid "&File Import" msgstr "檔案匯入(&F)" -#: globalPlugins/WorldVoiceXVED2/__init__.py:55 +#: globalPlugins/WorldVoiceXVED2/__init__.py:56 msgid "Import File." msgstr "匯入檔案..." -#: globalPlugins/WorldVoiceXVED2/__init__.py:57 +#: globalPlugins/WorldVoiceXVED2/__init__.py:58 msgid "WorldVoice(VE)" msgstr "WorldVoice(VE)" -#: globalPlugins/WorldVoiceXVED2/__init__.py:68 +#: globalPlugins/WorldVoiceXVED2/__init__.py:69 msgid "Import file..." msgstr "匯入檔案..." -#: globalPlugins/WorldVoiceXVED2/__init__.py:80 +#: globalPlugins/WorldVoiceXVED2/__init__.py:82 msgid "Import fail" msgstr "匯入失敗" -#: globalPlugins/WorldVoiceXVED2/__init__.py:81 -#: globalPlugins/WorldVoiceXVED2/__init__.py:86 +#: globalPlugins/WorldVoiceXVED2/__init__.py:83 +#: globalPlugins/WorldVoiceXVED2/__init__.py:88 msgid "Import File" msgstr "匯入檔案" -#: globalPlugins/WorldVoiceXVED2/__init__.py:85 +#: globalPlugins/WorldVoiceXVED2/__init__.py:87 msgid "" "For the new file to import, NVDA must be restarted. Are you want to restart " "NVDA now ?" msgstr "為了讓新檔案匯入, NVDA 必需重新啟動。您要立即重新啟動 NVDA 嗎?" -#: globalPlugins/WorldVoiceXVED2/__init__.py:93 +#: globalPlugins/WorldVoiceXVED2/__init__.py:95 msgid "" "You have no core(driver 2) installed.\n" "Do you want to install the core(driver 2) now?" @@ -167,23 +167,23 @@ msgstr "" "您尚未安裝核心(driver 2)。\n" "您是否要現在進行核心安裝?" -#: globalPlugins/WorldVoiceXVED2/__init__.py:95 +#: globalPlugins/WorldVoiceXVED2/__init__.py:97 msgid "No core installed." msgstr "尚未安裝核心。" -#: globalPlugins/WorldVoiceXVED2/__init__.py:108 +#: globalPlugins/WorldVoiceXVED2/__init__.py:110 msgid "SpeechSettingsDialog have already been opened" msgstr "語音設定對話框已開啟" -#: globalPlugins/WorldVoiceXVED2/__init__.py:114 +#: globalPlugins/WorldVoiceXVED2/__init__.py:116 msgid "SpeechSymbolsDialog have already been opened" msgstr "Unicode 設定對話框已開啟" -#: globalPlugins/WorldVoiceXVED2/__init__.py:118 +#: globalPlugins/WorldVoiceXVED2/__init__.py:120 msgid "popup SpeechSettingsDialog" msgstr "彈出 SpeechSettingsDialog" -#: globalPlugins/WorldVoiceXVED2/__init__.py:126 +#: globalPlugins/WorldVoiceXVED2/__init__.py:128 msgid "popup SpeechSymbolsDialog" msgstr "彈出 SpeechSymbolsDialog" @@ -243,40 +243,51 @@ msgstr "拉丁字元假設的語言:" msgid "Language assumed for CJK characters:" msgstr "中日韓字元假設的語言:" -#: synthDrivers/WorldVoiceXVED2/__init__.py:71 +#: synthDrivers/WorldVoiceXVED2/__init__.py:44 msgid "Number &Language" msgstr "數字語言(&L)" -#: synthDrivers/WorldVoiceXVED2/__init__.py:75 -#: synthDrivers/WorldVoiceXVED2/__init__.py:84 -msgid "Number Mode" -msgstr "數字模式" +#: synthDrivers/WorldVoiceXVED2/__init__.py:48 +msgid "Number Language" +msgstr "數字語言" -#: synthDrivers/WorldVoiceXVED2/__init__.py:80 +#: synthDrivers/WorldVoiceXVED2/__init__.py:53 msgid "Number &Mode" msgstr "數字模式(&M)" -#: synthDrivers/WorldVoiceXVED2/__init__.py:89 +#: synthDrivers/WorldVoiceXVED2/__init__.py:57 +msgid "Number Mode" +msgstr "數字模式" + +#: synthDrivers/WorldVoiceXVED2/__init__.py:62 msgid "Pause time when encountering spaces between Chinese" msgstr "當遇到中文與中文間的空白時暫停長度" -#: synthDrivers/WorldVoiceXVED2/__init__.py:95 +#: synthDrivers/WorldVoiceXVED2/__init__.py:68 msgid "Ignore comma between number" msgstr "忽略在數字間的逗號" -#: synthDrivers/WorldVoiceXVED2/__init__.py:100 +#: synthDrivers/WorldVoiceXVED2/__init__.py:73 msgid "Ignore language information of document" msgstr "忽略文件中的語言資訊" -#: synthDrivers/WorldVoiceXVED2/__init__.py:354 +#: synthDrivers/WorldVoiceXVED2/__init__.py:78 +msgid "Enable WorldVoice setting rules to detect text language" +msgstr "啟用 WorldVoice 設定規則來偵測文字語言" + +#: synthDrivers/WorldVoiceXVED2/__init__.py:81 +msgid "Enable WorldVoice rules" +msgstr "啟用 WorldVoice 規則" + +#: synthDrivers/WorldVoiceXVED2/__init__.py:338 msgid "default" msgstr "預設" -#: synthDrivers/WorldVoiceXVED2/__init__.py:370 +#: synthDrivers/WorldVoiceXVED2/__init__.py:351 msgid "value" msgstr "數值" -#: synthDrivers/WorldVoiceXVED2/__init__.py:371 +#: synthDrivers/WorldVoiceXVED2/__init__.py:352 msgid "number" msgstr "數字" diff --git a/addon/locale/zh_TW/LC_MESSAGES/nvda.po b/addon/locale/zh_TW/LC_MESSAGES/nvda.po index 7b97c46..f46e748 100644 --- a/addon/locale/zh_TW/LC_MESSAGES/nvda.po +++ b/addon/locale/zh_TW/LC_MESSAGES/nvda.po @@ -5,10 +5,10 @@ # msgid "" msgstr "" -"Project-Id-Version: 'WorldVoice' '1.5'\n" +"Project-Id-Version: 'WorldVoice' '1.6'\n" "Report-Msgid-Bugs-To: 'nvda-translations@groups.io'\n" -"POT-Creation-Date: 2020-12-28 20:55+0800\n" -"PO-Revision-Date: 2020-12-28 20:58+0800\n" +"POT-Creation-Date: 2021-02-03 08:50+0800\n" +"PO-Revision-Date: 2021-02-03 08:51+0800\n" "Last-Translator: \n" "Language-Team: \n" "Language: zh_TW\n" @@ -112,54 +112,54 @@ msgstr "" msgid "unicode rule edited" msgstr "unicode 規則已編輯" -#: globalPlugins/WorldVoiceXVED2/__init__.py:51 +#: globalPlugins/WorldVoiceXVED2/__init__.py:52 msgid "&Speech Settings" msgstr "語音設定(&S)" -#: globalPlugins/WorldVoiceXVED2/__init__.py:51 +#: globalPlugins/WorldVoiceXVED2/__init__.py:52 msgid "Speech Settings." msgstr "語音設定。" -#: globalPlugins/WorldVoiceXVED2/__init__.py:53 +#: globalPlugins/WorldVoiceXVED2/__init__.py:54 msgid "&Unicode Settings" msgstr "&Unicode 設定" -#: globalPlugins/WorldVoiceXVED2/__init__.py:53 +#: globalPlugins/WorldVoiceXVED2/__init__.py:54 msgid "Unicode Settings." msgstr "Unicode 設定。" -#: globalPlugins/WorldVoiceXVED2/__init__.py:55 +#: globalPlugins/WorldVoiceXVED2/__init__.py:56 msgid "&File Import" msgstr "檔案匯入(&F)" -#: globalPlugins/WorldVoiceXVED2/__init__.py:55 +#: globalPlugins/WorldVoiceXVED2/__init__.py:56 msgid "Import File." msgstr "匯入檔案..." -#: globalPlugins/WorldVoiceXVED2/__init__.py:57 +#: globalPlugins/WorldVoiceXVED2/__init__.py:58 msgid "WorldVoice(VE)" msgstr "WorldVoice(VE)" -#: globalPlugins/WorldVoiceXVED2/__init__.py:68 +#: globalPlugins/WorldVoiceXVED2/__init__.py:69 msgid "Import file..." msgstr "匯入檔案..." -#: globalPlugins/WorldVoiceXVED2/__init__.py:80 +#: globalPlugins/WorldVoiceXVED2/__init__.py:82 msgid "Import fail" msgstr "匯入失敗" -#: globalPlugins/WorldVoiceXVED2/__init__.py:81 -#: globalPlugins/WorldVoiceXVED2/__init__.py:86 +#: globalPlugins/WorldVoiceXVED2/__init__.py:83 +#: globalPlugins/WorldVoiceXVED2/__init__.py:88 msgid "Import File" msgstr "匯入檔案" -#: globalPlugins/WorldVoiceXVED2/__init__.py:85 +#: globalPlugins/WorldVoiceXVED2/__init__.py:87 msgid "" "For the new file to import, NVDA must be restarted. Are you want to restart " "NVDA now ?" msgstr "為了讓新檔案匯入, NVDA 必需重新啟動。您要立即重新啟動 NVDA 嗎?" -#: globalPlugins/WorldVoiceXVED2/__init__.py:93 +#: globalPlugins/WorldVoiceXVED2/__init__.py:95 msgid "" "You have no core(driver 2) installed.\n" "Do you want to install the core(driver 2) now?" @@ -167,23 +167,23 @@ msgstr "" "您尚未安裝核心(driver 2)。\n" "您是否要現在進行核心安裝?" -#: globalPlugins/WorldVoiceXVED2/__init__.py:95 +#: globalPlugins/WorldVoiceXVED2/__init__.py:97 msgid "No core installed." msgstr "尚未安裝核心。" -#: globalPlugins/WorldVoiceXVED2/__init__.py:108 +#: globalPlugins/WorldVoiceXVED2/__init__.py:110 msgid "SpeechSettingsDialog have already been opened" msgstr "語音設定對話框已開啟" -#: globalPlugins/WorldVoiceXVED2/__init__.py:114 +#: globalPlugins/WorldVoiceXVED2/__init__.py:116 msgid "SpeechSymbolsDialog have already been opened" msgstr "Unicode 設定對話框已開啟" -#: globalPlugins/WorldVoiceXVED2/__init__.py:118 +#: globalPlugins/WorldVoiceXVED2/__init__.py:120 msgid "popup SpeechSettingsDialog" msgstr "彈出 SpeechSettingsDialog" -#: globalPlugins/WorldVoiceXVED2/__init__.py:126 +#: globalPlugins/WorldVoiceXVED2/__init__.py:128 msgid "popup SpeechSymbolsDialog" msgstr "彈出 SpeechSymbolsDialog" @@ -243,40 +243,51 @@ msgstr "拉丁字元假設的語言:" msgid "Language assumed for CJK characters:" msgstr "中日韓字元假設的語言:" -#: synthDrivers/WorldVoiceXVED2/__init__.py:71 +#: synthDrivers/WorldVoiceXVED2/__init__.py:44 msgid "Number &Language" msgstr "數字語言(&L)" -#: synthDrivers/WorldVoiceXVED2/__init__.py:75 -#: synthDrivers/WorldVoiceXVED2/__init__.py:84 -msgid "Number Mode" -msgstr "數字模式" +#: synthDrivers/WorldVoiceXVED2/__init__.py:48 +msgid "Number Language" +msgstr "數字語言" -#: synthDrivers/WorldVoiceXVED2/__init__.py:80 +#: synthDrivers/WorldVoiceXVED2/__init__.py:53 msgid "Number &Mode" msgstr "數字模式(&M)" -#: synthDrivers/WorldVoiceXVED2/__init__.py:89 +#: synthDrivers/WorldVoiceXVED2/__init__.py:57 +msgid "Number Mode" +msgstr "數字模式" + +#: synthDrivers/WorldVoiceXVED2/__init__.py:62 msgid "Pause time when encountering spaces between Chinese" msgstr "當遇到中文與中文間的空白時暫停長度" -#: synthDrivers/WorldVoiceXVED2/__init__.py:95 +#: synthDrivers/WorldVoiceXVED2/__init__.py:68 msgid "Ignore comma between number" msgstr "忽略在數字間的逗號" -#: synthDrivers/WorldVoiceXVED2/__init__.py:100 +#: synthDrivers/WorldVoiceXVED2/__init__.py:73 msgid "Ignore language information of document" msgstr "忽略文件中的語言資訊" -#: synthDrivers/WorldVoiceXVED2/__init__.py:354 +#: synthDrivers/WorldVoiceXVED2/__init__.py:78 +msgid "Enable WorldVoice setting rules to detect text language" +msgstr "啟用 WorldVoice 設定規則來偵測文字語言" + +#: synthDrivers/WorldVoiceXVED2/__init__.py:81 +msgid "Enable WorldVoice rules" +msgstr "啟用 WorldVoice 規則" + +#: synthDrivers/WorldVoiceXVED2/__init__.py:338 msgid "default" msgstr "預設" -#: synthDrivers/WorldVoiceXVED2/__init__.py:370 +#: synthDrivers/WorldVoiceXVED2/__init__.py:351 msgid "value" msgstr "數值" -#: synthDrivers/WorldVoiceXVED2/__init__.py:371 +#: synthDrivers/WorldVoiceXVED2/__init__.py:352 msgid "number" msgstr "數字" diff --git a/addon/synthDrivers/WorldVoiceXVED2/__init__.py b/addon/synthDrivers/WorldVoiceXVED2/__init__.py index 1d648d0..854d755 100644 --- a/addon/synthDrivers/WorldVoiceXVED2/__init__.py +++ b/addon/synthDrivers/WorldVoiceXVED2/__init__.py @@ -17,6 +17,7 @@ from . import languageDetection from . import _config from generics.models import SpeechSymbols +from . import speechcommand import addonHandler addonHandler.initTranslation() @@ -28,34 +29,6 @@ comma_number_pattern = re.compile(r"(?<=[0-9]),(?=[0-9])") chinese_space_pattern = re.compile(r"(?<=[\u4e00-\u9fa5])\s+(?=[\u4e00-\u9fa5])") -english_number = { - ord("0"): "zero", - ord("1"): "one", - ord("2"): "two", - ord("3"): "three", - ord("4"): "four", - ord("5"): "five", - ord("6"): "six", - ord("7"): "seven", - ord("8"): "eight", - ord("9"): "nine", - # ord("."): "dot", -} -english_number = {key: " {} ".format(value) for key, value in english_number.items()} -chinese_number = { - ord("0"): u"\u96f6", - ord("1"): u"\u4e00", - ord("2"): u"\u4e8c", - ord("3"): u"\u4e09", - ord("4"): u"\u56db", - ord("5"): u"\u4e94", - ord("6"): u"\u516d", - ord("7"): u"\u4e03", - ord("8"): u"\u516b", - ord("9"): u"\u4e5d", - ord("."): u"\u9ede", -} - class SynthDriver(SynthDriver): name = "WorldVoiceXVED2" description = "WorldVoice(VE)" @@ -72,7 +45,7 @@ class SynthDriver(SynthDriver): availableInSettingsRing=True, defaultVal="default", # Translators: Label for a setting in synth settings ring. - displayName=_("Number Mode"), + displayName=_("Number Language"), ), driverHandler.DriverSetting( "nummod", @@ -100,6 +73,13 @@ class SynthDriver(SynthDriver): _("Ignore language information of document"), defaultVal=False, ), + driverHandler.BooleanDriverSetting( + "uwv", + _("Enable WorldVoice setting rules to detect text language"), + availableInSettingsRing=True, + defaultVal=True, + displayName=_("Enable WorldVoice rules"), + ), ] supportedCommands = { speech.IndexCommand, @@ -170,7 +150,7 @@ def terminate(self): log.error("Vocalizer terminate", exc_info=True) def speak(self, speechSequence): - if config.conf["speech"]["autoLanguageSwitching"] \ + if self.uwv \ and _config.vocalizerConfig['autoLanguageSwitching']['useUnicodeLanguageDetection'] \ and _config.vocalizerConfig['autoLanguageSwitching']['afterSymbolDetection']: speechSequence = self._languageDetector.add_detected_language_commands(speechSequence) @@ -208,7 +188,7 @@ def speak(self, speechSequence): charMode = command.state s = "\x1b\\tn=spell\\" if command.state else "\x1b\\tn=normal\\" chunks.append(s) - elif isinstance(command, speech.LangChangeCommand): + elif isinstance(command, speech.LangChangeCommand) or isinstance(command, speechcommand.WVLangChangeCommand): if command.lang == currentLanguage: # Keep on the same voice. continue @@ -237,6 +217,10 @@ def speak(self, speechSequence): pitch = self._voiceManager.getVoiceParameter(currentInstance, _vocalizer.VE_PARAM_PITCH, type_=int) pitchOffset = self._percentToParam(command.offset, _vocalizer.PITCH_MIN, _vocalizer.PITCH_MAX) - _vocalizer.PITCH_MIN chunks.append("\x1b\\pitch=%d\\" % (pitch+pitchOffset)) + elif isinstance(command, speechcommand.SplitCommand): + self._speak(currentInstance, chunks) + chunks = [] + hasText = False if chunks: self._speak(currentInstance, chunks) @@ -254,8 +238,8 @@ def patchedSpeak(self, speechSequence, symbolLevel=None, priority=None): temp.append(command) speechSequence = temp if self._dli: - speechSequence = self.removeLangChangeCommand(speechSequence) - if config.conf["speech"]["autoLanguageSwitching"] \ + speechSequence = self.patchedRemoveLangChangeCommandSpeechSequence(speechSequence) + if self.uwv \ and _config.vocalizerConfig['autoLanguageSwitching']['useUnicodeLanguageDetection'] \ and not _config.vocalizerConfig['autoLanguageSwitching']['afterSymbolDetection']: speechSequence = self._languageDetector.add_detected_language_commands(speechSequence) @@ -354,9 +338,6 @@ def _get_availableNumlans(self): "default": driverHandler.StringParameterInfo("default", _("default")), }, **{ locale: driverHandler.StringParameterInfo(locale, name) for locale, name in zip(self._locales, self._localeNames) - # }, **{ - # "chinese_number": driverHandler.StringParameterInfo("chinese_number", _("chinese number")), - # "english_number": driverHandler.StringParameterInfo("english_number", _("english number")), }) def _get_numlan(self): @@ -396,15 +377,7 @@ def _set_dli(self,value): self._dli = value def patchedNumSpeechSequence(self, speechSequence): - if False: - pass - elif self._numlan == "chinese_number": - speechSequence = [command.translate(chinese_number) if isinstance(command, str) else command for command in speechSequence] - elif self._numlan == "english_number": - speechSequence = [command.translate(english_number) if isinstance(command, str) else command for command in speechSequence] - else: - speechSequence = self.coercionNumberLangChange(speechSequence, self._numlan, self._nummod) - return speechSequence + return self.coercionNumberLangChange(speechSequence, self._numlan, self._nummod) def patchedSpaceSpeechSequence(self, speechSequence): if not int(self._chinesespace) == 0: @@ -438,13 +411,37 @@ def patchedSpaceSpeechSequence(self, speechSequence): speechSequence = tempSpeechSequence return speechSequence - def removeLangChangeCommand(self, speechSequence): + def patchedRemoveLangChangeCommandSpeechSequence(self, speechSequence): result = [] for command in speechSequence: if not isinstance(command, speech.LangChangeCommand): result.append(command) return result + def patchedLengthSpeechSequence(self, speechSequence): + result = [] + for command in speechSequence: + if isinstance(command, str): + result.extend(self.lengthsplit(command, 100)) + else: + result.append(command) + return result + + def lengthsplit(self, string, length): + result = [] + pattern = re.compile(r"[\s]") + spaces = pattern.findall(string) + others = pattern.split(string) + fragment = "" + for other, space in zip(others, spaces): + fragment += other + space + if len(fragment) > length: + result.append(fragment) + result.append(speechcommand.SplitCommand()) + fragment = "" + fragment += others[-1] + result.append(fragment) + return result def resplit(self, pattern, string, mode): result = [] @@ -454,7 +451,7 @@ def resplit(self, pattern, string, mode): if mode == 'value': result.extend([other, speech.LangChangeCommand('StartNumber'), number, speech.LangChangeCommand('EndNumber')]) elif mode == 'number': - result.extend([other, speech.LangChangeCommand('StartNumber'), ' '.join(number), speech.LangChangeCommand('EndNumber')]) + result.extend([other, speech.LangChangeCommand('StartNumber'), ' '.join(number).replace(" . ", "."), speech.LangChangeCommand('EndNumber')]) result.append(others[-1]) return result diff --git a/addon/synthDrivers/WorldVoiceXVED2/_vocalizer.py b/addon/synthDrivers/WorldVoiceXVED2/_vocalizer.py index c1b7ae1..80b2d14 100644 --- a/addon/synthDrivers/WorldVoiceXVED2/_vocalizer.py +++ b/addon/synthDrivers/WorldVoiceXVED2/_vocalizer.py @@ -9,6 +9,7 @@ import addonHandler import synthDriverHandler import config +import globalVars from logHandler import log import nvwave import winKernel @@ -104,8 +105,9 @@ def callback(instance, userData, message): log.error("Vocalizer callback", exc_info=True) return NUAN_OK - -_basePath = os.path.dirname(__file__) +_basePath = os.path.join(globalVars.appArgs.configPath, "WorldVoice-workspace") +if not os.path.isdir(os.path.join(_basePath, 'common')): + _basePath = os.path.dirname(__file__) _tuningDataDir = os.path.join(_basePath, "tuningData") msvcrDll = None diff --git a/addon/synthDrivers/WorldVoiceXVED2/languageDetection/__init__.py b/addon/synthDrivers/WorldVoiceXVED2/languageDetection/__init__.py index e2b26f1..b6d36c7 100644 --- a/addon/synthDrivers/WorldVoiceXVED2/languageDetection/__init__.py +++ b/addon/synthDrivers/WorldVoiceXVED2/languageDetection/__init__.py @@ -10,7 +10,7 @@ import languageHandler import speech from .. import _config - +from .. import speechcommand BASIC_LATIN = [ u"en", u"ha", u"so", u"id", u"la", u"sw", u"eu", @@ -107,7 +107,7 @@ def add_detected_language_commands(self, speechSequence): curLang = defaultLang tmpLang = curLang.split("_")[0] for command in speechSequence: - if isinstance(command, speech.LangChangeCommand): + if isinstance(command, speechcommand.WVLangChangeCommand): if command.lang is None: curLang = defaultLang else: @@ -147,7 +147,7 @@ def add_detected_language_commands(self, speechSequence): sb = StringIO() tmpLang = newLangFirst charset = None - yield speech.LangChangeCommand(newLang) + yield speechcommand.WVLangChangeCommand(newLang) yield c continue @@ -173,7 +173,7 @@ def add_detected_language_commands(self, speechSequence): if sb.getvalue(): yield sb.getvalue() sb = StringIO() - yield speech.LangChangeCommand(curLang) + yield speechcommand.WVLangChangeCommand(curLang) tmpLang = curLang.split("_")[0] sb.write(c) continue @@ -209,9 +209,9 @@ def add_detected_language_commands(self, speechSequence): sb = StringIO() tmpLang = newLangFirst if newLang == curLang: - yield speech.LangChangeCommand(newLang) + yield speechcommand.WVLangChangeCommand(newLang) else: - yield speech.LangChangeCommand(tmpLang) + yield speechcommand.WVLangChangeCommand(tmpLang) sb.write(c) # Send the string, if we have one: if sb.getvalue(): diff --git a/addon/synthDrivers/WorldVoiceXVED2/speechcommand.py b/addon/synthDrivers/WorldVoiceXVED2/speechcommand.py new file mode 100644 index 0000000..5d0f703 --- /dev/null +++ b/addon/synthDrivers/WorldVoiceXVED2/speechcommand.py @@ -0,0 +1,23 @@ +from typing import Optional, Callable + +from speech import SynthCommand, SynthParamCommand + +class WVLangChangeCommand(SynthParamCommand): + """A command to switch the language within speech.""" + + def __init__(self, lang: Optional[str]): + """ + @param lang: the language to switch to: If None then the NVDA locale will be used. + """ + self.lang = lang + self.isDefault = not lang + + def __repr__(self): + return "WVLangChangeCommand (%r)"%self.lang + +class SplitCommand(SynthCommand): + """Insert a split command when text exceed max length. + """ + + def __repr__(self): + return "SplitCommand()" diff --git a/buildVars.py b/buildVars.py index 5712aa5..66a0e59 100644 --- a/buildVars.py +++ b/buildVars.py @@ -19,7 +19,7 @@ # Translators: Long description to be shown for this add-on on add-on information from add-ons manager "addon_description" : _("WorldVoice"), # version - "addon_version" : "1.5", + "addon_version" : "1.6", # Author(s) "addon_author" : "Tseng Woody ", # URL for the add-on documentation support diff --git a/readme.md b/readme.md index 2dca7a9..7307de1 100644 --- a/readme.md +++ b/readme.md @@ -1,6 +1,6 @@ # WorldVoice -WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2019.3 以上。 +WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2019.3 以上版本。 主要包括有多國語音自動切換、各別語音速度設定、朗讀行為客製(數字讀法、中文空格間隔)、自訂文字地區等功能。 @@ -11,7 +11,7 @@ WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2 * 核心包可透過 WorldVoice -> 檔案匯入將 zip 壓縮包匯入語音元件工作區。 * 語音包安裝方式 * 基本:使用兼容於 Vocalizer for NVDA 的語音包addon,[官方下載點](https://vocalizer-nvda.com/downloads)。 - * 進階:可透過各種語音包內直接複製其內的地區資料夾(ex: en, mnc, mnt)等並將其壓成 zip 壓縮包後透過 WorldVoice 介面的檔案匯入功能匯入addon內,與核心包相同需留意匯入之工作區,如無特殊需求建議使用 addon 版本安裝,因 addon 版本可共享同時提供第 1 驅動與第 2 驅動使用。 + * 進階:可透過各種語音包內直接複製其內的地區資料夾(ex: en, mnc, mnt)等並將其壓成 zip 壓縮包後透過 WorldVoice 介面的檔案匯入功能匯入 addon 內,如無特殊需求建議使用 addon 版本安裝,因當 WorldVoice 升級版本時 addon 版本語音包不會被刪除亦無需重新安裝。 ## 相依性套件 @@ -22,7 +22,9 @@ WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2 * NVDA+ctrl+S 選擇 WorldVoice 語音合成器。 * NVDA+ctrl+V 有基本語音速度、音調、音量等基本設定,其中數字模式、中文空白間隔為 WorldVoice 多的客製設定。 * 數字讀法:分為 2 個維度設定選項「數字語言」與「數字模式」,數字語言設定數字朗讀時使用的地區語音、數字模式分為數值與數字兩種 - * 中文空白間隔:可設定中文間有空白時,欲停頓長度,數字愈小停頓愈短, 0 為不停頓。 + * 「當遇到中文與中文間的空白時暫停長度」:可設定中文間有空白時,欲停頓長度,數字愈小停頓愈短, 0 為不停頓。 + * 「忽略在數字間的逗號」選項勾選時,可讓數字位數的逗號標錯位置仍能正常朗讀數值。 + * 「啟用 WorldVoice 設定規則來偵測文字語言」勾選時,會使用語音設定內的規則來偵測文字語言並切換語音朗讀。 * WorldVoice -> 語音設定:可設定不同地區所使用的語音角色、各別語音角色速度、音調、音量、自動語音切換設定。 * 先選擇地區後語音列表會列出該地區可用的語音角色,選擇後即完成該地區與語音角色的對應紀錄。 * 當語音角色有選擇時,下方速度、音調、音量滑桿會變為該語音角色的設定值。 @@ -80,3 +82,11 @@ WorldVoice 是依據 VE driver 為基礎開發而成的 addon。運行於 NVDA 2 * 將自動語言切換設定與語音設定視窗合併 * 地區與語音對應加入 no-select 用來取消對應 * 支援快速鍵彈出語音設定與 Unicode 設定 + +### v1.6 + +* 修正數字模式下小數點不朗讀問題 +* 更新 VE 核心包工作目錄,未來更新時可無需重新匯入 +* 將「使用 WorldVoice 設定規則針測語言」的開關與「自動切換語言」的開關分開,避免部份情境兩者不相容問題。 +* 修正啟用 unicode 自動語言針測時,預設語音與 NVDA 語言地區不相同但同語系時無法切換的問題 +* 修正自動切換語言無勾選時 WorldVoice 變更語音語言命令被濾掉的問題