java - 条形码扫描仪使用 ML Kit 仅读取 QR 码

标签 java android barcode-scanner firebase-mlkit

我正在尝试使用 ML Kit 在 android studio 中构建条形码扫描仪。我有一个运行良好的代码,它只能检测二维码。我想让条形码扫描仪能够读取所有类型的条形码,主要是食品条形码。我正在尝试获取条形码的原始值,以便在数据库中进行搜索并将相关信息显示到屏幕上。

下面是我用来检测二维码的代码。

public class MainActivity extends AppCompatActivity {
    CameraView camera_view;
    boolean isDetected = false;
    private Button btn_start_again;

    FirebaseVisionBarcodeDetectorOptions options;
    FirebaseVisionBarcodeDetector detector;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        Dexter.withActivity(this)
                .withPermissions(new String [] {Manifest.permission.CAMERA,Manifest.permission.RECORD_AUDIO})
                .withListener(new MultiplePermissionsListener() {

                    @Override
                    public void onPermissionsChecked(MultiplePermissionsReport report) {

                        setUpCamera();

                    }

                    @Override
                    public void onPermissionRationaleShouldBeShown(List<PermissionRequest> permissions, PermissionToken token) {

                        Toast.makeText(getApplicationContext(),"You must accept the permissions",Toast.LENGTH_LONG).show();

                    }
                }).check();

    }

    private void setUpCamera() {

        btn_start_again =(Button)findViewById(R.id.btn_again);
        btn_start_again.setEnabled(false);

        btn_start_again.setOnClickListener((View v) -> isDetected = !isDetected);

        camera_view = (CameraView) findViewById(R.id.cameraview);
        camera_view.setLifecycleOwner(this);

        camera_view.addFrameProcessor(new FrameProcessor() {
            @Override
            public void process(@NonNull Frame frame) {

                processImage(getVisionImageFromFrame(frame));


            }
        });

        FirebaseVisionBarcodeDetectorOptions options =
                new FirebaseVisionBarcodeDetectorOptions.Builder()
                        .setBarcodeFormats(
                                FirebaseVisionBarcode.FORMAT_QR_CODE,
                                FirebaseVisionBarcode.FORMAT_AZTEC)
                        .build();
        detector = FirebaseVision.getInstance().getVisionBarcodeDetector(options);

    }

    private void processImage(FirebaseVisionImage image) {

        if(!isDetected){

            detector.detectInImage(image)
                    .addOnSuccessListener(new OnSuccessListener<List<FirebaseVisionBarcode>>() {
                        @Override
                        public void onSuccess(List<FirebaseVisionBarcode> firebaseVisionBarcodes) {

                            processResult(firebaseVisionBarcodes);

                        }
                    })

                    .addOnFailureListener(new OnFailureListener() {
                        @Override
                        public void onFailure(@NonNull Exception e) {

                            Toast.makeText(getApplicationContext(),"e.getMessage()",Toast.LENGTH_LONG).show();

                        }
                    });


        }

    }

    private void processResult(List<FirebaseVisionBarcode> firebaseVisionBarcodes) {

        if(firebaseVisionBarcodes.size() > 0 ){

            isDetected = true;
            btn_start_again.setEnabled(isDetected);

            for (FirebaseVisionBarcode item:firebaseVisionBarcodes){

                Rect bounds = item.getBoundingBox();
                Point[] corners = item.getCornerPoints();

                String rawValue = item.getRawValue();

                int value_type = item.getValueType();
                switch (value_type){
                    case FirebaseVisionBarcode.TYPE_TEXT:
                    {
                        createDialog(item.getRawValue());
                    }
                    break;
                    case FirebaseVisionBarcode.TYPE_URL:
                    {

                        Intent intent =  new Intent(Intent.ACTION_VIEW, Uri.parse(item.getRawValue()));
                        startActivity(intent);

                    }
                    case FirebaseVisionBarcode.TYPE_CONTACT_INFO:
                    {

                        String info = new StringBuilder("Name:")
                                /*.append(item.getContactInfo().getName().getFormattedName())
                                .append("\n")*/
                                .append("Address")
                                .append(item.getContactInfo().getAddresses().get(0).getAddressLines())
                                .append("\n")
                                .append("Email:")
                                .append(item.getContactInfo().getEmails().get(0).getAddress())
                                .toString();
                        createDialog(info);

                    }
                    break;

                    default:
                    {

                        createDialog(rawValue);

                    }
                    break;


                }

            }

        }

    }

    private void createDialog(String text) {

        AlertDialog.Builder builder = new AlertDialog.Builder(this);

        builder.setMessage(text);
        builder.setPositiveButton("OK", ((DialogInterface dialog, int i) -> dialog.dismiss()));

        AlertDialog dialog = builder.create();
        dialog.show();

    }

    private FirebaseVisionImage getVisionImageFromFrame(Frame frame) {

        byte[] data = frame.getData();
        FirebaseVisionImageMetadata metadata = new FirebaseVisionImageMetadata.Builder()
                .setFormat(FirebaseVisionImageMetadata.IMAGE_FORMAT_NV21)
                .setHeight(frame.getSize().getHeight())
                .setWidth(frame.getSize().getWidth())
                .build();
                //.setRotation(frame.getRotation())

        return FirebaseVisionImage.fromByteArray(data,metadata);
    }
}

最佳答案

您还遇到了硬件问题。

Android 设备的摄像头通常只有在正确对焦的情况下才能读取条形码,并且只有后置摄像头才会发生这种情况,因为前置摄像头通常没有自动对焦功能。

相反,即使没有很好地聚焦,QR 码也会被读取。

此外,普通相机读取条形码的速度很慢,如果您想要一台可以快速读取所有代码的设备,请寻找一个带有内置条形码阅读器的设备,它们被称为 PDA,尽管它们比智能手机贵得多.

关于java - 条形码扫描仪使用 ML Kit 仅读取 QR 码,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59436192/

相关文章:

java - Mockito returnsFirstArg() 使用

android - 在 fragment 内初始化 map

Android广播接收器不工作

node.js USB (hid) 条码扫描仪读取缓冲区

java - Android 应用程序 - 每当蓝牙键盘连接/断开连接时触发 onCreate

java - 在 JSTL 中将小数解析为整数

java - java中比较两个字符串以忽略大小写和特殊字符?

android - 在 Android 中连续旋转 ImageView

从外部蓝牙扫描仪捕获 iOS key 代码

java - 将列表作为参数传递给 JPQL 命名查询不起作用