I'm trying to use a ListActivity on my Android App but it isn't working the way it should.
Here is my Activity :
public class MainActivity extends ListActivity {
public void onCreate(Bundle savedInstanceState){
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_terminals_list); //The special layout
TerminalsArrayAdapter adapter = new TerminalsArrayAdapter(this); // A custom adapter
setListAdapter(adapter);
RequestTask task = new RequestTask(adapter); // An Async task
task.execute("/terminals/all");
}
}
Here is my layout :
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<ListView
android:id="@android:id/list"
android:layout_width="match_parent"
android:layout_height="wrap_content" >
</ListView>
<TextView
android:id="@android:id/empty"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Loading..." />
</LinearLayout>
Here is my custom adapter :
public class TerminalsArrayAdapter extends ArrayAdapter<String[]> {
private Activity mContext;
private ArrayList<String[]> mObjects = new ArrayList<String[]>();
public TerminalsArrayAdapter(Activity context) {
super(context, R.layout.terminals_listview_item);
this.mContext = context;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
View elementView;
if(convertView==null){
LayoutInflater inflater = mContext.getLayoutInflater();
elementView = inflater.inflate(R.layout.terminals_listview_item, parent);
...
// Some things with my view
} else {
elementView = convertView;
}
...
// Some things with my view
return elementView;
}
public void updateTerminals(ArrayList<String[]> newObject){
mObjects.clear();
mObjects.addAll(newObject);
notifyDataSetChanged();
Log.d("TerminalsArrayAdapter", "Dataset Changed !");
}
}
And here is my Async task :
public class RequestTask extends AsyncTask<String, Void, ArrayList<String[]>>{
private final TerminalsArrayAdapter mAdapter;
public RequestTask(TerminalsArrayAdapter adapter) {
mAdapter = adapter;
}
@Override
protected ArrayList<String[]> doInBackground(String... params) {
...
// retrieve some data from my server
return response;
}
@Override
protected void onPostExecute(ArrayList<String[]> response) {
Log.d("response_server","GOT IT !");
mAdapter.updateTerminals(response);
}
}
As I understood, the ListView will be shown only if the adapter is not empty. If it is empty, it will be the TextView which will be displayed.
This is the way my app should work :
- The app creates an empty adapter. This will display the "Loading..." TextView
- The app creates a new Async task which will retrieve some needed data from my server
- When the Async task finishes, it will call the .updateTerminals() method
- This method will update the entries of the custom adapter and call notifyDataSetChanged()
- The app should now display the ListView with the freshly retrieved data
I tried to figure out what was wrong with my code, but I wasn't able to. I'd love to hear your suggestions/solutions ! Thanks !
PS: Tell me if you need any thing to understand my issue better.
TerminalsArrayAdapter adapter = new TerminalsArrayAdapter(this); // A custom adapter setListAdapter(adapter);
fom onCreate and put it in onPostExecute. Add the objects directly in onPostExecute. RemovemAdapter.updateTerminals(response)
from onPost|EExecute. – greenapps