ImageAnalysis 用例 CameraX 人脸检测
Posted
技术标签:
【中文标题】ImageAnalysis 用例 CameraX 人脸检测【英文标题】:ImageAnalysis usecase CameraX Facedetection 【发布时间】:2021-07-23 14:57:12 【问题描述】:我正在尝试开发一款使用 CameraX 和 MLKit Facedetecion API 分析相机实时帧的应用。它在预览用例中工作正常,但图像分析用例根本不起作用。
我不明白为什么,因为我正在关注最新的官方文档。我的代码:
@Override
protected void onCreate(Bundle savedInstanceState)
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
previewView = findViewById(R.id.previewView);
if (previewView == null)
Toast.makeText(this,
"PreviewView not found",
Toast.LENGTH_SHORT).show();
iv = findViewById(R.id.face_image_view);
if (iv == null)
Toast.makeText(this,
"ImageView not found",
Toast.LENGTH_SHORT).show();
cameraProviderFuture = ProcessCameraProvider.getInstance(this);
cameraProviderFuture.addListener(() - >
try
ProcessCameraProvider cameraProvider = cameraProviderFuture.get();
if (allPermissionsGranted())
bindPreview(cameraProvider);
Log.i(TAG, "here1");
else
ActivityCompat.requestPermissions(this, REQUIRED_PERMISSIONS, REQUEST_CODE_PERMISSION);
catch (ExecutionException | InterruptedException e)
// No errors need to be handled for this Future.
// This should never be reached.
, ContextCompat.getMainExecutor(this));
void bindPreview(@NonNull ProcessCameraProvider cameraProvider)
cameraProvider.unbindAll();
//bind preview
Preview preview = new Preview.Builder()
.build();
CameraSelector cameraSelector = new CameraSelector.Builder()
.requireLensFacing(CameraSelector.LENS_FACING_FRONT)
.build();
preview.setSurfaceProvider(previewView.getSurfaceProvider());
//bind image analysis
ImageAnalysis imageAnalysis =
new ImageAnalysis.Builder()
.setTargetResolution(new Size(previewView.getWidth(), previewView.getHeight()))
.setBackpressureStrategy(ImageAnalysis.STRATEGY_KEEP_ONLY_LATEST)
.build();
imageAnalysis.setAnalyzer(executor, new ImageAnalysis.Analyzer()
@Override
public void analyze(@NonNull ImageProxy imageProxy)
int rotationDegrees = imageProxy.getImageInfo().getRotationDegrees();
Log.i(TAG, "here analyzer");
@SuppressLint("UnsafeOptInUsageError") Image mediaImage = imageProxy.getImage();
if (mediaImage != null)
InputImage image =
InputImage.fromMediaImage(mediaImage, rotationDegrees);
initDrawingUtils(image);
//START configuration of the facedetector
FaceDetectorOptions realTimeOpts =
new FaceDetectorOptions.Builder()
.setContourMode(FaceDetectorOptions.CONTOUR_MODE_ALL)
.build();
FaceDetector detector = FaceDetection.getClient(realTimeOpts);
//END of configuration of face detector
// START detector
detector.process(image)
.addOnSuccessListener(
new OnSuccessListener < List < Face >> ()
@Override
public void onSuccess(List < Face > faces)
if (!faces.isEmpty())
//Get information about detected faces
processFaces(faces);
else
canvas.drawColor(Color.TRANSPARENT, PorterDuff.Mode.MULTIPLY);
Log.i(TAG, "vuoto");
)
.addOnFailureListener(
e - >
e.printStackTrace();
);
);
Log.i(TAG, "here4");
//add preview and analysis to the lifecycle
cameraProvider.bindToLifecycle((LifecycleOwner) this, cameraSelector, preview, imageAnalysis);
Log.i(TAG, "here5");
代码永远不会到达分析器,因此不会处理实时帧。有人可以帮帮我吗?
【问题讨论】:
代码对我来说看起来是正确的。如果你能创建一个最小的可重现示例并将其放在 GitHub 上,我可以帮你调试。 我在 imageAnalysis.setAnalyzer 中使用“Runnable::run”而不是“executor”解决了 【参考方案1】:不确定这是否是主要问题,但您似乎在处理图像后忘记关闭 ImageProxy。尝试将此侦听器添加到 process 方法返回的值:
.addOnCompleteListener(task -> imageProxy.close());
来自文档:
如果您正在使用 CameraX API,请确保在使用完 ImageProxy 后关闭它,例如,通过将 OnCompleteListener 添加到从 process 方法返回的 Task 中。有关示例,请参见快速入门示例应用中的 VisionProcessorBase 类。
【讨论】:
感谢您的回答,但无论如何都不起作用【参考方案2】:回答有点晚,反正我今天也遇到并解决了同样的问题。
您应该在analyze
方法的末尾调用ImageProxy.close()
,这将允许传送下一张图像进行分析:
imageAnalysis.setAnalyzer(executor, new ImageAnalysis.Analyzer()
@Override
public void analyze(@NonNull ImageProxy imageProxy)
int rotationDegrees = imageProxy.getImageInfo().getRotationDegrees();
@SuppressLint("UnsafeOptInUsageError")
Image mediaImage = imageProxy.getImage();
if (mediaImage != null)
...
imageProxy.close() // <-- Add this line
【讨论】:
以上是关于ImageAnalysis 用例 CameraX 人脸检测的主要内容,如果未能解决你的问题,请参考以下文章
CameraX ImageAnalysis 设置 TargetResolution 小于 640x480
如何使用 Android CameraX ImageAnalysis 提高帧速率?
如何在android studio中获取camera2 api中的每一帧,例如camera api中的PreviewCallback和camerax中的ImageAnalysis.Analyzer?