Reputation: 275
i get error An exception occurred: android.os.NetworkOnMainThreadException even when i already use AsyncTask. Error is on LongOperation.java at the line
while ((line = reader.readLine()) != null) {
here is the code:
package com.example.myfirstapp;
import java.util.concurrent.ExecutionException;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.TextView;
public class AsyncTaskActivity extends Activity implements OnClickListener {
Button btn;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
btn = (Button) findViewById(R.id.button1);
btn.setOnClickListener(this);
}
public void onClick(View view) {
switch (view.getId()) {
case R.id.button1:
try {
TextView txt = (TextView) findViewById(R.id.output);
txt.setText(new LongOperation().execute("http://search.twitter.com/search.json?q=javacodegeeks").get());
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (ExecutionException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
break;
}
}
}
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical" >
<ProgressBar
android:id="@+id/progressBar"
style="?android:attr/progressBarStyleHorizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:indeterminate="false"
android:max="10"
android:padding="10dip" >
</ProgressBar>
<Button
android:id="@+id/button1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Start Progress" >
</Button>
<TextView
android:id="@+id/output"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Replace" />
</LinearLayout>
package com.example.myfirstapp;
import java.io.BufferedReader;
import java.io.InputStream;
import java.io.InputStreamReader;
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.params.BasicHttpParams;
import org.apache.http.params.HttpConnectionParams;
import org.apache.http.params.HttpParams;
import android.os.AsyncTask;
import android.util.Log;
public class LongOperation extends AsyncTask<String, Void, String> {
InputStream is = null;
@Override
protected String doInBackground(String... urls) {
try {
HttpClient httpclient = new DefaultHttpClient();
HttpPost httppost = new HttpPost(urls[0]);
HttpResponse response = httpclient.execute(httppost);
HttpEntity entity = response.getEntity();
HttpParams myParams = new BasicHttpParams();
HttpConnectionParams.setConnectionTimeout(myParams, 10000);
HttpConnectionParams.setSoTimeout(myParams, 10000);
is = entity.getContent();
} catch (Exception e) {
Log.e("log_tag", "Error in http connection " + e.toString());
}
return is.toString();
}
@Override
protected void onPostExecute(String result) {
try {
BufferedReader reader = new BufferedReader(new InputStreamReader(
is, "iso-8859-1"), 8);
StringBuilder sb = new StringBuilder();
String line = "";
while ((line = reader.readLine()) != null) {
sb.append(line + "\n");
}
is.close();
result = sb.toString();
// System.out.println("Result = " + result);
} catch (Exception e) {
Log.e("log_tag", "Error converting result " + e.toString());
}
}
@Override
protected void onPreExecute() {
}
@Override
protected void onProgressUpdate(Void... values) {
}
}
is there anyone can help?
Upvotes: 0
Views: 684
Reputation: 133580
new LongOperation().execute("http://search.twitter.com/search.json?q=javacodegeeks").get()
Calling get()
does not make it asynchronous anymore. Blocks the ui thread.
public final Result get ()
Waits if necessary for the computation to complete, and then retrieves its result.
You need
new LongOperation().execute("http://search.twitter.com/search.json?q=javacodegeeks")
I would use a interface as a callback to communicate the result back to the activity.
Something like the answer by blackbelt in the below link
How do I return a boolean from AsyncTask?
Also move all your network related operation to doInbackground
and update ui in onPostExecute
Example:
public class MainActivity extends Activity implements LongOperation.callBack {
Button btn;
TextView txt;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
txt = (TextView) findViewById(R.id.textView1);
btn = (Button) findViewById(R.id.button1);
btn.setOnClickListener(new OnClickListener()
{
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
new LongOperation(MainActivity.this).execute("http://search.twitter.com/search.json?q=javacodegeeks");
}
});
}
@Override
public void returnText(String value) {
// TODO Auto-generated method stub
txt.setText(value);
}
}
activity_main.xml
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent" >
<Button
android:id="@+id/button1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_centerHorizontal="true"
android:text="Button" />
<TextView
android:id="@+id/textView1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentTop="true"
android:layout_centerHorizontal="true"
android:layout_marginTop="48dp"
android:text="TextView" />
</RelativeLayout>
LongOperation.java
public class LongOperation extends AsyncTask<String, Void, String> {
InputStream is = null;
String _response;
callBack cb;
ProgressDialog pd;
interface callBack
{
public void returnText(String value);
};
public LongOperation(Context context) {
// TODO Auto-generated constructor stub
cb = (callBack) context;
pd = new ProgressDialog(context);
pd.setMessage("LongOperation...");
}
@Override
protected String doInBackground(String... urls) {
try {
HttpClient httpclient = new DefaultHttpClient();
HttpPost httppost = new HttpPost(urls[0]);
HttpResponse response = httpclient.execute(httppost);
HttpEntity entity = response.getEntity();
HttpParams myParams = new BasicHttpParams();
HttpConnectionParams.setConnectionTimeout(myParams, 10000);
HttpConnectionParams.setSoTimeout(myParams, 10000);
HttpEntity resEntity = response.getEntity();
_response=EntityUtils.toString(resEntity);
is = entity.getContent();
} catch (Exception e) {
Log.e("log_tag", "Error in http connection " + e.toString());
}
return _response;
}
@Override
protected void onPostExecute(String result) {
super.onPostExecute(result);
pd.dismiss();
if(cb!=null)
{
cb.returnText(result);
}
}
@Override
protected void onPreExecute() {
super.onPreExecute();
pd.show();
}
@Override
protected void onProgressUpdate(Void... values) {
}
}
Upvotes: 2
Reputation: 152927
onPostExecute()
and onPreExecute()
run on the main UI thread. Move network operations to doInBackground()
.
Upvotes: 2