I am trying to populate a listview
in my android App (android studio) from a list to which I dynamically added Strings.
First, the list is declared as an attribute of the activity:
private List<String> your_array_list = new ArrayList<String>();
Then, I have the class where the method populatelist()
is called. There are other methods called in it, but they all work fine, populatelist()
is the only method that gives me an error:
private class SendMessage extends AsyncTask<Void, Void, Void> {
@Override
protected Void doInBackground(Void... params) {
try {
parse(message);
populatelist();
}
} catch (UnknownHostException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
}
And this is the method itself:
public void populatelist() {
// String[] myitems = {"World Weather Online","Open Weather Map","Weather"};
Log.d("Matcher", "Populate! Test 1");
ArrayAdapter<String> adapter = new ArrayAdapter<String>(this,R.layout.items,R.id.textting,your_array_list);
Log.d("Matcher", "Populate! Test 2");
ListView list;
Log.d("Matcher", "Populate! Test 3");
list = (ListView) findViewById(R.id.services);
Log.d("Matcher", "Populate! Test 4");
list.setAdapter(adapter);
Log.d("Matcher", "Populate! Test 5");
}
All the logs print except the last one "Test 5". When I run my app, I get the following error:
07-19 21:13:32.399 1575-1591/com.example.othmane.servicefinder E/AndroidRuntime﹕ FATAL EXCEPTION: AsyncTask #2
Process: com.example.othmane.servicefinder, PID: 1575
java.lang.RuntimeException: An error occured while executing doInBackground()
at android.os.AsyncTask$3.done(AsyncTask.java:300)
at java.util.concurrent.FutureTask.finishCompletion(FutureTask.java:355)
at java.util.concurrent.FutureTask.setException(FutureTask.java:222)
at java.util.concurrent.FutureTask.run(FutureTask.java:242)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:231)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1112)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587)
at java.lang.Thread.run(Thread.java:818)
Caused by: android.view.ViewRootImpl$CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch its views.
at android.view.ViewRootImpl.checkThread(ViewRootImpl.java:6247)
at android.view.ViewRootImpl.focusableViewAvailable(ViewRootImpl.java:2855)
at android.view.ViewGroup.focusableViewAvailable(ViewGroup.java:679)
at android.view.ViewGroup.focusableViewAvailable(ViewGroup.java:679)
at android.view.ViewGroup.focusableViewAvailable(ViewGroup.java:679)
at android.view.ViewGroup.focusableViewAvailable(ViewGroup.java:679)
at android.view.ViewGroup.focusableViewAvailable(ViewGroup.java:679)
at android.view.ViewGroup.focusableViewAvailable(ViewGroup.java:679)
at android.view.ViewGroup.focusableViewAvailable(ViewGroup.java:679)
at android.view.View.setFlags(View.java:9603)
at android.view.View.setFocusableInTouchMode(View.java:6741)
at android.widget.AdapterView.checkFocus(AdapterView.java:722)
at android.widget.ListView.setAdapter(ListView.java:488)
at com.example.othmane.servicefinder.MainActivity.populatelist(MainActivity.java:277)
at com.example.othmane.servicefinder.MainActivity$SendMessage.doInBackground(MainActivity.java:100)
at com.example.othmane.servicefinder.MainActivity$SendMessage.doInBackground(MainActivity.java:67)
at android.os.AsyncTask$2.call(AsyncTask.java:288)
at java.util.concurrent.FutureTask.run(FutureTask.java:237)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:231)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1112)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:587)
at java.lang.Thread.run(Thread.java:818)
Does anyone see any mistake of how I try to populate the list ? I followed a tutorial to do it, but I don't know why it does not work.
Read the logcat and you will see the answer:
android.view.ViewRootImpl$CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch its views. at
The error is caused by you are trying to populate view in the background thread. In order to perform work in the main thread, you need to call onPostExecute method.
Here is the example from one of my app:
public class FetchArtistData extends AsyncTask<String,Void, List<Artist>> {
private static final String TAG="FetchArtistData";
@Override
protected List<Artist> doInBackground(String... params) {
SpotifyApi api=new SpotifyApi();
SpotifyService spotify=api.getService();
ArtistsPager results=spotify.searchArtists(params[0]);
List<Artist> list=results.artists.items;
Log.d(TAG, list.toString());
return list;
}
@Override
protected void onPostExecute(List<Artist> artists) {
mArtistList=(ArrayList<Artist>)artists;
Log.d(TAG,Integer.toString(mArtistList.size()));
updateAdapter(mArtistList);
}
}
Noticed that I update the view in onPostExecute.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.