我想实现Commonsware在此博客文章中所描述的内容:http://commonsware.com/blog/2010/08/08/11/activity-notification-notification-rorderification-ordered-broadcast.html。该帖子很有意义,我能够在此处浏览示例来源:https://github.com/commonsguy/cw-advandroid/tree/tree/master/broadcast。
我很好奇的是,如果您在清单中定义的类型的广播接收器仍将接收服务内部的LocalBroadcastManager.getInstance(UnzipService.this).sendBroadcast(broadcast);
。
如果我要问的是不清楚的,我要做的是使用localbroadcastmanager,因为我服务的广播不一定需要广泛看到系统,我宁愿让它们私密化如果可能的话,但是我还想显示通知如果用户关闭我的应用程序并且服务仍在运行。有没有办法将这两个功能组合起来,而无需在服务内部发送两次广播?
(我不想做的)喜欢: LocalBroadcastManager.getInstance(UnzipService.this).sendBroadcast(broadcast);
sendOrderedBroadcast(broadcast);
我很好奇的是,如果致电LocalBroadcastManager.getInstance(unzipservice.this).sendBroadcast(广播);服务内部的内部仍将被您清单中定义的类型的广播接收器捡起。
否。LocalBroadcastManager
仅与在LocalBroadcastManager
Singleton本身注册的接收器一起使用。此外,LocalBroadcastManager
不支持有序的广播,最后我检查了。
我要做的是使用LocalBroadcastManager,因为我服务的广播不一定需要被宽阔的系统,如果可能的话,我宁愿将它们保密
只要您不在清单中的BroadcastReceiver
上使用<intent-filter>
,因此使用显式的Intent
作为广播本身,您的广播只有您自己和管理广播的OS的位才能看到。其他应用程序将无法监视它。
如果您只有2个可能处理广播的对象(在您的情况下是活动和通知控制器),则可以仅使用LocalBroadcastManager实现订购广播的行为。p>一般想法是:
- 设置您的服务,以便在您想显示结果 时通过特定操作广播您的活动意图
- 在您的活动中,创建一个处理您的服务结果的广播媒介,并使用步骤1的操作在LocalBroadcastmanager上注册IntentFilter在LocalBroadcastmanager上进行注册。
- 在您的服务中,当结果可用时,请尝试使用LocalBroadcastManager.getInstance(context).sendBroadcast(意图)发送结果,此方法返回一个布尔值,该布尔值指示是否已将广播发送到至少一个接收器。如果此布尔人是错误的,则意味着您的活动无法处理您的广播,您应该显示通知。
在您的服务中:
public UnzipService extends IntentService {
public static final String ACTION_SHOWRESULT = UnzipService.class.getCanonicalName() + ".ACTION_SHOWRESULT";
@Override
protected void onHandleIntent(Intent intent) {
Thread.sleep(500); // Do the hard work
// Then try to notify the Activity about the results
Intent activityIntent = new Intent(this, YourActivity.class);
activityIntent.setAction(ACTION_SHOWRESULT);
activityIntent.putExtra(SOME_KEY, SOME_RESULTVALUE); // Put the result into extras
boolean broadcastEnqueued = LocalBroadcastManager.getInstance(this).sendBroadcast(activityIntent);
if (!broadcastEnqueued) { // Fallback to notification!
PendingIntent pendingIntent = PendingIntent.getActivity(this, (int) System.currentTimeMillis(), activityIntent, PendingIntent.FLAG_UPDATE_CURRENT);
((NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE))
.notify(SOME_ID, new NotificationCompat.Builder(this)
.setContentIntent(pendingIntent)
.setTicker("results available")
.setContentText("results")
.build());
}
}
}
在您的活动中:
public YourActivity extends Activity {
private BroadcastReceiver resultReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
processResult(intent); // Results Intent received through local broadcast
}
}
private IntentFilter resultFilter = new IntentFilter(UnzipService.ACTION_SHOWRESULT);
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate();
Intent intent = getIntent();
if (UnzipService.ACTION_SHOWRESULT.equals(intent.getAction())) {
// The Activity has been launched with a tap on the notification
processResult(intent); // Results Intent contained in the notification PendingIntent
}
}
@Override
protected void onResume() {
super.onResume();
LocalBroadcastManager.getInstance(this)
.registerReceiver(resultReceiver, resultFilter);
}
@Override
protected void onPause() {
LocalBroadcastManager.getInstance(this)
.unregisterReceiver(resultReceiver);
super.onPause();
}
private void processResult(Intent intent) {
// Show the results from Intent extras
}
}
这应该是一个完整的工作示例。
我希望这有助于谁试图通过支持库与LocalBroadcastmanager实施有序的广播!
我知道您想实现以下内容:
"我有一个在后台发生的事件。如果活动在屏幕上,我想更新活动。否则,我想提出通知。"(@thecommonsblog)
您可以通过实现重污染物来实现此行为。示例Restful API服务和http://itekblog.com/background-processing-with-intentservice-class/
您基本上要做的是实例您的活动中的重新估计,并通过意图将其传递给服务像包裹的参数。然后,每次您的服务要更新UI时,服务都会验证NULL的Resultreceiver对象。如果不是null,则可以通过OnReceiverEsult接口更新UI。否则,您会提出通知。当您的活动解散时,请确保将重新估计的服务设置为NULL。
希望它有帮助。
ps:imo,广播太多了,难以控制。
使用LocalBroadcastManager,广播变得易于使用。
如果在后台发生事件,我不支持更新活动。用户可能已经在活动中做其他事情。在我看来,通知就足够了。它总是可见的,并且一直保持直到用户否定为止。Gmail和Gcal这样的工作;如果新邮件出现,Gmail不会更新当前屏幕。如果您想知道如何处理用户已经在应用程序中时处理通知的任务流,请参见Notifications API指南,还请用户2培训课程。