在Android上使用TTS:大声朗读标点符号

问题描述 投票:7回答:2

背景:我的应用程序正在向用户拥有的任何TTS引擎发送句子。句子是用户生成的,可能包含标点符号。

问题:Some users report that在SVOX,Loquendo和其他人可能会大声朗读标点符号(TTS说“逗号”等)。

题:

  1. 我应该删除所有标点符号吗?
  2. 我应该使用this kind of API转换标点符号吗?
  3. 我应该让TTS引擎处理标点符号吗?

看到Loquendo问题的同一用户,对于另一个名为FBReader的Android应用程序没有这个问题。所以我猜第三种选择不是正确的做法。

android text-to-speech
2个回答
2
投票

我的一个应用程序遇到了同样的问题。

输入字符串是:

Next alarm in 10 minutes,it will be 2:45 pm

并且TTS引擎会说:

Next alarm in 10 minutes comma it will be 2:45 pm

只需在逗号之后添加一个空格就可以修复问题:

Next alarm in 10 minutes, it will be 2:45 pm

这是一个愚蠢的错误,也许你的问题比这更复杂,但它对我有用。 :)


2
投票

所以,你担心用户可能会选择作为默认值的后巷获取的文本到语音引擎......可能是因为你不希望你的应用看起来很糟糕,因为这个引擎未知/不良行为。可以理解的。

(好的)事实是,除非您决定在应用程序中嵌入引擎,否则TTS的行为实际上不是您的责任(难度:难,推荐?否)。

引擎可以而且应该被认为遵守Android规则和行为规定here ...并且假定在Android系统设置(home \ settings \ language&locale \ TTS)中提供他们自己的足够的配置选项,其中可能包括或不包括发音选项。还应该假定用户足够智能以安装他们满意的引擎。

对于预测和“纠正”未知和不需要的引擎行为(至少在您没有自己测试的引擎中)来说,这是一个滑坡。

一个简单而好的选择(难度:容易):

  • 在您的应用中进行设置:“忽略标点符号。”

更好的选择(难度:中等):

  • 如果您在用户设备上检测到的引擎容易出现此问题,请执行上述操作,但仅显示“忽略标点符号”设置选项。

此外,需要注意的一点是,引擎之间存在许多差异(无论是使用嵌入式语音与在线,响应时间,初始化时间,对Android规范的可靠性/依从性,跨Android API级别的行为,跨自己版本历史记录的行为)声音的质量,更不用说语言能力了......对于用户而言,与标点符号是否发音相比,这些差异可能更为重要。

你说“我的应用程序正在向用户提供的任何TTS引擎发送句子”。嗯......“那就是你的问题。”为什么不让用户选择使用什么引擎?

并引导我们......

一个更好的选择(难度:艰难和好![以我的拙见]):

  • 从谷歌和三星开始,确定你的应用程序将“支持”的一些“已知良好”引擎。我猜想现在有不到5%的设备没有这些引擎。
  • 在您计划支持的所有Android API级别上尽可能多地研究和测试这些引擎......至少在他们是否发出标点符号的情况下。
  • 随着时间的推移,如果您愿意,可以测试更多引擎,并在后续应用更新中将它们添加到支持的引擎。
  • 在应用程序启动时运行算法,检测安装了哪些引擎,然后将该信息用于您自己的受支持引擎列表:

private ArrayList<String> whatEnginesAreInstalled(Context context) {
    final Intent ttsIntent = new Intent();
    ttsIntent.setAction(TextToSpeech.Engine.ACTION_CHECK_TTS_DATA);
    final PackageManager pm = context.getPackageManager();
    final List<ResolveInfo> list = pm.queryIntentActivities(ttsIntent, PackageManager.GET_META_DATA);
    ArrayList<String> installedEngineNames = new ArrayList<>();
    for (ResolveInfo r : list) {
        String engineName = r.activityInfo.applicationInfo.packageName;
        installedEngineNames.add(engineName);

        // just logging the version number out of interest
        String version = "null";
        try {
            version = pm.getPackageInfo(engineName,
            PackageManager.GET_META_DATA).versionName;
            } catch (Exception e) {
                Log.i("XXX", "try catch error");
            }
        Log.i("XXX", "we found an engine: " + engineName);
        Log.i("XXX", "version: " + version);
    }
    return installedEngineNames;
}

  • 在您的应用程序设置中,显示您决定支持的所有引擎作为选项(即使当前未安装)。这可以是一组简单的RadioButtons,其标题对应于不同的引擎名称。如果用户选择了一个未安装的用户,请通知他们并为他们提供安装意图的选项。
  • 在SharedPreferences中保存用户选择的引擎名称(String),并在您的应用程序中需要TTS时将其选择用作TextToSpeech构造函数的最后一个参数。
  • 如果用户安装了一些奇怪的引擎,即使它无法识别/不支持,也将其作为选项提供,但告知他们已选择未知/未测试的引擎。
  • 如果用户选择了支持但已知发音标点符号(坏)的引擎,那么在选择该引擎时,会弹出一个警告对话框,警告用户,并说明他们可以通过“忽略标点符号“已经提到的设置。

SIDE-NOTES:

  • 不要让SVOX / PICO(模拟器)引擎让你太担心 - 它有很多缺陷,甚至没有设计或保证在Android上运行API~20以上,但仍然包含在模拟器映像中,最高可达API~24 ,导致“不可预测的结果”,实际上并没有反映现实。我还没有在过去七年左右的任何真实硬件设备上看到这个引擎。
  • 既然你说“句子是用户生成的”,我会更担心解决他们打算输入什么语言的问题!我会留意这个问题! :)
© www.soinside.com 2019 - 2024. All rights reserved.