12

编辑:我应该已经提到了这一点,但我正在服务中运行此代码。整个应用程序由一个小部件按钮打开/关闭,并且没有任何活动。


更新:我尝试将 SDK 源附加到项目中,以便更准确地了解故障发生的位置,但从外观上看,仅包含公共 API,这似乎使它们不太有用。 . 任何人都可以建议至少一种调试方法来解决这个问题吗?我有点卡住了。


我正在尝试使用 Android 的语音识别包来记录用户语音并将其翻译成文本。不幸的是,当我尝试开始收听时,我收到了一个 ANR 错误,它没有指向任何特定的内容。

正如 SpeechRecognizer API 所指出的,如果您尝试从主线程调用它,则会引发 RuntimeException。这会让我想知道处理是否过于苛刻......但我知道其他应用程序为此目的使用 Android API,而且它通常非常活泼。

java.lang.RuntimeException: SpeechRecognizer should be used only from the application's main thread

这是我试图从我的服务中调用的代码的(修剪)示例。这是正确的方法吗?

感谢您花时间提供帮助。这一直是我无法克服的障碍。

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(RecognizerIntent.EXTRA_RESULTS);
        if (voiceResults == null) {
            Log.e(getString(R.string.log_label), "No voice results");
        } else {
            Log.d(getString(R.string.log_label), "Printing matches: ");
            for (String match : voiceResults) {
                Log.d(getString(R.string.log_label), match);
            }
        }
    }

    @Override
    public void onReadyForSpeech(Bundle params) {
        Log.d(getString(R.string.log_label), "Ready for speech");
    }

    @Override
    public void onError(int error) {
        Log.d(getString(R.string.log_label),
                "Error listening for speech: " + error);
    }

    @Override
    public void onBeginningOfSpeech() {
        Log.d(getString(R.string.log_label), "Speech starting");
    }
};
recognizer.setRecognitionListener(listener);
recognizer.startListening(intent);
4

6 回答 6

5

确保使用 RECORD_AUDIO 权限。

于 2011-12-29T20:23:19.190 回答
4

从服务中,您必须从在主线程上运行的 looper 创建识别器。此外,RecognizerIntent.EXTRA_RESULTS 应该是 SpeechRecognizer.RESULTS_RECOGNITION。

伪代码:

public class VoiceRecognition implements RecognitionListener, Runnable 
{
    @Override
    public void run()
    {
        recognizer = SpeechRecognizer.createSpeechRecognizer(yourContext);
        recognizer.setRecognitionListener((RecognitionListener) this);

         intent = new Intent(RecognizerIntent.ACTION_RECOGNIZE_SPEECH);
         //... all the intent stuff ...
         intent.putExtra(RecognizerIntent.EXTRA_MAX_RESULTS, 5);
         recognizer.startListening(intent);
    }
    @Override
    public void onResults(Bundle results)
    {
       ArrayList<String> matches;
       matches=results.getStringArrayList(SpeechRecognizer.RESULTS_RECOGNITION);
    }
 }

....
VoiceRecognition voiceRecognizer = new VoiceRecognition();
Handler loopHandler = new Handler(Looper.getMainLooper());
loopHandler.post(voiceRecognizer);
于 2012-04-17T02:48:16.560 回答
4

您不需要自己创建 SpeechRecognizer 类,也不需要实现 RecognizerListener。谷歌公开它们是为了很好,但它们看起来很复杂,可能仅供专家使用。

要从用户语音中获取文本,您只需使用 RecognizerIntent.ACTION_RECOGNIZE_SPEECH 启动内置语音识别器 Activity,然后在 onActivityResult 中等待结果返回。看看这里的示例代码:

http://developer.android.com/resources/samples/ApiDemos/src/com/example/android/apis/app/VoiceRecognition.html

我从这篇文章中提取了它。

http://developer.android.com/resources/articles/speech-input.html

祝你好运。

于 2011-01-03T00:51:37.523 回答
1

这是我遇到的问题,可能与您的问题有关。无论如何,从这一行我得到了空值:

  ArrayList<String> voiceResults = results                .getStringArrayList(RecognizerIntent.EXTRA_RESULTS);  

将其更改为此完全解决了问题:

  ArrayList<String> voiceResults = results                .getStringArrayList("results_recognition");  

我从捆绑包中打印出密钥集,这是唯一的值。请注意,“results_recognition”的值不是存储在 RecognizerIntent.EXTRA_RESULTS 中的字符串的值。我认为这是一个错误,或者至少应该是,因为使用 RecognizerIntent.EXTRA_RESULTS 在进行语音识别的 Activity 方式中可以正常工作,但在有人使用 SpeechRecognizer 时就不行。

无论如何,我很可能不会再查看这个网站,但是如果您有任何问题,请给我发电子邮件,因为我现在确实可以在没有任何提示、哔声或其他任何东西的情况下进行语音识别。

于 2011-04-13T22:17:28.750 回答
1

我通过安装 Google Voice 应用程序让它工作

于 2011-05-06T07:41:51.623 回答
1

而不是getApplicationContext(),使用this(即您的服务实例)。android.app.Service继承自上下文。

于 2011-01-06T20:41:00.777 回答