解决如何让AsyncTask终止操作

受到这个的启发终于结局了如何在AsyncTask运行中终止其操作。

单纯的onCancelled(true)是不行的

下面把代码贴出来~实现了登陆功能。

AsyncTask简介,它使创建需要与用户界面交互的长时间运行的任务变得更简单。相对来说AsyncTask更轻量级一些,适用于简单的异步处理,不需要借助线程和Handler即可实现。

 

[java][/java]
  1. package com.isummation.exampleapp;
  2. import java.io.BufferedReader;
  3. import java.io.InputStreamReader;
  4. import java.net.URLEncoder;
  5. import java.net.UnknownHostException;
  6. import org.apache.http.HttpResponse;
  7. import org.apache.http.client.HttpClient;
  8. import org.apache.http.client.methods.HttpGet;
  9. import org.apache.http.impl.client.DefaultHttpClient;
  10. import org.apache.http.params.CoreProtocolPNames;
  11. import org.apache.http.protocol.BasicHttpContext;
  12. import org.apache.http.protocol.HttpContext;
  13. import org.json.JSONObject;
  14. import android.app.Activity;
  15. import android.app.Dialog;
  16. import android.app.ProgressDialog;
  17. import android.content.DialogInterface;
  18. import android.content.DialogInterface.OnCancelListener;
  19. import android.os.AsyncTask;
  20. import android.os.Bundle;
  21. import android.view.View;
  22. import android.view.View.OnClickListener;
  23. import android.widget.Button;
  24. import android.widget.EditText;
  25. import android.widget.Toast;
  26. public class UserLogin extends Activity {
  27.     private EditText etUsername;
  28.     private EditText etPassword;
  29.     private ProgressDialog progressDialog;
  30.     private static final int PROGRESSDIALOG_ID = 0;
  31.     private static final int SERVER_ERROR = 1;
  32.     private static final int NETWORK_ERROR = 2;
  33.     private static final int CANCELLED = 3;
  34.     private static final int SUCCESS = 4;
  35.     private String ServerResponse;
  36.     private LoginTask loginTask;
  37.     @Override
  38.     public void onCreate(Bundle savedInstanceState) {
  39.         super.onCreate(savedInstanceState);
  40.         setContentView(R.layout.login);
  41.         etUsername = (EditText) findViewById(R.id.txt_username);
  42.         etPassword = (EditText) findViewById(R.id.txt_password);
  43.         Button login_button = (Button) this.findViewById(R.id.login_button);
  44.         login_button.setOnClickListener(new OnClickListener() {
  45.             public void onClick(View viewParam) {
  46.                 if (etUsername.getText().toString().length() == 0
  47.                         || etPassword.getText().toString().length() == 0) {
  48.                     Toast.makeText(getApplicationContext(),
  49.                             “Please enter username and password”,
  50.                             Toast.LENGTH_SHORT).show();
  51.                 } else {
  52.                     //Show dialog by passing id
  53.                     showDialog(PROGRESSDIALOG_ID);
  54.                 }
  55.             }
  56.         });
  57.     }
  58.     protected Dialog onCreateDialog(int id) {
  59.         switch(id) {
  60.         case PROGRESSDIALOG_ID:
  61.             removeDialog(PROGRESSDIALOG_ID);
  62.             //Please note that forth parameter is true for cancelable Dialog
  63.             //Also register cancel event listener
  64.             //if the litener is registered then forth parameter has no effect
  65.             progressDialog = ProgressDialog.show(UserLogin.this, “Authenticating”,
  66.                     “Please wait…”, true, true, new OnCancelListener(){
  67.                         public void onCancel(DialogInterface dialog) {
  68.                             //Check the status, status can be RUNNING, FINISHED and PENDING
  69.                             //It can be only cancelled if it is not in FINISHED state
  70.                             if (loginTask != null && loginTask.getStatus() != AsyncTask.Status.FINISHED)
  71.                                 loginTask.cancel(true);
  72.                         }
  73.                     });
  74.             break;
  75.         default:
  76.             progressDialog = null;
  77.         }
  78.         return progressDialog;
  79.     }
  80.     @Override
  81.     protected void onPrepareDialog(int id, Dialog dialog) {
  82.         switch (id) {
  83.         case PROGRESSDIALOG_ID:
  84.             //check if any previous task is running, if so then cancel it
  85.             //it can be cancelled if it is not in FINISHED state
  86.             if (loginTask != null && loginTask.getStatus() != AsyncTask.Status.FINISHED)
  87.                 loginTask.cancel(true);
  88.             loginTask = new LoginTask(); //every time create new object, as AsynTask will only be executed one time.
  89.             loginTask.execute();
  90.         }
  91.     }
  92.     class LoginTask extends AsyncTask<Void, Integer, Void> {
  93.         @Override
  94.         protected Void doInBackground(Void… unused) {
  95.             try {
  96.                 ServerResponse = null; //don’t forget to make it null, as task can be called again
  97.                 HttpClient httpClient = new DefaultHttpClient();
  98.                 HttpContext localContext = new BasicHttpContext();
  99.                 HttpGet httpGet = new HttpGet(
  100.                         getString(R.string.WebServiceURL)
  101.                                 + “/cfc/iphonewebservice.cfc?returnformat=json&method=validateUserLogin&username=”
  102.                                 + URLEncoder.encode(etUsername.getText()
  103.                                         .toString(), “UTF-8”)
  104.                                 + “&password=”
  105.                                 + URLEncoder.encode(etPassword.getText()
  106.                                         .toString(), “UTF-8”));
  107.                 httpClient.getParams().setParameter(
  108.                         CoreProtocolPNames.USER_AGENT,”Some user agent string”);
  109.                 //call it just before you make server call
  110.                 //calling after this statement and canceling task will no meaning if you do some update database kind of operation
  111.                 //so be wise to choose correct place to put this condition
  112.                 //you can also put this condition in for loop, if you are doing iterative task
  113.                 //now this very important
  114.                 //if you do not put this condition and not maintaining execution, then there is no meaning of calling .cancel() method
  115.                 //you should only check this condition in doInBackground() method, otherwise there is no logical meaning
  116.                 if (isCancelled())
  117.                 {
  118.                     publishProgress(CANCELLED); //Notify your activity that you had canceled the task
  119.                     return (null); // don’t forget to terminate this method
  120.                 }
  121.                 HttpResponse response = httpClient.execute(httpGet,
  122.                         localContext);
  123.                 BufferedReader reader = new BufferedReader(
  124.                         new InputStreamReader(
  125.                                 response.getEntity().getContent(), “UTF-8”));
  126.                 ServerResponse = reader.readLine();
  127.                 publishProgress(SUCCESS); //if everything is Okay then publish this message, you may also use onPostExecute() method
  128.             } catch (UnknownHostException e) {
  129.                 removeDialog(PROGRESSDIALOG_ID);
  130.                 e.printStackTrace();
  131.                 publishProgress(NETWORK_ERROR);
  132.             } catch (Exception e) {
  133.                 removeDialog(PROGRESSDIALOG_ID);
  134.                 e.printStackTrace();
  135.                 publishProgress(SERVER_ERROR);
  136.             }
  137.             return (null);
  138.         }
  139.         @Override
  140.         protected void onProgressUpdate(Integer… errorCode) {
  141.             switch (errorCode[0]) {
  142.             case CANCELLED:
  143.                 removeDialog(PROGRESSDIALOG_ID);
  144.                 Toast.makeText(getApplicationContext(), “Cancelled by user”,
  145.                         Toast.LENGTH_LONG).show();
  146.                 break;
  147.             case NETWORK_ERROR:
  148.                 removeDialog(PROGRESSDIALOG_ID);
  149.                 Toast.makeText(getApplicationContext(), “Network connection error”,
  150.                         Toast.LENGTH_LONG).show();
  151.                 break;
  152.             case SERVER_ERROR:
  153.                 removeDialog(PROGRESSDIALOG_ID);
  154.                 Toast.makeText(getApplicationContext(), “Server error”,
  155.                         Toast.LENGTH_LONG).show();
  156.                 break;
  157.             case SUCCESS:
  158.                 removeDialog(PROGRESSDIALOG_ID);
  159.                 try {
  160.                     if (ServerResponse != null) {
  161.                         JSONObject JResponse = new JSONObject(ServerResponse);
  162.                         String sMessage = JResponse.getString(“MESSAGE”);
  163.                         int success = JResponse.getInt(“SUCCESS”);
  164.                         if (success == 1) {
  165.                             //proceed further
  166.                             //you may start new activity from here
  167.                             //after that you may want to finish this activity
  168.                             UserLogin.this.finish();
  169.                             //Remember when you finish an activity, it doesn’t mean that you also finish thread or AsynTask started within that activity
  170.                             //So you must implement onDestroy() method and terminate those threads.
  171.                         } else {
  172.                             //just showing invalid username password from server response
  173.                             Toast.makeText(getApplicationContext(), sMessage,
  174.                                     Toast.LENGTH_SHORT).show();
  175.                         }
  176.                     }
  177.                 } catch (Exception e){
  178.                     Toast.makeText(getApplicationContext(), “Server error”,
  179.                             Toast.LENGTH_LONG).show();
  180.                     e.printStackTrace();
  181.                 }
  182.                 break;
  183.             }
  184.         }
  185.         @Override
  186.         protected void onPostExecute(Void unused) {
  187.         }
  188.     }
  189.     @Override
  190.     protected void onDestroy(){
  191.         //you may call the cancel() method but if it is not handled in doInBackground() method
  192.         if (loginTask != null && loginTask.getStatus() != AsyncTask.Status.FINISHED)
  193.             loginTask.cancel(true);
  194.         super.onDestroy();
  195.     }
  196. }

标签