本讲是Android Camera专题系列的第21讲,我们介绍Android Camera2 API专题的createCaptureSession详解,包括如下五部分内容:
- createCaptureSession (SessionConfiguration config)注意事项
- 根据不同的场景选择Surface
- 流配置表说明
- Regular流配置表
- Reprocessing流配置表(参考:第17讲 Android Camera2 API Reprocessable Capture Session详解一)
- Constrained high-speed recording流配置
视频在线观看:
加入知识星球与更多Camera同学交流
- 星球名称:深入浅出Android Camera
- 星球ID: 17296815
createCaptureSession (SessionConfiguration config)注意事项
创建CameraCaptureSession
-
创建CameraCaptureSession时,需要包含所有的Output/Input Surfaces
-
创建好CameraCaptureSession后,提交的CaptureRequest中带的Surfaces只能在这组Surfaces里面选择
创建CameraCaptureSession一般需要几百毫秒,Camera HAL会对一些硬件做上电操作、创建Pipeline动作等等
CameraCaptureSession的切换
-
直接调用createCaptureSession,前面的CameraCaptureSession会被close掉
-
最快的切换方式
- 先调用旧CameraCaptureSession#abortCaptures,再创建新的CameraCaptureSession
根据不同的场景选择Surface
场景 | Surface组件 | 使用方法 |
---|---|---|
Preview | SurfaceView | surfaceCreated(SurfaceHolder holder)时调用SurfaceHolder.setFixedSize(int, int)设置Size,然后调用SurfaceHolder.getSurface()来获取Surface |
OpenGL ES处理(Preview) | SurfaceTexture | 调用SurfaceTexture.setDefaultBufferSize(int, int)设置Size,然后通过new Surface(SurfaceTexture)来获取Surface |
录像 | MediaCodec | 配置完MediaCodec后,调用MediaCodec.createInputSurface()来获取Surface |
录像 | MediaRecorder | 配置完MediaRecorder后,调用MediaRecorder.getSurface()来获取Surface |
YUV处理 | Renderscript | 配置好Allocation后,调用Allocation.getSurface()来获取Surface |
抓图(Raw/YUV/JPEG…) | ImageReader | 配置好ImageReader后,调用ImageReader.getSurface()来获取Surface |
Reprocess | CameraCaptureSession | CameraCaptureSession创建好后,调用CameraCaptureSession#getinputsurface来获取Surface |
流配置表说明
Format
-
PRIV: ImageFormat.PRIVATE,对App透明的
-
YUV: ImageFormat.YUV_420_888
-
JPEG: ImageFormat.JPEG
-
RAW: ImageFormat.RAW_SENSOR
Size
-
PREVIEW:跟屏幕宽高比一致,<=1080P
-
RECORD: CamcorderProfile中定义的最大录像Size
-
MAXIMUM: StreamConfigurationMap#getOutputSizes中的最大值
-
MULTI_RES : MultiResolutionStreamConfigurationMap#getOutputInfo(int)获取到的值
超出流配置表限制
如何理解是否超出表格限制
-
某一行表示一个Streams Configuration组合,比如这一行支持8MP YUV和2MP PRIV
-
[8 MP YUV, 2 MP PRIV] 或者 [2 MP YUV, 2 MP PRIV]组合配置能成功
-
[8 MP YUV, 4 MP PRIV], 或者 [4 MP YUV, 4 MP PRIV], 或者 [8 MP PRIV, 2 MP YUV]不能确保是否成功
-
-
如果App使用超出下面表格限制的Surfaces来创建Session,有三种可能发生
-
CameraCaptureSession能创建成功,并能正常工作
-
CameraCaptureSession能创建成功,但帧率无法达到StreamConfigurationMap#getOutputMinFrameDuration的要求
-
CameraCaptureSession创建失败
-
-
也有可能可以成功创建Session,可以通过如下两种方式尝试
-
isSessionConfigurationSupported(SessionConfiguration)
-
调用createCaptureSession看是否不会发生Exception 或 收到onConfigured回调
-
Regular流配置表
Regular Capture - LEGACY
Regular Capture - LIMITED
Regular Capture - FULL
Regular Capture – RAW Capability
Regular Capture – BURST Capability
Regular Capture – LEVEL_3
Regular Capture – Concurrent stream
Regular Capture – MultiResolutionoutputs Legacy Level
Regular Capture – MultiResolutionoutputs LIMITED Level
Regular Capture – 特殊对待QCIF
-
前面介绍的一定支持的流配置表时,提到只要小于这个表中的Size也能支持,但有一个例外:QCIF(176x144)
-
因为通常Camera底层的downscale能力都是有限的(最大能downscale多少倍),如果从>= 1920x1080的分辨率downscale到176x144,有可能不支持
Constrained high-speed recording流配置
支持CONSTRAINED_HIGH_SPEED_VIDEO Capability
帧率>=120FPS
与普通Capture Session比,有如下限制
-
最多支持2个Output Surfaces
-
每个Output Surface的Size必须一样,来自StreamConfigurationMap#getHighSpeedVideoSizes
-
只能通过captureBurst 或 setRepeatingBurst方法向Camera底层送CaptureRequest List,CaptureRequest List来自CameraConstrainedHighSpeedCaptureSession#createHighSpeedRequestList
-
FPS Range必须来自StreamConfigurationMap#getHighSpeedVideoFpsRangesFor