Logcat showing WindowLeaked

71 views Asked by At

Even though there are no crashes in my app. But logcat showing this debug log. I wanna know what thing causing this problem. I don't much about threads so may be this is related to lousy use of threads.

06-12 12:37:37.349  12433-12433/com.ets.medecord E/WindowManager﹕ Activity com.ets.medecord.LoginActivity has leaked window com.android.internal.policy.impl.PhoneWindow$DecorView@405403d0 that was originally added here
    android.view.WindowLeaked: Activity com.ets.medecord.LoginActivity has leaked window com.android.internal.policy.impl.PhoneWindow$DecorView@405403d0 that was originally added here
            at android.view.ViewRoot.<init>(ViewRoot.java:259)
            at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:148)
            at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:91)
            at android.view.Window$LocalWindowManager.addView(Window.java:465)
            at android.app.Dialog.show(Dialog.java:241)
            at com.ets.medecord.LoginActivity.attemptLogin(LoginActivity.java:125)
            at com.ets.medecord.LoginActivity.access$300(LoginActivity.java:45)
            at com.ets.medecord.LoginActivity$1.onClick(LoginActivity.java:87)
            at android.view.View.performClick(View.java:2506)
            at android.view.View$PerformClick.run(View.java:9112)
            at android.os.Handler.handleCallback(Handler.java:587)
            at android.os.Handler.dispatchMessage(Handler.java:92)
            at android.os.Looper.loop(Looper.java:130)
            at android.app.ActivityThread.main(ActivityThread.java:3835)
            at java.lang.reflect.Method.invokeNative(Native Method)
            at java.lang.reflect.Method.invoke(Method.java:507)
            at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:864)
            at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:622)
            at dalvik.system.NativeStart.main(Native Method)

This is code which I am using, see if this can. Here I try to dismiss dialog after worker thread finishes it's job.

final String user_email = email;
final String user_password = password;
Log.d(TAG, "email:" + email);
Log.d(TAG, "password:" + password);
pDialog = new ProgressDialog(this);
pDialog.setMessage("Loading....");
pDialog.show();
new Thread(new Runnable() {
    @Override
    public void run() {
        HttpClient httpClient = new DefaultHttpClient();
        HttpResponse httpResponse = null;
        HttpPost httpPost = new HttpPost("http://elitetotality.com/medicord/");
        List<NameValuePair> nameValuePair = new ArrayList<>();
        nameValuePair.add(new BasicNameValuePair("tag", "login"));
        nameValuePair.add(new BasicNameValuePair("email", user_email));
        nameValuePair.add(new BasicNameValuePair("password", user_password));
        try {
            httpPost.setEntity(new UrlEncodedFormEntity(nameValuePair));
        } catch (UnsupportedEncodingException e) {
            e.printStackTrace();
        }
        try {
            httpResponse = httpClient.execute(httpPost);
        } catch (IOException e) {
            e.printStackTrace();
        }


        try {
            BufferedReader reader = new BufferedReader(new InputStreamReader(
                    httpResponse.getEntity().getContent(), "UTF-8"));
            StringBuilder builder = new StringBuilder();

            for (String line = null; (line = reader.readLine()) != null; ) {
                builder.append(line).append("\n");
            }

            String httpResponseString = builder.toString();
            strResponse = httpResponseString;
            Log.d(TAG, httpResponseString);

        } catch (IOException e) {
            e.printStackTrace();
        }

        handler.post(new Runnable() {
            @Override
            public void run() {
                pDialog.hide();
                pDialog.dismiss();
            }
        });
        JSONObject reader;
        try {
            if(strResponse != null){
                reader = new JSONObject(strResponse);
                String error = reader.get("error").toString();
                Log.d(JSON_TAG, error);
                if(error.equals("false")) {
                    String userName = reader.getJSONObject("user").get("name").toString();
                    editor.putBoolean("isLoggedIn", true);
                    editor.putString("userName", userName);
                    editor.apply();
                    startActivity(new Intent(getApplicationContext(), RandomProfileActivity.class));
                    finish();
                } else {

                    handler.post(new Runnable() {
                        @Override
                        public void run() {
                            Toast.makeText(getApplicationContext(),"Either email or password is incorrect!"
                                    ,Toast.LENGTH_SHORT).show();
                        }
                    });
                }


            }

        } catch(JSONException e) {
            e.printStackTrace();
        } catch (NullPointerException e) {
            e.printStackTrace();
        }


    }
}).start();
2

There are 2 answers

1
Gent Ahmeti On BEST ANSWER

A more detailed answer

Change this part of the code:

    handler.post(new Runnable() {
        @Override
        public void run() {
            pDialog.hide();
            pDialog.dismiss();
        }
    });

to:

pDialog.dismiss();

Handler.post puts the runnable code to be run sometime after the current method finishes. That's why you got the leaking warning, you were leaking a dialog.

Android provides AsyncTask to make short term asynchronous operations. You can use onPreExecute to show your Dialog and onPostExecute to dissmis it.

0
Kartheek On

You're trying to dismiss a Dialog after you've exited an Activity. Since your worker threads will continue to execute even after your activity is destroyed. If you try to dismiss the dialog after the Activity is destroyed it will cause leaked window exception

Try to add this code to your activity.

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