android摄像头的动态聚焦区域
我正在构建一个android摄像头应用程序(不使用camera2 api),在室外条件下拍摄一些物体的近景照片。照片需要在突发模式下拍摄,即一旦启动,相机将连续拍摄5张照片,所有照片都需要对焦。用户在拍照时可能正在移动相机,用户将无法手动选择焦点。物体颜色较暗,有时相机视图中的明亮物体会使相机过度曝光。android摄像头的动态聚焦区域,android,camera,autofocus,Android,Camera,Autofocus,我正在构建一个android摄像头应用程序(不使用camera2 api),在室外条件下拍摄一些物体的近景照片。照片需要在突发模式下拍摄,即一旦启动,相机将连续拍摄5张照片,所有照片都需要对焦。用户在拍照时可能正在移动相机,用户将无法手动选择焦点。物体颜色较暗,有时相机视图中的明亮物体会使相机过度曝光。 我知道如何将焦点区域设置为相机参数,但焦点区域的位置必须自动更改,以便其始终聚焦在相机视图中的暗区域。黑暗物体的位置在相机视图中是不固定的,因此在设置焦点区域之前,应用程序必须在每一帧中寻找黑暗
我知道如何将焦点区域设置为相机参数,但焦点区域的位置必须自动更改,以便其始终聚焦在相机视图中的暗区域。黑暗物体的位置在相机视图中是不固定的,因此在设置焦点区域之前,应用程序必须在每一帧中寻找黑暗像素。
我正在考虑在
onPreviewFrame()
回调中检查暗区域,但我不确定这是否是正确的方法。以前有人这样做过吗?谁能给我指出正确的方向?例如,是否有一个项目可以让android摄像头始终使用人脸检测器聚焦在人脸上?我试图在互联网上查找,但找不到任何相关项目。您必须实施触摸式聚焦。像这样的事情:
@Override
public boolean onTouchEvent(MotionEvent event) {
if(event.getAction() == MotionEvent.ACTION_DOWN){
float x = event.getX();
float y = event.getY();
float touchMajor = event.getTouchMajor();
float touchMinor = event.getTouchMinor();
Rect touchRect = new Rect(
(int)(x - touchMajor/2),
(int)(y - touchMinor/2),
(int)(x + touchMajor/2),
(int)(y + touchMinor/2));
if (mTouchEventListener != null)
mTouchEventListener.touchFocus(touchRect, false);
}
@TargetApi(Build.VERSION_CODES.ICE_CREAM_SANDWICH)
public void touchFocus(Rect tfocusRect, boolean useInMid) {
if (mCamera == null) return;
try{
mCamera.cancelAutoFocus();
//Convert from View's width and height to +/- 1000
Rect targetFocusRect = (useInMid || sfv == null) ? new Rect() :
new Rect(tfocusRect.left * 2000/sfv.getWidth() - 1000,
tfocusRect.top * 2000/sfv.getHeight() - 1000,
tfocusRect.right * 2000/sfv.getWidth() - 1000,
tfocusRect.bottom * 2000/sfv.getHeight() - 1000);
final List<Camera.Area> focusList = new ArrayList<Camera.Area>();
Camera.Area focusArea = new Camera.Area(targetFocusRect, 1000);
focusList.add(focusArea);
Parameters para = mCamera.getParameters();
O.Log.d(TAG,para.getMaxNumFocusAreas() + ";" + para.getMaxNumMeteringAreas() + " >> " + tfocusRect.toString());
para.setFocusAreas(focusList);
para.setMeteringAreas(focusList);
try{
mCamera.setParameters(para);
}catch(RuntimeException e){
O.Log.e(TAG, "setParameters failed", e);
}
mCamera.autoFocus(myAutoFocusCallback);
// _.setCameraTorch(1);
}catch (Exception e){
O.Log.e(TAG, "Touch Focus Camera Error", e);
}
}
private static AutoFocusCallback myAutoFocusCallback = new AutoFocusCallback() {
@Override
public void onAutoFocus(boolean success, Camera camera) {
// TODO Auto-generated method stub
}
};
touchFocus看起来像这样:
@Override
public boolean onTouchEvent(MotionEvent event) {
if(event.getAction() == MotionEvent.ACTION_DOWN){
float x = event.getX();
float y = event.getY();
float touchMajor = event.getTouchMajor();
float touchMinor = event.getTouchMinor();
Rect touchRect = new Rect(
(int)(x - touchMajor/2),
(int)(y - touchMinor/2),
(int)(x + touchMajor/2),
(int)(y + touchMinor/2));
if (mTouchEventListener != null)
mTouchEventListener.touchFocus(touchRect, false);
}
@TargetApi(Build.VERSION_CODES.ICE_CREAM_SANDWICH)
public void touchFocus(Rect tfocusRect, boolean useInMid) {
if (mCamera == null) return;
try{
mCamera.cancelAutoFocus();
//Convert from View's width and height to +/- 1000
Rect targetFocusRect = (useInMid || sfv == null) ? new Rect() :
new Rect(tfocusRect.left * 2000/sfv.getWidth() - 1000,
tfocusRect.top * 2000/sfv.getHeight() - 1000,
tfocusRect.right * 2000/sfv.getWidth() - 1000,
tfocusRect.bottom * 2000/sfv.getHeight() - 1000);
final List<Camera.Area> focusList = new ArrayList<Camera.Area>();
Camera.Area focusArea = new Camera.Area(targetFocusRect, 1000);
focusList.add(focusArea);
Parameters para = mCamera.getParameters();
O.Log.d(TAG,para.getMaxNumFocusAreas() + ";" + para.getMaxNumMeteringAreas() + " >> " + tfocusRect.toString());
para.setFocusAreas(focusList);
para.setMeteringAreas(focusList);
try{
mCamera.setParameters(para);
}catch(RuntimeException e){
O.Log.e(TAG, "setParameters failed", e);
}
mCamera.autoFocus(myAutoFocusCallback);
// _.setCameraTorch(1);
}catch (Exception e){
O.Log.e(TAG, "Touch Focus Camera Error", e);
}
}
private static AutoFocusCallback myAutoFocusCallback = new AutoFocusCallback() {
@Override
public void onAutoFocus(boolean success, Camera camera) {
// TODO Auto-generated method stub
}
};
我发现这个问题有点模棱两可,所以我对它进行了编辑。感谢回复,但我需要自动设置焦点,而不是通过用户触摸屏幕。相机必须检测黑暗区域本身并改变焦点。你可以自己修改这个焦点区域。焦点区域不重要,但重要的是它的位置。我需要相机应用程序自动选择焦点。