要学好网站开发要会什么,金华网站建设多少钱,wordpress5.1友情链接,金昌北京网站建设文章目录 前言MediaSessionCarMediaService作用是什么#xff1f;提供了哪些接口#xff1f;如何使用#xff1f;CarMediaService的实现总结 前言
CarMediaService 是AAOS中统一管理媒体播放控制、信息显示和用户交互等功能的服务。这一服务依赖于android MediaSession框架… 文章目录 前言MediaSessionCarMediaService作用是什么提供了哪些接口如何使用CarMediaService的实现总结 前言
CarMediaService 是AAOS中统一管理媒体播放控制、信息显示和用户交互等功能的服务。这一服务依赖于android MediaSession框架。 所以首先需要简单的了解一下MediaSession。
MediaSession
MediaSession 框架规范了音视频应用中界面与播放器之间的通信接口实现界面与播放器之间的完全解耦。MediaSession 框架定义了媒体会话和媒体控制器两个重要的类它们为构建多媒体播放器应用提供了一个完善的技术架构。 AAOS上面的MediaSession的控制框图如上主要是MediaControl和MediaSession两个类直接的交互。 MediaControl是UI端控制Service端的类在AAOS中所有的app播放控制客户端的实现都是carMediaApp中MediaControl的实现的包括蓝牙audio localplayer界面中暂停播放下一首 上一首等等。 MediaSession是服务端 这个服务端包括蓝牙的src\com\android\bluetooth和/apps/Car/LocalMediaPlayer。这这里面实现了Mediassion 的callback 用来响应client 端UI的控制。 而响应之后的状态改变可以通过继承MediaControl的callback 在客户端实现。
CarMediaService
作用是什么提供了哪些接口如何使用 用途 CarMediaService通过CarMediaManager给外部应用提供使用的API。 这些api允许开发者控制车辆中的主要媒体源以及获取与这一媒体源相关的更新信息。通过这个 API 来实现媒体播放控制、信息显示和用户交互等功能。 接口 CarMediaManger是客户端 通过AIDL的接口 调用到CarMediaService中。 提供的AIDIL的接口如下
获取/设置提供模式下当前活动的媒体源。 其中模式包括播放和浏览 是指应用的操作可以是浏览媒体 或者是操作播放媒体。 其中MediaSource的理解可以认为是执行具体播放操作的一个应用 是媒体播放控制的对象比如蓝牙音乐播放器、本地的播放器等等。注册/反注册回调监听媒体活动源的更新。同样模式可以是浏览或者播放。
综上可以看到carMediaService 是实现所有媒体相关的ui 浏览和控制的统一管理。 监听媒体源的变化控制活动和非活动媒体源的播放、退出、暂停等等。
interface ICarMedia {/** Gets the currently active media source for the provided mode */ComponentName getMediaSource(int mode);/** Sets the currently active media source for the provided mode */void setMediaSource(in ComponentName mediaSource, int mode);/** Register a callback that receives updates to the active media source */void registerMediaSourceListener(in ICarMediaSourceListener callback, int mode);/** Unregister a callback that receives updates to the active media source */void unregisterMediaSourceListener(in ICarMediaSourceListener callback, int mode);/** Retrieve a list of media sources, ordered by most recently used */ListComponentName getLastMediaSources(int mode);/** Returns whether the browse and playback sources can be changed independently. */boolean isIndependentPlaybackConfig();/** Sets whether the browse and playback sources can be changed independently. */void setIndependentPlaybackConfig(boolean independent);
}使用流程
首先获取CarMediaManager然后注册MediaSource变化的监听在mediasource有变化的时候更新ui。 mHandler new Handler(application.getMainLooper());mMediaSourceListener componentName - mHandler.post(() - updateModelState(mInputFactory.getMediaSource(componentName)));try {mCarMediaManager mInputFactory.getCarMediaManager(mCar);mCarMediaManager.addMediaSourceListener(mMediaSourceListener, mode);MediaSource src mInputFactory.getMediaSource(mCarMediaManager.getMediaSource(mode));if (Log.isLoggable(TAG, Log.INFO)) {Log.i(TAG, Initializing with src);}updateModelState(src);} catch (CarNotConnectedException e) {Log.e(TAG, Car not connected, e);}CarMediaService的实现 carMediaService中初始化流程
获取mPrimaryMediaComponents 获取的方式是通过遍历系统的所有package、然后查看有MediaBroswerService的package。 在AAOS 默认Bluetooth有MediaBroswerService所以默认的package是com.android.bluetooth。
private ComponentName getMediaService(NonNull ComponentName componentName) {String packageName componentName.getPackageName();String className componentName.getClassName();PackageManager packageManager mContext.getPackageManager();Intent mediaIntent new Intent();mediaIntent.setPackage(packageName);mediaIntent.setAction(MediaBrowserService.SERVICE_INTERFACE);ListResolveInfo mediaServices packageManager.queryIntentServicesAsUser(mediaIntent,PackageManager.GET_RESOLVED_FILTER, ActivityManager.getCurrentUser());for (ResolveInfo service : mediaServices) {String serviceName service.serviceInfo.name;if (!TextUtils.isEmpty(serviceName)// If className is not specified, returns the first service in the package;// otherwise returns the matched service.// TODO(b/136274456): find a proper way to handle the case where there are// multiple services and the className is not specified. (TextUtils.isEmpty(className) || serviceName.equals(className))) {return new ComponentName(packageName, serviceName);}}}注册MediaSessionActive的回调 当服务端的MediaSession 设置为active的时候回调到这个SessionChangedListener中 启动MediaConnectService MediaConnectorService会调用MediaConnectorService的onStartCommand。 onStartCommand中会获取当前应用的MediaControl设置到PlaybackViewModel。 PlaybackViewModel利用这个control对MediaSession的service端进行控制。 控制是在service端实现mediaControl的onPrepare、onPlay等实现的。 如果MediaSession当前是播放的状态那么会stop掉。如果不是的话 会先进行prepare操作。 private void initUser(UserIdInt int userId) {mPrimaryMediaComponents[MEDIA_SOURCE_MODE_PLAYBACK] isCurrentUserEphemeral()? getDefaultMediaSource() : getLastMediaSource(MEDIA_SOURCE_MODE_PLAYBACK);mPrimaryMediaComponents[MEDIA_SOURCE_MODE_BROWSE] isCurrentUserEphemeral()? getDefaultMediaSource() : getLastMediaSource(MEDIA_SOURCE_MODE_BROWSE);mActiveUserMediaController null;updateMediaSessionCallbackForCurrentUser();notifyListeners(MEDIA_SOURCE_MODE_PLAYBACK);notifyListeners(MEDIA_SOURCE_MODE_BROWSE);startMediaConnectorService(shouldStartPlayback(mPlayOnBootConfig), currentUser);}}
SessionChanged 的回调 SessionChanged回调到onActiveSessionsChanged。回调的参数是所有active的mediaControl。这里面会遍历所有control如果control的状态是playing 并且其MediaSource跟当前存储的PrimaryMediaSource不一样的话 会更新control的MediaSource到PrimaryMediaSource。 private class SessionChangedListener implements OnActiveSessionsChangedListener {Overridepublic void onActiveSessionsChanged(ListMediaController controllers) {if (ActivityManager.getCurrentUser() ! mCurrentUser) {Slog.e(CarLog.TAG_MEDIA, Active session callback for old user: mCurrentUser);return;}mMediaSessionUpdater.registerCallbacks(controllers);}}MediaController的回调 这个会回调到onPlaybackStateChanged回调的状态是playing而且跟回调之前的状态不一样的时候 也会调用setPrimaryMediaSource进行primary mediasource的更新。 public void onPlaybackStateChanged(Nullable PlaybackState state) {if (state.getState() PlaybackState.STATE_PLAYING state.getState() ! mPreviousPlaybackState) {ComponentName mediaSource getMediaSource(mMediaController.getPackageName(),getClassName(mMediaController));if (mediaSource ! null) {setPrimaryMediaSource(mediaSource, MEDIA_SOURCE_MODE_PLAYBACK);}}mPreviousPlaybackState state.getState();}}总结
CarMediaService 的实现是通过注册MediaSessionActive 和 MediaController的callback 来监听当前用户所有应用 有关媒体播放浏览等事件。当事件发生时 更新AAOS界面的信息和控制的控件。