Android stopForeground和stopSelf的调用不';关闭应用程序后无法工作
我无法停止音乐服务 程序如下:Android stopForeground和stopSelf的调用不';关闭应用程序后无法工作,android,android-service,Android,Android Service,我无法停止音乐服务 程序如下: 我开始我的活动 我开始我的音乐服务 我完全关闭我的应用程序,服务与MainActivity解除绑定 我的BroadcastReceiver注册了一个从通知按钮按下的按钮,所以我调用stopForeground,但是这个调用没有执行 有人知道为什么吗 我的音乐服务课程: public class MusicService extends Service implements MediaPlayer.OnPreparedListener, MediaP
public class MusicService extends Service
implements MediaPlayer.OnPreparedListener, MediaPlayer.OnErrorListener, MediaPlayer.OnCompletionListener,
AudioManager.OnAudioFocusChangeListener {
@Override
public void onCreate() {
super.onCreate();
mediaPlayer = new MediaPlayer();
iSongPosition = 0;
playMode = PlayMode.PASS;
bPreparing = false;
bNotReceiverRegistered = false;
mediaPlayer.setWakeMode(getApplicationContext(), PowerManager.PARTIAL_WAKE_LOCK);
mediaPlayer.setAudioStreamType(AudioManager.STREAM_MUSIC);
mediaPlayer.setOnPreparedListener(this);
mediaPlayer.setOnCompletionListener(this);
mediaPlayer.setOnErrorListener(this);
audioManager = (AudioManager) getSystemService(AUDIO_SERVICE);
int iAudioReqResult = audioManager.requestAudioFocus(this, AudioManager.STREAM_MUSIC, AudioManager.AUDIOFOCUS_GAIN);
if (iAudioReqResult != AudioManager.AUDIOFOCUS_REQUEST_GRANTED) {
new AlertDialog.Builder(this)
.setTitle("Sorry.")
.setMessage("Musixs wasn't able to gain the AudioStream garanted!")
.setCancelable(false)
.show();
}
serviceInterface = new ServiceInterface() { ... };
nManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
notificationBroadcast = new NotificationBroadcast();
PlayActivity.setServiceInterface(serviceInterface);
IntentFilter intentFilter = new IntentFilter();
intentFilter.addAction(NotificationBroadcast.NOTIFY_PLAYPAUSE);
intentFilter.addAction(NotificationBroadcast.NOTIFY_PREVIOUS);
intentFilter.addAction(NotificationBroadcast.NOTIFY_NEXT);
intentFilter.addAction(NotificationBroadcast.NOTIFY_CANCEL);
if (!bNotReceiverRegistered) {
registerReceiver(notificationBroadcast, intentFilter);
bNotReceiverRegistered = true;
}
preferences = PreferenceManager.getDefaultSharedPreferences(getApplicationContext());
}
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
return START_STICKY;
}
@Nullable
@Override
public IBinder onBind(Intent intent) {
return musicBinder;
}
@Override
public boolean onUnbind(Intent intent) {
return super.onUnbind(intent);
}
@Override
public boolean onError(MediaPlayer mp, int what, int extra) {
mp.reset();
return false;
}
@Override
public void onPrepared(MediaPlayer mp) {
mp.start();
notification = Build_Notification();
SharedPreferences.Editor editor = preferences.edit();
editor.putLong(Constants.Preferences.lastPlayedSong, getActualSong().getID());
editor.apply();
startForeground(NOTIFY_ID, notification);
bPreparing = false;
}
@Override
public void onDestroy() {
super.onDestroy();
if (mediaPlayer != null) {
if (mediaPlayer.isPlaying()) {
mediaPlayer.stop();
}
mediaPlayer.reset();
mediaPlayer.release();
mediaPlayer = null;
}
if (bNotReceiverRegistered) {
unregisterReceiver(notificationBroadcast);
}
}
//region Methods
public void playSong(int index) {
mediaPlayer.reset();
iSongPosition = index;
Song playSong = sSongs[iSongPosition];
long playSongID = playSong.getID();
Uri trackUri = ContentUris.withAppendedId(MediaStore.Audio.Media.EXTERNAL_CONTENT_URI, playSongID);
try {
mediaPlayer.setDataSource(getApplicationContext(), trackUri);
}
catch (IOException ioe) {
ioe.printStackTrace();
}
bPreparing = true;
mediaPlayer.prepareAsync();
if (mediaplayerEvent != null) {
mediaplayerEvent.onNewSong(getActualSong());
}
}
public void playNext() {
iSongPosition++;
if (iSongPosition == sSongs.length) {
iSongPosition = 0;
}
playSong(iSongPosition);
}
public void playPrev() {
iSongPosition--;
if (iSongPosition < 0) {
iSongPosition = sSongs.length - 1;
}
playSong(iSongPosition);
}
public Song getActualSong() {
return (sSongs != null && sSongs.length > 0) ? sSongs[iSongPosition] : null;
}
public void start() {
if (mediaplayerEvent != null) {
mediaplayerEvent.onPlayPauseToggle(true);
}
mediaPlayer.start();
notification = Build_Notification();
startForeground(NOTIFY_ID, notification);
}
public void pause() {
if (mediaplayerEvent != null) {
mediaplayerEvent.onPlayPauseToggle(false);
}
mediaPlayer.pause();
notification = Build_Notification();
nManager.notify(NOTIFY_ID, notification);
}
public void playPause() {
if (isPlaying()) {
pause();
}
else {
if (isActive()) {
start();
}
else {
playSong(iSongPosition);
if (mediaplayerEvent != null) {
mediaplayerEvent.onPlayPauseToggle(true);
}
}
}
}
public void stop() {
mediaPlayer.stop();
System.out.println("Trying to stop"); //this got print out
stopForeground(true);
System.out.println("Stopped service"); //this not
}
private Notification Build_Notification() {
NotificationCompat.Builder nBuilder;
Intent notIntent = new Intent(getApplicationContext(), MainActivity.class);
notIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
PendingIntent notOpenOnClick = PendingIntent.getActivity(getApplicationContext(), 0, notIntent, PendingIntent.FLAG_UPDATE_CURRENT);
RemoteViews smallContentView = new RemoteViews(getPackageName(), R.layout.notification_small);
RemoteViews bigContentView = new RemoteViews(getPackageName(), R.layout.notification_expanded);
nBuilder = new NotificationCompat.Builder(this);
nBuilder.setSmallIcon(R.drawable.not_playing)
.setOngoing(true)
.setContentTitle(getActualSong().getTitle())
.setContentIntent(notOpenOnClick);
Notification not = nBuilder.build();
setListeners(smallContentView);
setListeners(bigContentView);
not.contentView = smallContentView;
not.bigContentView = bigContentView;
if (isPlaying()) {
not.contentView.setImageViewResource(R.id.not_btnPlayPause, R.drawable.ic_pause_48dp);
not.bigContentView.setImageViewResource(R.id.not_btnPlayPause, R.drawable.ic_pause_48dp);
}
else {
not.contentView.setImageViewResource(R.id.not_btnPlayPause, R.drawable.ic_play_48dp);
not.bigContentView.setImageViewResource(R.id.not_btnPlayPause, R.drawable.ic_play_48dp);
}
not.contentView.setTextViewText(R.id.not_txvTitle, getActualSong().getTitle());
not.contentView.setTextViewText(R.id.not_txvAlbum, getActualSong().getAlbum());
not.bigContentView.setTextViewText(R.id.not_txvTitle, getActualSong().getTitle());
not.bigContentView.setTextViewText(R.id.not_txvAlbum, getActualSong().getAlbum());
return not;
}
private void setListeners(RemoteViews view) {
Intent previous = new Intent(NotificationBroadcast.NOTIFY_PREVIOUS);
Intent next = new Intent(NotificationBroadcast.NOTIFY_NEXT);
Intent playpause = new Intent(NotificationBroadcast.NOTIFY_PLAYPAUSE);
Intent cancel = new Intent(NotificationBroadcast.NOTIFY_CANCEL);
PendingIntent pPrevious = PendingIntent.getBroadcast(getApplicationContext(), 0, previous, PendingIntent.FLAG_UPDATE_CURRENT);
view.setOnClickPendingIntent(R.id.not_btnPrevious, pPrevious);
PendingIntent pPlayPause = PendingIntent.getBroadcast(getApplicationContext(), 0, playpause, PendingIntent.FLAG_UPDATE_CURRENT);
view.setOnClickPendingIntent(R.id.not_btnPlayPause, pPlayPause);
PendingIntent pNext = PendingIntent.getBroadcast(getApplicationContext(), 0, next, PendingIntent.FLAG_UPDATE_CURRENT);
view.setOnClickPendingIntent(R.id.not_btnNext, pNext);
PendingIntent pCancel = PendingIntent.getBroadcast(getApplicationContext(), 0, cancel, PendingIntent.FLAG_UPDATE_CURRENT);
view.setOnClickPendingIntent(R.id.not_btnCancel, pCancel);
}
//endregion
public class MusicBinder extends Binder {
public MusicService getService() {
return MusicService.this;
}
}
}
由于应用程序如前所述已关闭,因此通知是处理MusicService的唯一设备
我的主要问题是:
这不起作用:
...
System.out.println("Trying to stop"); //This is print out in the logcat
stopForeground(true);
System.out.println("stopped"); //This is not print out in the logcat
...
→ 我的结论是:服务在方法stopForeground
中的某个地方卡住了。服务也不会因为重新启动而终止(见logcat)。如果我的onBind返回的是START\u NOT\u STICKY
而不是START\u STICKY
,则不会重新创建服务,但它根本不会停止
谢谢 我也遇到了同样的问题,并在更改代码顺序后解决了。当然,您的代码停止服务是在方法onstartCommand的最后一行再次启动的,所以您只需调用startForeground(NOTIFY_ID,notification);在此处输入代码方法的第一行
public int onStartCommand(Intent intent, int flags, int startId) {
Log.d(TAG, "onStartCommand: start service ");
startForeground(101,mBuilder.build());
....
....
...
....
}
在您的切换情况下,您停止服务,但逐行编译运行代码,以便在最后一行更改顺序时再次启动服务,并且工作正常与我相同的问题,在更改代码顺序后解决了您的代码停止服务,当然,但您在方法onstartCommand的最后一行再次启动它,所以您只需调用startForeground(通知ID,通知);在此处输入代码方法的第一行
public int onStartCommand(Intent intent, int flags, int startId) {
Log.d(TAG, "onStartCommand: start service ");
startForeground(101,mBuilder.build());
....
....
...
....
}
在您的交换机中,您停止服务,但逐行编译运行代码,以便它在最后一行变更单时再次启动服务,并且工作正常发布您的
活动中的相关代码
。不清楚你的问题是什么。如果这有帮助的话,我可以发布我的两个课程。。。我的问题:stopForeground
如果我的应用程序关闭并且服务正在播放音乐,则不会执行!您有一个方法stop()
。我不知道是谁调用了这个方法。这个方法叫什么?我希望它现在清楚了!让我们假设stopForeground
可以工作,但通知仍然无法被刷走。要使其工作,您的设备必须至少为API 21,并且您的应用程序的targetSdkVersion必须至少为21。这是安卓系统的一个已知错误,每个应用程序都通过在通知中添加一个“X”按钮来解决它。如果是这种情况,请参阅以获取帮助。从您的活动发布相关代码。不清楚你的问题是什么。如果这有帮助的话,我可以发布我的两个课程。。。我的问题:stopForeground
如果我的应用程序关闭并且服务正在播放音乐,则不会执行!您有一个方法stop()
。我不知道是谁调用了这个方法。这个方法叫什么?我希望它现在清楚了!让我们假设stopForeground
可以工作,但通知仍然无法被刷走。要使其工作,您的设备必须至少为API 21,并且您的应用程序的targetSdkVersion必须至少为21。这是安卓系统的一个已知错误,每个应用程序都通过在通知中添加一个“X”按钮来解决它。如果是这种情况,请参阅以获取帮助。