在解除asynctask中的进度对话框时,Android app强制关闭

时间:2012-12-21 12:46:08

标签: android android-asynctask progressdialog

我在主活动中使用子类来执行asynctask。我计划将其移到一个单独的文件中,之后我更喜欢这样做以确认它是否正常工作。我正在尝试使用进度对话框执行HTTPRequest,因为可能需要很长的等待时间。我在doInBackground()中什么也没做,因为我读过你无法从那里访问UI层。最终发生的事情是我在onPreExecute()上显示我的进度对话框并在onPostExecute()中将其关闭。我在上面单独调用每个任务可能是我问题的99%但是我需要能够将我的活动传递给他们正常运行的任务。

我已经将很多步骤分解成小块。我得到一个空指针异常,这让我相信我的问题来自于不使用execute(),但我似乎无法弄清楚它是如何工作的。

new CodeRetrievalItem().onPreExecute(MyActivity.this);

new CodeRetrievalItem().onPostExecute(MyActivity.this);

class CodeRetrievalItem extends AsyncTask<Void, Void, Void>{

ProgressDialog dialog;
protected void onPreExecute(Activity actpass){
        dialog = new  ProgressDialog(actpass);
    dialog.setMessage("Loading");
    dialog.setIndeterminate(false); 
    dialog.setCancelable(false);
    dialog.show();

}

@Override
protected Void doInBackground(Void... arg0) {
    // TODO Auto-generated method stub
    return null;
}

protected void onPostExecute(Activity actpass){

            // Execute HTTP Request
    try{
        dialog.dismiss();
    }
    catch(Exception e){
        Toast.makeText(actpass, "IOE response " + e.toString(), Toast.LENGTH_LONG).show();
    }

}

}

2 个答案:

答案 0 :(得分:2)

您使用AsyncTask完全错误。您的代码中存在几个主要错误。

AsyncTask保护方法

不要自己打电话。在documentation for AsyncTask中,您可以找到:

  

不要手动调用onPreExecute(),onPostExecute(Result),doInBackground(Params ...),onProgressUpdate(Progress ...)。

您必须通过调用AsyncTask方法启动execute(Params...)。这将导致:

  1. onPreExecute()在后​​台执行开始之前调用,并在主线程上调用
  2. doInBackground(Params...)在后​​台调用
  3. 后台执行完成后,在主线程上调用onPostExecute(Result)
  4. 除非你致电execute(Params...),否则不会发生任何事情。

    通用参数

    此外,您的通用参数存在问题。 AsyncTask有三个通用参数AsyncTask<Params, Progress, Result>(在您的情况下为AsyncTask<Void, Void, Void>,您必须在方法参数中匹配这些参数。

    因此创建:

    1. onPreExecute()代替onPreExecute(Activity actpass)
    2. onPostExecute(Void)代替onPostExecute(Activity actpass)
    3. 您定义的那些方法不以任何方式绑定到异步执行,它们只是类中的一些额外方法。

      如果您需要访问AsyncTask内的活动,请以不同的方式传递(例如在构造函数中)。请注意,将Activity传递给AsyncTask可能会导致内存泄漏(最好在此处使用WeakReference<T>)并且访问onPostExecute(Result)中的对话框如果处理不当可能会导致崩溃

答案 1 :(得分:1)

像这样更改您的代码

new CodeRetrievalItem(MyActivity.this).execute();



class CodeRetrievalItem extends AsyncTask<Void, Void, Void>{
Activity context;
public CodeRetrievalItem(Activity actpass)
{
context=actpass;
}
ProgressDialog dialog;
protected void onPreExecute(Activity actpass){
        dialog = new  ProgressDialog(context);
    dialog.setMessage("Loading");
    dialog.setIndeterminate(false); 
    dialog.setCancelable(false);
    dialog.show();

}

@Override
protected Void doInBackground(Void... arg0) {
    // TODO Auto-generated method stub
    return null;
}

protected void onPostExecute(Activity actpass){

            // Execute HTTP Request
    try{
        dialog.dismiss();
    }
    catch(Exception e){
        Toast.makeText(context, "IOE response " + e.toString(), Toast.LENGTH_LONG).show();
    }