问题
I'm trying to get JSON but I have to do it in AsyncTask , because I get this in logcat AndroidRuntime(18153): Caused by: android.os.NetworkOnMainThreadException
.
Here is my code:
public class LatestAlbums extends Activity {
TextView t;
// url to make request
private static String url = "www.example.com";
// JSON Node names
private static final String TAG_ALBUMS = "albums";
private static final String TAG_ID = "id";
private static final String TAG_NAME = "name";
private static final String TAG_SINGER = "singer";
private static final String TAG_GENRE = "genre";
private static final String TAG_MIX = "mix";
private static final String TAG_THUMB = "thumb";
private static final String TAG_SONGS = "songs";
private static final String TAG_SONG_TITLE = "song";
private static final String TAG_SONG_ARTIST = "artist";
private static final String TAG_SONG_MP3 = "mp3";
private static final String TAG_SONG_MP4 = "mp4";
private static final String TAG_SONG_THUMB = "thumb";
// albums JSONArray
JSONArray albums = null;
JSONArray sngs = null;
JSONObject objects = null;
@Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.favorites);
t = (TextView) findViewById(R.id.json);
loadJSON();
}
public void loadJSON() {
// Creating JSON Parser instance
JSONParser jParser = new JSONParser();
// getting JSON string from URL
JSONObject json = jParser.getJSONFromUrl(url);
try {
// Getting Array of albums
albums = json.getJSONArray(TAG_ALBUMS);
sngs=json.getJSONArray(TAG_SONGS);
// looping through All albums
for (int i = 0; i < albums.length(); i++) {
JSONObject c = albums.getJSONObject(i);
// Storing each json item in variable
String album_id = c.getString(TAG_ID);
String album_name = c.getString(TAG_NAME);
String album_singer = c.getString(TAG_SINGER);
String album_genre = c.getString(TAG_GENRE);
String album_thumb = c.getString(TAG_THUMB);
// songs are again JSON Object
for (int j = 0; i < sngs.length(); j++) {
JSONObject s = sngs.getJSONObject(j);
JSONObject songs = s.getJSONObject(TAG_SONGS);
String artist = s.getString(TAG_SONG_ARTIST);
String mp3 = s.getString(TAG_SONG_MP3);
String mp4 = s.getString(TAG_SONG_MP4);
String song_thumb = s.getString(TAG_SONG_THUMB);
String song_title = s.getString(TAG_SONG_TITLE);
}
Log.v("--", "Albums \n" + " " + album_id + " " + album_name
+ " " + album_genre + " " + album_singer + " "
+ album_thumb);
}
} catch (JSONException e) {
e.printStackTrace();
}
}
}
Can anybody please tell me how to do this?
回答1:
Load your JSON object in background (doing the network operation) and process the result in the UI thread, i.e.:
URL requestUrl = "...";
new AsyncTask<URL, Void, JSONObject>() {
@Override
protected Boolean doInBackground(URL... urls) {
loadJSON(url);
}
@Override
protected void onPostExecute(JSONObject jsonData) {
try {
// Getting Array of albums
albums = json.getJSONArray(TAG_ALBUMS);
sngs=json.getJSONArray(TAG_SONGS);
// looping through All albums
etc.
}
}.execute(requestUrl);
public void loadJSON(URL url) {
// Creating JSON Parser instance
JSONParser jParser = new JSONParser();
// getting JSON string from URL
JSONObject json = jParser.getJSONFromUrl(url);
return json;
}
Check out this for more information.
Cheers!
回答2:
Best and easy way to read JSON and set it to the Adapter .
AsyncTask has three methods.
in PreExecute and PostExecute
you can set any view Properties (As you are on Main UI Thread) but in doInBackground
(operation other than interacting with UI goes here) it reads the JSON
package com.example.tabs;
import java.util.ArrayList;
import java.util.HashMap;
import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.client.HttpClient;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.util.EntityUtils;
import org.json.JSONArray;
import org.json.JSONObject;
import android.app.Activity;
import android.app.ProgressDialog;
import android.content.Intent;
import android.os.AsyncTask;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.ListView;
import android.widget.Toast;
import com.example.adapters.CalendarAdapter;
import com.example.description.CalendarDescription;
public class Calendar extends Activity {
String url = "Enter your URL here ";
GetData data;
ProgressDialog progressDialog;
ListView list_of_calendar;
ArrayList<HashMap<String, String>> list = new ArrayList<HashMap<String, String>>();
@Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.calendar);
list_of_calendar = (ListView) findViewById(R.id.list_of_calendar);
new GetData().execute();
//new GetData(url).execute();//you can pass it like this and see comment in doInBackground
//ListView listView = getListView();
list_of_calendar.setOnItemClickListener(new OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view,
int position, long id)
{
HashMap<String, String> map = list.get(position);
Intent intent = new Intent(Calendar.this, CalendarDescription.class);
intent.putExtra("name", map.get("name"));
intent.putExtra("date", map.get("date"));
intent.putExtra("description", map.get("description"));
startActivity(intent);
}
});
}
private class GetData extends AsyncTask<String, Void, JSONObject> {
@Override
protected void onPreExecute() {
super.onPreExecute();
progressDialog = ProgressDialog.show(Calendar.this,
"", "");
}
@Override
protected JSONObject doInBackground(String... params) {
String response;
try {
HttpClient httpclient = new DefaultHttpClient();
HttpPost httppost = new HttpPost(url);
//HttpPost httppost = new HttpPost(params[0]);//you can also pass it and get the Url here.
HttpResponse responce = httpclient.execute(httppost);
HttpEntity httpEntity = responce.getEntity();
response = EntityUtils.toString(httpEntity);
Log.d("response is", response);
return new JSONObject(response);
} catch (Exception ex) {
ex.printStackTrace();
}
return null;
}
@Override
protected void onPostExecute(JSONObject result)
{
super.onPostExecute(result);
progressDialog.dismiss();
if(result != null)
{
try
{
JSONObject jobj = result.getJSONObject("result");
String status = jobj.getString("status");
if(status.equals("true"))
{
JSONArray array = jobj.getJSONArray("data");
for(int x = 0; x < array.length(); x++)
{
HashMap<String, String> map = new HashMap<String, String>();
map.put("name", array.getJSONObject(x).getString("name"));
map.put("date", array.getJSONObject(x).getString("date"));
map.put("description", array.getJSONObject(x).getString("description"));
list.add(map);
}
CalendarAdapter adapter = new CalendarAdapter(Calendar.this, list);
list_of_calendar.setAdapter(adapter);
}
}
catch (Exception e)
{
e.printStackTrace();
}
}
else
{
Toast.makeText(Calendar.this, "Network Problem", Toast.LENGTH_LONG).show();
}
}
}
}
Edit
the code is for the url
http://www.socialgeolocate.com/DayCare/webservices/Get_calender.php?
回答3:
This is how a asynctask works
do your parsing in
doInBackground()
and do the thing with retrieved data in
onPostExecute()
来源:https://stackoverflow.com/questions/15719942/get-json-in-asynctask-android