- CompoundButton 源码分析
- LinearLayout 源码分析
- SearchView 源码解析
- LruCache 源码解析
- ViewDragHelper 源码解析
- BottomSheets 源码解析
- Media Player 源码分析
- NavigationView 源码解析
- Service 源码解析
- Binder 源码分析
- Android 应用 Preference 相关及源码浅析 SharePreferences 篇
- ScrollView 源码解析
- Handler 源码解析
- NestedScrollView 源码解析
- SQLiteOpenHelper/SQLiteDatabase/Cursor 源码解析
- Bundle 源码解析
- LocalBroadcastManager 源码解析
- Toast 源码解析
- TextInputLayout
- LayoutInflater 和 LayoutInflaterCompat 源码解析
- TextView 源码解析
- NestedScrolling 事件机制源码解析
- ViewGroup 源码解析
- StaticLayout 源码分析
- AtomicFile 源码解析
- AtomicFile 源码解析
- Spannable 源码分析
- Notification 之 Android 5.0 实现原理
- CoordinatorLayout 源码分析
- Scroller 源码解析
- SwipeRefreshLayout 源码分析
- FloatingActionButton 源码解析
- AsyncTask 源码分析
- TabLayout 源码解析
文章来源于网络收集而来,版权归原创者所有,如有侵权请及时联系!
3.3 Prepare
通过之前的经验我们可以很快的知道 prepare 应该对应的是 AwesomePlayer 中的 prepare:
status_t AwesomePlayer::prepare() {
...
return prepare_l();
}
status_t AwesomePlayer::prepare_l() {
...
status_t err = prepareAsync_l();
...
return mPrepareResult;
}
status_t AwesomePlayer::prepareAsync_l() {
if (mFlags & PREPARING) {
return UNKNOWN_ERROR; // async prepare already pending
}
if (!mQueueStarted) {
mQueue.start();
mQueueStarted = true;
}
modifyFlags(PREPARING, SET);
mAsyncPrepareEvent = new AwesomeEvent(
this, &AwesomePlayer::onPrepareAsyncEvent);
mQueue.postEvent(mAsyncPrepareEvent);
return OK;
}mQueue 是 TimedEventQueue ,TimedEventQueue 和 Handler 很相似,使用 pthread 和 队列来管理消息。在这里通过异步方式回调 onPrepareAsyncEvent 方法:
void AwesomePlayer::onPrepareAsyncEvent() {
Mutex::Autolock autoLock(mLock);
beginPrepareAsync_l();
}
void AwesomePlayer::beginPrepareAsync_l() {
// 取消 prepare
if (mFlags & PREPARE_CANCELLED) {
ALOGI("prepare was cancelled before doing anything");
abortPrepare(UNKNOWN_ERROR);
return;
}
// 网络媒体
if (mUri.size() > 0) {
status_t err = finishSetDataSource_l();
if (err != OK) {
abortPrepare(err);
return;
}
}
// 是否包含视频
if (mVideoTrack != NULL && mVideoSource == NULL) {
// 初始化视频解码器
status_t err = initVideoDecoder();
if (err != OK) {
abortPrepare(err);
return;
}
}
// 是否包含音频
if (mAudioTrack != NULL && mAudioSource == NULL) {
// 初始化音频解码器
status_t err = initAudioDecoder();
if (err != OK) {
abortPrepare(err);
return;
}
}
modifyFlags(PREPARING_CONNECTED, SET);
// 不同的播放源类型
if (isStreamingHTTP()) {
// 网络流媒体
postBufferingEvent_l();
} else {
// 本地媒体
finishAsyncPrepare_l();
}
}
void AwesomePlayer::finishAsyncPrepare_l() {
if (mIsAsyncPrepare) {
if (mVideoSource == NULL) {
notifyListener_l(MEDIA_SET_VIDEO_SIZE, 0, 0);
} else {
notifyVideoSize_l();
}
notifyListener_l(MEDIA_PREPARED);
}
// 设置 player 的状态
mPrepareResult = OK;
modifyFlags((PREPARING|PREPARE_CANCELLED|PREPARING_CONNECTED), CLEAR);
modifyFlags(PREPARED, SET);
mAsyncPrepareEvent = NULL;
// 同步线程之间的状态
mPreparedCondition.broadcast();
// mAudioTearDown 默认为 false,当暂停的时候通过回调方法将其改为 true
if (mAudioTearDown) {
if (mPrepareResult == OK) {
if (mExtractorFlags & MediaExtractor::CAN_SEEK) {
seekTo_l(mAudioTearDownPosition);
}
if (mAudioTearDownWasPlaying) {
modifyFlags(CACHE_UNDERRUN, CLEAR);
play_l();
}
}
mAudioTearDown = false;
}
}经过一番设置后,prepare 的过程也算是完成了。这一部分主要是对 player 的状态进行设置,通过消息机制让让调用端也知道这边的 player 状态。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论