记录一下SnapdragonCamera的相关流程。
从上一篇 SnapdragonCamera源码分析(一)CameraActivity可以知道,桌面点击相机图标实质上启动的是CameraActivity,且根据启动的Intent信息及其使用的CameraAPI2来看,启动后默认相机模式为拍照模式,使用的Module为CaptureModule.java。
CaptureModule在CameraActivity的onCreate()方法内被init():
@Override
public void init(CameraActivity activity, View parent) {
mActivity = activity;
mRootView = parent;
mSettingsManager = SettingsManager.getInstance();
mSettingsManager.createCaptureModule(this);
mSettingsManager.registerListener(this);
if (isBackCameraId()) {
CURRENT_ID = BACK_MODE;
} else {
CURRENT_ID = FRONT_MODE;
}
mSettingsManager.init();
mFirstPreviewLoaded = false;
Log.d(TAG, "init");
for (int i = 0; i < MAX_NUM_CAM; i++) {
mCameraOpened[i] = false;
mTakingPicture[i] = false;
}
for (int i = 0; i < MAX_NUM_CAM; i++) {
mState[i] = STATE_PREVIEW;
}
SceneModule module;
for (int i = 0; i < mSelectableModes.length; i++) {
module = new SceneModule();
module.mode = CameraMode.values()[i];
mSceneCameraIds.add(module);
}
mPostProcessor = new PostProcessor(mActivity, this);
mFrameProcessor = new FrameProcessor(mActivity, this);
mContentResolver = mActivity.getContentResolver();
initModeByIntent();
initCameraIds();
mUI = new CaptureUI(activity, this, parent);
mUI.initializeControlByIntent();
mFocusStateListener = new FocusStateListener(mUI);
mLocationManager = new LocationManager(mActivity, this);
}
1、初始化mSettingsManager,并注册相关设置项改变监听;顾名思义SettingsManager主要用来管理Camera设置项的管理,包括闪光灯状态、画质等设置项,当设置项改变时通过回调onSettingsChanged()方法处理。
2、判断当前前后摄模式,初始化CURRENT_ID;
3、默认设置所有可用Camera Devices的状态为非打开状态、非拍照状态、处于预览状态。
4、为每一种拍照模式初始化一个SceneModule对象,这个对象主要用于记录管理相应的Camera ID
六大模式:
private String[] mSelectableModes = {
"Video", "HFR", "Photo", "Bokeh", "SAT", "ProMode"};
public enum CameraMode {
VIDEO,
HFR,
DEFAULT,
RTB,
SAT,
PRO_MODE
}
5、初始化mPostProcessor、mFrameProcessor,主要处理预览、拍照等由底层返回的帧数据;
6、根据Activity启动的Intent action初始化拍照模式mIntentMode、mQuickCapture等;
7、获取所有可用Camera Device的设备描述信息CameraCharacteristics,根据Camera Devices的设备类型、是否前后摄判断设置之前为每个拍照模式设置的SceneModule对象,并且此时会初始化mCurrentSceneMode为“photo”。
1>通过TAG "org.codeaurora.qcamera3.logicalCameraType.logical_camera_type"来判断设备类型:
public static CameraCharacteristics.Key<Byte> logical_camera_type =
new CameraCharacteristics.Key<>("org.codeaurora.qcamera3.logicalCameraType.logical_camera_type", Byte.class);
2>通过CameraCharacteristics.LENS_FACING判断是否前后摄:
int facing = characteristics.get(CameraCharacteristics.LENS_FACING);
8、初始化CaptureUI,此主要用于管理当前拍照模式下所有UI方面的控制切换显示;
public void initializeControlByIntent() {
mThumbnail = (ImageView) mRootView.findViewById(R.id.preview_thumb);
mThumbnail.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (!CameraControls.isAnimating() && !mModule.isTakingPicture() &&
!mModule.isRecordingVideo())
mActivity.gotoGallery();
}
});
if (mModule.getCurrentIntentMode() != CaptureModule.INTENT_MODE_NORMAL) {
mCameraControls.setIntentMode(mModule.getCurrentIntentMode());
}
}
初始化缩略图控件,并为其设置点击跳转到相册的事件。
9、初始化mFocusStateListener,用于处理Camera对焦状态,具体用作CaptureUI内:
mFocusStateListener = new FocusStateListener(mUI);
public class FocusStateListener {
private static final String TAG = "SnapCam_FocusStateListe";
private CaptureUI mUI;
public FocusStateListener(CaptureUI ui) {
mUI = ui;
}
public void onFocusStatusUpdate(int focusState) {
switch (focusState) {
case CaptureResult.CONTROL_AF_STATE_ACTIVE_SCAN:
Log.d(TAG, "CONTROL_AF_STATE_ACTIVE_SCAN onFocusStarted");
mUI.onFocusStarted();
break;
case CaptureResult.CONTROL_AF_STATE_FOCUSED_LOCKED:
Log.d(TAG, "CONTROL_AF_STATE_FOCUSED_LOCKED onFocusSucceeded");
mUI.onFocusSucceeded(false);
break;
case CaptureResult.CONTROL_AF_STATE_NOT_FOCUSED_LOCKED:
Log.d(TAG, "CONTROL_AF_STATE_NOT_FOCUSED_LOCKED onFocusFailed");
mUI.onFocusFailed(false);
break;
case CaptureResult.CONTROL_AF_STATE_PASSIVE_FOCUSED:
Log.d(TAG, "CONTROL_AF_STATE_PASSIVE_FOCUSED onFocusSucceeded");
mUI.onFocusSucceeded(true);
break;
case CaptureResult.CONTROL_AF_STATE_PASSIVE_SCAN:
Log.d(TAG, "CONTROL_AF_STATE_PASSIVE_SCAN onFocusStarted");
mUI.onFocusStarted();
break;
case CaptureResult.CONTROL_AF_STATE_PASSIVE_UNFOCUSED:
Log.d(TAG, "CONTROL_AF_STATE_PASSIVE_UNFOCUSED onFocusFailed");
mUI.onFocusFailed(true);
break;
case CaptureResult.CONTROL_AF_STATE_INACTIVE:
Log.d(TAG, "CONTROL_AF_STATE_INACTIVE clearFocus");
mUI.clearFocus();
break;
}
}
}
10、初始化mLocationManager,主要用于处理应用内所有关于定位相关的操作。
即完成mCurrentModule的初始化
再来看CaptureUI,由于此方法篇幅较长,通篇进行一些控件初始化设置,挑选对本篇内容的关键比较重要的部分进行记录:
mSettingsManager = SettingsManager.getInstance();
mSettingsManager.registerListener(this);
实例化mSettingsManager,并为其注册设置项改变的监听,实现onSettingsChanged()方法;
mActivity.getLayoutInflater().inflate(R.layout.capture_module,
(ViewGroup) mRootView, true);
mPreviewCover = mRootView.findViewById(R.id.preview_cover);
// display the view
mSurfaceView = (AutoFitSurfaceView) mRootView.findViewById(R.id.mdp_preview_content);
mSurfaceHolder = mSurfaceView.getHolder();
mSurfaceHolder.addCallback(callback);
mSurfaceView.addOnLayoutChangeListener(new View.OnLayoutChangeListener() {
@Override
public void onLayoutChange(View v, int left, int top, int right,
int bottom, int oldLeft, int oldTop, int oldRight,
int oldBottom) {
int width = right - left;
int height = bottom - top;
if (mFaceView != null) {
mFaceView.onSurfaceTextureSizeChanged(width, height);
}
if (mT2TFocusRenderer != null) {
mT2TFocusRenderer.onSurfaceTextureSizeChanged(width, height);
}
}
});
mSurfaceViewMono = (AutoFitSurfaceView) mRootView.findViewById(R.id.mdp_preview_content_mono);
mSurfaceViewMono.setZOrderMediaOverlay(true);
mSurfaceHolderMono =