Как определить обратный вызов для завершения AsyncTask

#java #android #android-fragments #android-asynctask #fragment-oncreateview

Вопрос:

У меня есть фрагмент Android, который запрашивает веб-страницу с помощью AsyncTask и извлекает заголовок страницы, который должен отображаться в текстовом представлении. Я вызываю AsyncTask в onCreateView().

Проблема в том, что существует заметная задержка до завершения AsyncTask и создания и отображения представления фрагмента. Похоже, он не работает асинхронно.

Код выглядит следующим образом:

 GetWebsiteAsyncTask getWebsiteAsyncTask = new GetWebsiteAsyncTask(); String websiteTitle = getWebsiteAsyncTask.execute().get(); websiteViewModel.setTitle(websiteTitle);  

С помощью AsyncTask, определенной как:

 class GetWebsiteAsyncTask extends AsyncTasklt;Void, Void, Stringgt; {   private static final String TAG = GetWebsiteAsyncTask.class.getName();   @Override  protected String doInBackground(Void... voids) {  try {  Document doc = Jsoup.connect("https://www.google.com").get();  return doc.title();  } catch (Exception e) {  Log.e(TAG, Log.getStackTraceString(e));  }  return null;  } }  

Комментарии:

1. подсказка: onPostExecute проверьте документацию

2. Ладно, у меня все получилось. Я думаю, что на самом деле было очевидно, что мне понадобится обратный вызов для завершения асинхронного метода. Вызов get() должен быть похож на использование .Result в асинхронном методе C#.

Ответ №1:

Следуя совету Селвина в комментарии, я изменил код для использования делегата обратного вызова в AsyncTask следующим образом:

1.

 public interface AsyncResponse {  void processFinish(String output); }  
 class GetWebsiteAsyncTask extends AsyncTasklt;Void, Void, Stringgt; {   public AsyncResponse delegate = null;   @Override  protected void onPostExecute(String result) {  delegate.processFinish(result);  } }  
 public class WebsiteFragment extends Fragment implements AsyncResponse   
 GetWebsiteAsyncTask getWebsiteAsyncTask = new GetWebsiteAsyncTask(); getWebsiteAsyncTask.delegate = this; getWebsiteAsyncTask.execute();  
 @Override public void processFinish(String output) {  websiteViewModel.setTitle(output); }  

Комментарии:

1. Пожалуйста, обратите внимание, что AsyncTask устарел и больше не должен использоваться.

2. Спасибо за подсказку. Я изменил код для использования: ExecutorService исполнитель = Исполнители.newSingleThreadExecutor();