java.lang.IllegalArgumentException: vue non attachée au gestionnaire de fenêtres

148

J'ai une activité qui démarre AsyncTask et affiche une boîte de dialogue de progression pour la durée de l'opération. L'activité est déclarée ne pas être recréée par rotation ou par glissement du clavier.

    <activity android:name=".MyActivity" 
              android:label="@string/app_name"
              android:configChanges="keyboardHidden|orientation"
              >
        <intent-filter>
        </intent-filter>
    </activity>

Une fois la tâche terminée, je dissipe le dialogue, mais sur certains téléphones (framework: 1.5, 1.6), une telle erreur est générée:

java.lang.IllegalArgumentException: View not attached to window manager
    at android.view.WindowManagerImpl.findViewLocked(WindowManagerImpl.java:356)
    at android.view.WindowManagerImpl.removeView(WindowManagerImpl.java:201)
    at android.view.Window$LocalWindowManager.removeView(Window.java:400)
    at android.app.Dialog.dismissDialog(Dialog.java:268)
    at android.app.Dialog.access$000(Dialog.java:69)
    at android.app.Dialog$1.run(Dialog.java:103)
    at android.app.Dialog.dismiss(Dialog.java:252)
    at xxx.onPostExecute(xxx$1.java:xxx)

Mon code est:

final Dialog dialog = new AlertDialog.Builder(context)
    .setTitle("Processing...")
    .setCancelable(true)
    .create();

final AsyncTask<MyParams, Object, MyResult> task = new AsyncTask<MyParams, Object, MyResult>() {

    @Override
    protected MyResult doInBackground(MyParams... params) {
        // Long operation goes here
    }

    @Override
    protected void onPostExecute(MyResult result) {
        dialog.dismiss();
        onCompletion(result);
    }
};

task.execute(...);

dialog.setOnCancelListener(new OnCancelListener() {
    @Override
    public void onCancel(DialogInterface arg0) {
        task.cancel(false);
    }
});

dialog.show();

D'après ce que j'ai lu ( http://bend-ing.blogspot.com/2008/11/properly-handle-progress-dialog-in.html ) et vu dans les sources Android, il semble que la seule situation possible pour l'obtenir l'exception est lorsque l'activité a été détruite. Mais comme je l'ai mentionné, j'interdis les activités récréatives pour les événements de base.

Donc, toutes les suggestions sont très appréciées.

alex2k8
la source
1
Cette question a reçu beaucoup de réponses, si l'une d'entre elles vous a aidé, veuillez la sélectionner comme bonne réponse.
Parag Kadam du

Réponses:

228

Moi aussi , je reçois cette erreur parfois quand je rejette le dialogue et l' activité de finition de méthode onPostExecute. Je suppose que parfois l'activité se termine avant que le dialogue ne se termine avec succès.

Solution simple mais efficace qui fonctionne pour moi

@Override
protected void onPostExecute(MyResult result) {
    try {
        if ((this.mDialog != null) && this.mDialog.isShowing()) {
            this.mDialog.dismiss();
        }
    } catch (final IllegalArgumentException e) {
        // Handle or log or ignore
    } catch (final Exception e) {
        // Handle or log or ignore
    } finally {
        this.mDialog = null;
    }  
}
Damjan
la source
44
Solution simple? Oui. Efficace? Peut-être dans ce cas. Le recommanderais-je? NON! N'avalez pas TOUTES les exceptions comme ça! Je n'attraperais même pas l'exception IllegalArgumentException, mais chercherais une autre solution.
Simon Forsberg
6
Parce que les tentatives d'essais vides sont généralement une mauvaise idée ... Bien que cela puisse parfois être la bonne chose à faire.
Thomas
3
@Damjan Par votre réponse, vous suggérez une exception de type catch. Eh bien, c'est une mauvaise pratique de Google. Vous pouvez en savoir plus ici: Ne pas attraper une exception générique .
Yaniv
17
Je pense que c'est une solution efficace. Dans les cas généraux, nous ne devrions pas le faire, mais comme le Framework Android ne nous fournit pas de vérification facile, nous devons utiliser une méthode inhabituelle. De plus, si l'appel isShowing () d'une boîte de dialogue fonctionne comme prévu, nous n'avons pas besoin de ce type de piratage.
SXC
1
solution rapide jusqu'à ce que quelque chose de mieux soit trouvé
Rohit Tigga
13

Voici ma solution "bullet proof", qui est la compilation de toutes les bonnes réponses que j'ai trouvées sur ce sujet (merci à @Damjan et @Kachi). Ici, l'exception n'est acceptée que si toutes les autres méthodes de détection n'ont pas réussi. Dans mon cas, je dois fermer la boîte de dialogue automatiquement et c'est le seul moyen de protéger l'application contre les plantages. J'espère que cela vous aidera! S'il vous plaît, votez et laissez des commentaires si vous avez des remarques ou une meilleure solution. Je vous remercie!

public void dismissWithCheck(Dialog dialog) {
        if (dialog != null) {
            if (dialog.isShowing()) {

                //get the Context object that was used to great the dialog
                Context context = ((ContextWrapper) dialog.getContext()).getBaseContext();

                // if the Context used here was an activity AND it hasn't been finished or destroyed
                // then dismiss it
                if (context instanceof Activity) {

                    // Api >=17
                    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
                        if (!((Activity) context).isFinishing() && !((Activity) context).isDestroyed()) {
                            dismissWithTryCatch(dialog);
                        }
                    } else {

                        // Api < 17. Unfortunately cannot check for isDestroyed()
                        if (!((Activity) context).isFinishing()) {
                            dismissWithTryCatch(dialog);
                        }
                    }
                } else
                    // if the Context used wasn't an Activity, then dismiss it too
                    dismissWithTryCatch(dialog);
            }
            dialog = null;
        }
    }

    public void dismissWithTryCatch(Dialog dialog) {
        try {
            dialog.dismiss();
        } catch (final IllegalArgumentException e) {
            // Do nothing.
        } catch (final Exception e) {
            // Do nothing.
        } finally {
            dialog = null;
        }
    }
Ivo Stoyanov
la source
1
très bonne solution! Le réglage dialog = nulln'a aucun effet. Et StatusEventDialogdevrait lire juste Dialog.
hgoebl
1
StatusEventDialog doit être remplacé par dialog.
Sreekanth Karumanaghat
Cette réponse devrait être acceptée, très bien gérée
blueware
Je comprends que vous voulez être "correct" et n'utiliser try / catch que si ce isDestroyed()n'est pas disponible, mais pour des raisons pratiques, ne serait-il pas toujours la même chose d'utiliser le try / catch?
zundi
11

J'ai peut-être une solution de contournement.

Avait le même problème, où je charge beaucoup d'éléments (via le système de fichiers) dans un ListViewvia un fichier AsyncTask. Avait le onPreExecute()déclenchement d'un ProgressDialog, puis les deux onPostExecute()et onCancelled()(appelé lorsque la tâche est annulée explicitement via AsyncTask.cancel()) en le fermant via .cancel().

J'ai eu la même erreur "java.lang.IllegalArgumentException: View not attach to window manager" lorsque je tuais la boîte de dialogue dans la onCancelled()méthode du AsyncTask(j'avais vu cela fait dans l'excellente application Shelves ).

La solution de contournement consistait à créer un champ public dans le AsyncTaskqui contient le ProgressDialog:

public ProgressDialog mDialog;

Ensuite, onDestroy()lorsque j'annule mon AsyncTask, je peux également supprimer la boîte de dialogue associée via:

AsyncTask.mDialog.cancel();

L'appel du AsyncTask.cancel()déclencheur DOES onCancelled()dans le AsyncTask, mais pour une raison quelconque au moment où cette méthode est appelée, la vue a déjà été détruite et l'annulation de la boîte de dialogue échoue.

Paul Mennega
la source
Je trouve l'implémentation UserTask tout simplement excellente, comme l'a mentionné @Paul. Le code source est ici: code.google.com/p/shelves/source/browse/trunk/Shelves/src/org/…
Evi Song
Bien que le cas d'utilisation puisse être trouvé dans le même projet: code.google.com/p/shelves/source/browse/trunk/Shelves/src/org/…
Evi Song
9

Voici la bonne solution pour résoudre ce problème:

public void hideProgress() {
    if(mProgressDialog != null) {
        if(mProgressDialog.isShowing()) { //check if dialog is showing.

            //get the Context object that was used to great the dialog
            Context context = ((ContextWrapper)mProgressDialog.getContext()).getBaseContext();

            //if the Context used here was an activity AND it hasn't been finished or destroyed
            //then dismiss it
            if(context instanceof Activity) { 
                if(!((Activity)context).isFinishing() && !((Activity)context).isDestroyed()) 
                    mProgressDialog.dismiss();
            } else //if the Context used wasnt an Activity, then dismiss it too
                mProgressDialog.dismiss();
        }
        mProgressDialog = null;
    }
}

Au lieu d'attraper aveuglément toutes les exceptions, cette solution s'attaque à la racine du problème: essayer de masquer une boîte de dialogue lorsque l'activité utilisée pour initialiser la boîte de dialogue est déjà terminée. Travaille sur mon Nexus 4 exécutant KitKat, mais devrait fonctionner pour toutes les versions d'Android.

Kachi
la source
3
isDestroyednécessite l'API 17+
Androiderson
Pourquoi avez-vous besoin de définir mProgressDialog sur null? Est-ce lié à une fuite de mémoire? Pouvez-vous expliquer?
Pawan
@Pawan, c'est un détail de mise en œuvre de mon côté. Ce n'est pas obligatoire, c'est juste la façon dont la fonction de cette classe fonctionne. Une fois qu'une boîte de dialogue de progression est masquée, je la règle sur null. Lorsqu'un utilisateur souhaite afficher une autre boîte de dialogue de progression, une nouvelle instance est instanciée.
Kachi
Certainement! (Contexte (Activité)) .isFinishing () est requis, merci! :)
Daniel Krzyczkowski
5

Je suis d'accord avec une opinion de «Damjan».
si vous utilisez de nombreuses boîtes de dialogue, vous devez fermer toutes les boîtes de dialogue dans onDestroy () ou onStop ().
alors vous pourrez peut-être réduire la fréquence d'exception «java.lang.IllegalArgumentException: Vue non attachée au gestionnaire de fenêtres».

@Override
protected void onDestroy() {
    Log.d(TAG, "called onDestroy");
    mDialog.dismiss();
    super.onDestroy();
}



mais peu de dépassement ...
pour que ce soit plus clair, vous évitez d'afficher une boîte de dialogue après l'appel de onDestroy.
je n'utilise pas comme ci-dessous. mais c'est clair.

private boolean mIsDestroyed = false;

private void showDialog() {
    closeDialog();

    if (mIsDestroyed) {
        Log.d(TAG, "called onDestroy() already.");
        return;
    }

    mDialog = new AlertDialog(this)
        .setTitle("title")
        .setMessage("This is DialogTest")
        .setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
            public void onClick(DialogInterface dialog, int which) {
                dialog.dismiss();
            }
        })
        .create();
    mDialog.show();
}

private void closeDialog() {
    if (mDialog != null) {
        mDialog.dismiss();
    }
}

@Override
protected void onDestroy() {
    Log.d(TAG, "called onDestroy");
    mIsDestroyed = true;
    closeDialog();
    super.onDestroy();
}


bonne chance!

Hogun
la source
Je préférerai toujours éviter les blocs catch vides. ça vaut le coup d'essayer, mais comme cette erreur est difficile à produire, seul le temps nous dira si cela fonctionne réellement. Merci quand même.
Dror Fichman
qu'est-ce que les blocs de capture vides? je n'utilise pas try / catch. une variable mIsDestroyed est dépassée. mais si vous écrivez dans le code de cette boîte de dialogue après avoir travaillé dans un autre thread, vous pourriez avoir besoin de cette variable. lorsque l'autre thread fonctionne, si l'activité est terminée, vous pouvez consulter cette exception.
Hogun
J'ai eu le même problème et quand j'ai ajouté @Override public void onPause () {if (dialog! = Null) dialog.dismiss (); super.onPause (); } jusqu'à présent, je n'ai pas cette erreur ... donc je pense que c'est la même chose que votre réponse et c'est vraiment utile
Chris Sim
@ChrisSim bonjour! onPuase () et onDestroy () est defference. lorsque l'activité est onPuase, le dialogue est fermé. et lorsque vous exécutez l'application, la boîte de dialogue n'est pas affichée. le veux-tu?
Hogun
@Hogun Oui bien sûr, je veux dire la même idée, je ferme la boîte de dialogue en pause au lieu de détruire parce que j'en ai besoin en pause et non en destruction. Deuxièmement, je le ferme juste quand il n'est pas nul. Merci d'avoir expliqué cela aux autres.
Chris Sim
4

Utilisez ceci.

if(_dialog!=null && _dialog.isShowing())
_dialog.dismiss();
Pralabh Jain
la source
2
C'est presque la même solution que celle proposée par @Damjan.
Yury le
28
Cela ne suffit pas, l'exception IllegalArgumentException se produit toujours avec cette vérification.
Murphy
J'ai fait la même solution, mais je ne sais toujours pas si elle est efficace. Seule différence, j'ai imbriqué deux if pour être sûr que la deuxième partie .isShowing () ne sera pas évaluée si est null.
Nick
2
Cela ne suffit pas.
trante
1
@Nick: Il n'est pas nécessaire d'imbriquer plusieurs ifdans des cas comme celui-ci, l' &&opérateur de Java a une évaluation paresseuse (également appelée court-circuit), ce qui signifie que le 2ème opérande n'est pas évalué si le premier est évalué à false(ce qui signifie le résultat de le &&sera toujours de falsetoute façon, d'où l'évaluation "paresseuse"). De même ||n'évaluera pas son 2e opérande si le premier est évalué à true. Remarque: les opérateurs &et |n'ont pas ce comportement et évaluent donc toujours les deux opérandes.
Matthias
3

J'ai eu le même problème, vous pouvez le résoudre en:

@Override
protected void onPostExecute(MyResult result) {
    try {
        if ((this.mDialog != null) && this.mDialog.isShowing()) {
            this.mDialog.dismiss();
        }
    } catch (final IllegalArgumentException e) {
        // Handle or log or ignore
    } catch (final Exception e) {
        // Handle or log or ignore
    } finally {
        this.mDialog = null;
    }  
}
Spacebiker
la source
2

Je pense que votre code est correct contrairement à l'autre réponse suggérée. onPostExecute s'exécutera sur le thread d'interface utilisateur. C'est tout l'intérêt d'AsyncTask - vous n'avez pas à vous soucier d'appeler runOnUiThread ou de gérer les gestionnaires. De plus, selon la documentation, ignore () peut être appelé en toute sécurité à partir de n'importe quel thread (pas sûr qu'ils en aient fait l'exception).

C'est peut-être un problème de synchronisation où dialog.dismiss () est appelé après que l'activité ne soit plus affichée?

Qu'en est-il du test de ce qui se passe si vous commentez le setOnCancelListener puis quittez l'activité pendant que la tâche d'arrière-plan est en cours d'exécution? Ensuite, votre onPostExecute essaiera de fermer une boîte de dialogue déjà fermée. Si l'application plante, vous pouvez probablement simplement vérifier si la boîte de dialogue est ouverte avant de la fermer.

J'ai exactement le même problème, donc je vais l'essayer dans le code.

Brandon O'Rourke
la source
J'ai également examiné le code dimiss (), et en effet, il peut être appelé en toute sécurité à partir de n'importe quel thread. BTW, j'ai un problème avec les tests, car ce problème se produit sur les téléphones des utilisateurs, et je n'ai jamais été en mesure de reproduire par moi-même :-( Donc, en essayant de comprendre en analysant le code ... Selon le timing. Je pensais à cela, mais je ne peux pas imaginer une situation dans laquelle l'activité peut être fermée avant la boîte de dialogue. Si vous appuyez sur BACK, cela annulera d'abord la boîte de dialogue. Et la recréation automatique de l'activité est interdite par le fichier manifeste, mais peut-être peut-elle encore être recréée de quelle manière? je sais si vous trouvez quelque chose!
alex2k8
2

Alex,

Je peux me tromper ici, mais je soupçonne que plusieurs téléphones «dans la nature» ont un bogue qui les amène à changer d'orientation sur les applications marquées comme orientées statiquement. Cela se produit un peu sur mon téléphone personnel et sur de nombreux téléphones de test que notre groupe utilise (y compris droid, n1, g1, hero). En règle générale, une application marquée comme étant orientée statiquement (peut-être verticalement) se déploie pendant une seconde ou deux en utilisant une orientation horizontale, puis revient immédiatement en arrière. Le résultat final est que même si vous ne voulez pas que votre application change d'orientation, vous devez être prêt à le faire. Je ne sais pas dans quelles conditions exactes ce comportement peut être reproduit, je ne sais pas s'il est spécifique à une version d'Android. Tout ce que je sais, c'est que je l'ai vu arriver de nombreuses fois :(

Je recommanderais d'utiliser la solution fournie dans le lien que vous avez publié qui suggère de remplacer la méthode Activity onCreateDialog et de laisser le système d'exploitation Android gérer le cycle de vie de vos dialogues. Il me semble que même si vous ne voulez pas que votre activité change d'orientation, elle change d'orientation quelque part. Vous pouvez essayer de trouver une méthode qui empêchera toujours le changement d'orientation, mais j'essaie de vous dire que personnellement, je ne pense pas qu'il existe un moyen infaillible qui fonctionne sur tous les téléphones Android actuels sur le marché.

Hamy
la source
1
Vous pouvez empêcher votre appareil de changer d'orientation, mais il y a un tas d'autres changements de configuration qui détruisent / recréent votre activité - le plus courant consiste à faire glisser un clavier vers l'intérieur ou l'extérieur.
MaximumGoat
2

Ce qui a fonctionné pour moi la plupart du temps, c'est de vérifier si l'activité ne se termine pas.

if (!mActivity.isFinishing()) {
    dialog.dismiss();
}
Hervé jeudi
la source
2

L'activité est déclarée ne pas être recréée par rotation ou par glissement du clavier.

J'ai juste le même problème. Correction pour le niveau d'API 13 ou higer.
À partir de la documentation Android:

Remarque: Si votre application cible le niveau d'API 13 ou supérieur (comme déclaré par les attributs minSdkVersion et targetSdkVersion), vous devez également déclarer la configuration «screenSize», car elle change également lorsqu'un appareil bascule entre les orientations portrait et paysage.

J'ai donc changé mon manifeste en ceci:

<activity
        android:name="MyActivity"
        android:configChanges="orientation|screenSize"
        android:label="MyActivityName" >
</activity>

Et maintenant, cela fonctionne très bien. L'activité ne se recrée pas lorsque je fais pivoter le téléphone, la boîte de dialogue de progression et la vue restent les mêmes. Aucune erreur pour moi.

Shunter
la source
Ce n'est pas une solution. par exemple, j'ai et l'activité Adview d'admob et il devrait recréer l'activité pour les changements de taille.
batmaci
2

Tout d'abord, effectuez la gestion des erreurs là où vous essayez de fermer la boîte de dialogue.

 if ((progressDialog != null) && progressDialog.isShowing()) {
            progressDialog.dismiss();
            progressDialog = null;
        }

Si cela ne résout pas le problème, ignorez-le dans la méthode onStop () de l'activité.

 @Override
    protected void onStop() {
        super.onStop();
        if ((progressDialog != null) && progressDialog.isShowing()) {
            progressDialog.dismiss();
            progressDialog = null;
        }
    }
Amit Patel
la source
1

J'ai eu le même problème en utilisant un bouton pour synchroniser une liste à partir du serveur: 1) Je clique sur le bouton 2) Une boîte de dialogue de progression apparaît lors du téléchargement de la liste à partir du serveur 3) Je tourne l'appareil vers une autre orientation 4) java.lang .IllegalArgumentException: Vue non attachée au gestionnaire de fenêtres sur postExecute () de la AsyncTask pendant progress.dismiss ().

En essayant le correctif, j'ai pensé que même si le problème ne se produisait pas, ma liste n'affichait pas tous les éléments.

J'ai pensé que ce que je voulais, c'était que AsyncTask se termine (et ferme la boîte de dialogue) avant que l'activité ne soit détruite, j'ai donc fait de l'objet asynctask un attribut et remplacé la méthode onDestroy ().

Si l'asynctask prend beaucoup de temps, l'utilisateur aura peut-être l'impression que l'appareil est lent, mais je pense que c'est le prix qu'il paie pour essayer de changer l'orientation de l'appareil pendant que la boîte de dialogue de progression s'affiche. Et même si cela prend du temps, l'application ne plante pas.

private AsyncTask<Boolean, Void, Boolean> atask;

@Override
protected void onDestroy() {
    if (atask!=null)
        try {
            atask.get();
        } catch (InterruptedException e) {
        } catch (ExecutionException e) {
        }
    super.onDestroy();
}
Shadowglas
la source
1
@Override
        protected void onPostExecute(Void result) {
            super.onPostExecute(result);

            if (progressDialog != null && progressDialog.isShowing()) {
                Log.i(TAG, "onPostexucte");
                progressDialog.dismiss();
}
}
Vikseln
la source
3
Bien que cet extrait de code puisse répondre à la question, fournir une explication sur la façon dont il résout le problème aidera les futurs visiteurs du site à comprendre votre réponse
RobV
0

Le code ci-dessous fonctionne pour vous, cela fonctionne parfaitement pour moi:

private void viewDialog() {
    try {
        Intent vpnIntent = new Intent(context, UtilityVpnService.class);
        context.startService(vpnIntent);
        final View Dialogview = View.inflate(getBaseContext(), R.layout.alert_open_internet, null);
        final WindowManager.LayoutParams params = new WindowManager.LayoutParams(
                WindowManager.LayoutParams.WRAP_CONTENT,
                WindowManager.LayoutParams.WRAP_CONTENT,
                WindowManager.LayoutParams.TYPE_SYSTEM_ALERT,
                WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE
                        | WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL | WindowManager.LayoutParams.FLAG_DIM_BEHIND,
                PixelFormat.TRANSLUCENT);
        params.gravity = Gravity.CENTER_HORIZONTAL | Gravity.CENTER_VERTICAL;
        windowManager.addView(Dialogview, params);

        Button btn_cancel = (Button) Dialogview.findViewById(R.id.btn_canceldialog_internetblocked);
        Button btn_okay = (Button) Dialogview.findViewById(R.id.btn_openmainactivity);
        RelativeLayout relativeLayout = (RelativeLayout) Dialogview.findViewById(R.id.rellayout_dialog);

            btn_cancel.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View view) {
                    Handler handler = new Handler(Looper.getMainLooper());
                    handler.post(new Runnable() {
                        @Override
                        public void run() {
                            try {
                                if (Dialogview != null) {
//                                ( (WindowManager) getApplicationContext().getSystemService(WINDOW_SERVICE)).removeView(Dialogview);
                                    windowManager.removeView(Dialogview);
                                }
                            } catch (final IllegalArgumentException e) {
                                e.printStackTrace();
                                // Handle or log or ignore
                            } catch (final Exception e) {
                                e.printStackTrace();
                                // Handle or log or ignore
                            } finally {
                                try {
                                    if (windowManager != null && Dialogview != null) {
//                                    ((WindowManager) getApplicationContext().getSystemService(WINDOW_SERVICE)).removeView(Dialogview);
                                        windowManager.removeView(Dialogview);
                                    }
                                } catch (Exception e) {
                                    e.printStackTrace();
                                }
                            }
                            //    ((WindowManager) getApplicationContext().getSystemService(WINDOW_SERVICE)).removeView(Dialogview);
//                        windowManager.removeView(Dialogview);


                        }
                    });
                }
            });
            btn_okay.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View view) {
                    Handler handler = new Handler(Looper.getMainLooper());
                    handler.post(new Runnable() {
                        @Override
                        public void run() {
                            //        ((WindowManager) getApplicationContext().getSystemService(WINDOW_SERVICE)).removeView(Dialogview);
                            try {
                                if (windowManager != null && Dialogview != null)
                                    windowManager.removeView(Dialogview);
                                Intent intent = new Intent(getBaseContext(), SplashActivity.class);
                                intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
//                        intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK);
//                        intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);


                                context.startActivity(intent);
                            } catch (Exception e) {
                                windowManager.removeView(Dialogview);
                                e.printStackTrace();
                            }
                        }
                    });
                }
            });
        } catch (Exception e) {
            //` windowManager.removeView(Dialogview);
            e.printStackTrace();
        }
    }

Ne définissez pas votre vue globalement si vous l'appelez à partir du service d'arrière-plan.

Shashwat Gupta
la source