一、OpenCore简介
OpenCore是Android的多媒体核心,采用C++实现,定义了全功能的操作系统移植层(OSCL),各种基本的功能均被封装成类的形式,各层次之间的接口多使用继承等方式。
从宏观上来看,它主要包含了两大方面的内容:
- PVPlayer:提供媒体播放器的功能,完成各种音频(Audio)、视频(Video)流的回放(Playback)功能。
- PVAuthor:提供媒体流记录的功能,完成各种音频(Audio)、视频(Video)流的以及静态图像捕获功能 。
二、OpenCore在Android系统中的位置
首先来一张抽象一点的图(如下):
从上图我们可以感觉到OpenCore封装了一些接口给应用程序。具体是什么呢?下面以音频/视频播放器为例,看看具体的过程:
其中,
-
- VideoView.java是一个media集成的高层的JAVA类,这个类的文件在/frameworks/base/core/java/android/widget/。它集成了MediaPlayer和SurfaceView的类,可以作为一个UI元素(View)直接放在界面中,用于视频的播放。
- MediaPlayer.java和MediaRecorder.java为基本的处理音频数据的Java类,它里面直接调用很多本地接口。
- android_media_MediaPlayer.cpp和android_media_MediaRecorder.cpp封装了相应的JNI接口。
三、多媒体播放的过程
视频文件(流)播放过程就像一个状态机。图形如下,其中椭圆形代表MediaPlayer类的状态;线代表状态变化,由源状态指向目标状态,它旁边标注有状态变化的条件,其中单箭头的线表示同步(synchronous)方法调用,双箭头表示异步(asynchronous)方法调用。
这幅状态运行图显示了视频播放时的各种状态之间的切换方法,除此之外,为了方便用户处理,在一些状态下,系统会调用回调函数,只要用户提前注册好相应的回调函数即可。
状态
|
回调函数
|
注册方法
|
Error
|
OnErrorListener.onError()
|
setOnErrorListener(android.media.MediaPlayer.OnErrorListener)
|
Prepared
|
OnPreparedListener.onPrepared()
|
setOnPreparedListener(android.media.MediaPlayer.OnPreparedListener)
|
Started
| OnBufferingUpdateListener.onBufferingUpdate() | setOnBufferingUpdateListener(OnBufferingUpdateListener) |
使用seekTo(int)后
|
OnSeekComplete.onSeekComplete()
| setOnSeekCompleteListener(OnSeekCompleteListener) |
PlaybackCompleted
|
OnCompletionListener.onCompletion()
|
setOnCompletionListener(OnCompletionListener)
|
四、OpenCore内部的重要概念
OSCL:Operating System Compatibility Library (操作系统兼容库),包含了一些操作系统底层的操作,为了更好地在不同操作系统移植。包含了基本数据类型、配置、字符串工具、IO、错误处理、线程等内容,类似一个基础的C++库。
PVMF:PacketVideo Multimedia Framework(PV多媒体框架),在框架内实现一个 文件解析(parser)和 组成(composer)、 编解码的 NODE,也可以继承其通用的接口,在用户层实现一些NODE。
PVMF:PacketVideo Multimedia Framework(PV多媒体框架),在框架内实现一个 文件解析(parser)和 组成(composer)、 编解码的 NODE,也可以继承其通用的接口,在用户层实现一些NODE。
五、OpenCore的内部调度过程
PlayerDriver创建后进入
OSCL线程来处理消息,
engine创建完各个
node节点并将其连接起来,剩下的就是node间的通讯问题,各node状态变化会触发oscl对其下一次调度,参与到oscl调度中的模块都必须提供一个
Run函数,oscl会去call这个函数。
内部流程图如下:
文件的播放过程如下:
-
- 判断源文件的格式,根据文件格式创建对应的文件解析节点ParseNode: PVPlayerRecognizerRegistry负责文件格式识别,并将结果返回给PVPlayerEngine;
- 通过文件解析节点(ParseNode)来完成音视频文件格式的解析,并将文件中的音频、视频数据送到对应的解码节点进行解码;
- 解码节点(DecNode)通过调用底层的opencoreMAX通用接口实现媒体数据的解码;对于一个普通的视频文件,存在2个解码节点:音频解码节点和视频解码节点;
六、解码的内部流程:
参考OpenMax的相关介绍。
七、Android上的视频输出方案
为了使opencore的视频播放支持Android系统,谷歌定义了两套视频输出方案,一种是由硬件厂商实现硬件加速的视频输出(
libopencorehw.so),硬件视频输出里面可以调用硬件Overlay模块对输出的视频数据进行硬件混叠,这样输出效率会非常的高;另外一种为谷歌定义的软视频输出,该软视频输出定义为
AndroidSurfaceOutput类,这种方案中系统会调用SurfaceFilnger对输出视频数据进行混叠,该混叠为软件混叠,执行效率比较低。
八、OpenCore的测试方式
参考《Build OpenCORE 2.05 on x86 Linux.PDF》和《pvplayer_engine_unit_test_guide.pdf》http://blog.csdn.net/ponder008/article/details/6414103
转自:http://blog.csdn.net/ponder008/article/details/6414103