OpenMax在Android上的实现
摘要:本文简要介绍了OpenMax 的集成层,并阐述了其在Android上的实现和运行过程。
关键字:OMX, 多媒体框架, IL, Android, Stagefright
1、OpenMax 集成层介绍
OpenMax是一个多媒体应用程序的框架标准。它自上而下分为三层,Application Layer, Integration Layer和Development Layer。应用层规定了应用程序和多媒体中间层的标准接口,使应用程序的移植性更好。集成层定义了多媒体组件的接口,使得多媒体框架能以一种统一的方式访问多媒体Codec和组件,以便在嵌入式流媒体框架中快速集成加速编解码器。。开发层为Codec厂商和硬件厂商提供了一套API,使开发更加便捷。
图1 OpenMax的分层结构
OMX集成层由Client、Core、Component和Port组成,Client通过Core得到对应Component的Handle,而后通过命令直接和Component进行交互。每个Component至少有一个Port进行数据交互,如Decoder有一个输入Port接收码流,一个输出Port输出YUV序列。Component内部可能通过消息处理机制完成Client要求的任务。
图2 OMX IL层的组成
在Android中,OpenMax IL层,通常可以用于多媒体引擎的插件,Android2.2的多媒体引擎StageFright都可以使用OpenMax作为插件,主要用于编解码(Codec)处理。
在Android的框架层,定义了由Android封装的OpenMax接口,和标准的接口概念基本相同,使用C++类型的接口,并且使用了Android的Binder IPC机制实现了函数远程调用。Android封装OpenMax的接口被StageFright使用。
解码Component通过输入Port和输出Port来进行交互,可以通过和OMXCodec共享buffer来进行编解码。
图3 StageFright的OMX结构
2、OMX相关的类关系
StageFright的核心播放器AwesomePlayer中包含了sp<MediaSource>型的mVideoSource指针,初始化时指向OMXCodec的实际对象。OMXCodec使用了Binder机制,实现了远程函数调用,且函数调用模式于本地函数无异,其中IOMX作为接口类定义了OMX的大部分接口函数。OMX的具体实现时,OMXMaster类用于管理OMX的插件,OMXNodeInstance类代表OMX的具体实例,完成和Component的调用和交互,内部类CallbackDispatcher是一个主动类,它用于调度处理回调函数传回的消息。OMXNodeInstance和CallbackDispatcher一一对应,协同工作,完成不同实例的消息处理。
图4 OMX相关类关系图
OMXNodeInstance类中最重要的几个函数为:
allocateBuffer: Client通过调用此函数让Component分配Buffer。
useBuffer: Client通过此函数将已分配好的Buffer传给Component,让其使用。
freeBuffer: Client通过调用此函数让Component释放allocateBuffer()分配的Buffer。
fillBuffer: Client通过调用此函数传递空的Buffer给Component,让其将处理好的数据填入其中。此函数会调用OMX标准接口OMX_FillThisBuffer()。
emptyBuffer: Client通过调用此函数传递输入Buffer给Component,让其读取其中的数据进行编解码等处理。此函数会调用OMX标准接口OMX_ EmptyThisBuffer ()。
OnEmptyBufferDone: Component完成对输入buffer的读取后,调用此回调函数,向Client发送EmptyBufferDone消息。
OnFillBufferDone: Component完成相应处理将输出数据填入输出Buffer后,调用此回调函数,向Client发送FillBufferDone消息。
以Decoder为例,说明OMX Codec执行解码的过程,
图5 OMX Codec解码序列图
OMXCodec使用emptyBuffer()函数(IL层中为OMX_EmptyThisBuffer()传递未解码的buffer给component,component收到该命令后会读取input port buffer中的数据,将其组装成帧进行解码,读取buffer中的数据完成后会调用EmptyBufferDone通知OMXCodec。
Compoment使用EmptyBufferDone消息通知OMXCodec已完成input buffer的读取, 具体的实现是通过调用回调函数OnEmptyBufferDone()实现的。OMXCodec收到该命令后会通过mVideoTrack读取新的视频码流到input port的buffer中,并调用OMX_EmptyThisBuffer通知component。
OMXCodec使用OMX_FillThisBuffer传递空的bffer给component用于存储解码后的帧,Component收到该命令后将解码好的帧数据复制到该buffer上,然后调用FillBufferDone通知OMXCodec。
Compoment使用FillBufferDone通知OMXCodec已完成output port buffer的填充,具体的实现是通过调用回调函数OnFillBufferDone()实现的。OMXCodec收到该命令后将解码好的帧存入可显示队列中,AwesomePlayer调用OMXCodec::read()函数读出可显示队列的对头送给Renderer完成颜色转换等操作再传递给mISurface进行图像绘制,同时Render调用release()函数,其中的SignalBufferDone()会用OMX_FillThisBuffer通知component有空的buffer可填充。
OpenMax在Android上的实现相关推荐
- android4.0 音频框架 opensl openmax,适用于android的OpenSL ES指南-面向Android的OpenSL ES
本文将详细说明NDK中OpenSL ES™的实现与OpenSL ES 1.0.1参考规范的不同.在使用规范中的示例代码时,可能需要修改它以在Android上工作. 除非另有说明,所有功能都可以在And ...
- android上传本地图片到服务器上,Android使用post方式上传图片到服务器的方法
本文实例讲述了Android使用post方式上传图片到服务器的方法.分享给大家供大家参考,具体如下: /** * 上传文件到服务器类 * * @author tom */ public class U ...
- 构建node.js基础镜像_在Android上构建Node.js应用程序
构建node.js基础镜像 by Aurélien Giraud 通过AurélienGiraud 在Android上构建Node.js应用程序-第1部分:Termux,Vim和Node.js (Bu ...
- 如何为Android上的产品设计一款合适的图标
如 果你已经完成了你的app,你一定会马上向其它人宣布这件事情.但是你需要注意一个很重要的问题,那就是app的图标.你的图标可能在项目启动之 前就已经设计好了,但我不喜欢这样,如果app没有完成实际上 ...
- Android上的MVP:如何组织显示层的内容
MVP(Model View Presenter)模式是著名的MVC(Model View Controller)模式的一个演化版本,目前它在Android应用开发中越来越重要了,大家也都在讨论关于M ...
- android上的i-jetty (1)环境搭建
android上的i-jetty (1)环境搭建 android ftp swiftp http://code.google.com/p/swiftp/ 介绍下如果把android设备作为一个web ...
- 在Android上实现HttpServer
本文讲的是在Android上实现HttpServer,在最近的项目中因为要用Android作为一个服务器去做一个实时接收数据的功能,所以这个时候就要去做一个Android本地的微型服务器. 那么此时我 ...
- 安卓平台运行python_在 android 上运行 python 的方法
android官方目前没有支持在android设备运行python,但是网上有一些项目组做了这个事情:http://geeknizer.com/install-run-python-apps-scri ...
- android heic图片,如何在Windows / MacOS / Android上打開HEIC照片
HEIC顧名思義是指高效率圖像文件格式.它是種更好儲存照片的方式,因為跟JPEG格式相比,它的照片容量較小且能保持高畫質的照片. 使用HEIC有很多好處.以下是HEIC比JPEG更好的原因. HEIC ...
最新文章
- python自动化办公脚本下载-python自动化办公:文件篇(自动整理文件,一键完成)...
- Dockerfile镜像的制作
- large_IPYi_09ef000018c21215
- 嫦娥奔月(KMP,找循环节)及其扩展KMP
- 对高并发流量控制的一点思考
- 3-pycharm找不到库的解决办法
- cesium billboard 设置距离控制可见度
- 傲梦python笔试题_python笔试题
- codevs1018 单词接龙(DFS)
- 为何身为程序员的你,不选择开源?
- string 常用函数
- 毕向东的Java基础视频教程的学习,作为java基础的基础学习视频
- C语言自学之路九(用C语言编写小游戏-扫雷)
- 浏览器内核学习笔记一
- 实测:熊猫烧香考验五大杀毒软件
- 相机参数(焦距)初始化对三维重建过程的影响
- Objective-C简介
- Octave 安装步骤(仅供记录)
- 字符数组与字符串的转换
- 谷歌弃用20多年的OKR,再创内卷神器?
热门文章
- 在CSDN的第一篇文章
- uniapp跳转第三方地图导航
- 【K3s】第3篇 解决K3s状态一直是ContainerCreating
- Unix系统 - 存储管理中的文件系统
- 解决laravel Use of undefined constant JSON_INVALID_UTF8_SUBSTITUTE - assumed ‘JSON_INVAL
- 关于 ExpandableListView 的列子
- linux mplayer 一键安装,MPlayer Linux安装教程
- 安卓 linux 信令,呼叫信令
- Unity学习笔记:监听函数有什么卵用?(似乎就是从一件事过渡到另一件事?)
- 考研复试_英语面试_必备的30个问题