如何使用 PendingIntent 从服务到客户端/活动进行通信?

2023-12-23

我一直在 Android 开发者网站上阅读以下文本,特别是在框架主题 -> 服务 -> 启动服务 http://developer.android.com/guide/topics/fundamentals/services.html#StartingAService.

其中规定如下:

如果服务不提供绑定,则使用 startService() 传递的意图是应用程序组件和服务之间的唯一通信模式。但是,如果您希望服务发回结果,那么启动服务的客户端可以为广播创建一个 PendingIntent(使用 getBroadcast()),并将其传递到启动服务的 Intent 中的服务。然后,该服务可以使用广播来传递结果。

我对此有几个问题:

  1. 这段文字是否都适用于Services and IntentServices ?
  2. 如何(按代码方式)从内部实现这一点Service; 然后,该服务可以使用广播来传递结果。以及提到的广播将在哪里将结果传递给原始客户端/活动?是否有一些方法应该被覆盖(比如onActivityResult()) 或者其他的东西?


Question was asked few months ago, but in case anyone is still looking for answer I hope I can help.

在下面的示例中,我们有本地服务,负责执行一些耗时的操作。 Activity 向服务发出请求,但不绑定到服务 - 只是通过请求发送意图。此外,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();
      Message msg = mServiceHandler.obtainMessage();
      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. 对原始客户/活动做出响应.

您可以拥有抽象活动,您的所有活动都将从该抽象活动中扩展。此抽象活动可以自动将自身注册/注销为广播接收器中的响应侦听器。实际上这里没有太多选项,但重要的是,如果您保留对活动的静态引用,那么您必须在活动被销毁时删除该引用。

Regards,
Ramps

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

如何使用 PendingIntent 从服务到客户端/活动进行通信? 的相关文章

  • 如何在android中显示保存在sdcard文件夹中的图像[关闭]

    这个问题不太可能对任何未来的访客有帮助 它只与一个较小的地理区域 一个特定的时间点或一个非常狭窄的情况相关 通常不适用于全世界的互联网受众 为了帮助使这个问题更广泛地适用 访问帮助中心 help reopen questions 当我正在显
  • 按下按钮时应用不同的样式

    有没有办法在按下按钮时将样式应用于按钮 如果我有一种风格样式 xml
  • 如何在 Linux 内核中定义并触发我自己的新软中断?

    我想在 Linux 内核中创建自己的软中断 这是正确的方法吗 In the init我想触发该模块的softirq我将添加一个调用 394 void open softirq int nr void action struct softir
  • 如何使用 Google Maps for Android V2 处理地图移动结束?

    我想在地图中心更改后立即对地址进行地理编码 如何使用新的 Android 版 Google 地图 V2 处理地图移动 我说的是用户用手指拖动地图的情况 查看新的地图 API Override public void onMapReady G
  • Android 深度链接至 Instagram 应用

    Instagram 已经发布了 iOS 深层链接的 url 方案 但尚未为 Android 创建文档 有没有办法深入链接到 Android 上的 Instagram 应用程序 以转到 Instagram 应用程序中的特定位置 例如 Inst
  • 在 android 中建立与 MySQL 的池连接

    我需要从我的 Android 应用程序访问 MySQL 数据库 现在所有的工作都通过 DriverManager getConnection url 等等 但我必须从多个线程访问数据库 所以我必须使用连接池 问题1 是 com mysql
  • Android:后台Activity可以执行代码吗?

    后台的活动是否被视为 正在运行 并且可以执行代码 还是处于挂起状态 他们暂停了 活动生命周期 http developer android com reference android app Activity html ActivityLi
  • Android 手机作为 GSM 调制解调器在 PC 上发送/接收短信?

    是否可以将 Android 移动设备用作 PC 上的 GSM 调制解调器 我正在 net下开发应用程序来发送 接收短信等 现在我想通过 USB 将我的 Android 设备连接到我的 PC 并将其用作 GSM 调制解调器来与其通信 这里是参
  • 从 BroadcastReceiver 类调用活动方法

    我知道我可以做一个内部接收器类来调用接收器中的任何方法 但我的主要活动太大了 要做的事情也很多 因此 我需要一个扩展广播接收器的类 但它不是内部类 并且可以从我的主要活动中调用一种方法 我不知道是否可能 但我的活动是家庭活动和 single
  • Android 2.3 模拟器在更新位置时崩溃

    我正在使用 Eclipse 编写和调试 Android 应用程序 我需要做的事情之一是更新设备的位置 因此我尝试使用模拟器控制窗口中的位置控制面板 在 手动 选项卡上 我选择 十进制 输入有效的纬度和经度 然后单击 发送 不幸的是 接下来发
  • 如何在 Android 中从 WorkManager 取消工作?

    我已经保存了 WorkManagerUUID转换成String在领域数据库中 这是代码 Constraints constraints new Constraints Builder setRequiredNetworkType Netwo
  • Android 中的处理程序与异步调用

    目前我正在使用处理程序来调用 Web 服务方法以使其在后台运行 问题是它需要更多的时间来给出响应 在性能方面似乎更昂贵 现在我计划使用异步调用 哪一个是最好的 Android 中的处理程序和异步调用有什么区别 请帮我想出一个最好的解决方案
  • 在 Samsung Galaxy S5 Android 5.0 上使用 MediaPlayer 加载音频流需要超过 10 秒

    由于更新至 Android 5 0 MediaPlayer 在 Samsung Galaxy S5 上无法正常工作 启动音频流后加载时间超过 10 秒 示例代码 MediaPlayer mPlayer new MediaPlayer Str
  • 如何检查 Android 中的同步设置

    我正在构建一个 Android 应用程序 我需要检查设备中注册的每个单独帐户的同步设置 我知道我可以通过 ContentResolver 类来做到这一点 但我遇到了一些问题 我已设法获取设备上所有帐户的列表 但我不知道在运行时从哪里获取特定
  • 找不到符号 NOTIFICATION_SERVICE?

    package com test app import android app Notification import android app NotificationManager import android app PendingIn
  • 通过系统应用程序以编程方式静默安装 apk(无需 root)

    我有带有 android sharedUserId android uid system UID 1000 的系统级应用程序 设备未root INSTALL PACKAGES 权限包含在清单中 我可以静默安装下载的 apk 吗 我已经发现这
  • 没有支持 FEATURE_CAMERA_EXTERNAL 的 Android 设备

    根据this doc https source android com devices camera external usb cameras一些 Android 设备允许使用 Camera2 API 访问外部 USB 摄像头 我检查了大约
  • CamcorderProfile.videoCodec 返回错误值

    根据docs https developer android com reference android media CamcorderProfile html 您可以使用CamcorderProfile获取设备默认视频编解码格式 然后将其
  • 我的应用程序中的后退按钮出现问题[关闭]

    很难说出这里问的是什么 这个问题是含糊的 模糊的 不完整的 过于宽泛的或修辞性的 无法以目前的形式得到合理的回答 如需帮助澄清此问题以便重新打开 访问帮助中心 help reopen questions 我想在手机关闭时清除共享首选项值 你
  • Android 屏幕方向错误

    我使用的是 Android HTC HERO 2 1 版本 我写的活动

随机推荐

  • 在 Outlook VBA 中,如何更改主题以便它更改资源管理器窗格中的主题?

    当我收到电子邮件时 我会修改主题行 使其更具可读性 并且由某个自动电子邮件程序生成的 对话 实际上包含所有主题 我可以更改电子邮件视图窗格中的主题 但资源管理器窗格中的主题保持不变 如何强制更改资源管理器窗格中的主题 我必须复制电子邮件并删
  • 将 RDF .ttl 文件合并到一个文件数据库中 - 过滤并仅保留所需的数据/三元组

    我需要将 1000 多个 ttl 文件合并到一个文件数据库中 如何通过过滤源文件中的数据来合并它们 并仅保留目标文件中所需的数据 Thanks 有很多选项 但最简单的方法可能是使用 Turtle 解析器读取所有文件 并让该解析器将其输出传递
  • 无法使用 rdd.toDF() 但spark.createDataFrame(rdd) 有效[重复]

    这个问题在这里已经有答案了 我有一个以下形式的 RDDRDD string List Tuple 如下所示 u C1589 HG02922 83779208 2 677873089 0 当尝试运行以下代码将其转换为数据帧时 spark cr
  • 如何将图标和输入文本放在同一行?

    我想在左侧放置一个图标 在右侧放置一个输入类型文本 占据所有剩余空间 ico input type text 如果我将两者都设置为display inline block并设置输入的宽度为100 it 越线 因为10
  • 与其他类似类相比,HandlerThread 的最佳使用

    我试图了解使用的最佳用例HandlerThread 根据定义 用于启动具有循环器的新线程的便捷类 然后可以使用循环器创建处理程序类 请注意 仍然必须调用 start 我可能是错的 但我可以通过使用来实现类似的功能Thread Looper
  • `document` 未定义 Electron

    我正在尝试使用以下方法从文件中读取 JSONfs模块 并将其显示在div带身份证list在电子应用程序中 我的代码在index js看起来像这样 dialog showOpenDialog filenames gt if filenames
  • 如何从另一个目录获取 ruby​​ 文件

    我试图要求一个我在另一个文件中创建的 rake 文件 这两个文件位于两个不同的目录中 我在第一个文件的顶部有 require 在 require 之后的引号内有第二个文件的名称 它告诉我它无法加载此类文件 这是否意味着因为它位于不同的目录中
  • Pandas 从同一数据框中减去 2 行

    如何在以下数据帧 df 中从另一行中减去一行 RECL LCC 1 2 3 RECL LCC 35 107655 36 015210 28 877135 RECL PI 36 961519 43 499506 19 538975 我想做类似
  • Django FormView 和分页

    如果表单有效 我正在使用 django 的 FormView 返回对象集 我的视图函数是这样的 class IdeaView FormView template name contributor browse photo html def
  • 无法启动应用程序(CreateProcess 错误=87),无法使用缩短类路径解决方法

    当我在 Windows 上的 Eclipse 中启动应用程序时 我收到以下错误 执行命令行时发生异常 无法运行程序 CreateProcess error 87 参数不正确 我过去通过缩短 CLASSPATH 解决了这个问题 我现在已经到了
  • 如何维护 Web 应用程序中的状态 - 因为 HTTP 是无状态的

    我是构建 Web 应用程序的新手 刚刚开始学习和设置 Grails 我计划构建一个具有 4 到 5 页流程的应用程序 由于HTTP是无状态协议 那么通常页面之间的状态是如何维护的 我很好奇这里接受的标准是什么 我应该创建会话范围的对象并在页
  • 与 ASP.NET MVC 2 中的 SelectList 作斗争

    我有一个看起来像这样的模型 public class SampleModel public static SampleModel Create return new SampleModel Boolean true set several
  • 如何从命令行打开 SourceTree?

    有没有一种快速简单的方法可以从命令行打开 SourceTree 中的 git 存储库 我从终端做了很多 git 工作 但有时没有什么可以替代良好的历史视图 差异 希望能够在不使用书签的情况下打开 安装 SourceTree 命令行工具将为您
  • 如何从完成块中检索返回值?

    是否可以在主线程上运行完成块 例如 我有一个返回值的方法 int test here one method is called with completion block with return type void obj somemeth
  • 使用 sqlmodel 在 fastapi 中深度嵌套响应模型

    我想在这里重复一下之前的内容question https stackoverflow com questions 74719687 getting joined tables from sqlmodel as a nested respon
  • 将静态库链接到其他静态库

    我有一小段代码依赖于许多静态库 a 1 a n 我想将该代码打包在静态库中并使其可供其他人使用 我的静态库 我们称之为 X 编译得很好 我创建了一个简单的示例程序 它使用 X 中的函数 但是当我尝试将其链接到 X 时 我收到许多关于缺少库
  • 在 Unity3d 中打开 iPhone 和 Android 设备相机

    我正在开发一个应用程序 需要在全视图中打开设备摄像头 并且我正在为 iOS 和 Android 制作这个应用程序 那么谁能告诉我如何在 Unity 中为所有 Android 和 iPhone 设备打开全屏设备摄像头 这对我来说会有很大的帮助
  • 选择另一个选项卡时的 popToRootViewController

    Context 我同时使用 TabViewController 和 NavigationController 这两个选项卡是RECENT and POPULAR他们会显示帖子列表 想象你在里面RECENT选项卡并单击帖子 您将进入posts
  • 是否可以设置现有 Azure blob 的内容处置?

    基于刺激在这里的答案 Azure 存储 API 内容配置 https stackoverflow com questions 20719641 azure storage api contentdisposition 以及在这里找到的信息
  • 如何使用 PendingIntent 从服务到客户端/活动进行通信?

    我一直在 Android 开发者网站上阅读以下文本 特别是在框架主题 gt 服务 gt 启动服务 http developer android com guide topics fundamentals services html Star