0

Ich habe ein Android-Spiel, das die Libgdx-Game-Engine verwendet. Ich habe eine Android-Aktivität (mAndroidLauncher), die die AndroidApplication-Klasse von Libgdx erweitert. Es gibt eine Methode, die ein Android-Alarm-Dialog erstellt:Warum verursacht runOnUIhread immer noch looper.prepare() Fehlermeldung

mAndroidLauncher.runOnUiThread(new Runnable() { 
    @Override 
    public void run() { 
     AlertDialog.Builder builder = new AlertDialog.Builder(mAndroidLauncher.getContext()); 
     builder.setTitle("Notice"); 
     builder.setMessage("Alert!!!"); 
     builder.setNeutralButton("OK", new DialogInterface.OnClickListener() { 
      public void onClick(DialogInterface dialog, int which) { 
       //OK 
      } 
     }); 
     AlertDialog dialog = builder.create(); 
     dialog.show(); 
    } 
}); 

Ich habe einen Absturz in der Google Play Developer Console wie folgt:

java.lang.RuntimeException: Can't create handler inside thread that has not called Looper.prepare() 
at android.os.Handler.<init>(Handler.java:208) 
at android.os.Handler.<init>(Handler.java:122) 
at android.app.Dialog.<init>(Dialog.java:109) 
at android.app.AlertDialog.<init>(AlertDialog.java:114) 
at android.app.AlertDialog$Builder.create(AlertDialog.java:931) 
at com.google.android.gms.common.e.a(Unknown Source) 
at com.google.android.gms.common.e.a(Unknown Source) 
at com.my.game.l.a(Unknown Source) 
at com.my.game.l.g(Unknown Source) 
at com.my.game.l.c(Unknown Source) 
at com.my.game.a.b(Unknown Source) 
at com.my.game.b.f.a(Unknown Source) 
at com.my.game.q.b(Unknown Source) 
at com.badlogic.gdx.backends.android.i.onDrawFrame(Unknown Source) 
at android.opengl.GLSurfaceView$GLThread.guardedRun(GLSurfaceView.java:1557) 
at android.opengl.GLSurfaceView$GLThread.run(GLSurfaceView.java:1263) 

Dies ist der einzige Ort in meiner app, dass ich ein verwenden AlertDialog, deshalb bin ich zuversichtlich, dass dies die Methode ist, die den Absturz verursacht. Warum würde runOnUiThread diesen Fehler verursachen? Muss ich noch etwas tun, um sicherzustellen, dass der AlertDialog aus einem Thread mit einem Looper erstellt wird?

EDIT: Danke CommonsWare. Der Fehler kommt tatsächlich von den Google Play-Diensten. Insbesondere hatte ich einen Aufruf an gameHelper.beginUserInitiatedSignIn(), der nicht in runOnUiThread() eingeschlossen war. Obwohl seltsam war, dies nicht einen Fehler für alle Handys verursachen

+3

Der Code, den Sie nicht diese Stack-Trace erzeugen zeigte. "Dies ist der einzige Ort in meiner App, an dem ich einen AlertDialog verwende" - es ist nicht Ihr "AlertDialog". Es ist eines von Play Services. – CommonsWare

+0

Vielen Dank für Ihre Hilfe. Woher weißt du, dass es von Play Services stammt? Und wie/wo kann ich herausfinden, was den Fehler verursacht? – mrleeboze

+2

"Woher weißt du, dass es von Play Services stammt?" - weil der Absturz von 'com.google.android.gms.common.e.a()' kommt, und das ist Play Services. "Und wie/wo kann ich herausfinden, was den Fehler verursacht?" - Wenn Ihr Code in Ihrem Stack-Trace "com.my.game" ist, verwenden Sie ProGuard-Mapping-Dateien, um herauszufinden, wo "com.my.game.l.a()" steht. – CommonsWare

Antwort

0
new Handler(Looper.getMainLooper()).postDelayed(new Runnable() 
      { 
       @Override 
       public void run() 
       { 
        //Do something here 
        AlertDialog.Builder builder = new AlertDialog.Builder(mAndroidLauncher.getContext()); 
     builder.setTitle("Notice"); 
     builder.setMessage("Alert!!!"); 
     builder.setNeutralButton("OK", new DialogInterface.OnClickListener() { 
      public void onClick(DialogInterface dialog, int which) { 
       //OK 
      } 
     }); 
     AlertDialog dialog = builder.create(); 
     dialog.show(); 
       } 
      }, 0); 
0

kann man nicht nennen runOnUIThread() {} direkt Aktivitätsnamen wie statische Methode aufrufen ... deklarieren ein Objekt in mAndroidLauncher als

public static Activity acitivity = this; 

und rufen runOnUIThread als

mAndroidLauncher.activity.runOnUiThread(new Runnable() { 
    @Override 
    public void run() { 
     AlertDialog.Builder builder = new AlertDialog.Builder(mAndroidLauncher.getContext()); 
     builder.setTitle("Notice"); 
     builder.setMessage("Alert!!!"); 
     builder.setNeutralButton("OK", new DialogInterface.OnClickListener() { 
      public void onClick(DialogInterface dialog, int which) { 
       //OK 
      } 
     }); 
     AlertDialog dialog = builder.create(); 
     dialog.show(); 
    } 
}); 
Verwandte Themen