Media Playback with MediaSessionCompat (Android Development Patterns Ep 4)
Articles Blog

Media Playback with MediaSessionCompat (Android Development Patterns Ep 4)

[MUSIC PLAYING] IAN LAKE: Oh. Actions like pausing
your music should never be too far away, just in case. Android has offered
a lot of ways to do that– lock
screen controls, media controls for
notifications, Android Wear, and even Android
Auto, to name a few. How does your audio app get
started with all this goodness? It’s simple with
MediaSessionCompat, a single API available via the
Android Support Library that does much of the
work of integrating with Android for you. I’m Ian Lake, and I’ll go over
what MediaSessionCompat is, and how you can get started
on getting your media metadata and controls everywhere. Think of a media session as
the public face of your media playback. No matter if you’re playing
audio, video, or even remotely via Google Cast, unless you tell
the system what you’re doing, it can’t help you. And it gives you a lot
of ways to help you, if you publish metadata– such
as album art and artist name– and tell it what media
controls– such as play and pause– you support. But I’m getting ahead of myself. Let’s just create a
MediaSessionCompat object to start. Alas, on Android versions
prior to Lollipop, this requires one
preliminary step, creating what we call a
media button receiver. This is what captures
media controls from things like Bluetooth
headsets and Android Wear, and delivers them to your app
on devices below Android 5.0. It’s a simple
broadcast receiver, you register in your
manifest like this, and translates the
key event you receive into actions for your app. Generally, just delegating the
actual pause and play commands to the service actually
controlling your media playback. Check out our training
docs for an example. OK, finally, a
MediaSessionCompat. You’ll need a context– any
string to serve as a debugging tag– and the component name
of your media button receiver. The last null is
a pending intent you can use instead of the
component name on Android 4.3. It is created for
us if we pass null, and it’s usually the
right thing to do. Now you probably want
to do three things before going any farther. Set the appropriate flags to say
we actually have media button controls, and want those media
button events sent to our app. Next, we’ll want
to set a callback. This is where Lollipop
and higher devices will get callbacks on
play, on pause, and others when a button is pressed. Finally, set the
session to active when you’re ready
to play something. This is the cue to the
system to route media buttons and other controls to your app. OK, so the plumbing
is set up and ready, but we never actually tell
our media session anything about our media playback. How will it know what is playing
or what controls we support? First part is handled
by MediaMetadataCompat. It uses a builder
pattern, where you just add all the
information you have, then call setMetadata
on your media session. But still no media controls. Ah, it’s because we haven’t
done the other part, publishing a playback state. PlaybackStateCompat
actually has two purposes, the current state– such
as playing or paused or buffering, set via
its setState method– and the current actions– such
as stop or pause or play-pause, set via its setActions method. It contains both because
usually the actions change at the same time as the state. A stop state probably
doesn’t have a pause action, for example. That’s enough to get
MediaSessionCompat working. You’ll find integrated media
and Bluetooth buttons for all API 8 and higher devices,
and lock screen controls for Ice Cream Sandwich, Jelly
Bean, and KitKat devices. You’ll also find that
MediaSessionCompat works great with
NotificationCompat and MediaStyle, part of the
AppCompat support library, giving you great looking
media notifications on all API levels, even including
inline media controls on API 14 and higher devices. Just remember to
call SetMediaSession with the special
unique media session token from your media session. This is what connects your
media session to Android Wear, and you gives you media
controls on Wear for Android 5.0 and higher. Oh, don’t forget to call
release when you’re all done with your media session. Really, don’t forget. We’ve only touched on the
basics of MediaSessionCompat. We haven’t talked about
media browsers or media controllers or a
whole host of things built on top of media session. But this should get you started,
and make your media playback information and playback
controls available everywhere it can be. I’m looking forward to
seeing your awesome media using MediaSessionCompat,
and I hope it helps you build better apps. And, release.

10 thoughts on “Media Playback with MediaSessionCompat (Android Development Patterns Ep 4)

  1. Hi IanLake,

    Thanks for android videos.

    This video about mediaSessionsCompat is not explained better in pretty
    much understandable format for basics about them.

    Navin Prasad

  2. Hi Ian, I can't seem to find the training documentation for MediaSession, all I see are the javadocs. Can you post a link please?

  3. Thank you for this excellent video! After struggling for 4 hours with a variety of articles to get the Bluetooth headset controls working correctly this 4 minute video did it for me! Nice and clear explanation regarding Media…Compat classes 🙂 And yes, I did use the MediaButtonReceiver class from v23.1.0 Support library.

  4. I did exactly what's shown in the video. Everything works but lockscreen wallpaper doesn't change into album art!.

  5. +Ian Lake. My app is not the one providing the audio, but I want to be able to control the current music player with the new MediaControllerCompat class. Is this possible? Currently I am using the MediaSessionManager class to get a list of MediaSessions, but this seems a really clunky API because you have to create a NotificationListener and the user has to grant a permission (plus it leaks memory). Is there any sample code out there for replacing MediaSessionManager with the new classes.. a gist maybe? All the examples out there are only written from the perspective of a music player. Thanks.

  6. +Ian Lake – I did all you said but on KitKat media metadata is not showing on the receiver. It does work in Lollipop. It also works on KitKat with the default players. But doesn't work with MediaSessionCompat. I installed 5.1.1 and 4.4.4 on the same device (Nexus 7 2012) – sending metadata on 5.1.1 works – on 4.4.4. doesn't.

  7. Hey Ian, some of my users have complained that their car stereos do not update track progress/position (stays at 0). Am I supposed to call MediaSessionCompat.setPlaybackState() every second with a new position value in PlaybackStateCompat.setState()?

  8. Any idea how to request an object from the mediaBrowserService in the Activity. I'm implementing my own queue and don't really wanna use the queue given.

  9. Is there any way to check the playback state of the MediaController from the Activity if a user leaves then returns? MediaControllerCompat.getMediaController(mActivity).getPlaybackState() throws a NullReferenceError.

Leave a Reply

Your email address will not be published. Required fields are marked *

Back To Top