В результате произошла утечка окна, которое было первоначально добавлено

Какова эта ошибка и почему это происходит?

05-17 18:24:57.069: ERROR/WindowManager(18850): Activity com.mypkg.myP has leaked window [email protected] that was originally added here
05-17 18:24:57.069: ERROR/WindowManager(18850): android.view.WindowLeaked: Activity ccom.mypkg.myP has leaked window [email protected] that was originally added here
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.view.ViewRoot.<init>(ViewRoot.java:231)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:148)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:91)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.view.Window$LocalWindowManager.addView(Window.java:424)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.app.Dialog.show(Dialog.java:239)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at com.mypkg.myP$PreparePairingLinkageData.onPreExecute(viewP.java:183)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.os.AsyncTask.execute(AsyncTask.java:391)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at com.mypkg.myP.onCreate(viewP.java:94)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1047)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2544)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2621)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.app.ActivityThread.access$2200(ActivityThread.java:126)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1932)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.os.Handler.dispatchMessage(Handler.java:99)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.os.Looper.loop(Looper.java:123)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at android.app.ActivityThread.main(ActivityThread.java:4595)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at java.lang.reflect.Method.invokeNative(Native Method)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at java.lang.reflect.Method.invoke(Method.java:521)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:860)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:618)
05-17 18:24:57.069: ERROR/WindowManager(18850):     at dalvik.system.NativeStart.main(Native Method)

Ответ 1

Вы пытаетесь показать диалоговое окно после выхода из Activity.

[EDIT]

Этот вопрос является одним из лучших поисков в Google для разработчиков Android, поэтому добавление нескольких важных моментов из комментариев, которые могут быть более полезными для будущего исследователя, без углубленного обсуждения комментариев.

Ответ 1:

Вы пытаетесь показать диалоговое окно после выхода из Activity.

Ответ 2

В некоторых случаях эта ошибка может быть немного ошибочной (хотя ответ по-прежнему полностью точен), то есть в моем случае необработанное исключение было выброшено в AsyncTask, что вызвало Активность для выключения, затем открытый прогрессдиалог вызвал это Исключение.. так что "реальное" исключение было немного раньше в журнале

Ответ 3

Отклонить вызов() в экземпляре диалога, который вы создали, прежде чем выйти из Активность, например. in onPause() или onDestroy()

Ответ 2

Решение состоит в вызове dismiss() в Dialog, созданном вами в viewP.java:183, перед выходом из Activity, например. в onPause(). Все Window s & Dialog должны быть закрыты перед тем, как оставить Activity.

Ответ 3

Если вы используете AsyncTask, возможно, сообщение журнала может быть обманным. Если вы посмотрите в своем журнале, вы можете найти еще одну ошибку, возможно, одну из ваших методов doInBackground() вашего AsyncTask, которая заставит ваш текущий Activity взорваться, и, как только вернется AsyncTask. Знаете, вы знаете все остальное. Некоторые другие пользователи уже объяснили, что здесь: -)

Ответ 4

Я вызвал эту ошибку, ошибочно называя hide() вместо dismiss() на AlertDialog.

Ответ 5

Вы можете получить это исключение просто простой/немой ошибкой, например (случайно), вызвав finish() после отображения AlertDialog, если вы пропустите выражение о вызове break в инструкции switch...

   @Override
   public void onClick(View v) {
    switch (v.getId()) {
        case R.id.new_button:
            openMyAlertDialog();
            break; <-- If you forget this the finish() method below 
                       will be called while the dialog is showing!
        case R.id.exit_button:
            finish();
            break;
        }
    }

Метод finish() закроет Activity, но AlertDialog все еще отображается!

Поэтому, когда вы внимательно смотрите на код, ища проблемы с плохой резьбой или сложное кодирование и т.д., не упускайте из виду лес для деревьев. Иногда это может быть просто что-то такое же простое и немое, как недостающий оператор break.:)

Ответ 6

Эта проблема возникает при попытке показать диалоговое окно после выхода из Activity.

Я просто решил эту проблему, просто записав следующий код:

@Override
public void onDestroy(){
    super.onDestroy();
    if ( progressDialog!=null && progressDialog.isShowing() ){
        progressDialog.cancel();
    }
}

В принципе, из какого класса вы начали progressDialog, переопределите метод onDestroy и сделайте это. Он решил проблему "Проблема с утечкой окна".

Ответ 7

Ответы на этот вопрос были правильными, но немного смущающими для меня, чтобы понять, почему. После игры около 2 часов причина этой ошибки (в моем случае) ударила меня:

Вы уже знаете, начиная с чтения других ответов, что X has leaked window [email protected][] означает, что диалог закрыт, когда ваше приложение закрыто. Но почему?

Может быть, ваше приложение разбилось по какой-то другой причине, пока ваш диалог был открыт

Это приведет к закрытию вашего приложения из-за некоторой ошибки в вашем коде, что приведет к открытию диалогового окна одновременно с закрытием приложения из-за другой ошибки.

Итак, просмотрите свое логическое. Решите первую ошибку, а затем вторая ошибка решит себя enter image description here

Одна ошибка вызывает другую, которая вызывает другую, как DOMINOS!

Ответ 8

Недавно я столкнулся с той же проблемой.

Причина этой проблемы заключается в том, что закрытие операции перед диалогом отменяется. Существуют разные причины для того, чтобы это произошло. Те, о которых упоминалось выше, также верны.

Я попал в ситуацию, потому что в потоке я вызывал функцию, которая бросала исключение. Из-за чего окно было уволено и, следовательно, исключение.

Ответ 9

Это может помочь.

if (! isFinishing()) {

    dialog.show();

    }

Ответ 10

Отключить диалог, когда действие уничтожает

@Override
protected void onDestroy()
{
    super.onDestroy();
    if (pDialog!=null && pDialog.isShowing()){
        pDialog.dismiss();
    }
}

Ответ 11

У меня было такое же непонятное сообщение об ошибке, и я понятия не имел, почему. Учитывая подсказки из предыдущих ответов, я изменил свои вызовы без GUI на mDialog.finish(), чтобы быть mDialog.dismiss(), и ошибки исчезли. Это не повлияло на поведение моего виджета, но оно было сбито с толку и вполне могло помешать важной утечке памяти.

Ответ 12

Я получал эти журналы в приложении для видеопроигрывателя. Эти сообщения были брошены, когда видеопроигрыватель был закрыт. Интересно, что я использовал эти журналы один раз в нескольких сериях случайным образом. Также мое приложение не участвует ни в одном progressdialog. Наконец, я столкнулся с этой проблемой при реализации ниже.

@Override
protected void onPause()
{
    Log.v("MediaVideo", "onPause");
    super.onPause();
    this.mVideoView.pause();
    this.mVideoView.setVisibility(View.GONE);
}

@Override
protected void onDestroy()
{
    Log.v("MediaVideo", "onDestroy");
    super.onDestroy();
}

@Override
protected void onResume()
{
    Log.v("MediaVideo", "onResume");
    super.onResume();
    this.mVideoView.resume();
}

Отмените OnPause с помощью вызова mVideoView.pause() и установите visibility в GONE. Таким образом, я могу решить проблему с ошибкой "Activity has leaked window".

Ответ 13

У меня была такая же проблема, и я нашел эту страницу, и, хотя моя ситуация была другая, я назвал finish из блока if прежде чем он определил окно предупреждения.

Таким образом, просто вызов dismiss не будет работать (как это еще не было сделано), но после прочтения ответа Алекса Воловой и осознания этого было поле оповещения, вызывающее его. Я попытался добавить оператор return сразу после финиша внутри, if блок и это исправило проблему.

Я подумал, как только ты позвонил, он остановил все и закончил там, но это не так. Кажется, он доходит до конца блока кода, а затем заканчивается.

Итак, если вы хотите реализовать ситуацию, когда иногда она заканчивается, прежде чем делать какой-то код, вам нужно поставить оператор возврата сразу после финиша, или он продолжит движение и будет действовать так, как будто конец был вызван в конце блок кода не там, где вы его назвали. Вот почему я получал все эти странные ошибки.

private picked(File aDirectory){
     if(aDirectory.length()==0){
        setResult(RESULT_CANCELED, new Intent()); 
        finish(); 
        return;
    }
     AlertDialog.Builder alert= new AlertDialog.Builder(this); // Start dialog builder
     alert
        .setTitle("Question")
        .setMessage("Do you want to open that file?"+aDirectory.getName());
    alert
        .setPositiveButton("OK", okButtonListener)
        .setNegativeButton("Cancel", cancelButtonListener);
    alert.show();
}

Если вы не вернете возвращение сразу после того, как я позвонил в финал, он будет действовать так, как если бы вы вызвали его после alert.show(); и, следовательно, он сказал бы, что окно просочилось, закончив сразу после того, как вы запустили диалог, хотя это не так, все же это так.

Я думал, что добавлю это как здесь, так как это показывает, что команда финиша действовала по-другому, тогда я подумал, что это так, и я думаю, есть другие люди, которые думают так же, как и я, прежде чем я это обнаружил.

Ответ 14

Это не ответ на вопрос, но он имеет отношение к теме.

Если действие определило атрибут в манифесте

 android:noHistory="true"

то после выполнения onPause() контекст активности теряется. Таким образом, все представление, использующее этот контекст, может привести к этой ошибке.

Ответ 15

Не только пытайтесь показать предупреждение, но также можно вызвать, когда вы закончите конкретный экземпляр активности и попытаетесь запустить новую активность/службу или попытаться ее остановить.

Пример:

OldActivity instance;

    oncreate() {
       instance=this;
    }
    instance.finish();
    instance.startActivity(new Intent(ACTION_MAIN).setClass(instance, NewActivity.class));

Ответ 16

Ошибка "Activity has leaked window that was originally added..." возникает, когда вы пытаетесь показать предупреждение после Activity эффективно finished.

У вас есть два варианта: AFAIK:

  • Перепишите логин вашего оповещения: вызовите dismiss() на dialog, прежде чем выйдите из своей активности.
  • Поместите dialog в другой поток и запустите его на thread (независимо от текущего Activity).

Ответ 17

Была проблема, когда я закончил действие, когда ProgressDialog все еще показывался.

Итак, сначала скройте диалоговое окно, а затем завершите действие.

Ответ 18

Попробуйте этот код:

public class Sample extends Activity(){
@Override
 public void onCreate(Bundle instance){

}
 @Override
    public void onStop() {
        super.onStop();
      progressdialog.dismiss(); // try this
    }

}

Ответ 19

Это может быть, если у вас есть ошибка в функции doInBackground() и введите этот код.

Попытайтесь добавить диалог наконец. Сначала проверьте и исправьте doInBackground() функцию

protected void onPreExecute() {
     super.onPreExecute();
     pDialog = new ProgressDialog(CreateAccount.this);
     pDialog.setMessage("Creating Product..");
     pDialog.setIndeterminate(false);
     pDialog.setCancelable(true);
     pDialog.show();

 }

 protected String doInBackground(String...args) {
     ERROR CAN BE IS HERE
 }

 protected void onPostExecute(String file_url) {
     // dismiss the dialog once done
     pDialog.dismiss();

Ответ 20

Это случилось со мной, когда я использую ProgressDialog в AsyncTask. На самом деле я использую метод hide() в onPostExecute. Основываясь на ответе @Alex Volovoy, мне нужно использовать dismiss() с ProgressDialog, чтобы удалить его в onPostExecute и сделать его.

progressDialog.hide(); // Don't use it, it gives error

progressDialog.dismiss(); // Use it

Ответ 21

Вы должны сделать Progressdialog объект в onPreExecute методе AsyncTask, и вы должны dismiss его использовать для метода onPostExecute.

Ответ 22

Как правило, эта проблема возникает из-за диалога прогресса: вы можете решить эту проблему, используя любой из следующих способов в своей деятельности:

 // 1):
          @Override
                protected void onPause() {
                    super.onPause();
                    if ( yourProgressDialog!=null && yourProgressDialog.isShowing() )
                  {
                        yourProgressDialog.cancel();
                    }
                }

       // 2) :
         @Override
            protected void onDestroy() {
                super.onDestroy();
                if ( yourProgressDialog!=null && yourProgressDialog.isShowing()
               {
                    yourProgressDialog.cancel();
                }
            }

Ответ 23

В моем случае причина заключалась в том, что я забыл включить разрешение в файл манифеста Android.

Как я узнал? Ну, точно так же, как @Bobby говорит в комментарии под принятым ответом, просто прокрутите дальше до ваших журналов, и вы увидите первую причину или событие, которое действительно выбросило исключение. По-видимому, сообщение "Activity имеет просочившееся окно, которое было первоначально добавлено", является только Исключением, результатом которого является первое исключение.

Ответ 24

Лучшее решение - это просто добавить диалог в диалог try catch и reject при возникновении исключения

Просто используйте ниже код

 try {
        dialog.show();
    } catch (Exception e) {
        dialog.dismiss();
    }

Ответ 25

Попробуйте под кодом, он будет работать в любое время, когда вы отпустите диалог прогресса, и он увидит, доступен ли его экземпляр или нет.

try {
        if (null != progressDialog && progressDialog.isShowing()) {
            progressDialog.dismiss();
            progressDialog = null;
        }
    } catch (Exception e) {
        e.printStackTrace();
    }

Ответ 26

Исключенные из окна исключения имеют две причины:

1), показывая диалог, когда контекст активности не существует, для его устранения вы должны показать диалог только, что вы уверены, что существует действие:

if(getActivity()!= null && !getActivity().isFinishing()){
        Dialog.show();
}

2) не отмените диалог соответствующим образом, чтобы решить использовать этот код:

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

Ответ 27

Лучшее решение поставлено перед показом progressbar или progressDialog

if (getApplicationContext().getWindow().getDecorView().isShown()) {

  //Show Your Progress Dialog

}

Ответ 28

Просто убедитесь, что ваша активность не закрывается неожиданно из-за некоторых исключений, возникающих где-то в вашем коде. Как правило, это происходит в async-задаче, когда активность сталкивается с принудительным закрытием в doinBackground, а затем asynctask возвращает метод onPostexecute.

Ответ 29

  if (mActivity != null && !mActivity.isFinishing() && mProgressDialog != null && mProgressDialog.isShowing()) {
        mProgressDialog.dismiss();
    }

Ответ 30

Проблема по мне заключается в том, что вы пытаетесь вызвать диалог сразу после того, как действие завершается, поэтому согласно мне, что вы можете сделать, это дать некоторую задержку с помощью Handler, и вы будете решены, например:

 Handler handler=new Handler();
     handler.postDelayed(new Runnable() {
                @Override
                public void run() {
                     dialog.show();
                     //or
                     dialog.dismiss();

                }
            },100);