性能不佳的 ML Kit 条码扫描

Posted

技术标签:

【中文标题】性能不佳的 ML Kit 条码扫描【英文标题】:Bad performance ML Kit barcode scanning 【发布时间】:2021-12-31 23:31:56 【问题描述】:

我正在使用 Google 的 ML Kit 进行条形码扫描,并从 Google 提供的示例和教程中收集了以下代码。然而,表演是戏剧性的。识别条码需要几秒钟,可以是 10、15 秒。有什么办法可以改善吗?

另外,这如何与倒置条形码一起使用?我发现我需要反转图像,但是,如果在分析器中我尝试获取 image.bitmapInternal 或 image.byteBuffer,它总是为空。

构建.gradle

 implementation 'com.google.mlkit:barcode-scanning:17.0.0'
 // CameraX core library using camera2 implementation
implementation "androidx.camera:camera-camera2:1.0.2"
// CameraX Lifecycle Library
implementation "androidx.camera:camera-lifecycle:1.0.2"
// CameraX View class
implementation "androidx.camera:camera-view:1.0.0-alpha31"

然后,在一个片段中:

typealias BarCodeListener = (barCode: String) -> Unit
const val TAG = "ConnectorScanner"
[...]

override fun onResume() 
    super.onResume()
    cameraExecutor = Executors.newSingleThreadExecutor()
    startCamera()


private fun startCamera() 
    val cameraProviderFuture = ProcessCameraProvider.getInstance(requireContext())
    val resolution = Size(720, 1280)
    cameraProviderFuture.addListener(
        // Used to bind the lifecycle of cameras to the lifecycle owner
        val cameraProvider: ProcessCameraProvider = cameraProviderFuture.get()

        // Preview
        val preview = Preview.Builder()
            .setTargetResolution(resolution)
            .build()
            .also 
                it.setSurfaceProvider(binding.viewFinder.surfaceProvider)
            

        imageCapture = ImageCapture.Builder()
            .setTargetResolution(resolution)
            .setCaptureMode(ImageCapture.CAPTURE_MODE_MAXIMIZE_QUALITY)
            .build()

        val imageAnalyzer = ImageAnalysis.Builder()
            .setBackpressureStrategy(ImageAnalysis.STRATEGY_KEEP_ONLY_LATEST)
            .build()
            .also 
                it.setAnalyzer(cameraExecutor, BarCodeAnalyzer  barCode ->
                    if (BuildConfig.DEBUG) 
                        Toast.makeText(context, "Code: $barCode", Toast.LENGTH_LONG).show()
                    
                    viewModel.onConnectorCodeScanned(barCode)
                    cameraProvider.unbindAll()
                )
            

        // Select back camera as a default
        val cameraSelector = CameraSelector.DEFAULT_BACK_CAMERA

        try 
            // Unbind use cases before rebinding
            cameraProvider.unbindAll()

            // Bind use cases to camera
            cameraProvider.bindToLifecycle(
                this, cameraSelector, preview, imageCapture, imageAnalyzer
            )

         catch (exc: Exception) 
            Log.e(TAG, "Use case binding failed", exc)
            showErrorDialog()
        

    , ContextCompat.getMainExecutor(requireContext()))

图像分析器

private class BarCodeAnalyzer(private val listener: BarCodeListener) : ImageAnalysis.Analyzer 
    val options = BarcodeScannerOptions.Builder()
        .setBarcodeFormats(
            Barcode.FORMAT_DATA_MATRIX
        )
        .build()

    @SuppressLint("UnsafeOptInUsageError")
    override fun analyze(imageProxy: ImageProxy) 
        val mediaImage = imageProxy.image
        mediaImage?.let 
            val image =
                InputImage.fromMediaImage(it, imageProxy.imageInfo.rotationDegrees)
                val scanner = BarcodeScanning.getClient(options)

            scanner.process(image)
                .addOnSuccessListener  barcodes ->
                    if (barcodes.isNotEmpty()) 
                        barcodes.firstOrNull()?.rawValue?.let  barcode ->
                            Log.d(TAG, barcode)
                            listener(barcode)
                        
                        imageProxy.close()
                    
                
        
        imageProxy.close()
    

【问题讨论】:

你可以在这里查看我的二维码示例 - ***.com/a/64504871/3437352。条形码也会非常相似。 【参考方案1】:

幸运的是,我找到了性能问题的解决方案,它添加了一个 OnCompleteListener 并在那里关闭图像。所以分析器将是

scanner.process(image)
                .addOnSuccessListener  barcodes ->
                    if (barcodes.isNotEmpty()) 
                        barcodes.firstOrNull()?.rawValue?.let  barcode ->
                            Log.d(TAG, barcode)
                                listener(barcode)
                        
                    
                
                .addOnCompleteListener 
                    imageProxy.close()
                
        

现在条码的扫描速度快如闪电!

【讨论】:

以上是关于性能不佳的 ML Kit 条码扫描的主要内容,如果未能解决你的问题,请参考以下文章

带有 Google google_ml_kit 的条形扫描仪:^0.6.0

MLKit 是一个强大易用的工具包。通过 ML Kit 您可以很轻松的实现文字识别条码识别图像标记人脸检测对象检测等功能

MLKit 是一个强大易用的工具包。通过 ML Kit 您可以很轻松的实现文字识别条码识别图像标记人脸检测对象检测等功能

基于 Google ML Kit 快速集成二维码扫描,速度比 zxing 快,可配置相册,闪光灯,相机可以调整焦距放大缩小,自定义扫描线颜色,自定义背景颜色,自定义遮罩层,支持同时扫多个二维码和条形码

基于 Google ML Kit 快速集成二维码扫描,速度比 zxing 快,可配置相册,闪光灯,相机可以调整焦距放大缩小,自定义扫描线颜色,自定义背景颜色,自定义遮罩层,支持同时扫多个二维码和条形码

性能不佳的 SQL 查询