Android Execute Asyntask within another class from another class - android

I have a class inside which there is another class that extends AsyncTask. As,
public class Dashboard extends Activity {
-------------
--------------
--------------
public class getUnreadMessageCount extends AsyncTask<String, String, JSONObject> {
protected JSONObject doInBackground(){
*********some database stuff************
}
protected void onPostExecute(JSONObject json) {
count = Integer.parseInt(json.getString("messsage_count"));
// Set Text to the textview
messageCount.setText(count);
}
}
}
Now I am using GCMIntentService Class for notification. How can I call and execute the getUnreadMessageCount in the following
private void sendNotification(String content_id, int type, String msg) {
}
I tried as
private void sendNotification(String content_id, int type, String msg) {
Dashboard dashboard = new Dashboard;
dashboard.Dashboard dashboard----
}
But it does not work. How could I solve this problem.

What I see here is very bad style and not according to the Java-Code-Conventions. You are naming a class like a method. In java generally, all Class names are written in capital letters and should be nouns.
public class getUnreadMessageCount extends AsyncTask
should be called (at least):
public class GetUnreadMessageCount extends AsyncTask
or much better:
// make clear it is an async task
public class GetUnreadMessageCountTask extends AsyncTask
This is how to start the AsyncTask:
private void sendNotification(String content_id, int type, String msg) {
new GetUnreadMessageCountTask().execute();
}
The execute(...) method can also take parameters, depending on your specification of the AsyncTask. For a general explaination of the AsyncTask, have a look here: How to use AsyncTask

Related

How can I loop my AsyncTask to download a data blob in a loop?

I'm running httpsCommand (shown below, via clientTask() from MainActivity) and downloading about 1KB of data from a webserver. I plan to update a ListView in MainActivity (I think that's possible, but I recall it being a bit annoying last time I did it) with the downloaded data inside myListAllDoneListener(). I'd like to run this in a loop every 5 minutes to check for new data.
I've tried running new myCLientTask().execute()... inside a while loop (using Thread.sleep and try/catch) but it only seemed to run one loop and crashed after 15 seconds or so. Found a similar question but it's not quite answered. How can I background this data download?
// ** MainActivity.java **
public class MainActivity extends AppCompatActivity
{
...
#Override
protected void onCreate(Bundle savedInstanceState)
{
new clientTask(getApplicationContext(), myListAllDoneListener, ...);
...
private AsyncTaskCompleteListener myListAllDoneListener = new AsyncTaskCompleteListener()
{
#Override
public void onComplete(ArrayList<String> data, String msg, int statuscode)
{
// update listview with new data
...
//** clientTask.java **
public class clientTask extends Activity
{
ArrayList<String> mData;
...
public clientTask (Context ctx, AsyncTaskCompleteListener ... String cmd, ...)
{
...
new myClientTask().execute();
...
private class myClientTask extends AsyncTask<Object, Object, Object>
{
...
protected Object doInBackground (Object... params)
{
mData = httpsCommand (mCmd);
...
You can't use Thread.sleep in activity. It will block your UI. To run a periodic task
Look this stackoverflow answer using Handlers.
Also, there are some things wrong with your code. You shouldn't create object of an Activity class and use it for such things.

Cannot access variables from Async Task

I am new to android.I have spent too much time solving this issue with no success.
So i have service Serv.java.
public class Serv extends Service {
private String a = "aa";
private String b = "bb";
private String c = "100";
//called by some class.
public void setcc(String s) {
c=s;//c="cc"
}
//Using alarm manager to start the service.
//I call function callMe from OnStart.
void callMe(Context context){
//which calls an async task
new VAsyncTask().execute("");
}
private class VerifyCPIAsyncTask extends AsyncTask<String, Void, Void> {
protected void onPreExecute() {
}
protected Void doInBackground(String... urls) {
//I am able to access a and b.(aa and bb)
//but not c.(It still shows 100 and not cc)
}
........
}
But when i run the same service again it shows correct value for c(cc).There is problem when i am accessing for the first time.
EDIT- The flow works fine if i make private String c to private static String c.
And i have put logs in my onCreate and onStartCommand.They do not print the latest value of variable c.so there is no use passing (latest)variable c to preexecute or even create a constructor in the aysnctask(cause i still get the old value of variable c).
Please help.
Thanks.
its difficult to tell without knowing from where/what and how your flow is?
you can override the constructor and pass the values as async task parameter .
*
private class VerifyCPIAsyncTask extends AsyncTask<String, Void, Void>
{
int cc
VerifyCPIAsyncTask (int a) {
cc= a;
}
protected void onPreExecute() {
}
}*
and call your async task as new VAsyncTask(cc).execute("");
it is safer approach.

Substitute for activity argument when calling a class from AsyncTask

here's a portion of my code:
public class Login extends Activity {
private class LoginUser extends AsyncTask<String, String, Boolean> {
#Override
protected void onPostExecute(Boolean returnResult) {
DialogSelectAccount dsa=new DialogSelectAccount(getParent());
dsa.show();
}
}
}
public class DialogSelectAccount extends Dialog implements android.view.View.OnClickListener {
public DialogSelectAccount(Activity a) {
super(a);
}
}
but when I run the app, it get a NPE error at the "super(a)" under the public DialogSelectAccount();
but when I changed my code to
public class Login extends Activity {
private class LoginUser extends AsyncTask<String, String, Boolean> {
#Override
protected void onPostExecute(Boolean returnResult) {
test();
}
}
public void test(){
DialogSelectAccount dsa=new DialogSelectAccount(this);
dsa.show();
}
}
it works. So what if I don't want to create a separate method like above and calls DialogSelectAccount directly inside the onPostExecute, what should I pass as the argument?
Thanks
So what if I don't want to create a separate method like above and calls DialogSelectAccount directly inside the onPostExecute, what should I pass as the argument?
answer:
DialogSelectAccount dsa=new DialogSelectAccount(Login.this);
This is rather general java question, for more on inner classes read here: Getting hold of the outer class object from the inner class object
The dialog class needs a Context attribute.
When you say getParent() - I suppose it does not return context.
You can keep the context attribute in a global class and retrieve it - though I will not recommend that.

android asynctask sending callbacks to ui [duplicate]

This question already has answers here:
How to get the result of OnPostExecute() to main activity because AsyncTask is a separate class?
(17 answers)
Closed 6 years ago.
I have the following asynctask class which is not inside the activity. In the activity I'm initializing the asynctask, and I want the asynctask to report callbacks back to my activity.
Is it possible? Or does the asynctask must be in the same class file as the activity?
protected void onProgressUpdate(Integer... values)
{
super.onProgressUpdate(values);
caller.sometextfield.setText("bla");
}
Something like this?
You can create an interface, pass it to AsyncTask (in constructor), and then call method in onPostExecute()
For example:
Your interface:
public interface OnTaskCompleted{
void onTaskCompleted();
}
Your Activity:
public class YourActivity implements OnTaskCompleted{
// your Activity
}
And your AsyncTask:
public class YourTask extends AsyncTask<Object,Object,Object>{ //change Object to required type
private OnTaskCompleted listener;
public YourTask(OnTaskCompleted listener){
this.listener=listener;
}
// required methods
protected void onPostExecute(Object o){
// your stuff
listener.onTaskCompleted();
}
}
EDIT
Since this answer got quite popular, I want to add some things.
If you're a new to Android development, AsyncTask is a fast way to make things work without blocking UI thread. It does solves some problems indeed, there is nothing wrong with how the class works itself. However, it brings some implications, such as:
Possibility of memory leaks. If you keep reference to your Activity, it will stay in memory even after user left the screen (or rotated the device).
AsyncTask is not delivering result to Activity if Activity was already destroyed. You have to add extra code to manage all this stuff or do you operations twice.
Convoluted code which does everything in Activity
When you feel that you matured enough to move on with Android, take a look at this article which, I think, is a better way to go for developing your Android apps with asynchronous operations.
I felt the below approach is very easy.
I have declared an interface for callback
public interface AsyncResponse {
void processFinish(Object output);
}
Then created asynchronous Task for responding all type of parallel requests
public class MyAsyncTask extends AsyncTask<Object, Object, Object> {
public AsyncResponse delegate = null;//Call back interface
public MyAsyncTask(AsyncResponse asyncResponse) {
delegate = asyncResponse;//Assigning call back interfacethrough constructor
}
#Override
protected Object doInBackground(Object... params) {
//My Background tasks are written here
return {resutl Object}
}
#Override
protected void onPostExecute(Object result) {
delegate.processFinish(result);
}
}
Then Called the asynchronous task when clicking a button in activity Class.
public class MainActivity extends Activity {
#Override
public void onCreate(Bundle savedInstanceState) {
Button mbtnPress = (Button) findViewById(R.id.btnPress);
mbtnPress.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
MyAsyncTask asyncTask =new MyAsyncTask(new AsyncResponse() {
#Override
public void processFinish(Object output) {
Log.d("Response From Asynchronous task:", (String) output);
mbtnPress.setText((String) output);
}
});
asyncTask.execute(new Object[] { "Youe request to aynchronous task class is giving here.." });
}
});
}
}
Thanks
IN completion to above answers, you can also customize your fallbacks for each async call you do, so that each call to the generic ASYNC method will populate different data, depending on the onTaskDone stuff you put there.
Main.FragmentCallback FC= new Main.FragmentCallback(){
#Override
public void onTaskDone(String results) {
localText.setText(results); //example TextView
}
};
new API_CALL(this.getApplicationContext(), "GET",FC).execute("&Books=" + Main.Books + "&args=" + profile_id);
Remind: I used interface on the main activity thats where "Main" comes, like this:
public interface FragmentCallback {
public void onTaskDone(String results);
}
My API post execute looks like this:
#Override
protected void onPostExecute(String results) {
Log.i("TASK Result", results);
mFragmentCallback.onTaskDone(results);
}
The API constructor looks like this:
class API_CALL extends AsyncTask<String,Void,String> {
private Main.FragmentCallback mFragmentCallback;
private Context act;
private String method;
public API_CALL(Context ctx, String api_method,Main.FragmentCallback fragmentCallback) {
act=ctx;
method=api_method;
mFragmentCallback = fragmentCallback;
}
I will repeat what the others said, but will just try to make it simpler...
First, just create the Interface class
public interface PostTaskListener<K> {
// K is the type of the result object of the async task
void onPostTask(K result);
}
Second, create the AsyncTask (which can be an inner static class of your activity or fragment) that uses the Interface, by including a concrete class. In the example, the PostTaskListener is parameterized with String, which means it expects a String class as a result of the async task.
public static class LoadData extends AsyncTask<Void, Void, String> {
private PostTaskListener<String> postTaskListener;
protected LoadData(PostTaskListener<String> postTaskListener){
this.postTaskListener = postTaskListener;
}
#Override
protected void onPostExecute(String result) {
super.onPostExecute(result);
if (result != null && postTaskListener != null)
postTaskListener.onPostTask(result);
}
}
Finally, the part where your combine your logic. In your activity / fragment, create the PostTaskListener and pass it to the async task. Here is an example:
...
PostTaskListener<String> postTaskListener = new PostTaskListener<String>() {
#Override
public void onPostTask(String result) {
//Your post execution task code
}
}
// Create the async task and pass it the post task listener.
new LoadData(postTaskListener);
Done!

how to pass the result of asynctask onpostexecute method into the parent activity android

I am developing an application in which i need to send the value of the asynctask's onPostExecute method's result in to the previous activity , ie the activity in which the aync task is being called.pls put some codes. Anyhelp is appreciated
Two ways:
Declare class extending AsyncTask as private class in parent Activity
Pass Handler or Activity itself as param of class extending AsyncTask
If I were you, I'd follow the first option.
Look at DOCS:
class MyActivitySubclass extends Activity {
function runOnPostExecute(){
// whatever
}
private class MyTask extends AsyncTask<Void, Void, Void> {
void doInBackground(Void... params){
// do your background stuff
}
void onPostExecute(Void... result){
runOnPostExecute();
}
}
}
Note 1
Code placed in body of function onPostExecute is already run on Activity thread, you should just mention that this keywords leads to MyTask.this and not MyActivitySubclass.this
Well if your AsyncTask is an inner class, you could simply call a method in your activity from onPostExecute():
public class MyActivity extends Activity {
public void someMethod(String someParam) {
// do something with string here
}
public class InnerTask extends AsyncTask<...> {
protected void onPostExecute(result) {
someMethod(Send parameters);
}
}
}
The onPostExecute method is fired on the main UI thread, so anything done there is already on the AsyncTasks caller.
http://developer.android.com/reference/android/os/AsyncTask.html
Fire an event in the OnPostExecute.
Its an add on to the answer by Marek Sebera, he pointed to use a handler. To keep the code simple and intuitive use an interface. This isn't alien concept, we use it all the time for callback functions (eg: OnClickListner etc..). The code would look some thing like this.
public class InnerTask extends AsyncTask<...>
{
interface ResultHandler
{
void gotResult(<> result);
}
private ResultHandler myResult;
//constructor
public InnerTask(....params...,ResultHandler callback)
{
...
this.myResult = callback;
}
protected void onPostExecute(<>result)
{
...
myResult.gotResult(result);
}
}
public class MyActivity extends Activity implements InnerTask.ResultHandler
{
#Override
protected void onCreate(Bundle savedInstanceState)
{
//do something
//if you want the InnerTask to execute here
InnerTask i = new InnerTask(....params...,this); //send 'this' as parameter
i.execute();
}
#Override
public void gotResult(<> result)
{
//from onPostExecute
}
}
If we want to use the same AsynTask class at multiple sites we can use this type of implementation instead of using nested classes implementation.

Categories

Resources