0

У меня длинный расчет, который принимает данные датчиков в качестве аргументов.Запрос фоновой задачи для запуска несколько раз в Android

После получения результата вычисления я хотел бы вызвать метод для обновления представления.

Этот расчет может занять некоторое время, поэтому я не могу запустить его внутри кода операции, поскольку получаю данные датчика, потому что поток пользовательского интерфейса замерзает или замедляется.

Поскольку я хочу запускать этот расчет каждый раз, когда получаю новые данные датчика, какие варианты меня предлагает Android?

Я пробовал использовать AsyncTask. Я бы запустил AsyncTask для запуска вычисления с использованием новых данных датчика, и метод обновления View получил бы вызов внутри его onPostExecute.

К сожалению, этот подход вызвал проблемы с синхронизацией анимации: AsyncTask может завершиться после следующего, и обновление View будет вызвано с устаревшей информацией, что делает ее анимацию неустойчивой.

Я также пробовал использовать ту же AsyncTask с executeOnExecutor, передав на него Single Thread Executor, но это не остановило дрожание анимации.

Наконец, я попытался запустить IntentService с обратным вызовом ResultReceiver внутри MainActivity. Хотя я могу запустить его, он работает только один раз. Я не понял, для чего предназначены IntentServices? Я не могу запустить его несколько раз (используя метод, который создает намерение с дополнительными параметрами и вызывает с ним startService).

Резюме: У меня медленный метод, который работает с данными датчика. Я хочу запускать его в фоновом режиме каждый раз, когда я получаю новые данные датчика, и использую его результат/ответ для обновления представления.

Любые предложения?

+0

использования Rx Java это работает так же, как и задача async, и работает лучше. –

ответ

0

Ваша служба здесь .....

public class One extends Service { 
public static final long NOTIFY_INTERVAL = 10 * 1000; 
private Handler handler = new Handler(); 
private Timer timer = null; 

@Override 
public IBinder onBind(Intent intent) { 
    return null; 
} 

@Override 
public void onCreate() 
{ 
    if (timer != null) 
    { 
     timer.cancel(); 
    } else 
    { 
     timer = new Timer(); 
    } 
    timer.scheduleAtFixedRate(new DisplayTime(), 0, NOTIFY_INTERVAL); 
} 

class DisplayTime extends TimerTask 
{ 

    @Override 
    public void run() { 
     handler.post(new Runnable() { 

      @Override 
      public void run() { 
       recall(); 
       Toast.makeText(getApplicationContext(), "run", Toast.LENGTH_SHORT).show(); 
      } 

     }); 
    } 
public void recall() { 

     // Write here Async Task Method...... 
    } 
}   
    @Override 
    public void onDestroy() 
    { 
    super.onDestroy(); 
    Toast.makeText(getApplicationContext(), "des", Toast.LENGTH_SHORT).show(); 
    } 
} 
+0

Как моя активность будет взаимодействовать с этой услугой? Скажем, если моя активность получает обновления данных датчиков, как она может отправить их этой службе и получить от нее ответ? – vekat

+0

Могу ли я увидеть ваш код MainActivity? - @vekat –

+0

Привет @ вулкан-секрет, мне удалось связаться с Activity с помощью ResultReceiver. Я не очень точно использовал ваш подход (мне не нужен TimerTask), но для меня работала функция подкласса Service и использование HandlerThread. – vekat

0

Хотя я не уверен, какую анимацию вы используете, в зависимости от структуры вашего приложения и кода, некоторые из параметров могут быть скорее, чем обновление данных в onPostExecute(), если вы можете сделать это в метод обратного вызова анимации, который сообщает вам, что анимация завершена, то есть рассчитайте ее в асинтете, но обновите свой арраист или что вы используете в методе обратного вызова анимации. Во-вторых, если у вас есть общее представление о том, сколько времени требуется для завершения анимации, вы можете применить обработчик с таймером и попытаться совместить обе операции, вызвав анимацию с задержкой. Аналогичным образом вы можете использовать широковещательный приемник или интерфейс, если операция пользовательского интерфейса осуществляется через действия.

0

можно реализовать onProgressUpdate() метод AsyncTask, то в вашем doInBackground() вы можете позвонить publishProgress() вы можете обновить пользовательский интерфейс в onProgressUpdate()

Смежные вопросы