2017-03-23 1 views
0

Je suis un peu novice et essaie de construire une application basée sur https://inducesmile.com/android/android-camera2-api-example-tutorial/ pour aider un individu difficile à voir. J'ai besoin d'utiliser un contrôleur de jeu Bluetooth pour contrôler le niveau de zoom en temps réel - quand un bouton est pressé, le niveau de zoom change. J'ai enlevé le bouton "Prendre l'image" et la bannière supérieure pour que je puisse utiliser le plein écran. J'ai essayé de changer le niveau de zoom dans différentes méthodes: createCameraPreview, updatePreview et dispatchKeyEvent mais ça ne marche pas. Où devrais-je appliquer le nouveau captureRequestBuilder avec le zoom Rect mis à jour? Merci.Zoom en temps réel Camera2

+import ... 

public class AndroidCameraApi extends AppCompatActivity { 
    private static final String TAG = "AndroidCameraApi"; 
    private TextureView textureView; 
    private static final SparseIntArray ORIENTATIONS = new SparseIntArray(); 
    static { 
     ORIENTATIONS.append(Surface.ROTATION_0, 90); 
     ORIENTATIONS.append(Surface.ROTATION_90, 0); 
     ORIENTATIONS.append(Surface.ROTATION_180, 270); 
     ORIENTATIONS.append(Surface.ROTATION_270, 180); 
    } 
    private String cameraId; 
    protected CameraDevice cameraDevice; 
    protected CameraCaptureSession cameraCaptureSessions; 
    protected CaptureRequest captureRequest; 
    protected CaptureRequest.Builder captureRequestBuilder; 
    private Size imageDimension; 
    private ImageReader imageReader; 
    private File file; 
    private static final int REQUEST_CAMERA_PERMISSION = 200; 
    private boolean mFlashSupported; 
    private Handler mBackgroundHandler; 
    private HandlerThread mBackgroundThread; 

    private int kc; //kc is keyCode from bluetooth controller 
    Rect zoomCropPreview = new Rect(1094, 822, 2186, 1642); //zoomed in 
    //Rect zoomCropPreview = new Rect(0,0,4032,3024); //full screen 

    @Override 
    protected void onCreate(Bundle savedInstanceState) {    //onCreate set up layout, texture, take pciture button 
     super.onCreate(savedInstanceState); 
     //this.requestWindowFeature(Window.FEATURE_NO_TITLE); //remove title bar 
     this.getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN); //remove notification mar 
     setContentView(R.layout.activity_android_camera_api); 
     textureView = (TextureView) findViewById(R.id.texture); //set up texture 
     assert textureView != null; 
     textureView.setSurfaceTextureListener(textureListener); 
    } 

    TextureView.SurfaceTextureListener textureListener = new TextureView.SurfaceTextureListener() { 
     @Override 
     public void onSurfaceTextureAvailable(SurfaceTexture surface, int width, int height) { 
      //open your camera here 
      openCamera(); 
     } 
    }; 

    private void openCamera() { 
     CameraManager manager = (CameraManager) getSystemService(Context.CAMERA_SERVICE); 
     Log.e(TAG, "is camera open"); 
     try { 
      cameraId = manager.getCameraIdList()[0]; 
      CameraCharacteristics characteristics = manager.getCameraCharacteristics(cameraId); 
      Float maxDigitalZoom = characteristics.get(CameraCharacteristics.SCALER_AVAILABLE_MAX_DIGITAL_ZOOM); //get maximum digital zoom (=8) 
      Rect asd = characteristics.get(CameraCharacteristics.SENSOR_INFO_ACTIVE_ARRAY_SIZE); 
      StreamConfigurationMap map = characteristics.get(CameraCharacteristics.SCALER_STREAM_CONFIGURATION_MAP); 
      assert map != null; 
      imageDimension = map.getOutputSizes(SurfaceTexture.class)[0]; 
      // Add permission for camera and let user grant the permission 
      if (ActivityCompat.checkSelfPermission(this, Manifest.permission.CAMERA) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) { 
       ActivityCompat.requestPermissions(AndroidCameraApi.this, new String[]{Manifest.permission.CAMERA, Manifest.permission.WRITE_EXTERNAL_STORAGE}, REQUEST_CAMERA_PERMISSION); 
       return; 
      } 
      manager.openCamera(cameraId, stateCallback, null); 
     } catch (CameraAccessException e) { 
      e.printStackTrace(); 
     } 
     Log.e(TAG, "openCamera X"); 
    } 

    private final CameraDevice.StateCallback stateCallback = new CameraDevice.StateCallback() { 
     @Override 
     public void onOpened(CameraDevice camera) { 
      //This is called when the camera is open 
      Log.e(TAG, "onOpened"); 
      cameraDevice = camera; 
      createCameraPreview(); 
     } 

     @Override 
     public void onDisconnected(CameraDevice camera) { 
      cameraDevice.close(); 
     } 

     @Override 
     public void onError(CameraDevice camera, int error) { 
      cameraDevice.close(); 
      cameraDevice = null; 
     } 
    }; 

    protected void createCameraPreview() { 
     try { 
      SurfaceTexture texture = textureView.getSurfaceTexture(); 
      assert texture != null; 
      texture.setDefaultBufferSize(imageDimension.getWidth(), imageDimension.getHeight()); 
      Surface surface = new Surface(texture); 
      captureRequestBuilder = cameraDevice.createCaptureRequest(CameraDevice.TEMPLATE_PREVIEW); 
      captureRequestBuilder.addTarget(surface); 
      //try to change zoom- didn't work 
      //captureRequestBuilder.set(CaptureRequest.SCALER_CROP_REGION, zoomCropPreview); 
      cameraDevice.createCaptureSession(Arrays.asList(surface), new CameraCaptureSession.StateCallback() { 
       @Override 
       public void onConfigured(@NonNull CameraCaptureSession cameraCaptureSession) { 
        //The camera is already closed 
        if (null == cameraDevice) { 
         return; 
        } 
        // When the session is ready, we start displaying the preview. 
        //try to change zoom here- didn't work 
        //captureRequestBuilder.set(CaptureRequest.SCALER_CROP_REGION, zoomCropPreview); 
        cameraCaptureSessions = cameraCaptureSession; 
        updatePreview();     //update preview screen 
       } 

       @Override 
       public void onConfigureFailed(@NonNull CameraCaptureSession cameraCaptureSession) { 
        Toast.makeText(AndroidCameraApi.this, "Configuration change", Toast.LENGTH_SHORT).show(); 
       } 
      }, null); 
     } catch (CameraAccessException e) { 
      e.printStackTrace(); 
     } 
    } 

    protected void updatePreview() { 
     if (null == cameraDevice) { 
      Log.e(TAG, "updatePreview error, return"); 
     } 
// Original 
     //captureRequestBuilder.set(CaptureRequest.CONTROL_MODE, CameraMetadata.CONTROL_MODE_AUTO); 
//Modified 
     captureRequestBuilder.set(CaptureRequest.SCALER_CROP_REGION, zoomCropPreview); 
     try { 
      cameraCaptureSessions.setRepeatingRequest(captureRequestBuilder.build(), null, mBackgroundHandler); 
     } catch (CameraAccessException e) { 
      e.printStackTrace(); 
     } 
    } 

//******************************** 
// Change zoom based on Bluetooth controller 
//******************************** 
    @Override 
    public boolean dispatchKeyEvent(KeyEvent event) { 
     kc = event.getKeyCode(); 
     Log.i("key pressed", String.valueOf(kc)); 
//as a test, just change from zoomed in to full screen 
     zoomCropPreview.set(0,0,4032,3024);  //change to full screen 
     Log.i("zoomCropPreview", (zoomCropPreview).flattenToString()); 
     //try to change zoom- didn't work 
     captureRequestBuilder.set(CaptureRequest.SCALER_CROP_REGION, zoomCropPreview); 
     return super.dispatchKeyEvent(event); 
    } 

    final CameraCaptureSession.CaptureCallback captureCallbackListener = new CameraCaptureSession.CaptureCallback() { 
     @Override 
     public void onCaptureCompleted(CameraCaptureSession session, CaptureRequest request, TotalCaptureResult result) { 
      super.onCaptureCompleted(session, request, result); 
      Toast.makeText(AndroidCameraApi.this, "Saved:" + file, Toast.LENGTH_SHORT).show(); 
      createCameraPreview(); 
     } 
    }; 

    protected void startBackgroundThread() { 
     mBackgroundThread = new HandlerThread("Camera Background"); 
     mBackgroundThread.start(); 
     mBackgroundHandler = new Handler(mBackgroundThread.getLooper()); 
    } 

    protected void stopBackgroundThread() { 
     mBackgroundThread.quitSafely(); 
     try { 
      mBackgroundThread.join(); 
      mBackgroundThread = null; 
      mBackgroundHandler = null; 
     } catch (InterruptedException e) { 
      e.printStackTrace(); 
     } 
    } 

    private void closeCamera() { 
     if (null != cameraDevice) { 
      cameraDevice.close(); 
      cameraDevice = null; 
     } 
     if (null != imageReader) { 
      imageReader.close(); 
      imageReader = null; 
     } 
    } 

    @Override 
    public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) { 
     if (requestCode == REQUEST_CAMERA_PERMISSION) { 
      if (grantResults[0] == PackageManager.PERMISSION_DENIED) { 
       // close the app 
       Toast.makeText(AndroidCameraApi.this, "Sorry!!!, you can't use this app without granting permission", Toast.LENGTH_LONG).show(); 
       finish(); 
      } 
     } 
    } 

    @Override 
    protected void onResume() { 
     super.onResume(); 
     Log.e(TAG, "onResume"); 
     startBackgroundThread(); 
     if (textureView.isAvailable()) { 
      openCamera(); 
     } else { 
      textureView.setSurfaceTextureListener(textureListener); 
     } 
    } 

    @Override 
    protected void onPause() { 
     Log.e(TAG, "onPause"); 
     //closeCamera(); 
     stopBackgroundThread(); 
     super.onPause(); 
    } 
}  

Répondre

0

Vous devez appeler cameraCaptureSessions.setRepeatingRequest à nouveau une fois que vous avez mis à jour tous les paramètres de captureRequestBuilder.

La simple mise à jour du constructeur ne fait rien, elle modifie simplement un ensemble de paramètres. Vous devez indiquer à la caméra d'utiliser réellement le nouveau bundle pour que tout se passe.