【问题标题】:How to speed up the initialization of Text to speech如何加快文本到语音的初始化
【发布时间】:2015-05-14 17:07:18
【问题描述】:

我正在开发一个应用程序,该应用程序需要使用 Text to Speech 类才能阅读文本。问题是初始化非常慢,大约 4 秒。我遵循了本教程:http://code.tutsplus.com/tutorials/use-text-to-speech-on-android-to-read-out-incoming-messages--cms-22524。我做了一些研究,但没有找到真正好的答案,或者我想念它们。

例如,我通过在线程中调用我的 checkTTS 函数尝试了这个solution,但没有可见的结果。 Herehere,他们说我有意图的 checkTTS 函数可能不是那么有用,我可以看看我需要的语言是否可用。

所以我的问题:

  • 我真的可以只检查我的语言是否存在吗?ACTION_CHECK_TTS_DATA 和只检查语言是否可用之间真正的大区别是什么?
  • 我可以改进其他方面吗?

这是我的活动代码:

public class MyActivity extends Activity {
    private Speaker _speaker;
    private final int CHECK_CODE = 0x1;
    private final int SHORT_DURATION = 1000;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        System.out.println("I'm just before checkTTS");
        checkTTS();
    }


    private void checkTTS(){
        System.out.println("I'm in checkTTS");
        Intent check = new Intent();
        check.setAction(TextToSpeech.Engine.ACTION_CHECK_TTS_DATA);
        startActivityForResult(check, CHECK_CODE);
    }

    @Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        if(requestCode == CHECK_CODE){
            if(resultCode == TextToSpeech.Engine.CHECK_VOICE_DATA_PASS){
                System.out.println("I'm in onActivityResult");
                _speaker = new Speaker(this);
            }else {
                Intent install = new Intent();
                install.setAction(TextToSpeech.Engine.ACTION_INSTALL_TTS_DATA);
                startActivity(install);
            }
        }
    }

    @Override
    protected void onDestroy() {    
        super.onDestroy();
        _speaker.destroy();
    }
}

这是我的演讲者课程:

public class Speaker implements OnInitListener {
    private TextToSpeech _tts;
    private boolean _ready = false;
    private boolean _allowed = false;

    public Speaker(Context context){
        _tts = new TextToSpeech(context, this);
    }   

    public void setSpeedRate(float speechrate) {
        _tts.setSpeechRate(speechrate);
    }

    public boolean isAllowed(){
        return _allowed;
    }

    public void allow(boolean allowed){
        _allowed = allowed;
    }

    @Override
    public void onInit(int status) {
        System.out.println("I'm in onInit from Speaker");
        if(status == TextToSpeech.SUCCESS){
            _tts.setLanguage(Locale.UK);
            _ready = true;
        } else{
            _ready = false;
        }
    }

    public void speak(String text){
        if(_ready && _allowed) {
            HashMap<String, String> hash = new HashMap<String,String>();
            hash.put(TextToSpeech.Engine.KEY_PARAM_STREAM, String.valueOf(AudioManager.STREAM_NOTIFICATION));
            _tts.speak(text, TextToSpeech.QUEUE_ADD, hash);
        }
    }

    public boolean isSpeaking() {
        return _tts.isSpeaking();
    }

    public void pause(int duration){
        _tts.playSilence(duration, TextToSpeech.QUEUE_ADD, null);
    }

    public void stop() {
        _tts.stop();
    }

    public void destroy(){
        _tts.shutdown();
    }
}

这是来自 eclipse 的日志:

15:14:58.897: D/dalvikvm(23966): GC_CONCURRENT freed ...
15:15:00.014: I/System.out(23966): I'm just before checkTTS
15:15:00.014: I/System.out(23966): I'm in checkTTS
15:15:00.046: D/AbsListView(23966): unregisterIRListener() is called 
15-13 15:15:01.272: I/System.out(23966): I'm in onActivityResult
15:15:01.311: I/TextToSpeech(23966): Sucessfully bound to com.samsung.SMT
15:15:01.663: D/AbsListView(23966): onVisibilityChanged() is called, visibility : 4
15:15:01.663: D/AbsListView(23966): unregisterIRListener() is called 
15:15:02.600: I/TextToSpeech(23966): Connected to ComponentInfo{com.samsung.SMT/...}
15:15:02.608: I/TextToSpeech(23966): onServiceConnected but waiting
15:15:02.608: I/System.out(23966): I'm in onInit from Speaker
15:15:02.616: I/System.out(23966): Speaker ready
15:15:02.616: I/TextToSpeech(23966): onServiceConnected waiting end

感谢您的帮助, 此致, Zed13

Ps : 对错误深表歉意...

编辑:有趣的事实,三星语音启动速度似乎比谷歌语音更快...

【问题讨论】:

  • 它在三星语音上运行速度更快的原因是三星手机默认使用三星 TTSEngine,它没有像谷歌 TTS 引擎那样的初始化滞后。说到这里,您找到解决问题的方法了吗?

标签: java android performance initialization text-to-speech


【解决方案1】:
  1. 根据Android API,ACTION_CHECK_TTS_DATA“从平台 TextToSpeech 引擎启动活动,以验证系统上资源文件的正确安装和可用性”。在这种情况下,在收到 CHECK_VOICE_DATA_PASS 之前创建 TTS 实例是没有意义的。或者,如果出于某种原因(状态标志等)您确信系统已安装所需的 TTS 资源,您可以使用“乐观的方法”,即跳过此步骤,初始化 TTS 实例(例如,在您的onCreate 方法)并在检查available languagesif some language is supported 之后。由于您正在跳过一个步骤(ACTION_CHECK_TTS_DATA),如果一切顺利,您的初始化将会更快。

您可以检查系统 looking to this code 中安装的引擎,并使用该信息来启动更准确的 ACTION_CHECK_TTS_DATA 意图。

  1. 从性能的角度来看,其余代码看起来不错。但是,请记住,您可以同时启动 ACTION_CHECK_TTS_DATA 意图并初始化 TTS 实例!如果缺少某些内容,则 Intent 已经启动,并且 TTS 将无法按预期工作。如果设备拥有所有 TTS 资源,则 Intent 将通过并且 TTS 已初始化。您可以查看 Audio News app 作为此行为的示例;)

【讨论】:

  • 我做了修改,我赢了 2 秒。所以现在我的问题是,认为 TTS 将安装在 android 4.0 或更高版本的智能手机上是否乐观?在我的 Galaxy S3、Galaxy Tab 2 和 xperia 上都可以。
  • 如果您查看somehow old post,“虽然所有支持 TTS 功能的 Android 设备都附带引擎,但某些设备的存储空间有限,并且可能缺少特定于语言的资源文件。如果用户想要安装这些资源,TTS API 使应用程序能够查询平台语言文件的可用性,并可以启动它们的下载和安装。因此,在创建活动时,一个好的第一步是检查是否存在TTS 资源”。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-08-13
  • 1970-01-01
  • 2017-06-20
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多