Подтвердить что ты не робот

Как использовать PendingIntent для связи от Сервиса к клиенту/Деятельности?

Я читал следующий текст на сайте разработчиков Android, в частности под "Темы раздела" → "Службы" → "Запуск службы" .

Здесь говорится следующее:

Если служба также не обеспечивает привязку, цель, поставленная с помощью startService(), является единственным способом связи между компонентом приложения и службой. Однако, если вы хотите, чтобы служба отправила результат обратно, клиент, который запускает службу, может создать PendingIntent для трансляции (с помощью getBroadcast()) и доставить ее в службу в намерении, который запускает службу. Затем служба может использовать широковещательную передачу для доставки результата.

У меня есть несколько вопросов относительно этого:

  • Используется ли этот текст для Service и IntentService?
  • Как (кодовое) это должно быть достигнуто из Service; Затем служба может использовать широковещательную передачу для доставки результата., а также, где указанная передача доставляет результат первоначальному клиенту/активности? Есть ли какой-то метод, который должен быть перезаписан (например, onActivityResult()) или что-то еще?
4b9b3361

Ответ 1


Вопрос был задан несколько месяцев назад, но если кто-то все еще ищет ответ, я надеюсь, что смогу помочь.

В приведенном ниже примере у нас есть локальная служба, ответственная за выполнение некоторых трудоемких операций. Активность выполняет запросы к службе, но не привязывается к ней - просто отправляет намерение с запросом. Кроме того, Activity включает в себя информацию BroadcastReceiver, которая должна быть вызвана, когда услуга выполняется с запрошенной задачей. Информация передается PendingIntent. Служба обрабатывает задачу в фоновом потоке, и когда задача завершена, служба передает BroadcastReceiver с ответом.

1. Создайте подкласс BroadcastReceiver:

public class DataBroadcastReceiver extends BroadcastReceiver {
   static Logger log = LoggerFactory.getLogger(DataRequestService.class);   
   @Override
   public void onReceive(Context context, Intent intent) {
      log.info(" onReceive");
   }
}

Этот широковещательный приемник будет уведомлен из службы, когда задача будет выполнена.

2. Создать службу

public class DataRequestService extends Service {

   private final class ServiceHandler extends Handler {
      public ServiceHandler(Looper looper) {
         super(looper);
      }

      @Override
      public void handleMessage(Message msg) {
         log.info("handleMessage");
         //... performing some time-consuming operation         
         Bundle bundle = msg.getData();
         PendingIntent receiver = bundle.getParcelable("receiver");
         // Perform the operation associated with PendingIntent
         try {            
            //you can attach data from the operation in the intent.
            Intent intent = new Intent();
            Bundle b = new Bundle();
            //b.putString("key", value);
            intent.putExtras(b);
            receiver.send(getApplicationContext(), status, intent);
         } catch (CanceledException e) {         
         e.printStackTrace();
         }         
      }
   }

   @Override
   public void onStart(Intent intent, int startId) {
      Bundle bundle = intent.getExtras();
      msg.setData(bundle);
      mServiceHandler.sendMessage(msg);
   }

Ну, самая важная часть - в методе handleMessage(). Служба просто заставляет трансляцию работать для доставки результатов в широковещательный приемник.

3. Вам также необходимо зарегистрировать приемник и службу вещания в Manifest.xml

<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.ramps.servicetest"
    android:versionCode="1"
    android:versionName="1.0" >
   ....
       <service android:name=".service.DataRequestService" android:exported="false"/>
       <receiver android:name=".service.DataBroadcastReceiver"></receiver>
    </application>
</manifest><br>

4. И, наконец, сделайте запрос к своей службе из Activity:

Intent serviceIntent = new Intent(context, DataRequestService.class);   
   @Override
   public void onClick(View v) {
      //this is the intent that will be broadcasted by service.
      Intent broadcastReceiverIntent = new Intent(context, DataBroadcastReceiver.class);      
      //create pending intent for broadcasting the DataBroadcastReceiver
      PendingIntent pi = PendingIntent.getBroadcast(context, 0, broadcastReceiverIntent, 0);      
      Bundle bundle = new Bundle();            
      bundle.putParcelable("receiver", pi);
      //we want to start our service (for handling our time-consuming operation)
      Intent serviceIntent = new Intent(context, DataRequestService.class);
      serviceIntent.putExtras(bundle);
      context.startService(serviceIntent);
   }



5. Доставка ответа на оригинальный клиент/активность.

У вас может быть абстрактная деятельность, из которой все ваши действия будут расширяться. Эта функция abstrct может автоматически регистрировать/отменять регистрацию в качестве приемника ответа в широковещательном приемнике. На самом деле здесь не так много вариантов, но важно, чтобы, если вы сохраняете статические ссылки на свою активность, вы должны удалить ссылку, когда действие будет уничтожено.

С уважением,
Рампы