从Activity启动IntentService并在IntentService完成时刷新Activity

在我的Android应用程序中,我有一个带适配器的简单列表视图。 有一个繁重的查询是用数据填充列表视图。 所以我把它放到另一个线程中运行的IntentService中。

IntentService通常单独运行,只是为了查询一些数据并将其插入SQLite数据库。

但现在我想有以下可能性:

  1. 该活动使用startService()启动IntentService。
  2. IntentService做了很多工作。
  3. 当IntentService完成时,它应该通知活动有关结果的信息,以便可以刷新活动以显示新数据。

这可能吗? 我在这个主题的Stack Overflow上阅读了很多问题。 但在每一个问题中,都有另一种解决方案。 所以我想问你们所有人:哪种解决方案最符合我的目的?

  • 将IntentService绑定到Activity似乎不是最佳解决方案,因为可能存在与活动等配置更改的冲突。正确吗?
  • 这篇博文建议使用带有Parcelables的AIDL – 这对我来说听起来非常复杂。 有一种更简单的方法,不是吗?
  • 可以在活动中设置广播接收器,并在完成后在IntentService中触发此广播。
  • 有人说你应该使用createPendingResult()将PendingIntent传递给IntentService。 如果IntentService在其附加内容中发现PendingIntent,则使用它来触发Activity中的onActivityResult()。 这是选择的方式吗?

Solutions Collecting From Web of "从Activity启动IntentService并在IntentService完成时刷新Activity"

例如,我使用ResultReceiver在我的Activity (扩展ListActivity )的适配器上调用notifyDataSetChanged() )。 它可以适应你需要做的任何事情。

ResultReceiver代码:

 public class MyResultReceiver extends ResultReceiver { private Context context = null; protected void setParentContext (Context context) { this.context = context; } public MyResultReceiver(Handler handler) { super(handler); } @Override protected void onReceiveResult (int resultCode, Bundle resultData) { // Code to process resultData here ((BaseAdapter) ((ListActivity)context).getListAdapter()).notifyDataSetChanged(); } } 

MyActivity代码:

 public class MyActivity extends ListActivity { private MyResultReceiver theReceiver = null; ... private void callService () { theReceiver = new MyResultReceiver(new Handler()); theReceiver.setParentContext(this); Intent i = new Intent("com.mycompany.ACTION_DO_SOMETHING"); // Code to define and initialize myData here i.putExtra("someData", myData); i.putExtra("resReceiver", theReceiver); startService(i); } } 

IntentService代码:

 Bundle resultBundle = new Bundle(); ResultReceiver resRec = intent.getParcelableExtra("resReceiver"); // Do some work then put some stuff in resultBundle here resRec.send(12345, resultBundle); 

当IntentService完成时,它应该使用LocalBroadcastManager向任何已注册的活动发送意图。

IntentService将包含如下代码:

 private void sendBroadcast() { Intent intent = new Intent("myBroadcastIntent"); intent.putExtra("someName", someValue); LocalBroadcastManager.getInstance(this).sendBroadcast(intent); } 

接收通知的活动将包含以下代码:

 @Override protected void onCreate(Bundle savedInstanceState) { // ... BroadcastReceiver receiver = new BroadcastReceiver() { @Override public void onReceive(Context context, Intent intent) { String someValue = intent.getStringExtra("someName"); // ... do something ... } }; LocalBroadcastManager.getInstance(this) .registerReceiver(receiver, new IntentFilter("myBroadcastIntent")); } 

有关更深入的信息,请参阅博客文章使用LocalBroadcastManager In Service To Activity Communications 。

其他答案都没有引用官方的android文档

https://developer.android.com/training/run-background-service/report-status.html

这清楚地表明,对于Activity-IntentService通信“发送和接收状态的推荐方法是使用LocalBroadcastManager,它将广播Intent对象限制为您自己的应用程序中的组件”!

我建议在活动中使用广播接收器等待结果。 您的服务只会将sendBroadcast与自定义Intent

我认为活动巴士是要走的路。 简单有效的进程间通信。