MediaPalyer的基本用法:
private MediaPlayer mp = new MediaPlayer(); 开始播放: mp.setDataSource("/sdcard/test.mp3"); mp.prepare(); mp.start(); 播放完成监听: mp.setOnCompletionListener(new OnCompletionListener(){ @Override public void onCompletion(MediaPlayer mp) { mp.release(); } }); 播放暂停: mp.pause(); 播放终止: mp.stop();
|
MediaPlayer的构造函数
进入到MediaPlayer的源码部分,从第一步构造函数开始:
/*\frameworks\base\media\java\android\media\MediaPlayer.java*/
/** * Default constructor. Consider using one of the create() methods for * synchronously instantiating a MediaPlayer from a Uri or resource. * <p>When done with the MediaPlayer, you should call {@link #release()}, * to free the resources. If not released, too many MediaPlayer instances may * result in an exception.</p> */ public MediaPlayer() {
Looper looper;à 得到当前线程的Looper, 并创建EventHandler对象 if ((looper = Looper.myLooper()) != null) { mEventHandler = new EventHandler(this, looper); } else if ((looper = Looper.getMainLooper()) != null) { mEventHandler = new EventHandler(this, looper); } else { mEventHandler = null; }
/* Native setup requires a weak reference to our object. * It's easier to create it here than in C++. */ native_setup(new WeakReference<MediaPlayer>(this)); } |
首先看一下EventHandler的定义:
/*\frameworks\base\media\java\android\media\MediaPlayer.java*/
private class EventHandler extends Handler { private MediaPlayer mMediaPlayer;
public EventHandler(MediaPlayer mp, Looper looper) { super(looper); mMediaPlayer = mp; }
@Override public void handleMessage(Message msg) { if (mMediaPlayer.mNativeContext == 0) { Log.w(TAG, "mediaplayer went away with unhandled events"); return; } switch(msg.what) { case MEDIA_PREPARED: if (mOnPreparedListener != null) mOnPreparedListener.onPrepared(mMediaPlayer); return;
case MEDIA_PLAYBACK_COMPLETE: if (mOnCompletionListener != null) mOnCompletionListener.onCompletion(mMediaPlayer); stayAwake(false); return; … |
可见EventHandler是一个handler,根据收到的不同Message对上层进行回调。
再看一下native_setup函数定义:
/* \frameworks\base\media\java\android\media\MediaPlayer.java*/
private native final void native_setup(Object mediaplayer_this); |
可见是一个native函数调用,找到相关的实现:
/*\frameworks\base\media\jni\android_media_MediaPlayer.cpp*/
static void android_media_MediaPlayer_native_setup(JNIEnv *env, jobject thiz, jobject weak_this) { LOGV("native_setup"); sp<MediaPlayer> mp = new MediaPlayer(); if (mp == NULL) { jniThrowException(env, "java/lang/RuntimeException", "Out of memory"); return; }
// create new listener and give it to MediaPlayer sp<JNIMediaPlayerListener> listener = new JNIMediaPlayerListener(env, thiz, weak_this); mp->setListener(listener);
// Stow our new C++ MediaPlayer in an opaque field in the Java object. setMediaPlayer(env, thiz, mp);à SetIntField(thiz, fields.context, (int)player.get()),将创建的player与Java层的mNativeContext联系起来。mNativeContext在Java层的EventHandler.handleMessage中判断是否是对应的底层mediaplayer返回的信息。如果不是,就不处理。 } |
查看一下JNI层的listerner定义:
/*\frameworks\base\media\jni\android_media_MediaPlayer.cpp*/
// ---------------------------------------------------------------------------- // ref-counted object for callbacks class JNIMediaPlayerListener: public MediaPlayerListener { public: JNIMediaPlayerListener(JNIEnv* env, jobject thiz, jobject weak_thiz); ~JNIMediaPlayerListener(); void notify(int msg, int ext1, int ext2); private: JNIMediaPlayerListener(); jclass mClass; // Reference to MediaPlayer class jobject mObject; // Weak ref to MediaPlayer Java object to call on };
JNIMediaPlayerListener::JNIMediaPlayerListener(JNIEnv* env, jobject thiz, jobject weak_thiz) {
// Hold onto the MediaPlayer class for use in calling the static method // that posts events to the application thread. jclass clazz = env->GetObjectClass(thiz); if (clazz == NULL) { LOGE("Can't find android/media/MediaPlayer"); jniThrowException(env, "java/lang/Exception", NULL); return; } mClass = (jclass)env->NewGlobalRef(clazz);
// We use a weak reference so the MediaPlayer object can be garbage collected. // The reference is only used as a proxy for callbacks. mObject = env->NewGlobalRef(weak_thiz); }
JNIMediaPlayerListener::~JNIMediaPlayerListener() { // remove global references JNIEnv *env = AndroidRuntime::getJNIEnv(); env->DeleteGlobalRef(mObject); env->DeleteGlobalRef(mClass); }
void JNIMediaPlayerListener::notify(int msg, int ext1, int ext2) { JNIEnv *env = AndroidRuntime::getJNIEnv(); env->CallStaticVoidMethod(mClass, fields.post_event, mObject, msg, ext1, ext2, 0); } |
作用就是将JNI层的消息能上传到java层。
sp<MediaPlayer> mp = new MediaPlayer();的定义:
/*\frameworks\av\media\libmedia\mediaplayer.cpp*/
MediaPlayer::MediaPlayer() { ALOGV("constructor"); mListener = NULL; mCookie = NULL; mStreamType = AUDIO_STREAM_MUSIC; mCurrentPosition = -1; mSeekPosition = -1; mCurrentState = MEDIA_PLAYER_IDLE; mPrepareSync = false; mPrepareStatus = NO_ERROR; mLoop = false; mLeftVolume = mRightVolume = 1.0; mVideoWidth = mVideoHeight = 0; mLockThreadId = 0; mAudioSessionId = AudioSystem::newAudioSessionId(); AudioSystem::acquireAudioSessionId(mAudioSessionId); mSendLevel = 0; mRetransmitEndpointValid = false; } |
mAudioSessionId = AUdioSystem::newAudioSessionId();,得到新的AudioSessionId
/*\frameworks\av\media\libmedia\AudioSystem.cpp*/
int AudioSystem::newAudioSessionId() { const sp<IAudioFlinger>& af = AudioSystem::get_audio_flinger(); if (af == 0) return 0; return af->newAudioSessionId(); } |
AudioSystem::get_audio_flinger();获取AudioFlinger的BpBinder:
/*\frameworks\av\media\libmedia\AudioSystem.cpp*/
sp<IAudioFlinger> AudioSystem::gAudioFlinger;
const sp<IAudioFlinger>& AudioSystem::get_audio_flinger() { Mutex::Autolock _l(gLock); if (gAudioFlinger == 0) { sp<IServiceManager> sm = defaultServiceManager(); sp<IBinder> binder; do { binder = sm->getService(String16("media.audio_flinger")); if (binder != 0) break; ALOGW("AudioFlinger not published, waiting..."); usleep(500000); // 0.5 s } while (true); if (gAudioFlingerClient == NULL) { gAudioFlingerClient = new AudioFlingerClient(); } else { if (gAudioErrorCallback) { gAudioErrorCallback(NO_ERROR); } } binder->linkToDeath(gAudioFlingerClient); gAudioFlinger = interface_cast<IAudioFlinger>(binder); gAudioFlinger->registerClient(gAudioFlingerClient); } ALOGE_IF(gAudioFlinger==0, "no AudioFlinger!?");
return gAudioFlinger; } |
这里与AudioFlinger服务发生联系,暂且不理,以分析MediaPlayerService为主。
暂且知道通过audiosessionId,将mediaplayer,audioflinger绑定起来。每个audiosession和一个pid对应,组成了一个AudioSessionRef。AudioSessionRefs队列维护当前系统中运行的audiosession。
mp.setDataSource("/sdcard/test.mp3");
API中的setDataSource:
/*\frameworks\base\media\java\android\media\MediaPlayer.java*/
public void setDataSource(String path) throws IOException, IllegalArgumentException, SecurityException, IllegalStateException { setDataSource(path, null, null); }
private native void _setDataSource(FileDescriptor fd, long offset, long length) throws IOException, IllegalArgumentException, IllegalStateException; |
虽然进行了多种封装,但最终还是调用一个Native函数:
/*\frameworks\base\media\jni\android_media_MediaPlayer.cpp*/
static void android_media_MediaPlayer_setDataSourceFD(JNIEnv *env, jobject thiz, jobject fileDescriptor, jlong offset, jlong length) { sp<MediaPlayer> mp = getMediaPlayer(env, thiz); if (mp == NULL ) { jniThrowException(env, "java/lang/IllegalStateException", NULL); return; }
if (fileDescriptor == NULL) { jniThrowException(env, "java/lang/IllegalArgumentException", NULL); return; } int fd = jniGetFDFromFileDescriptor(env, fileDescriptor); ALOGV("setDataSourceFD: fd %d", fd); process_media_player_call( env, thiz, mp->setDataSource(fd, offset, length), "java/io/IOException", "setDataSourceFD failed." ); } |
/*\frameworks\av\media\libmedia\mediaplayer.cpp*/
status_t MediaPlayer::setDataSource(int fd, int64_t offset, int64_t length) { ALOGV("setDataSource(%d, %lld, %lld)", fd, offset, length); status_t err = UNKNOWN_ERROR; const sp<IMediaPlayerService>& service(getMediaPlayerService()); if (service != 0) { sp<IMediaPlayer> player(service->create(this, mAudioSessionId)); if ((NO_ERROR != doSetRetransmitEndpoint(player)) || (NO_ERROR != player->setDataSource(fd, offset, length))) { player.clear(); } err = attachNewPlayer(player); } return err; } |
看看MediaPlayer的定义:
class MediaPlayer : public BnMediaPlayerClient,
public virtual IMediaDeathNotifier
所以getMediaPlayerService()函数定义在IMediaDeathNotifier中:
/*\frameworks\av\media\libmedia\IMediaDeathNotifier.cpp*/
IMediaDeathNotifier::getMediaPlayerService() { ALOGV("getMediaPlayerService"); Mutex::Autolock _l(sServiceLock); if (sMediaPlayerService == 0) { sp<IServiceManager> sm = defaultServiceManager(); sp<IBinder> binder; do { binder = sm->getService(String16("media.player")); if (binder != 0) { break; } ALOGW("Media player service not published, waiting..."); usleep(500000); // 0.5 s } while (true);
if (sDeathNotifier == NULL) { sDeathNotifier = new DeathNotifier(); } binder->linkToDeath(sDeathNotifier); sMediaPlayerService = interface_cast<IMediaPlayerService>(binder); } ALOGE_IF(sMediaPlayerService == 0, "no media player service!?"); return sMediaPlayerService; } |
注意这里的defaultServiceManager()函数,它会返回一个IServiceManager对象,通过它来与ServiceManager进程进行交互。
/*\frameworks\native\libs\binder\IServiceManager.cpp*/
sp<IServiceManager> defaultServiceManager() { if (gDefaultServiceManager != NULL) return gDefaultServiceManager; { AutoMutex _l(gDefaultServiceManagerLock); while (gDefaultServiceManager == NULL) { gDefaultServiceManager = interface_cast<IServiceManager>( ProcessState::self()->getContextObject(NULL)); if (gDefaultServiceManager == NULL) sleep(1); } }
return gDefaultServiceManager; } |
看看ProcessState::self()->getContextObject(NULL)前面已经分析过,返回一个new BpBinder(handle);handle值为0。
看看interface_cast的定义:
/*\frameworks\native\include\binder\IInterface.h*/
template<typename INTERFACE> inline sp<INTERFACE> interface_cast(const sp<IBinder>& obj) { return INTERFACE::asInterface(obj); } |
定义的是一个函数模版,调用后相当于调用IServiceManager:: asInterface(obj),然而这又是在哪里定义的呢?
/*\frameworks\native\libs\binder\IServiceManager.h*/
class IServiceManager : public IInterface { public: DECLARE_META_INTERFACE(ServiceManager); |
有这样一个宏定义,这个宏又是在哪里呢?
/*\frameworks\native\include\binder\IInterface.h*/
#define DECLARE_META_INTERFACE(INTERFACE) \ static const android::String16 descriptor; \ static android::sp<I##INTERFACE> asInterface( \ const android::sp<android::IBinder>& obj); \ virtual const android::String16& getInterfaceDescriptor() const; \ I##INTERFACE(); \ virtual ~I##INTERFACE(); \ |
将DECLARE_META_INTERFACE(ServiceManager)定义转意:
static const android::String16 descriptor;à定义一个描述符字符串
static android::sp<IServiceManager> asInterface(const android::sp<android::IBinder>& obj);à定义一个asInterface函数
virtual const android::String16& getInterfaceDescriptor() const;
IServiceManager();
virtual ~IServiceManager(); |
在IServiceManager中还调用了一个宏:IMPLEMENT_META_INTERFACE(ServiceManager, "android.os.IServiceManager");查看这个宏的定义:
/*\frameworks\native\include\binder\IInterface.h*/
#define IMPLEMENT_META_INTERFACE(INTERFACE, NAME) \ const android::String16 I##INTERFACE::descriptor(NAME); \ const android::String16& \ I##INTERFACE::getInterfaceDescriptor() const { \ return I##INTERFACE::descriptor; \ } \ android::sp<I##INTERFACE> I##INTERFACE::asInterface( \ const android::sp<android::IBinder>& obj) \ { \ android::sp<I##INTERFACE> intr; \ if (obj != NULL) { \ intr = static_cast<I##INTERFACE*>( \ obj->queryLocalInterface( \ I##INTERFACE::descriptor).get()); \ if (intr == NULL) { \ intr = new Bp##INTERFACE(obj); \ } \ } \ return intr; \ } \ I##INTERFACE::I##INTERFACE() { } \ I##INTERFACE::~I##INTERFACE() { } \ |
同样转意如下:
const android::String16 IServiceManager::descriptor("android.os.IServiceManager");
const android::String16& IServiceManager::getInterfaceDescriptor() const { return IServiceManager::descriptor; }
android::sp<IServiceManager> IServiceManager::asInterface(const android::sp<android::IBinder>& obj) { android::sp<IServiceManager> intr; if (obj != NULL) { intr = static_cast<IServiceManager *>(obj->queryLocalInterface(IServiceManager::descriptor).get()); if (intr == NULL) { intr = new BpServiceManager(obj); } } return intr; }
IServiceManager::IServiceManager () { }
IServiceManager::~ IServiceManager() { } |
所以通过gDefaultServiceManager = interface_cast<IServiceManager>(
ProcessState::self()->getContextObject(NULL));
interface_cast的调用返回一个new BpServiceManager(obj);这里的obj就是ProcessState::self()->getContextObject(NULL)返回是一个new BpBinder()。
看看BpServiceManager的代码:
/*\frameworks\native\libs\binder\IServiceManager.cpp*/
class BpServiceManager : public BpInterface<IServiceManager> { public: BpServiceManager(const sp<IBinder>& impl) : BpInterface<IServiceManager>(impl) { } |
看看BpInterface的定义:
/*\frameworks\native\include\binder\IInterface.h*/
template<typename INTERFACE> class BpInterface : public INTERFACE, public BpRefBase { public: BpInterface(const sp<IBinder>& remote);
protected: virtual IBinder* onAsBinder(); };
template<typename INTERFACE> inline BpInterface<INTERFACE>::BpInterface(const sp<IBinder>& remote) : BpRefBase(remote) { } |
是一个模版类,构造函数调用父类BpRefBase的构造函数。
看看BpRefBase的构造函数:
/*\Android4.4\frameworks\native\libs\binder\Binder.cpp*/
BpRefBase::BpRefBase(const sp<IBinder>& o) : mRemote(o.get()), mRefs(NULL), mState(0) { extendObjectLifetime(OBJECT_LIFETIME_WEAK);
if (mRemote) { mRemote->incStrong(this); // Removed on first IncStrong(). mRefs = mRemote->createWeak(this); // Held for our entire lifetime. } } |
BpServiceManager的一个变量mRemote指向了一个BpBinder,通过defaultServiceManager()函数的调用返回一个BpServiceManager对象,它的mRemote值是个BpBinder类型(它的handle值为0)。