当应用程序进入后台时,MediaBrowserServiceCompat 停止播放音乐
Posted
技术标签:
【中文标题】当应用程序进入后台时,MediaBrowserServiceCompat 停止播放音乐【英文标题】:MediaBrowserServiceCompat stopped playing music when app goes background 【发布时间】:2020-12-22 02:49:03 【问题描述】:当应用程序进入后台时,Mediabrowsercompat 不播放音乐。如果我没有断开活动 onStop 方法中的 mediabrowsercompat 实例,那么它正在工作。但这不是解决方案,因为根据文档,一旦应用程序进入后台,我们必须断开服务。
这是我的 mediabroweserservicecomat 类(我正在使用 Exoplayer 播放音乐):
private static final String PLAYBACK_CHANNEL_ID = "100";
private static final int PLAYBACK_NOTIFICATION_ID =101 ;
private MediaSessionCompat mediaSessionCompat;
private PlaybackStateCompat.Builder stateBuilder;
private SimpleExoPlayer exoPlayer;
private Uri oldUri;
private AudioAttributes audioAttributes;
private PlayerNotificationManager playerNotificationManager;
@Override
public void onCreate()
super.onCreate();
Log.i("Test","Hi");
initPlayer();
initAttributes();
ComponentName mediaButtonReceiver = new ComponentName(getApplicationContext(), MediaButtonReceiver.class);
mediaSessionCompat = new MediaSessionCompat(getApplicationContext(), "Tag", mediaButtonReceiver, null);
mediaSessionCompat.setFlags(MediaSessionCompat.FLAG_HANDLES_MEDIA_BUTTONS|
MediaSessionCompat.FLAG_HANDLES_TRANSPORT_CONTROLS);
stateBuilder = new PlaybackStateCompat.Builder();
stateBuilder.setActions(PlaybackStateCompat.ACTION_PLAY|PlaybackStateCompat.ACTION_PLAY_PAUSE);
mediaSessionCompat.setPlaybackState(stateBuilder.build());
mediaSessionCompat.setCallback(mediaSessionCompatCallback);
setSessionToken(mediaSessionCompat.getSessionToken());
mediaSessionCompat.setActive(true);
Intent mediaButtonIntent = new Intent(Intent.ACTION_MEDIA_BUTTON);
mediaButtonIntent.setClass(this, MediaButtonReceiver.class);
PendingIntent pendingIntent = PendingIntent.getBroadcast(this, 0, mediaButtonIntent, 0);
mediaSessionCompat.setMediaButtonReceiver(pendingIntent);
@Override
public int onStartCommand(Intent intent, int flags, int startId)
MediaButtonReceiver.handleIntent(mediaSessionCompat,intent);
return super.onStartCommand(intent, flags, startId);
private MediaSessionCompat.Callback mediaSessionCompatCallback = new MediaSessionCompat.Callback()
@Override
public void onPlayFromUri(Uri uri, Bundle extras)
super.onPlayFromUri(uri, extras);
if (uri!=null)
MediaItem mediaSource = MediaItem.fromUri(uri);
if (uri!=oldUri)
play(mediaSource);
onPlay();
else
oldUri = uri;
@Override
public void onPlay()
super.onPlay();
Log.i("onPlay","onPlay");
//startService(new Intent(MusicService.this,MusicForegroundService.class));
playerNotificationManager = PlayerNotificationManager.createWithNotificationChannel(MusicService.this,
PLAYBACK_CHANNEL_ID, R.string.channel_name, PLAYBACK_NOTIFICATION_ID,
new PlayerNotificationManager.MediaDescriptionAdapter()
@Override
public CharSequence getCurrentContentTitle(Player player)
return "title";
@Nullable
@Override
public PendingIntent createCurrentContentIntent(Player player)
Intent intent = new Intent(getBaseContext(), PlayerFullViewActivity.class);
return PendingIntent.getActivity(getBaseContext(), 0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
@Nullable
@Override
public CharSequence getCurrentContentText(Player player)
return "content";
@Nullable
@Override
public Bitmap getCurrentLargeIcon(Player player, PlayerNotificationManager.BitmapCallback callback)
return null;
,
new PlayerNotificationManager.NotificationListener()
@Override
public void onNotificationPosted(int notificationId, Notification notification, boolean ongoing)
startForeground(notificationId,notification);
@Override
public void onNotificationCancelled(int notificationId, boolean dismissedByUser)
stopSelf();
);
playerNotificationManager.setPlayer(exoPlayer);
@Override
public void onPause()
super.onPause();
pause();
@Override
public void onStop()
playerNotificationManager.setPlayer(null);
super.onStop();
stop();
;
@Override
public void onDestroy()
super.onDestroy();
stop();
private void stop()
exoPlayer.setPlayWhenReady(false);
exoPlayer.release();
exoPlayer =null;
updatePlayBackState(PlaybackStateCompat.STATE_NONE);
mediaSessionCompat.setActive(false);
mediaSessionCompat.release();
@SuppressLint("WrongConstant")
private void pause()
if (exoPlayer!=null)
exoPlayer.setPlayWhenReady(false);
if (exoPlayer.getPlaybackState()==PlaybackStateCompat.STATE_PLAYING)
updatePlayBackState(PlaybackStateCompat.STATE_PAUSED);
private void play(MediaItem mediaSource)
if (exoPlayer==null)
initPlayer();
if (audioAttributes==null)
initAttributes();
exoPlayer.setAudioAttributes(audioAttributes,true);
exoPlayer.setMediaItem(mediaSource);
exoPlayer.prepare();
play();
private void initAttributes()
audioAttributes = new AudioAttributes.Builder().setUsage(C.USAGE_MEDIA)
.setContentType(C.CONTENT_TYPE_MUSIC)
.build();
private void initPlayer()
exoPlayer = new SimpleExoPlayer.Builder(this, new DefaultRenderersFactory(getBaseContext()),
new DefaultExtractorsFactory()).build();
private void play()
exoPlayer.setPlayWhenReady(true);
updatePlayBackState(PlaybackStateCompat.STATE_PLAYING);
mediaSessionCompat.setActive(true);
private void updatePlayBackState(int statePlaying)
mediaSessionCompat.setPlaybackState(new PlaybackStateCompat.Builder().
setState(statePlaying,0L,0).build());
@Nullable
@Override
public BrowserRoot onGetRoot(@NonNull String clientPackageName, int clientUid, @Nullable Bundle rootHints)
return new BrowserRoot("",null);
@Override
public void onLoadChildren(@NonNull String parentId, @NonNull Result<List<MediaBrowserCompat.MediaItem>> result)
result.sendResult(null);
这是我的活动课:
ActivityPlayerFullViewBinding activityPlayerFullViewBinding;
private MediaBrowserCompat mediaBrowserCompat;
private MediaBrowserCompat.ConnectionCallback connectionCallback = new MediaBrowserCompat.ConnectionCallback()
@Override
public void onConnected()
super.onConnected();
MediaSessionCompat.Token sessionToken = mediaBrowserCompat.getSessionToken();
if (sessionToken!=null)
try
MediaControllerCompat mediaControllerCompat = new
MediaControllerCompat(PlayerFullViewActivity.this, sessionToken);
MediaControllerCompat.setMediaController(PlayerFullViewActivity.this,mediaControllerCompat);
playPauseBuild();
Log.d("onConnected","ConnectionSuccess");
catch (RemoteException e)
e.printStackTrace();
@Override
public void onConnectionFailed()
super.onConnectionFailed();
Log.d("onConnectionFaild","ConnectionFailed");
;
MediaControllerCompat.Callback controllerCallback =
new MediaControllerCompat.Callback()
@Override
public void onMetadataChanged(MediaMetadataCompat metadata)
@Override
public void onPlaybackStateChanged(PlaybackStateCompat state)
;
@Override
protected void onCreate(Bundle savedInstanceState)
super.onCreate(savedInstanceState);
activityPlayerFullViewBinding = DataBindingUtil.setContentView(this,R.layout.activity_player_full_view);
ComponentName componentName = new ComponentName(this,MusicService.class);
mediaBrowserCompat = new MediaBrowserCompat(this,componentName,connectionCallback,null);
private void playPauseBuild()
MediaControllerCompat mediaController = MediaControllerCompat.getMediaController(PlayerFullViewActivity.this);
activityPlayerFullViewBinding.playPauseBtn
.setOnClickListener(new View.OnClickListener()
@Override
public void onClick(View v)
int state = mediaController.getPlaybackState().getState();
if (state== PlaybackStateCompat.STATE_PAUSED||state==PlaybackStateCompat.STATE_STOPPED||
state==PlaybackStateCompat.STATE_NONE)
mediaController.getTransportControls().playFromUri(
Uri.parse("https://www.mboxdrive.com/Eminem-Sing-For-The-Moment9jamo.com_.mp3"),null);
activityPlayerFullViewBinding.playPauseBtn.setText("Pause");
else if (state == PlaybackStateCompat.STATE_PLAYING ||
state == PlaybackStateCompat.STATE_BUFFERING ||
state == PlaybackStateCompat.STATE_CONNECTING)
mediaController.getTransportControls().pause();
activityPlayerFullViewBinding.playPauseBtn.setText("Play");
);
mediaController.registerCallback(controllerCallback);
@Override
protected void onStart()
super.onStart();
mediaBrowserCompat.connect();
@Override
public void onResume()
super.onResume();
setVolumeControlStream(AudioManager.STREAM_MUSIC);
@Override
protected void onStop()
super.onStop();
Log.i("onStop","onStop");
MediaControllerCompat mediaController = MediaControllerCompat.getMediaController(this);
if (mediaController != null)
mediaController.unregisterCallback(controllerCallback);
mediaBrowserCompat.disconnect();
【问题讨论】:
【参考方案1】:在浪费了两个不眠之夜之后。我找到了解决方法。我不知道这是否是处理这个问题的正确方法。但是,如果您曾经遇到过这个问题。你可以试试:
@Override
protected void onStart()
super.onStart();
if (!mediaBrowserCompat.isConnected())
mediaBrowserCompat.connect();
@Override
protected void onStop()
super.onStop();
Log.i("onStop","onStop");
MediaControllerCompat mediaController = MediaControllerCompat.getMediaController(this);
if (mediaController != null)
mediaController.unregisterCallback(controllerCallback);
// mediaBrowserCompat.disconnect();
@Override
protected void onDestroy()
super.onDestroy();
mediaBrowserCompat.disconnect();
【讨论】:
以上是关于当应用程序进入后台时,MediaBrowserServiceCompat 停止播放音乐的主要内容,如果未能解决你的问题,请参考以下文章
当应用程序从后台进入前台时,MPMoviePlayerController 黑屏