在AsyncHttpClient任务中正确管理ProgressDialog以避免泄露Windows Android

时间:2014-10-09 15:30:38

标签: android progressdialog loopj asynchttpclient

我正在开发一个Android应用程序。

我需要从我的应用程序向服务器发出多个请求,因此我使用的是AsyncHttpClient。

我的应用程序的一部分有一个用户个人资料和一个时间轴来显示一些事件。当用户登录时,我需要获取他们的个人资料信息以及他们的时间线信息,为此我必须向服务器发出3个不同的请求:

第一次请求:登录 - >将Cookie和会话信息保存到SharedPreferences中 第二次请求:获取个人资料 - >保存用户的个人信息。 第3次请求:获取用户时间表 - >保存与当前用户相关的帖子和​​事件。

这是我的登录请求:

public static void login(final String email, final String password,
            final Context context, final Context appContext, final Resources res) {

        prgDialog = new ProgressDialog(context);
        prgDialog.setMessage(res.getString(R.string.dialog_please_wait));
        prgDialog.setCancelable(false);
        prgDialog.show();
        cookieStore = new PersistentCookieStore(appContext);
        client.setCookieStore(cookieStore);

        RequestParams params = new RequestParams();
        params.put("user_session[email]", email);
        params.put("user_session[password]", password);

        client.addHeader("Accept", HEADER);

        client.post(getAbsoluteUrl(LOGIN_PATH), params,
                new JsonHttpResponseHandler() {

                    @Override
                    public void onFailure(int statusCode,
                            org.apache.http.Header[] headers,
                            java.lang.String responseString,
                            java.lang.Throwable throwable) {
                        prgDialog.hide();
                        if (statusCode == 404) {
                            Toast.makeText(context,
                                    res.getString(R.string.error_404),
                                    Toast.LENGTH_LONG).show();
                        } else if (statusCode == 500) {
                            Toast.makeText(context,
                                    res.getString(R.string.error_500),
                                    Toast.LENGTH_LONG).show();
                        } else if (statusCode == 401) {
                            Toast.makeText(context,
                                    res.getString(R.string.login_401),
                                    Toast.LENGTH_LONG).show();
                        } else {
                            Toast.makeText(
                                    context,
                                    "Unexpected Error occcured! [Most common Error: Device might not be connected to Internet or remote server is not up and running]",
                                    Toast.LENGTH_LONG).show();
                        }
                    }

                    @Override
                    public void onSuccess(int statusCode, Header[] headers,
                            JSONObject response) {
                        if (statusCode == 200) {
                            // In this case the JSONOBject has the user
                            // credentials, such as user_id, person_id
                            // user_instance_type and user_instance_id
                            // Parse them into an object that has the same
                            // attributes
                            Gson gson = new Gson();
                            UserCredentials userCredentials = gson.fromJson(
                                    response.toString(), UserCredentials.class);

                            setInitialPrefs(userCredentials, appContext);

                            // Get the user profile and save into the
                            // database
                            getUserProfile(userCredentials.getUser_id(),
                                    context, appContext, prgDialog);

                            // Get the timeline
                            getWalls(true, context, appContext, prgDialog);
                        }

                    }
                });
    }

这两个方法,getUserProfile和getWalls本身都是异步请求。这是代码:

public static void getUserProfile(int userId, final Context context,
            final Context appContext, final ProgressDialog prgDialog) {

        prgDialog.show();

        cookieStore = new PersistentCookieStore(appContext);
        client.setCookieStore(cookieStore);
        client.addHeader("Accept", HEADER);

        client.get(getAbsoluteUrl(USERS_PATH + userId),
                new JsonHttpResponseHandler() {
                    @Override
                    public void onFailure(int statusCode,
                            org.apache.http.Header[] headers,
                            java.lang.String responseString,
                            java.lang.Throwable throwable) {
                        prgDialog.hide();
                        if (statusCode == 404) {
                            Log.d(TAG, "404 getting profile");
                        } else if (statusCode == 500) {
                            Toast.makeText(
                                    context,
                                    context.getResources().getString(
                                            R.string.error_500),
                                    Toast.LENGTH_LONG).show();
                            } else if (statusCode == 401) {
                            Log.d(TAG, "401 getting profile");
                        } else {
                            Log.d(TAG, "Error getting profile");
                        }
                    }

                    @Override
                    public void onSuccess(int statusCode, Header[] headers,
                            JSONObject response) {

                        if (statusCode == 200) {
                            // In this case the JSONOBject has the user
                            // profile
                            // Parse them into an object that has the same
                            // attributes
                            Gson gson = new Gson();
                            UserProfile userProfile = gson.fromJson(
                                    response.toString(), UserProfile.class);
                            UserProfileController profileController = new UserProfileController(
                                    context);
                            profileController.insertProfile(userProfile);
                        }

                    }

                });
    }

public static void getWalls(final boolean firstTime, final Context context,
            Context appContext, final ProgressDialog prgDialog) {
        cookieStore = new PersistentCookieStore(appContext);

        prgDialog.show();
        client.setCookieStore(cookieStore);
        client.addHeader("Accept", HEADER);

        client.get(getAbsoluteUrl(WALLS_PATH), new JsonHttpResponseHandler() {
            @Override
            public void onFailure(int statusCode,
                    org.apache.http.Header[] headers,
                    java.lang.String responseString,
                    java.lang.Throwable throwable) {
                prgDialog.hide();
                if (statusCode == 404) {
                    Log.d(TAG, "404 getting walls");
                } else if (statusCode == 500) {
                    Toast.makeText(
                            context,
                            context.getResources().getString(
                                    R.string.error_500),
                            Toast.LENGTH_LONG).show();
                    } else if (statusCode == 401) {
                    Log.d(TAG, "401 getting walls");
                } else {
                    Log.d(TAG, "Error getting walls");
                }
            }

            @Override
            public void onSuccess(int statusCode, Header[] headers,
                    JSONObject response) {
                if (statusCode == 200) {
                    Gson gson = new Gson();

                    TimelineController.getInstance(context);

                    Timeline timeline = gson.fromJson(response.toString(),
                            Timeline.class);

                    TimelineController.insertTimeline(timeline);

                    if (firstTime) {
                        prgDialog.hide();
                        Intent i = new Intent(context, TimelineActivity.class);
                        i.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP
                                | Intent.FLAG_ACTIVITY_CLEAR_TASK
                                | Intent.FLAG_ACTIVITY_NEW_TASK);
                        context.startActivity(i);
                        ((AuthActivity) context).finish();
                    } else {
                        prgDialog.hide();
                        Intent i = new Intent(context, TimelineActivity.class);
                        i.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK
                                | Intent.FLAG_ACTIVITY_CLEAR_TOP);
                        context.startActivity(i);
                    }
                }
            }

        });
    }

如果您看到代码,我正在尝试使用进度对话框来保持它显示,直到最后一个请求完成(getWalls请求)

事情是,有时当我退出并再次使用相同或不同的用户登录时,我得到了android.view.WindowLeaked异常,我认为这是因为我没有很好地管理我的进度对话框。

如何正确管理进度对话框以避免泄露窗口?

希望任何人都可以帮助我,谢谢你提前。

1 个答案:

答案 0 :(得分:0)

假设问题是进度对话,您可以尝试使用静态show方法之一。以下代码确保进度对话框不是双倍或三倍显示:

if (progressDialog == null || !progressDialog.isShowing()) {
    progressDialog = ProgressDialog.show(activity, "Changing password ...", "Please wait.", true, false);
}

你定义:

private ProgressDialog progressDialog;