安卓系统的语音转文字

15

我想创建一个具有语音转文字功能的应用程序。

我知道使用 RecognizerIntent 可以实现这种能力:http://android-developers.blogspot.com/search/label/Speech%20Input

然而,我不想弹出新的 Intent,在我的当前应用程序中进行分析,并且我不希望弹出提示,说明它正在尝试录制您的声音。

有人有最佳实践吗?我也许想尝试 Sphinx 4,但我不知道它是否能在 Android 上运行 - 有没有任何建议或经验?!

我想知道是否可以修改这里的代码,以便不显示 UI 或按钮,只进行处理:http://developer.android.com/resources/samples/ApiDemos/src/com/example/android/apis/app/VoiceRecognition.html

谢谢!


你是在询问是否需要在不调用UI的情况下使用语音记录器吗? - uncaught_exceptions
我想要把语音转换为文本,但不想触发典型的“现在说”界面 - 我希望它在我当前运行的应用程序的后台完成。 - RenegadeAndy
4个回答

21

如果你不想使用RecognizerIntent来进行语音识别,你仍然可以使用SpeechRecognizer类来实现。然而,使用该类比使用intent稍微棘手一些。最后,我强烈建议在记录用户时让用户知道,否则当他最终发现时可能会非常沮丧。

注:以下是受启发(但已更改)的一个小例子, SpeechRecognizer causes ANR... I need help with Android speech API

Intent intent = new Intent(RecognizerIntent.ACTION_RECOGNIZE_SPEECH);
intent.putExtra(RecognizerIntent.EXTRA_LANGUAGE_MODEL,
        RecognizerIntent.LANGUAGE_MODEL_FREE_FORM);
intent.putExtra(RecognizerIntent.EXTRA_CALLING_PACKAGE,
        "com.domain.app");

SpeechRecognizer recognizer = SpeechRecognizer
        .createSpeechRecognizer(this.getApplicationContext());
RecognitionListener listener = new RecognitionListener() {
    @Override
    public void onResults(Bundle results) {
        ArrayList<String> voiceResults = results
                .getStringArrayList(SpeechRecognizer.RESULTS_RECOGNITION);
        if (voiceResults == null) {
            System.out.println("No voice results");
        } else {
            System.out.println("Printing matches: ");
            for (String match : voiceResults) {
                System.out.println(match);
            }
        }
    }

    @Override
    public void onReadyForSpeech(Bundle params) {
        System.out.println("Ready for speech");
    }

    /**
     *  ERROR_NETWORK_TIMEOUT = 1;
     *  ERROR_NETWORK = 2;
     *  ERROR_AUDIO = 3;
     *  ERROR_SERVER = 4;
     *  ERROR_CLIENT = 5;
     *  ERROR_SPEECH_TIMEOUT = 6;
     *  ERROR_NO_MATCH = 7;
     *  ERROR_RECOGNIZER_BUSY = 8;
     *  ERROR_INSUFFICIENT_PERMISSIONS = 9;
     *
     * @param error code is defined in SpeechRecognizer
     */
    @Override
    public void onError(int error) {
        System.err.println("Error listening for speech: " + error);
    }

    @Override
    public void onBeginningOfSpeech() {
        System.out.println("Speech starting");
    }

    @Override
    public void onBufferReceived(byte[] buffer) {
        // TODO Auto-generated method stub

    }

    @Override
    public void onEndOfSpeech() {
        // TODO Auto-generated method stub

    }

    @Override
    public void onEvent(int eventType, Bundle params) {
        // TODO Auto-generated method stub

    }

    @Override
    public void onPartialResults(Bundle partialResults) {
        // TODO Auto-generated method stub

    }

    @Override
    public void onRmsChanged(float rmsdB) {
        // TODO Auto-generated method stub

    }
};
recognizer.setRecognitionListener(listener);
recognizer.startListening(intent);

重要提示:请在 UI 线程中运行此代码,并确保您拥有所需的权限。

<uses-permission android:name="android.permission.RECORD_AUDIO" />

嘿 - 是的,他们会知道 - 这将成为游戏的一部分,所以很明显他们会想在那些特定的点上说话。语音识别器类可能是我想要使用的 - 但我很想有一个它的使用示例?有吗? - RenegadeAndy
1
我添加了一个小例子。这个例子可以在我的测试项目的onCreate()方法中运行良好。不要忘记获取适当的权限(RECORD_AUDIO)。 - Stephan
太棒了 - 在我的模拟器上运行返回:05-06 20:19:38.527: ERROR/SpeechRecognizer(1745): 没有选择语音识别服务。 - RenegadeAndy
你可能需要安装谷歌语音搜索应用程序才能运行来自谷歌的任何语音识别。不知道模拟器上是否可行。在我的Nexus上它运行得很好。 - Stephan
是的,从我的手机上运行得很好 - 但是为了方便使用,我想使用模拟器进行开发。我想这意味着我可能需要在另一个问题上询问... - RenegadeAndy
这在Android 11中不起作用,要使其起作用,只需在manifest.xml文件中添加此查询 <queries> <intent> <action android:name="android.speech.RecognitionService" /> </intent> </queries> - syed dastagir

6
在您的活动中,请执行以下操作:
Image button buttonSpeak = findView....;// initialize it.
buttonSpeak.setOnClickListener(new View.OnClickListener() {

        @Override
        public void onClick(View v) {
            promptSpeechInput();
        }
    });



private void promptSpeechInput() {
    Intent intent = new Intent(RecognizerIntent.ACTION_RECOGNIZE_SPEECH);
    intent.putExtra(RecognizerIntent.EXTRA_LANGUAGE_MODEL,
            RecognizerIntent.LANGUAGE_MODEL_FREE_FORM);
    intent.putExtra(RecognizerIntent.EXTRA_LANGUAGE, Locale.getDefault());
    intent.putExtra(RecognizerIntent.EXTRA_PROMPT,
            getString(R.string.speech_prompt));
    try {
        startActivityForResult(intent, REQ_CODE_SPEECH_INPUT);
    } catch (ActivityNotFoundException a) {
        Toast.makeText(getApplicationContext(),
                getString(R.string.speech_not_supported),
                Toast.LENGTH_SHORT).show();
    }
}

    @Override
   protected void onActivityResult(int requestCode, int resultCode, Intent 
     data) {
    super.onActivityResult(requestCode, resultCode, data);

    switch (requestCode) {
        case REQ_CODE_SPEECH_INPUT: {
            if (resultCode == RESULT_OK && null != data) {

                result = data
                        .getStringArrayListExtra(RecognizerIntent.EXTRA_RESULTS);

      EditText input ((EditText)findViewById(R.id.editTextTaskDescription));
      input.setText(result.get(0)); // set the input data to the editText alongside if want to.

            }
            break;
        }

    }
}

1
这会打开谷歌的默认识别UI对话框活动,但OP不想显示它。 - Fredrick Gauss

4
Android内置了一个客户端活动,可以通过意图启动,捕获您的语音并将音频发送到Google服务器进行识别。您可以构建类似的东西。您可以自己托管sphinx(或使用云识别服务,如Yapme.com),自己捕获声音,将音频发送到识别器,并将文本结果返回给您的应用程序。我不知道是否有方法在Android上利用Google识别服务而不使用Intent(或通过Chrome)。
到目前为止,我看到的普遍共识是,今天的智能手机实际上没有足够的计算能力来进行类似Sphinx的语音识别。您可能需要探索自己运行客户端识别器,但Google使用服务器识别。
有关一些相关信息,请参见:
- Google的语音搜索语音识别服务 - 是否可能在Android项目之外使用Android API? - 语音识别API

0

将权限添加到MANIFEST文件中:

"android.permission.RECORD_AUDIO"

当按钮被点击时调用getSpeechInput()函数(使用监听器)

public void getSpeechInput() {

    Intent intent = new Intent(RecognizerIntent.ACTION_RECOGNIZE_SPEECH);
    intent.putExtra(RecognizerIntent.EXTRA_LANGUAGE_MODEL, RecognizerIntent.LANGUAGE_MODEL_FREE_FORM);
    intent.putExtra(RecognizerIntent.EXTRA_LANGUAGE, Locale.getDefault());

    if (intent.resolveActivity(getPackageManager()) != null) {
        startActivityForResult(intent, 10);
    } else {
        Toast.makeText(this, "Your Device Don't Support Speech Input", Toast.LENGTH_SHORT).show();
    }
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    super.onActivityResult(requestCode, resultCode, data);

    switch (requestCode) {
        case 10:
            if (resultCode == RESULT_OK && data != null) {
                ArrayList<String> result = data.getStringArrayListExtra(RecognizerIntent.EXTRA_RESULTS);
                Toast.makeText(this, result.get(0), Toast.LENGTH_SHORT).show();

            }
            break;
    }
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接