自动化零件服务商 - 供应SMC,FESTO,CKD全新正品气动元件
自动化零件服务商 - 供应SMC,FESTO,CKD全新正品气动元件
自动化零件服务商 - 供应SMC,FESTO,CKD全新正品气动元件

前言

简单记录一下MediaController中skipToNext()源码分析,这里只是简单记录下一下,走个流程吧。记录于此,方便自己查阅。

  1. mMediaController.getTransportControls().skipToNext();
复制

流水账,勿喷!

正文

对于的使用,可以看参考文二。之前有简单记录一下,下面只是附上相关的代码片段。

  1. mMediaController = new MediaController(MainActivity.this, mMediaBrowser.getSessionToken());
  2. mMediaController.getTransportControls().skipToNext();
复制

一上面代码为例,进行源码跟踪。

MediaController.java

  1. frameworks\base\media\java\android\media\session\MediaController.java
复制
MediaController()
  1. public MediaController(@NonNull Context context, @NonNull MediaSession.Token token) {
  2.   if (context == null) {
  3.       throw new IllegalArgumentException("context shouldn't be null");
  4.   }
  5.   if (token == null) {
  6.       throw new IllegalArgumentException("token shouldn't be null");
  7.   }
  8.   if (token.getBinder() == null) {
  9.       throw new IllegalArgumentException("token.getBinder() shouldn't be null");
  10.   }
  11. //获取的是token中的Binder对象
  12.   mSessionBinder = token.getBinder();
  13.   //创建TransportControls对象
  14.   mTransportControls = new TransportControls();
  15.   mToken = token;
  16.   mContext = context;
  17. }
复制

TransportControls是内部类,里面主要封装了一下方法,skipToNext()等

getTransportControls()
  1. public @NonNull TransportControls getTransportControls() {
  2.   return mTransportControls;
  3. }
复制
TransportControls.skipToNext()
  1. public void skipToNext() {
  2.   try {
  3.       mSessionBinder.next(mContext.getPackageName());
  4.   } catch (RemoteException e) {
  5.       Log.wtf(TAG, "Error calling next.", e);
  6.   }
  7. }
复制

这里的mSessionBinder就是MediaController构造函数中初始化的。

  1. //通过MediaSession.Token的对象获取的
  2. mSessionBinder = token.getBinder();
复制

我们创建MediaController对象时传入的是mMediaBrowser.getSessionToken()。

下面跟一下,但先说结果。

mSessionBinder为MediaSessionRecord中的ControllerStub对象

MediaBrowser.java

  1. \frameworks\base\media\java\android\media\browse\MediaBrowser.java
复制

这里关注mMediaBrowser.getSessionToken()返回的是啥。

getSessionToken()
  1. public @NonNull MediaSession.Token getSessionToken() {
  2.   if (!isConnected()) {
  3.       throw new IllegalStateException("getSessionToken() called while not connected (state="
  4.               + mState + ")");
  5.   }
  6.   return mMediaSessionToken;
  7. }
复制

onServiceConnected()中给mMediaSessionToken赋值的。

onServiceConnected()
  1. private void onServiceConnected(final IMediaBrowserServiceCallbacks callback,
  2.       final String root, final MediaSession.Token session, final Bundle extra) {
  3.   mHandler.post(new Runnable() {
  4.       @Override
  5.       public void run() {
  6.           if (!isCurrent(callback, "onConnect")) {
  7.               return;
  8.           }
  9.           if (mState != CONNECT_STATE_CONNECTING) {
  10.               Log.w(TAG, "onConnect from service while mState="
  11.                       + getStateLabel(mState) + "... ignoring");
  12.               return;
  13.           }
  14.           mRootId = root;
  15.           //这里赋值的,
  16.           mMediaSessionToken = session;
  17.           mExtras = extra;
  18.           mState = CONNECT_STATE_CONNECTED;
  19.           mCallback.onConnected();
  20.           //略
  21.       }
  22.   });
  23. }
复制

而onServiceConnected()是在MediaBrowser.java中静态内部类ServiceCallbacks的onConnect()中调用的。

ServiceCallbacks
  1. private static class ServiceCallbacks extends IMediaBrowserServiceCallbacks.Stub {
  2.   private WeakReference<MediaBrowser> mMediaBrowser;
  3.   ServiceCallbacks(MediaBrowser mediaBrowser) {
  4.       mMediaBrowser = new WeakReference<MediaBrowser>(mediaBrowser);
  5.   }
  6.   //略
  7. }
复制

这里重点关注onConnect()

onConnect()
  1. private static class ServiceCallbacks extends IMediaBrowserServiceCallbacks.Stub {
  2.   private WeakReference<MediaBrowser> mMediaBrowser;
  3.   ServiceCallbacks(MediaBrowser mediaBrowser) {
  4.       mMediaBrowser = new WeakReference<MediaBrowser>(mediaBrowser);
  5.   }
  6.    
  7.   @Override
  8.   public void onConnect(String root, MediaSession.Token session,
  9.           final Bundle extras) {
  10.       MediaBrowser mediaBrowser = mMediaBrowser.get();
  11. Log.d(TAG,"onConnect 1 mediaBrowser: "+ mediaBrowser);
  12.       if (mediaBrowser != null) {
  13.           mediaBrowser.onServiceConnected(this, root, session, extras);
  14.       }
  15.   }
  16.   @Override
  17.   public void onConnectFailed() {
  18.       MediaBrowser mediaBrowser = mMediaBrowser.get();
  19.       if (mediaBrowser != null) {
  20.           mediaBrowser.onConnectionFailed(this);
  21.       }
  22.   }
  23.   //略
  24. }
复制

也就是上面的MediaSession.Token的变量session是从这里传入的,至于哪里传入的,就要看调用方法的地方了。

提前预告一下。ServiceCallbacks对象创建是在MediaServiceConnection.onServiceConnected()中,并传入到mServiceBinder的connect()中。

  1. mServiceConnection = new MediaServiceConnection();
  2. mServiceBinder.connect(mContext.getPackageName(), mRootHints,
  3.                     mServiceCallbacks);
复制

后面会介绍到的。

下面先看MediaBrowser的connect()了。

MediaBrowser.java

下面是MediaBrowser对象创建和连接的代码。

隐藏内容!
付费阅读后才能查看!
1
2
多个隐藏块只需支付一次

小结2

比较绕的,尤其重点关注参数的传入,到处都是回调参数。我只是走过过程,也不太会总结。

大部分时没必要这样纠结看,只要抓住重点就行。

对于MediaSession相关问题,主要涉及MediaSession,MediaSessionRecord,MediaSessionManager,MediaBrowserService这几个即可。

上面跟源码的比较随意,看到参数后才去看的

参考文章

  1. 《Android源码》

  2. MediaSession的简单使用

自动化零件服务商 - 供应SMC,FESTO,CKD全新正品气动元件

相关文章

自动化零件服务商 - 供应SMC,FESTO,CKD全新正品气动元件

暂无评论

none
暂无评论...