无法在未调用Looper.prepare()的线程中创建处理程序 - Google翻译

问题描述:

您好我正尝试使用谷歌翻译api来翻译字符串,当我点击按钮中的翻译。当我作为AVD运行时,它工作正常,问题是当我尝试使用智能手机进行部署时,单击翻译按钮时应用程序关闭,出现错误。无法在未调用Looper.prepare()的线程中创建处理程序 - Google翻译

Bundle bundle = getIntent().getExtras(); 
    String word = ""; 
    if(bundle.containsKey("Name")){ 
     word = (String) bundle.getString("Name"); 
     txtTarget.setText(word); 
     //envia para o translate api para traduzir a palavra pro portugues 
    } 

    final String finalWord = word; 
    btnResultado.setOnClickListener(new View.OnClickListener() { 
     public void onClick(View v) { 

      final Handler textViewHandler = new Handler(); 

      new AsyncTask<Void, Void, Void>() { 
       @Override 
       protected Void doInBackground(Void... params) { 

        Translate translate = TranslateOptions.newBuilder().setApiKey(API_KEY).build().getService(); 

        final Translation translation = translate.translate(finalWord, Translate.TranslateOption.targetLanguage("pt")); 

        textViewHandler.post(new Runnable() { 
         @Override 
         public void run() { 
          txtSource.setText(translation.getTranslatedText()); 
         } 
        }); 
        return null; 
       } 
      }.execute(); 
     } 
    }); 

错误:

Process: com.google.sample.cloudvision, PID: 8874 java.lang.RuntimeException: An error occurred while executing doInBackground() at android.os.AsyncTask$3.done(AsyncTask.java:309) at java.util.concurrent.FutureTask.finishCompletion(FutureTask.java:354) at java.util.concurrent.FutureTask.setException(FutureTask.java:223) at java.util.concurrent.FutureTask.run(FutureTask.java:242) at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:234) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1113) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:588) at java.lang.Thread.run(Thread.java:818) Caused by: java.lang.RuntimeException: Can't create handler inside thread that has not called Looper.prepare() at android.os.Handler.(Handler.java:200) at android.os.Handler.(Handler.java:114) at android.widget.Toast$TN.(Toast.java:345) at android.widget.Toast.(Toast.java:101) at android.widget.Toast.makeText(Toast.java:259) at com.google.sample.cloudvision.ActSegundaTela$1$1$1.doInBackground(ActSegundaTela.java:82) at com.google.sample.cloudvision.ActSegundaTela$1$1$1.doInBackground(ActSegundaTela.java:79) at android.os.AsyncTask$2.call(AsyncTask.java:295) at java.util.concurrent.FutureTask.run(FutureTask.java:237) at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:234) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1113) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:588) at java.lang.Thread.run(Thread.java:818)

你并不需要创建一个新的处理程序。您可以将任何视图用作处理程序。

txtSource.post(new Runnable() { 
    public void run(){ 
     txtSource.setText(... 
    } 
}); 

如果你真的想创建一个处理程序,然后在错误消息中提到,调用Looper.prepare();doInBackgroundLooper.loop()在上线的第一道防线。

doInBackground(){ 
    Looper.prepare(); 
    //your code 
    Lopper.loop(); 
} 

如果你的代码是一个活动里面还是有活动的参考,你可以直接做使用方法runOnUiThread

不知道哪一行是特别是在UI线程的东西,但是从Exception,看起来您的doInBackground()方法中的一种方法试图显示Toast。试图从后台线程显示View是一个禁忌,这是导致崩溃的原因。

您可以将块包装在try { } catch(Exception e) { ... }中以标识试图显示Toast的行 - 因为该块应该可能会从后台线程中拉出以防止Exception

+0

有没有真正的需要进一步调试,这是尝试在另一个线程上执行UI操作的经典结果。 –

+0

我用吐司来检查我的代码在哪里,我忘记清理并再次部署,但是用吐司我强调它运行到这一行为止“新的AsyncTask (){”并停止 – brunocdias