Interface update when working in the background

I have a database update operation that has activity that continues to update the percentage and runs inside AsyncTask.

Inside doInBackground (), I call the controller, which updates the database and constantly updates the percentage of activity, however, if I click the "Home" or "Back" button, the operation is canceled. What are you suggesting me to do?

I tried to start the service inside doInBackground () so that it works in the background, but it looks like it is not working.

My code is as follows:

public class UpdateDatabaseAsyncTask extends AsyncTask<Void, Integer, Integer> { @Override public void onPreExecute() { mCustomProgressBar.startAnimation(); } @Override public Integer doInBackground(Void... params) { return mController.updateDatabase(); } @Override public void onPostExecute(Integer result) { mCustomProgressBar.stopAnimation(); // finish the activity } @Override public void onProgressUpdate(Integer... value) { updatePercentageValue(value[0]); } public void callPublishProgress(Integer value) { publishProgress(value); } } 

And inside the controller, I call the callPublishProgress(value) method, which passes the current percentage value, so it will publishProgress(value) in the user interface.

I debugged and I pressed the home / back button and it just stopped the workflow.


Another solution that I tried started the Service to start in the background, regardless of how the user presses the home / back button or not, so I thought, and the Service would make a call to the controller method that does this work, and this will call callPublishProgress(value) to update the percentage value in the user interface.

However, what happens, the code reaches doInBackground() and starts the service, but it immediately goes to onPostExecute() , it just did not wait for the service to finish (of course! ). Therefore, it gives a NullPointerException . I was thinking of creating a loop inside doInBackground() with the flag set in the Service, so it would leave this loop until the service was finished (I used IntentService), but this did not work.

I also thought about using a timer. But I do not know.

I read articles in Threads documentation, etc. And he suggests using AsyncTask , as I tried. It also talks about runOnUiThread(Runnable) .

In any case, I need to do the operation in the background (perhaps using IntentService), so regardless of whether the user clicks the home button, he will continue to work, but he must update the percentage of the user interface, and when the user leaves the screen and returns to it, it shows the current percentage value updated on the screen.

What is the best solution for my case?

Thanks.

+6
source share
3 answers
 public class MyServce extends Service{ public static final String BROADCAST_ACTION = "com.myapp"; Intent intent; private final Handler handler = new Handler(); @Override public void onCreate() { super.onCreate(); intent = new Intent(BROADCAST_ACTION); } @Override public void onStart(Intent intent, int startId) { handler.removeCallbacks(sendUpdatesToUI); handler.postDelayed(sendUpdatesToUI, 1000); // 1 second } private Runnable sendUpdatesToUI = new Runnable() { public void run() { DoYourWorking(); handler.postDelayed(this, 1000); // 1 seconds } private void DoYourWorking() { ........ ........ intent.putExtra("key", progress); sendBroadcast(intent); } }; @Override public IBinder onBind(Intent intent) { // TODO Auto-generated method stub return null; } @Override public void onDestroy() { super.onDestroy(); handler.removeCallbacks(sendUpdatesToUI); } 

Now in your activity register the service is transferred

 private BroadcastReceiver brodcast = new BroadcastReceiver() { @Override public void onReceive(Context context, Intent intent) { //intent.getWhatever // update your progress //progressbar.setProgress } 

register broadcast

  registerReceiver(brodcast, new IntentFilter(MyService.BROADCAST_ACTION)); 
+3
source

It worked for me. I started a background service in a thread that just retrieves the values โ€‹โ€‹and updates the object in singleton mode.

In the view controller, I start a timer that continues to update the view, retrieving data from the object in singleton mode.

I had a little problem understanding the entire question text, so I'm not sure if you tried this. But this is what worked. In addition, the service was launched using START_STICKY

+1
source

Use IntentService (this is a separate thread service) and Handler to pass data to Activity.

+1
source

Source: https://habr.com/ru/post/914356/


All Articles