MultiMedia基础知识汇总

136 阅读10分钟

1 编程语言

1.1 Java

Java八股文

1.1 C++

CPP八股文 blog.csdn.net/zcc12299363…

2 音频子系统

Android Audio Framework

2.1 音频基础知识

2.1.1 音频常用编码格式

audio常用格式: AAC:高效编码,文件小,有损压缩 MP3:压缩比高,与原始音质没有明显下降 ogg/wav/ape

1.1 二级目录

3 视频子系统

Android Video Framework

3.1 视频基础知识

3.1.1 色彩空间

色彩空间 color space,分为2大类,RGB和YUV,RGB是红绿蓝,颜色的三原色,这个比较好理解,YUV是亮度与色彩分离的格式,早期电视都是黑白电视,只有亮度值Y,彩电之后加入了UV两种色度 Y:亮度(灰度)值 U:蓝色通道与亮度的差值 V:红色通道与亮度的差值 YUV的优势:人眼对亮度敏感,对色彩不敏感,通过减少部分UV的数据量,在不影响观感的情况下可以减少 视频的体积 其他还有如YUV420(I420、NV12、NV21)格式。 很明显YUV这种方式是比较适合人类的观察方式,根据人眼的特性,保留Y通道,适当的 降低UV通道来减少视频的体积,同时就可能的保留视频原始信息,因此YUV和RGB是可以通过公式转换的, 普通的解码器 输出的原始格式也是YUV,只有在最后渲染的时候才会转换成RGB这种格式,另外,MTK的解码器还有一些 私有格式,经过转换之后才会成YUV,也是为了节省带宽做的处理。 YUV420:比例4:1:1,也就是每4个Y共用一组UV通道,因此一个YUV占用8+2+2=12bit=1.5Byte 相机出来的格式默认是NV21,也就是先存储Y,再VU交替;NV12则是先存储Y,再UV交替。I420则是 uv单独存储在一个空间

YUV模型是根据亮度(Y分量)和2个色度(UV分量)来定义颜色空间,UV又叫做CbCr,我们最常见的颜色空间是YUV420,其他基本没见过,YUV420又分为2种,YUV420P和YUV420SP,也就是planar和semi-planar。YUV420这种数据,通过4个Y共用一个UV来达到数据压缩的目的,毕竟人眼对亮度比较敏感,对色度没那么敏感。

YUV420P数据分布为

这种是YU12格式,这里YUV分别在不同平面,也就是它有3个平面 还有一种YV12格式,是

这种也称为I420

YUV420SP分为两种,一种是NV12,一种是NV21。

NV21:

NV12:

它们都是uv交织排布的,uv顺序不同而名字不同。

3.1.2 视频编码帧

I帧:帧内编码,完整的帧 P帧:前向预测,非完整帧,参考前面的I帧或者P帧 B帧:双向预测,参考前后2帧(直播的特性决定它不会有B帧)

GOP:一组变化不大的视频帧,GOP是否固定的时间?不是 GOP的第一帧成为关键帧IDR(立即刷新帧),IDR帧是特殊的I帧,IDR阻断了参考关系,而普通的I帧 不一样,B帧有可能参考普通I帧之前的帧,它无法阻断参考关系。 DTS:解码时间戳,数据流送入解码器解码的时间,PTS是显示时间戳,在有B帧的情况下,二者不一样

3.1.3 视频常用格式

video常用格式: H264/H265/VP8/VP9 常用封装格式: mp4/mkv/avi/ts

3.1.3 MediaCodec常用

crop信息(x,y,m,n)左上坐标(x,y) 右下坐标(m,n),也就是解码宽高,宽=m-x+1,高=y-n+1 mediacodec的状态:(思考一下如果你创建mediacodec要做那些事情) 1.创建mediacodec后,处于uninitialized状态 2.config后,configured状态 3.start后,flushed状态,此时会清空所有buffer 4.buffer队列拿到第一个buffer时,进入running状态 5.stream带有eos标志时,进入eos状态 6.调用stop后,uninitialized状态

codec specific data 数据(h264/h265解码器要求的数据,sps/pps信息) 1.mediacodec要求的,所有正常数据来之前,必须先有csd数据 2.其中包含一些sps,pps信息,用于初始化、配置解码器参数等 H264 csd-0放sps信息、csd-1放pps信息 H265 只有csd-0,放sps、pps、vps信息 NAL头可以区分一帧是IPB帧

MediaFormat参数中,很多需要配置的信息,都是在编码的时候才需要的,如framerate key-frame等信息, 解码时候配置的参数不多

mediacodec常用操作 1.dequeueInputBuffer 返回一个空buffer的index 2.getInputBuffer(index) 返回对应index的buffer地址 3.queueInputBuffer 填充好数据之后,将数据送到mediacodec 4.dequeueOutputBuffer 获取解码器输出的buffer对应的index 5.releaseOutputBuffer 把index对应的buffer还给mediacodec 使用surface效率会高很多,dequeuOutputBuffer之后,直接releaseOutputBuffer,解码数据无需拷贝到 java侧,直接在native侧送给nativeWindow,省去copy动作,效率提高

mediacodec dequeue的buffer是从系统这边借的,用完后需要还回去,不然会一直占用。系统侧会统计该 buffer是否ownedbyClient端,如果一直被clinet拿着不占用,最后会导致没有空的buffer可用。

系统侧如何处理旋转: step1: APP解析头文件,解析到video的rotation step2: APP播放视频时调用mediacodec的configure函数,并把rotation传入 step3: MediaCodec ACodec对收到的消息进行处理,获取到rotation的信息。 step4: ACodec在创建nativewindow时将rotation信息传入。 step5: surface把rotation信息转换为transform的角度 step6: 播放视频时每解码完一帧就会把yuv数据送给surface去渲染,此时surface会根据设置的transform 的角度旋转yuv数据并render。 blog.csdn.net/cheriyou_/a…

dequeueInputBuffer 返回一个input buffer 的 index 通过消息机制设置timeout,如果timeout时间没返回结果,则err 具体的操作就是细分input和output buffer,从availBuffer中取出第一个可用buffer设好meta data (宽高)后返回去 mPortBuffers是申请的所有的buffer,其中空闲的是mAvailPortBuffers,存储空闲buffer的index,因此 它们的index不一样,其他都是同一片地址。

queueInputBuffer 将一个index送过来 从对应index中取出buffer然后通过CCodecBufferChannel去queueInputBuffer,这里面送到worklets, 也就是下一个buffer处理地址 这之后mPortBuffers的index就要释放到mAvailPortBuffers中了 ownedbyClient表示这个buffer是否 送给了worklets,送了之后就不属于client那边了。

releaseOutput 是将index送过去,然后buffer queueToOutputSurface 就送到surface上面去了,这 之后会被surfaceflinger取走消费

通过mimetype或者直接decoder name方式来创建解码器,mimetype就不能自己固定解码器,会让系统去 选择一个解码器decoder mediaCodec = MediaCodec.createDecoderByType(mimeType); mediaCodec = MediaCodec.createByCodecName("OMX.qcom.video.decoder.avc");//可以认为选择解码器

3.1.3 视频常用封装格式

MP4 BOX mp4由各种box组成,每种不同box的功能不一样 首先由一个ftype box,包含文件的一些信息 其次是moov box,里面包含了很多子box,meta-data信息等 媒体数据包含在mdat信息中,也包含了很多子box ftyp file type 文件版本,协议等信息 moov movie box 不包含具体数据,只包含对应信息 mdat meta data box 存放解码播放的数据

3.1.3 视频常用格式

3.2 二级目录

4 显示子系统

Android Display Framework

4.1 二级目录

4.2 二级目录

5 媒体框架介绍

MultiMedia OpenSource Framework

5.1 ExoPlayer

5.2 MediaTranscoder

5.3 ffmpeg

5.4 Exo media3

5.5 GPUImage

5.6 ijkplayer

6 流媒体知识

Streaming Multimedia

6.1 HLS

http live streaming,基本原理是将整个流分割成一个个小的基于http的文件来下载,每次只下载一些, 当流媒体正在播放的时候,可以根据网络的状况实施改变播放的分辨率和码率等信息(通过下载不同分辨率 和码率的http文件来实现)来允许码率自适应。 在开始流媒体会话时,客户端会下载一个包含元数据的m3u8 playlist文件,用于寻找媒体流。 直播的m3u8文件会不断更新,需要频繁请求,点播的m3u8文件不会变,请求一次即可。 客户端和服务器通过HTTP协议交互,以2级为例,先获取第一级m3u8,包含了服务端可以用于播放的一个 或多个带宽URL,这个URL可以获取第二级m3u8,包含了多个ts分片及其URL,通过此URL可以下载ts。 hls按照时间片来区分,如果中间改变了码率或者分辨率,则会播放完本片段,播放下个分段的时候再去切换

6.2 DASH

和HLS很像,唯一差别就是它里面的每个segment都包含了不同码率文件,根据网速选择对应文件,而HLS是所有 的码率放在一个级别里面,因此切换的时候要重新换一个等级。 区别就是横切还是竖切

6.3 RTMP

7 多媒体常用工具

Multimedia Tools

7.1 Adobe Audition

7.2 MediaInfo

7.3 UML

7.2 FFmpeg

8 解决过的难题

1、项目深入了解清楚,各方面的细节,遇到的问题,解决的方案和思路,如何表达沟通出来 2、调整项目的排放优先级,熟悉全部负责最有把我的放前面,有价值的放前面,不熟悉的放后面 3、项目包装,达到了哪些成功,做了哪些优化,如何包装的尽可能漂亮,亮出优化后的数据和成果,总结经验 4、熟悉1、2个项目,列出优化点,难点。已经尝试过的解决方案和解决思路 5、系统framework层可以放大比例,这是独特优势 6、直播项目,直播摄像头那部分好好写一些

播放器相关难点问题

如何用前因后果把一个事情描述清楚?

1、播放器性能流畅性问题 白天鹅折叠壁纸卡顿+相册视频方差卡顿 白天鹅折叠屏壁纸卡顿问题: 现象描述:特定试用用户打开屏幕,壁纸播放低概率卡顿 问题原因:开屏时,各进程初始化导致负载重,播放器相关线程得不到cpu调度,无法及时送数据和解码导致卡顿 解决方案:动态增加UX,提高播放器和解码器线程优先级

相册视频方差卡顿: 问题描述:特定机型,相册播放相机录制的视频,播放有粘滞感 问题原因:视频每帧渲染时长间隔不一致,导致卡顿,播放器release给surface,相册ondrawframe后eglswapbuffer耗时与vsync时钟的jank,系统vsync时钟不准确,误差较大 解决方案:播放器调整release时间+系统vsync时钟调准

ffmpeg解析器异常crash问题 问题现象:打开相册就crash 问题原因:获取缩略图的时候

3、兼容性问题 异常pts,dolby格式跳转,ffmpeg异常视频流问题