首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >创建点击焦点上的CameraSource - Android代码检测

创建点击焦点上的CameraSource - Android代码检测
EN

Stack Overflow用户
提问于 2016-04-16 20:00:19
回答 3查看 7.5K关注 0票数 2

我正在开发一个android应用程序,它允许用户检查QR代码内容并根据读取结果执行某些内容。

为了提高性能,我想实现两个方法:

  • onClickFocus (它允许用户在点击屏幕时对相机进行对焦)
  • 涡轮/关闭闪光灯(允许用户打开/关闭闪光灯)

我已经做了一些调查,并指出,对于管理相机和闪光灯,我需要能够管理作为对象本身的Camera

噩梦就是从这里开始的。

我使用下面的代码显示相机的结果和跟踪QR代码。

代码语言:javascript
复制
    import android.app.FragmentTransaction;
import android.content.Context;


import android.os.Bundle;
import android.os.Vibrator;
import android.support.v4.widget.DrawerLayout;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;
import android.util.SparseArray;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.widget.TextView;

import com.google.android.gms.vision.Detector;
import com.google.android.gms.vision.barcode.Barcode;
import com.google.android.gms.vision.barcode.BarcodeDetector;
import java.io.IOException;



public class MainReadActivity extends AppCompatActivity {


    public SurfaceView cameraView;
    private TextView barcodeInfo;
    public BarcodeDetector barcodeDetector;
    public CameraSource cameraSource;
    public Vibrator v;
    public String textInfo;
    public DrawerLayout mDrawerLayout;




    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main_read);
        v = (Vibrator) getSystemService(Context.VIBRATOR_SERVICE);

        mDrawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout_main);


        getSupportFragmentManager().findFragmentById(R.id.drawer_layout_main);

        cameraView = (SurfaceView) findViewById(R.id.camera_view);


        //barcodeInfo = (TextView) findViewById(R.id.code_info);

        barcodeDetector = new BarcodeDetector.Builder(this)
                .setBarcodeFormats(Barcode.QR_CODE)
                .build();


        cameraSource = new CameraSource.Builder(this, barcodeDetector).build();



        cameraView.getHolder().addCallback(new SurfaceHolder.Callback() {

            @Override
            public void surfaceCreated(SurfaceHolder holder) {


                try {
                    cameraSource.start(cameraView.getHolder());
                } catch (IOException ie) {
                    Log.e("CAMERA SOURCE", ie.getMessage());
                }

            }


            @Override
            public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
            }

            @Override
            public void surfaceDestroyed(SurfaceHolder holder) {
                cameraSource.stop();
            }

        });


        barcodeDetector.setProcessor(new Detector.Processor<Barcode>() {

            @Override
            public void release() {

            }


            @Override
            public void receiveDetections(Detector.Detections<Barcode> detections) {
                final SparseArray<Barcode> barcodes = detections.getDetectedItems();

                if (barcodes.size() != 0) {


                    new Runnable() {    // Use the post method of the TextView
                        public void run() {


                            v.vibrate(500);
                          // textInfo = barcodes.valueAt(0).displayValue;

                            MyFragmentDialog newf = new MyFragmentDialog();
                            FragmentTransaction transaction = getFragmentManager().beginTransaction();
                            transaction.replace(R.id.fragment_container, newf);

                            transaction.addToBackStack("tag");
                            transaction.commit();

                        }
                    };
                }
            }

        });







    }

    public void onBackPressed() {
        // do nothing
    }
}

所以,我需要从CameraSource获得摄像头(对吗?!)一旦不可能,我尝试使用GoogleSamples的git中的CameraSource类,它允许使用setFocusMode方法.但不幸的是我没有成功。

我也尝试使用API 21,因为API 22 不再支持摄像头和CameraPreferences。

我很确定这不仅是我的问题,而且找不到解决问题的办法。

有人能帮忙吗?

固定:

只需使用这个(github.com/googlesamples/android-vision/blob/master/visionSamples/barcode-reader/app/src/main/java/com/google/android/gms/samples/vision/barcodereader/ui/camera/CameraSource.java) CameraSource。是的,我知道,我建议过.但这次我解决了我的问题!因此,如果要使用这个,请确保您的编译如下所示:

代码语言:javascript
复制
compile 'com.google.android.gms:play-services:8.1.0'
EN

回答 3

Stack Overflow用户

发布于 2017-05-09 15:15:30

初始化它们并在OnCreate中定义它们

代码语言:javascript
复制
Camera.Parameters params;
Camera camera;
CameraSource cameraSource;
SurfaceView cameraView;
boolean isFlash = false;

调用changeFlashStatus()方法打开闪存,然后再调用它关闭闪存

代码语言:javascript
复制
public void changeFlashStatus() {
    Field[] declaredFields = CameraSource.class.getDeclaredFields();

    for (Field field : declaredFields) {
        if (field.getType() == Camera.class) {
            field.setAccessible(true);
            try {
                camera = (Camera) field.get(cameraSource);
                if (camera != null) {
                    params = camera.getParameters();
                    if (!isFlash) {
                        params.setFlashMode(Camera.Parameters.FLASH_MODE_TORCH);
                        flashImage.setColorFilter(getResources().getColor(R.color.yellow));
                        isFlash = true;
                    } else {
                        params.setFlashMode(Camera.Parameters.FLASH_MODE_OFF);
                        flashImage.setColorFilter(getResources().getColor(R.color.greyLight));
                        isFlash = false;
                    }
                    camera.setParameters(params);
                }

            } catch (IllegalAccessException e) {
                e.printStackTrace();
            }

            break;
        }
    }
}

要使相机聚焦,您需要一个特定的区域( Rect )将其传递给照相机,以便对该区域进行聚焦。因此,我们必须为surfaceView实现surfaceView,所以当我们触摸surfaceView时,我们创建了MotionEvent,它确定您准确地触摸了surfaceView的位置,然后我们可以从MotionEvent中提取Rect

在您的initCameraFocusListener()中调用OnCreate。在摄像机开拍后安全地打电话

代码语言:javascript
复制
private void initCameraFocusListener() {
    cameraView.setOnTouchListener(new View.OnTouchListener() {

        @Override
        public boolean onTouch(View v, MotionEvent event) {

            cameraFocus(event, cameraSource, Camera.Parameters.FOCUS_MODE_AUTO);

            return false;
        }
    });
}

private boolean cameraFocus(MotionEvent event, @NonNull CameraSource cameraSource, @NonNull String focusMode) {
    Field[] declaredFields = CameraSource.class.getDeclaredFields();

    int pointerId = event.getPointerId(0);
    int pointerIndex = event.findPointerIndex(pointerId);
    // Get the pointer's current position
    float x = event.getX(pointerIndex);
    float y = event.getY(pointerIndex);

    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));

    Rect focusArea = new Rect();

    focusArea.set(touchRect.left * 2000 / cameraView.getWidth() - 1000,
            touchRect.top * 2000 / cameraView.getHeight() - 1000,
            touchRect.right * 2000 / cameraView.getWidth() - 1000,
            touchRect.bottom * 2000 / cameraView.getHeight() - 1000);

    // Submit focus area to camera

    ArrayList<Camera.Area> focusAreas = new ArrayList<Camera.Area>();
    focusAreas.add(new Camera.Area(focusArea, 1000));

    for (Field field : declaredFields) {
        if (field.getType() == Camera.class) {
            field.setAccessible(true);
            try {
                camera = (Camera) field.get(cameraSource);
                if (camera != null) {
                    params = camera.getParameters();
                    params.setFocusMode(focusMode);
                    params.setFocusAreas(focusAreas);
                    camera.setParameters(params);

                    // Start the autofocus operation

                    camera.autoFocus(new Camera.AutoFocusCallback() {
                        @Override
                        public void onAutoFocus(boolean b, Camera camera) {
                            // currently set to auto-focus on single touch
                        }
                    });
                    return true;
                }

                return false;
            } catch (IllegalAccessException e) {
                e.printStackTrace();
            }

            break;
        }
    }
    return false;
}
票数 3
EN

Stack Overflow用户

发布于 2016-04-16 20:30:24

我使用这个库,它工作得很好,而且很容易实现。

https://github.com/dm77/barcodescanner

票数 0
EN

Stack Overflow用户

发布于 2016-04-16 20:40:09

答:Google示例:让CameraSource聚焦

要自动对焦,请在.setAutoFocusEnabled(true)上使用CameraSource.Builder()

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/36669064

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档