媒体控制器与媒体会话交互以查询和控制媒体应用的播放。在 Media3 中,MediaController
API 实现 Player
界面。使用媒体控制器的客户端应用示例包括
- Android 系统媒体控件
- Android Wear OS 伴侣应用
- Android Auto 和 Automotive OS
- 语音助手,例如 Google 助理
- 媒体控制器测试应用
媒体控制器在媒体应用内也很有用,例如,如果播放器和媒体会话位于与具有 UI 的 Activity
或 Fragment
分开的 Service
中。
创建 MediaController
要创建 MediaController
,首先要为相应的 MediaSession
创建一个 SessionToken
。在你的 Activity
或 Fragment
的 onStart()
方法中执行此操作是一个好地方。
Kotlin
val sessionToken = SessionToken(context, ComponentName(context, PlaybackService::class.java))
Java
SessionToken sessionToken = new SessionToken(context, new ComponentName(context, PlaybackService.class));
然后使用此 SessionToken
来构建 MediaController
,将控制器连接到给定会话。此过程异步进行,因此您应该监听结果并在结果可用时使用它。
Kotlin
val controllerFuture = MediaController.Builder(context, sessionToken).buildAsync() controllerFuture.addListener({ // MediaController is available here with controllerFuture.get() }, MoreExecutors.directExecutor())
Java
ListenableFuture<MediaController> controllerFuture = new MediaController.Builder(context, sessionToken).buildAsync(); controllerFuture.addListener(() -> { // MediaController is available here with controllerFuture.get() }, MoreExecutors.directExecutor());
使用 MediaController
MediaController
实现 Player
接口,因此您可以使用该接口中定义的命令来控制连接的 MediaSession
的播放。这意味着对 MediaController
调用 play()
将向连接的 MediaSession
发送命令,该命令随后将把命令委托给其底层的 Player
。
同样,您可以向控制器添加 Player.Listener
以监听 Player
状态的变化。有关使用 Player.Listener
的更多详细信息,请参阅 播放器事件 指南。 MediaController.Listener
接口为连接的 MediaSession
的事件和传入命令定义了额外的回调,例如 onAvailableSessionCommandsChanged()
(用于媒体会话更改可用会话命令时)和 onDisconnected()
(用于控制器与会话断开连接时)。
与其他组件一样,请记住在不再需要 MediaController
时释放它,例如在 Activity
或 Fragment
的 onStop()
方法中。
Kotlin
MediaController.releaseFuture(controllerFuture)
Java
MediaController.releaseFuture(controllerFuture);
释放控制器仍将传递发送到会话的所有待处理命令,并且仅在处理完这些命令或在超时时间段后(以先发生者为准)与会话服务解除绑定。
创建和使用 MediaBrowser
MediaBrowser
建立在 MediaController
提供的功能之上,还可以浏览媒体应用的 MediaLibraryService
提供的媒体库。
Kotlin
val browserFuture = MediaBrowser.Builder(context, sessionToken).buildAsync() browserFuture.addListener({ // MediaBrowser is available here with browserFuture.get() }, MoreExecutors.directExecutor())
Java
ListenableFuture<MediaBrowser> browserFuture = new MediaBrowser.Builder(context, sessionToken).buildAsync(); browserFuture.addListener(() -> { // MediaBrowser is available here with browserFuture.get() }, MoreExecutors.directExecutor());
要开始浏览媒体应用的内容库,请首先使用 getLibraryRoot()
检索根节点。
Kotlin
// Get the library root to start browsing the library tree. val rootFuture = mediaBrowser.getLibraryRoot(/* params= */ null) rootFuture.addListener({ // Root node MediaItem is available here with rootFuture.get().value }, MoreExecutors.directExecutor())
Java
// Get the library root to start browsing the library tree. ListenableFuture<LibraryResult<MediaItem>> rootFuture = mediaBrowser.getLibraryRoot(/* params= */ null); rootFuture.addListener(() -> { // Root node MediaItem is available here with rootFuture.get().value }, MoreExecutors.directExecutor());
然后,您可以通过使用 getChildren()
检索库中 MediaItem
的子项来浏览媒体库。例如,要检索根节点 MediaItem
的子项
Kotlin
// Get the library root to start browsing the library tree. val childrenFuture = mediaBrowser.getChildren(rootMediaItem.mediaId, 0, Int.MAX_VALUE, null) childrenFuture.addListener({ // List of children MediaItem nodes is available here with // childrenFuture.get().value }, MoreExecutors.directExecutor())
Java
ListenableFuture<LibraryResult<ImmutableList<MediaItem>>> childrenFuture = mediaBrowser.getChildren(rootMediaItem.mediaId, 0, Integer.MAX_VALUE, null); childrenFuture.addListener(() -> { // List of children MediaItem nodes is available here with // childrenFuture.get().value }, MoreExecutors.directExecutor());