ProgressDialog: come impedire la window perdita

Sto utilizzando ProgressDialog per impedire all'utente di interagire mentre il dispositivo sta scaricando le cose da Internet.

tutto funzionava bene finché il mio cliente non riuscì a produrre questo bug:

  • Implementazione di AsyncQueryHandler
  • Come rimanere in una posizione di scorrimento in RecyclerView dopo aver aggiunto elementi al primo indice e chiamata notifydatasetchange
  • Sincronizzare tutto il ListView in un ViewPager
  • Come gestire il clic sulle viste del figlio e toccare nel ViewGroups genitore?
  • L'applicazione si blocca quando si ripristina da background dopo un lungo periodo di tempo
  • "I progetti della libreria Android non possono essere lanciati"?
  • "07-06 17:10:50.363: ERROR/WindowManager(8821): Activity android.pixelrain.framework.PixelRainActivity has leaked window com.android.internal.policy.impl.PhoneWindow$DecorView@463f3e50 that was originally added here 07-06 17:10:50.363: ERROR/WindowManager(8821): android.view.WindowLeaked: Activity android.pixelrain.framework.PixelRainActivity has leaked window com.android.internal.policy.impl.PhoneWindow$DecorView@463f3e50 that was originally added here 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.view.ViewRoot.<init>(ViewRoot.java:251) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:148) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:91) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.view.Window$LocalWindowManager.addView(Window.java:424) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.app.Dialog.show(Dialog.java:241) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.app.ProgressDialog.show(ProgressDialog.java:107) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.app.ProgressDialog.show(ProgressDialog.java:90) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.pixelrain.HTTPHelper.DraftHelper.getDraft(DraftHelper.java:70) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.pixelrain.online.OnlineRetriver.getDraft(OnlineRetriver.java:312) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.pixelrain.HTTPHelper.DraftButtonGL.loadDraft(DraftButtonGL.java:72) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.pixelrain.HTTPHelper.DraftButtonGL.isTouched(DraftButtonGL.java:89) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.pixelrain.opengl.views.game.QuickStartGL.touchEnded(QuickStartGL.java:160) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.pixelrain.game.GameHandler.onTouchEvent(GameHandler.java:277) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.pixelrain.opengl.GLSurfaceViewChipmunk.onTouchEvent(GLSurfaceViewChipmunk.java:27) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.view.View.dispatchTouchEvent(View.java:3765) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:944) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:944) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:944) 07-06 17:10:50.363: ERROR/WindowManager(8821): at com.android.internal.policy.impl.PhoneWindow$DecorView.superDispatchTouchEvent(PhoneWindow.java:1701) 07-06 17:10:50.363: ERROR/WindowManager(8821): at com.android.internal.policy.impl.PhoneWindow.superDispatchTouchEvent(PhoneWindow.java:1116) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.app.Activity.dispatchTouchEvent(Activity.java:2093) 07-06 17:10:50.363: ERROR/WindowManager(8821): at com.android.internal.policy.impl.PhoneWindow$DecorView.dispatchTouchEvent(PhoneWindow.java:1685) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.view.ViewRoot.handleMessage(ViewRoot.java:1802) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.os.Handler.dispatchMessage(Handler.java:99) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.os.Looper.loop(Looper.java:144) 07-06 17:10:50.363: ERROR/WindowManager(8821): at android.app.ActivityThread.main(ActivityThread.java:4937) 07-06 17:10:50.363: ERROR/WindowManager(8821): at java.lang.reflect.Method.invokeNative(Native Method) 07-06 17:10:50.363: ERROR/WindowManager(8821): at java.lang.reflect.Method.invoke(Method.java:521) 07-06 17:10:50.363: ERROR/WindowManager(8821): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:868) 07-06 17:10:50.363: ERROR/WindowManager(8821): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:626) 07-06 17:10:50.363: ERROR/WindowManager(8821): at dalvik.system.NativeStart.main(Native Method)" 

    e non ho idea di come risolvere questo problema.

    qualsiasi idea che cosa provoca questo e come risolverlo?

    Il log registra l'errore in questa row:

      progressDialog = ProgressDialog.show(PixelRainActivity.staticThis, "",PixelRainActivity.staticThis.getResources().getString( R.string.draftProgressMessage), true); 

    risolverebbe il problema se l'ho cambiato a questo:

     this.runOnUiThread(new Runnable() { public void run() { progressDialog = ProgressDialog.show(PixelRainActivity.staticThis, "",PixelRainActivity.staticThis.getResources().getString( R.string.draftProgressMessage), true); } }); 

  • Uscire dalla memory dopo l'aggiornamento di buildToolsVersion '23 .0.1 'in studio Android
  • Come installare il file .apk in emulatore?
  • Dove è debug.keystore in Android Studio
  • Come progettare un stream in cui uno degli schermi è uno schermo di accesso?
  • Cassetto di navigazione e stream master / dettaglio
  • Crea applicazione Android che agisce come un collegamento al nostro sito mobile
  • 9 Solutions collect form web for “ProgressDialog: come impedire la window perdita”

    La perdita viene probabilmente dall'attributo PixelRainActivity.staticThis . Se stai mantenendo un riferimento ad un'attività, anche dopo che questa attività è stata distrutta, hai una perdita di memory.

    Il modo più semplice per risolvere è quello di utilizzare il Context dell'applicazione invece. Modificare la tua staticThis = this row nel metodo onCreate() a staticThis = this.getApplicationContext() e dovrebbe funzionare (e cambiare il tipo di staticThis in Context se questo non è già il caso)

    Uso:

     progressDialog.dismiss(); 

    nel lavoro finale

    cygnus ha una buona idea usare showDialog (MY_INT), where MY_INT è solo un valore costante che si sceglie solo per distinguerlo da qualsiasi altra window di dialogo simile che lanciate in questo modo. Lo prendi allo stesso modo con dismissDialog (MY_INT). Proprio non lanciarlo dal tuo metodo onPause. Potresti voler farlo invece dal metodo onResume dell'attività che l'utente sta andando. Quindi si ignora il metodo onCreateDialog di questa attività:

     @Override protected Dialog onCreateDialog(int id) { if(id == MY_INT) { ProgressDialog progressDialog = new ProgressDialog(this); progressDialog.setMessage("Your message string"); return progressDialog; } return super.onCreateDialog(id); } 

    Invece di utilizzare ProgressDialog.show() , prova a utilizzare

    Activity.showDialog() che dovrebbe gestire automaticamente il Dialog per te e impedire perdite.

    EDIT: quando si chiama showDialog(int) , si attiverà Activity.onCreateDialog(int) where è ansible creare il Dialog desiderato e restituire il Dialog si desidera visualizzare.

    Mi sono imbattuto in un problema simile con una window di avanzamento e un task di background. L'AsyncTask ( http://android-developers.blogspot.de/2009/05/painless-threading.html ) mi ha permesso di fare sia molto più pulito e senza la window sfinita.

    È meglio utilizzare un AsyncTask per get qualcosa da Internet in background. E non c'è bisogno di passare però un context statico. E l'attività

     new YourAsyncTask(context).execute(); 

    Chiama AsyncTask come sopra

     private class YourAsynTask extends AsyncTask<String,Void,String> { private Context context; private ProgressDialog progressDialog; //pass context in constructor public YourAsynTask(Context context) { this.context = context; } //show progress in onPre @Override protected void onPreExecute() { //show Progress code here. progressDialog = ProgressDialog.show(context, "", "Loading. Please wait...", true); } //dismiss Progress dialog in onPost @Override protected void OnPostExecute(String response) { if(progressDialog!=null) progressDialog.dismiss(); progressDialog = null; } } 

    Se si utilizza qualsiasi thread o AsyncTask e si scarica la roba da Internet e mostra la progress bar , è necessario utilizzare DialogFragment o annullare la dialog avanzamento quando l' Activity viene arrestata anche se si sta mostrando il progresso in Asynctask pugno annulla Asynctask e sovrascrive il metodo di callback Asynctask e distriggers il dialogo di avanzamento Là.

    Window leak in Activity o fragment si verifica in realtà perché si sta tentando di aggiungere una window e mentre si presenta è in foreground , ma quando si preme la casa si arresta e viene arrestata tramite l' onStop (). Così il tuo CustomView rimane attaccato alla window che ora è scomparsa. Di conseguenza, secondo il sistema, il tuo customView occupato lo spazio che non è stato rilasciato.

    Ci sono situazioni in cui è necessario verificare in onDetach o in onDestroy se la window di avanzamento è ancora visibile. Così:

     @Override public void onDetach() { if (mProgressDialog != null && mProgressDialog.isShowing()) mProgressDialog.dismiss(); super.onDetach(); } 

    Prova a call progressDialog.dismiss() prima che l'attività venga uccisa. Ho avuto la mia fissa così.

    L'Android è un fan Android di Google, tutto su telefoni Android, Android Wear, Android Dev e applicazioni Android Games e così via.