I use this code inorder to get the content of some website.
the textview stay empty. What I am doing wrong?
I added the jar into librires and also add internet permission to manifest.
public class MainActivity extends Activity {
MyTask mt;
TextView tvInfo;
String URL="http://www.example.com/";
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
tvInfo = (TextView) findViewById(R.id.textView1);
}
public void onclick(View v) {
mt = new MyTask();
mt.execute(URL);
}
class MyTask extends AsyncTask<String, Void, String> {
Document doc;
String title=null;
#Override
protected void onPreExecute() {
super.onPreExecute();
tvInfo.setText("Please wait");
}
#Override
protected String doInBackground(String... params) {
try {
TimeUnit.SECONDS.sleep(2);
// doc = Jsoup.connect(params[0]).get();
// String title = doc.title();
doc = Jsoup.connect("http://www.example.com/").get();
Element content = doc.select("a").first();
title = content.text();
Log.d("AsyncTask doInBackground","URL: " + params[0]);
} catch (InterruptedException e) {
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return title;
}
#Override
protected void onPostExecute(String result) {
super.onPostExecute(result);
tvInfo.setText(title);
}
}
}
I also not understand excaly when each method here is called
THANKS A LOT!
EDIT - the code after what was suggested in answer. Still not working:
public class MainActivity extends Activity implements OnClickListener{
MyTask mt;
TextView tvInfo;
String URL="http://www.example.com/";
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
tvInfo = (TextView) findViewById(R.id.textView1);
tvInfo.setOnClickListener(this);
}
private class MyTask extends AsyncTask<String, Void, String> {
#Override
protected String doInBackground(String... params) {
String title = "hh";
try{
Document doc = Jsoup.connect("http://google.com").userAgent("Mozilla").get();
title = doc.title();
System.out.println("title : " + title);
// get all links
Elements links = doc.select("a[href]");
for (Element link : links) {
// get the value from href attribute
System.out.println("\nlink : " + link.attr("href"));
System.out.println("text : " + link.text());
}
}
catch (IOException e) {
e.printStackTrace();
}
return title;
}
#Override
protected void onPostExecute(String result) {
tvInfo.setText(result);
}
#Override
protected void onPreExecute() {
tvInfo.setText("Please wait");
}
}
#Override
public void onClick(View v) {
mt = new MyTask();
mt.execute(URL);
}
}
The AsyncTask executes everything in doInBackground() inside of another thread, which does not have access to the GUI where your views are.
preExecute() and postExecute() offer you access to GUI before and after the heavy lifting occurs in this new thread, you can even pass the result of the long operation to postExecute() to then show any results of processing.
private class MyTask extends AsyncTask<String, Void, String> {
#Override
protected String doInBackground(String... params) {
try{
Document doc = Jsoup.connect("http://google.com").userAgent("Mozilla").get();
String title = doc.title();
System.out.println("title : " + title);
// get all links
Elements links = doc.select("a[href]");
for (Element link : links) {
// get the value from href attribute
System.out.println("\nlink : " + link.attr("href"));
System.out.println("text : " + link.text());
} catch (IOException e) {
e.printStackTrace();
}
}
#Override
protected void onPostExecute(String result) {
}
#Override
protected void onPreExecute() {
super.onPreExecute();
tvInfo.setText("Please wait");
}
}
Related
I used Json 1.9.2 library in Android to parse data from a website and then set the resulting data to a TextView in Android. But I am not able to set the fetched data on the TextView.
Sharing the relevant code. I'm using Fragments.
#Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
tv1 = (EditText) getActivity().findViewById(R.id.trending_textView);
new Title().execute();
}
private class Title extends AsyncTask<Void, Void, Void> {
String title;
#Override
protected void onPreExecute() {
super.onPreExecute();
mProgressDialog = new ProgressDialog(getActivity());
mProgressDialog.setTitle("Fetching the latest trends");
mProgressDialog.setMessage("#Trends");
mProgressDialog.setIndeterminate(false);
mProgressDialog.show();
}
#Override
public Void doInBackground(Void... params) {
try {
doc = Jsoup.connect(url).get();
Elements links = doc.getElementsByTag("a");
for (Element link : links) {
//String linkHref = link.attr("href");
linkText = link.text();
//System.out.println("#"+linkText);
}
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
#Override
public void onPostExecute(Void result) {
tv1.setText(linkText.toString());
mProgressDialog.dismiss();
}
}
Any help would be greatly appreciated.
you have to post the task result into UI thread by returning the result in doInbackground() method
and u will receive the result in onPostExecute() as argument , then you populate the views from there since onPostExecute() runs in UI thread
for more info :-
https://developer.android.com/reference/android/os/AsyncTask.html
#Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
tv1 = (EditText) getActivity().findViewById(R.id.trending_textView);
new Title().execute();
}
private class Title extends AsyncTask<Void, Void, Elements> {
String title;
#Override
protected void onPreExecute() {
super.onPreExecute();
mProgressDialog = new ProgressDialog(getActivity());
mProgressDialog.setTitle("Fetching the latest trends");
mProgressDialog.setMessage("#Trends");
mProgressDialog.setIndeterminate(false);
mProgressDialog.show();
}
#Override
public Elements doInBackground(Void... params) {
Elements links ;
try {
doc = Jsoup.connect(url).get();
links = doc.getElementsByTag("a");
} catch (Exeption e ) {
return null ;
}
return links;
}
#Override
public void onPostExecute(Elements ...links) {
if(links.get(0) == null) return ;
for (Element link : links.get(0)) {
//String linkHref = link.attr("href");
linkText = link.text();
// u might add scrolling behavior
tv.append(linktext + "\n");
//System.out.println("#"+linkText);
}
}
}
I have a class AsyncCallWS that get content from webservice. It worked well. However, I want to get result in the class AsyncCallWS, namely returnServer string in the MainActivity . Could you help me to solve it?
public class MainActivity extends Activity {
String resultRegister;
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
Button btnRegister =(Button) findViewById(R.id.btnRegister);
btnRegister.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(final View v) {
new AsyncCallWS().execute("123");
Log.d("DDD",resultRegister);
if(resultRegister.equals("")) {
Log.d("D", "OK");
}
else
{
Log.d("E", "False");
}
}
});
}
private class AsyncCallWS extends AsyncTask<String, Void, Void> {
#Override
protected Void doInBackground(String... params) {
Log.i(TAG, "doInBackground");
String id_num = params[0];
//toast(id);
String url_registerID="server path"+id_num ;
try {
String returnServer=getStringContent(id);
Log.d("D",returnServer);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return null;
}
#Override
protected void onPostExecute(Void result) {
Log.i(TAG, "onPostExecute");
}
#Override
protected void onPreExecute() {
Log.i(TAG, "onPreExecute");
}
#Override
protected void onProgressUpdate(Void... values) {
Log.i(TAG, "onProgressUpdate");
}
}
Remove 3rd parameter Void from this AsyncTask<String, Void, Void>
and replace it with String, i.e;
private class AsyncCallWS extends AsyncTask<String, Void, String>
After changing you'll get compilation errors in your doInBackground().. just change the return type from Void to String
protected String doInBackground(String... params)
Now you can get the String returned by this method in onPostExecute(String result)
The String result here is the String which is returned by doInBackground()
*EDIT *
public class MainActivity extends Activity {
String resultInActivity;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
new AsyncCallWS().execute("123");
//How to get respond from AsyncCallWS
}
private class AsyncCallWS extends AsyncTask<String, Void, Void> {
#Override
protected String doInBackground(String... params) {
Log.i(TAG, "doInBackground");
String id_num = params[0];
//toast(id);
String url_registerID="server path"+id_num ;
try {
String returnServer=getStringContent(id);
Log.d("D",returnServer);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return returnServer;
}
#Override
protected void onPostExecute(String result) {
Log.i(TAG, "onPostExecute");
resultInActivity = result;
if(resultRegister.equals("")) {
Log.d("D", "OK");
}
else
{
Log.d("E", "False");
}
}
#Override
protected void onPreExecute() {
Log.i(TAG, "onPreExecute");
}
#Override
protected void onProgressUpdate(Void... values) {
Log.i(TAG, "onProgressUpdate");
}
} // Asyntask ends
} // activity ends
The response from AsyncTask is produced in onPostExecute() from there you can perform tasks based on the response etc.
I highly recommend you read the AsyncTask Life Cycle
private class AsyncCallWS extends AsyncTask
Replace the third parameter with String which results doInBackground return String and corresponding postExecute method parameter as String
protected String doInBackground(String... params)
protected void onPostExecute(String result)
In Order to get it on MainActivity you have to do the following Steps
Create an Interface anywhere you want to and declare a method of any name which should have parameter of type String
interface ResponseHandler
{
void onResponse(String result)
}
In the MainActivity you have to implement that interface and you will
get the data here in this method
ResponseHandler handler = new ResponseHandler(){
#override
public void onResponse(String result)
{
// enter code here
}
};
After implementing this interface you can provide the instance of it to the AsyncTask constructor.
AsyncTask task = new AsyncTask(handler);
You will get the reference of ResponseHandler in AsyncTask
public AsyncTaskClass(ResponseHandler handler)
{
this.handler = handler
}
//enter code here
void onPostExecute(String result)
{
handler.onResponse(result)
}
This way you will get the result in your MainActivity.
public class Feedback extends ActivityGroup {
protected static LocalActivityManager mLocalActivityManager;
private EditText fd=null;
private Button send=null;
public int res_flag=0;
public String result="";
public String url="";
private RelativeLayout newaccount;
private TextView needhelp=null;
private String currentDateandTime="";
private boolean isonline;
protected String fd_text="";
public void replaceContentView(String id, Intent newIntent) {
View view = getLocalActivityManager().startActivity(id,newIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)) .getDecorView(); this.setContentView(view);
}
#Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.feedback);
initialization();
try{
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
currentDateandTime = sdf.format(new Date());
}catch (Exception e) {
System.out.println(e);
}
send.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
new Feedback.Retrieve().execute();
}
});
}
private void initialization()
{
fd=(EditText)findViewById(R.id.fd);
send=(Button)findViewById(R.id.send);
}
class Retrieve extends AsyncTask<Void, Integer, Integer> {
ProgressDialog pd = null;
#Override
protected void onPreExecute() {
// TODO Auto-generated method stub
super.onPreExecute();
pd = new ProgressDialog(Feedback.this);
pd.setMessage("Please wait while sending feedback..");
pd.setCancelable(false);
pd.show();
}
#Override
protected Integer doInBackground(Void... params) {
try{
System.out.println("IN BKGRND");
StrictMode.ThreadPolicy policy1 = new StrictMode.ThreadPolicy.Builder().permitAll().build();
StrictMode.setThreadPolicy(policy1);
url="url"+fd_text.toString().trim()+"&datetime="+currentDateandTime;
url=url.replace(" ","%20");
url=url.replace("+","%2B");
System.out.println(url);
JSONObject json = JSONfunctions.getJSONfromURL(url);
JSONObject response1=json.getJSONObject("response");
result=response1.getString("Success").toString().trim();
System.out.println(result);
if(result.equalsIgnoreCase("1"))
{
System.out.println("Logged In");
res_flag=1;
}
else
{
System.out.println("failed");
res_flag=5;
}
}
catch (JSONException e) {
System.out.println(e);
}catch (Exception e) {
System.out.println(e);
}
return null;
}
#Override
protected void onPostExecute(Integer result) {
super.onPostExecute(result);
pd.dismiss();
}
Error is:
android.view.WindowManager$BadTokenException: Unable to add window -- token android.app.LocalActivityManager$LocalActivityRecord#40e16110 is not valid; is your activity running?
PROBLEM
I calling activity through another tabhost.,It loading only the view .The webservice and button are not working ., When i click the buttons it shows above error.Help me to proceed guys..
Reference:
http://www.gamma-point.com/content/android-how-have-multiple-activities-under-single-tab-tabactivity
NOw the ActivityGroup is deprecated.., What should i use now..
For what you have posted, it doesn't seem like you need to use ActivityGroup at all. Simply extend your Feedback from Activity class. For example:
public class Feedback extends Activity
This is my code:
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Log.i(TAG, "onCreate");
setContentView(R.layout.list);
new GetBlockListAsyncTask().execute(BlockListActivity.this);
}
public void initializeDialog() {
dialog = ProgressDialog.show(BlockListActivity.this, "", "Loading data. Wait...", true);
dialog.show();
}
public void dismissDialog(){
dialog.dismiss();
}
The GetBlockListAsyncTask:
public class GetBlockListAsyncTask extends AsyncTask<Object, Boolean, String>{
private BlockListActivity callerActivity;
private String TAG = "GetBlockListAsyncTask";
private String stringCode = "";
#Override
protected String doInBackground(Object... params) {
callerActivity = (BlockListActivity)params[0];
try {
Log.d(TAG, "Start to sleep");
Thread.sleep(4000);
Log.d(TAG, "End sleep");
} catch (InterruptedException e) {
e.printStackTrace();
}
return null;
}
#Override
protected void onPostExecute(String response) {
callerActivity.dismissDialog();
}
#Override
protected void onPreExecute() {
callerActivity.initializeDialog();
}
}
It will show error:
'Caused by: java.lang.NullPointerException'
onPreExecute(GetBlockListAsyncTask.java:101)
I find a solution is that if I move the initializeDialog out of the AsyncTask and put it before the line new GetBlockListAsyncTask().execute(BlockListActivity.this); in onCreate, it works.
The question is how to make it work if I want to put the initializeDialog in the AsyncTask .
Try adding a public constructor to your AsyncTask that accepts the Activity Context as the first argument:
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// Create a new AsyncTask with the Activity Context
AsyncTask task = new GetBlockListAsyncTask(this);
// Execute the task
task.execute();
}
public class GetBlockListAsyncTask extends AsyncTask<Object, Boolean, String> {
private Context activityContext;
private String TAG = "GetBlockListAsyncTask";
private String stringCode = "";
//Constructor
public GetBlockListAsyncTask(Context c) {
// Store the activity context
activityContext = c;
}
#Override
protected String doInBackground(Object... params) {
try {
Log.d(TAG, "Start to sleep");
Thread.sleep(4000);
Log.d(TAG, "End sleep");
} catch (InterruptedException e) {
e.printStackTrace();
}
return null;
}
#Override
protected void onPostExecute(String response) {
activityContext.dismissDialog();
}
#Override
protected void onPreExecute() {
activityContext.initializeDialog();
}
}
I'm trying to implement async on Android but it keeps crashing my app, the code in doInBackground works if I put it in the oncreate so that i know that It works
any help is greatly appreciated
thanks
here's my code :
public class accueilEco extends Activity
{
String[] param = new String[5];
TextView nom;
TextView prenom;
ProgressDialog mDialog;
Context ctxt;
TelephonyManager tm;
connectEco ce;
#Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
nom = (TextView) findViewById(R.id.user);
ctxt = getBaseContext();
tm = (TelephonyManager) getSystemService(TELEPHONY_SERVICE);
new chargerParam().execute();
}
public class chargerParam extends AsyncTask<Void, Void, Void> {
#Override
protected void onPostExecute(Void result) {
// TODO Auto-generated method stub
}
#Override
protected void onPreExecute() {
// TODO Auto-generated method stub
}
#Override
protected Void doInBackground(Void... params) {
try
{
ce =new connectEco();
param = ce.recupereParam(tm.getDeviceId());
if(String.valueOf(param[4]) == String.valueOf(1))
{
Toast.makeText(ctxt, "Paramétres chargées" , Toast.LENGTH_LONG).show();
//setContentView(R.layout.home);
nom.setText(param[1]+" "+ param[2]+" - "+param[3]);
}
else
{
Toast.makeText(ctxt, "=> login" , Toast.LENGTH_LONG).show();
}
}
catch(Exception ex)
{
Toast.makeText(ctxt, "erreur" , Toast.LENGTH_LONG).show();
}
return null;
}
}
}
You cannot access UI objects from another thread than the UI thread. The code:
nom.setText(param[1]+" "+ param[2]+" - "+param[3]);
will throw the exception.
You can access the UI elements when you are in onPreExecute() or onPostExecute(Result). Accessing UI elements while youre in doInBackground, it'll result in exception.
To "fix" this you need to read through and understand the AsyncTask implementation. Instead of declaring your background task by AsyncTask<Void, Void, Void> you can provide an "result type" that the can be posted from the doInBackground method to the onPostExecute method (on the UI thread). AsyncTask<Void, Void, String> (the String type).
You would have to do something like this:
#Override
protected void onPostExecute(String result) {
if (result != null)
nom.setText(result);
// else show toast
}
#Override
protected String doInBackground(Void... params) {
try {
String[] param = new connectEco().recupereParam(tm.getDeviceId());
if (String.valueOf(param[4]) == String.valueOf(1))
return param[1]+" "+ param[2]+" - "+param[3];
} catch(Exception ex) {
// ignore and return null
}
return null;
}