异步任务崩溃了我的应用程序

时间:2012-04-08 14:49:37

标签: java android http listview android-asynctask

我正在尝试从HttpPost下载字符串,我正在使用Async类来执行此操作。但是,当我运行应用程序时,它会崩溃。这是我第一次使用Async类,我担心我有些傻,你能帮我找到错误吗?

请注意,我还想在获取字符串时更新我的​​列表视图。我尝试这样做,买一个单独的方法。

代码:

public static final String PREFS_NAME = "MyPrefsFile";
    BufferedReader in = null;
    String data = null;
    String username;
    List headlines;
    List links;
    String password;
    ArrayAdapter adapter;


    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
            // listview method
            ContactsandIm();
        new loadcontactsandIm().execute(PREFS_NAME);

    }

    public class loadcontactsandIm extends AsyncTask<String, Integer, String> {
        @Override
        protected String doInBackground(String... arg0) {
            // TODO Auto-generated method stub

            // Create a new HttpClient and Post Header
            HttpClient httpclient = new DefaultHttpClient();

            /* login.php returns true if username and password is equal to saranga */
            HttpPost httppost = new HttpPost("http://gta5news.com/login.php");

            try {

                List<NameValuePair> nameValuePairs = new ArrayList<NameValuePair>(2);
                nameValuePairs.add(new BasicNameValuePair("username", username));
                nameValuePairs.add(new BasicNameValuePair("password", password));
                httppost.setEntity(new UrlEncodedFormEntity(nameValuePairs));

                // Execute HTTP Post Request
                Log.w("HttpPost", "Execute HTTP Post Request");
                HttpResponse response = httpclient.execute(httppost);
                Log.w("HttpPost", "Execute HTTP Post Request");
                in = new BufferedReader(new InputStreamReader(response.getEntity()
                        .getContent()));
                StringBuffer sb = new StringBuffer("");
                String l ="";
                String nl ="";
                while ((l =in.readLine()) !=null) {
                    sb.append(l + nl);  
                }
                in.close();
                 data = sb.toString();
                 ListView lv = getListView();
                 lv.setTextFilterEnabled(true);

                headlines.add(data);




                setListAdapter(adapter);
                return null;

            } catch (ClientProtocolException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }
            return data;
        }

        private StringBuilder inputStreamToString(InputStream is) {
            String line = "";
            StringBuilder total = new StringBuilder();
            // Wrap a BufferedReader around the InputStream
            BufferedReader rd = new BufferedReader(new InputStreamReader(is));
            // Read response until the end
            try {
                while ((line = rd.readLine()) != null) {
                    total.append(line);
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
            // Return full string
            return total;
        }

        }


    public void ContactsandIm() {
        headlines = new ArrayList();

        //get prefs
        SharedPreferences settings = getSharedPreferences(PREFS_NAME, 0);
        String username = settings.getString("key1", null);
        String password = settings.getString("key2", null);
        if(username.equals("irock97"))  {
            Toast toast=Toast.makeText(this, "Hello toast", 2000);
            toast.setGravity(Gravity.TOP, -30, 50);
            toast.show();

        } else {
            Toast toast=Toast.makeText(this, "Hello toast", 2000);
            toast.setGravity(Gravity.TOP, -30, 150);
            toast.show();
        }
        ArrayAdapter adapter = new ArrayAdapter(this,
                android.R.layout.simple_list_item_1, headlines);


    }

}

logcat的:

03-25 13:47:37.356: E/AndroidRuntime(2484): FATAL EXCEPTION: AsyncTask #1
03-25 13:47:37.356: E/AndroidRuntime(2484): java.lang.RuntimeException: An error occured while executing doInBackground()
03-25 13:47:37.356: E/AndroidRuntime(2484):     at android.os.AsyncTask$3.done(AsyncTask.java:200)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at java.util.concurrent.FutureTask$Sync.innerSetException(FutureTask.java:273)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at java.util.concurrent.FutureTask.setException(FutureTask.java:124)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:307)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at java.util.concurrent.FutureTask.run(FutureTask.java:137)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1068)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:561)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at java.lang.Thread.run(Thread.java:1096)
03-25 13:47:37.356: E/AndroidRuntime(2484): Caused by: android.view.ViewRoot$CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch its views.
03-25 13:47:37.356: E/AndroidRuntime(2484):     at android.view.ViewRoot.checkThread(ViewRoot.java:2802)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at android.view.ViewRoot.requestLayout(ViewRoot.java:594)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at android.view.View.requestLayout(View.java:8125)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at android.view.View.requestLayout(View.java:8125)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at android.view.View.requestLayout(View.java:8125)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at android.view.ViewGroup.removeAllViews(ViewGroup.java:2255)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at com.android.internal.policy.impl.PhoneWindow.setContentView(PhoneWindow.java:196)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at android.app.Activity.setContentView(Activity.java:1647)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at android.app.ListActivity.ensureList(ListActivity.java:314)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at android.app.ListActivity.getListView(ListActivity.java:299)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at com.gta5news.bananaphone.ChatService$loadcontactsandIm.doInBackground(ChatService.java:87)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at com.gta5news.bananaphone.ChatService$loadcontactsandIm.doInBackground(ChatService.java:1)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at android.os.AsyncTask$2.call(AsyncTask.java:185)
03-25 13:47:37.356: E/AndroidRuntime(2484):     at java.util.concurrent.FutureTask$Sync.innerRun(FutureTask.java:305)

4 个答案:

答案 0 :(得分:2)

您在doInBackground中设置ListView适配器。永远不要在UI线程之外操纵UI

答案 1 :(得分:2)

您无法与主线程之外的任何其他线程中的UI元素进行交互。您需要在onPostExecute方法中执行ListView的所有交互。

基本上,您需要在doInBackground方法中编译Web请求中的所有数据,存储在您的任务实例上,然后在onPostExecute上获取列表视图并设置适配器并填充数据。

答案 2 :(得分:2)

你在doInBackground工作,并在onPostExecute上使用你的工作结果。

示例:

public class TestActivity extends Activity 
{
  private GetTask getTask;
  public ListView fList;

  @Override
  public void onCreate(Bundle savedInstanceState) 
  {
    getTask = new GetTask(); 
    getTask.execute();
    fList = (ListView) findViewById(R.id.lstview);
  }

  public class GetTask extends AsyncTask<Void, Void, List> 
  {
    @Override
    protected List doInBackground(Void... params) {
      return load();
    }      

    @Override
    protected void onPostExecute(List result) {
        ArrayAdapter adapter = new ArrayAdapter(this,
                android.R.layout.simple_list_item_1, headlines);

      fList.setAdapter(adapter);
    }
  }

  private List load() { 
    // get your data from http
    // add to your list, probably you can use model.
    List headlines;
    headlines.add(data);

    return headlines;
  }


}

答案 3 :(得分:1)

首先,您不能在doInBackground()中处理与UI相关的任务中的任何UI相关任务,我们有一个方法调用onPostExecute(),我们可以处理所有与ui相关的任务。 如果您仍然不想使用这些方法并在doInBackground()中处理它,那么您可以在下面的代码中执行::::

runOnUiThread(new Runnable() {
public void run() {
//your UI related code stuff    
    ListView lv = getListView();
    lv.setTextFilterEnabled(true);
    headlines.add(data);
    setListAdapter(adapter); //do what you like here
}
});