我有一项使用媒体播放器播放音乐的服务。该服务从一项活动开始,如果某件事正在播放,并且用户离开该活动,该服务应继续在后台播放。 在前台运行服务似乎可行(我可以看到通知),但是在接近所有情况下服务立即销毁(OnDestroy由系统在服务上调用)。 我知道使用startForeground并不意味着这个服务永远不会被杀死,但它会一直被破坏,所以我想只有很少的资源迫使系统杀死它,这不是原因。服务不断遭到破坏
这是我实现它的方式: 在活动的OnCreate中,我开始(在后台)并绑定服务。在的onPause我把服务的前景不被摧毁,以及:在我的服务
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_play);
// start service
startService(new Intent(this, MyService.class));
// connect to service
bindToService();
...
}
@Override
protected void onDestroy() {
unbindFromService();
super.onDestroy();
};
@Override
protected void onStart() {
super.onStart();
}
@Override
protected void onStop() {
super.onStop();
}
@Override
protected void onPause() {
super.onPause();
if (MediaPlayerService.getInstance().getStatus() == MEDIA_PLAYER_STATUS.Started) {
// current playing something => keep service running
mService.startForeground();
} else {
// stop service
stopService(new Intent(MainActivity.this, MyService.class));
}
}
@Override
protected void onResume() {
super.onResume();
// remove service from foreground
if (mService != null) {
mService.stopForeground();
}
}
void bindToService() {
// Establish a connection with the service. We use an explicit
// class name because we want a specific service implementation that
// we know will be running in our own process (and thus won't be
// supporting component replacement by other applications).
bindService(new Intent(MainActivity.this, MyService.class), mConnection, Context.BIND_AUTO_CREATE);
mIsBound = true;
}
void unbindFromService() {
if (mIsBound) {
// Detach our existing connection.
unbindService(mConnection);
mIsBound = false;
}
}
private final ServiceConnection mConnection = new ServiceConnection() {
@Override
public void onServiceConnected(ComponentName className, IBinder service) {
// This is called when the connection with the service has been
// established, giving us the service object we can use to
// interact with the service. Because we have bound to a explicit
// service that we know is running in our own process, we can
// cast its IBinder to a concrete class and directly access it.
mService = ((MyService.LocalBinder) service).getService();
mService.registerClient(MainActivity.this);
}
@Override
public void onServiceDisconnected(ComponentName className) {
// This is called when the connection with the service has been
// unexpectedly disconnected -- that is, its process crashed.
// Because it is running in our same process, we should never
// see this happen.
mService = null;
mService.unRegisterClient(MainActivity.this);
}
};
和启动/ stopForeground功能是这样的:
public void startForeground() {
String songName = "blabla";
// assign the song name to songName
PendingIntent pi = PendingIntent.getActivity(getApplicationContext(), 0,
new Intent(getApplicationContext(), MainActivity.class),
PendingIntent.FLAG_UPDATE_CURRENT);
Notification notification = new Notification();
notification.tickerText = songName;
notification.icon = R.drawable.ic_launcher;
notification.flags |= Notification.FLAG_ONGOING_EVENT;
notification.setLatestEventInfo(getApplicationContext(), "MusicPlayerSample",
"Playing: " + songName, pi);
startForeground(NOTIFICATION_ID, notification);
}
public void stopForeground() {
stopForeground(true);
}
任何想法,为什么服务状态越来越如果我离开这项活动,会被摧毁吗?
您也可以将它与该icky静态数据成员结合使用。从'onPause()'调用'startService()',并让服务从'onStartCommand()'移动到前台。然后,摆脱'mService'。 – CommonsWare
感谢迄今为止的答案。但是如果我不与它绑定,我该如何与服务进行交流?我需要将来自活动的命令发送到服务(例如“播放文件xy”)并且返回到“客户端”活动(例如“播放停止”)。 – Maik
我搜索了一下,发现了一些答案在这里:http://stackoverflow.com/questions/5597298/getting-data-from-an-unbound-service-in-android 但事实上,这或多或少是我我在做:我调用startService(在Activity的构造函数中),然后绑定它。那么为什么服务在我结束活动后仍然会被杀死? – Maik