/// <summary>
        /// https://codelabs.developers.google.com/codelabs/camerax-getting-started#3
        /// </summary>
        private void StartCamera()
        {
            var cameraProviderFuture = ProcessCameraProvider.GetInstance(this);

            cameraProviderFuture.AddListener(new Runnable(() =>
            {
                // Used to bind the lifecycle of cameras to the lifecycle owner
                var cameraProvider = (ProcessCameraProvider)cameraProviderFuture.Get();

                // Preview
                var preview = new Preview.Builder().Build();
                preview.SetSurfaceProvider(viewFinder.CreateSurfaceProvider());

                // Take Photo
                this.imageCapture = new ImageCapture.Builder().Build();

                // Frame by frame analyze
                var imageAnalyzer = new ImageAnalysis.Builder().Build();
                imageAnalyzer.SetAnalyzer(cameraExecutor, new LuminosityAnalyzer(luma =>
                                                                                 Log.Debug(TAG, $"Average luminosity: {luma}")
                                                                                 ));

                // Select back camera as a default, or front camera otherwise
                CameraSelector cameraSelector = null;
                if (cameraProvider.HasCamera(CameraSelector.DefaultBackCamera) == true)
                {
                    cameraSelector = CameraSelector.DefaultBackCamera;
                }
                else if (cameraProvider.HasCamera(CameraSelector.DefaultFrontCamera) == true)
                {
                    cameraSelector = CameraSelector.DefaultFrontCamera;
                }
                else
                {
                    throw new System.Exception("Camera not found");
                }

                try
                {
                    // Unbind use cases before rebinding
                    cameraProvider.UnbindAll();

                    // Bind use cases to camera
                    cameraProvider.BindToLifecycle(this, cameraSelector, preview, imageCapture, imageAnalyzer);
                }
                catch (Exception exc)
                {
                    Log.Debug(TAG, "Use case binding failed", exc);
                    Toast.MakeText(this, $"Use case binding failed: {exc.Message}", ToastLength.Short).Show();
                }
            }), ContextCompat.GetMainExecutor(this)); //GetMainExecutor: returns an Executor that runs on the main thread.
        }
Example #2
0
        // Declare and bind preview, capture and analysis use cases
        private void BindCameraUseCases()
        {
            // Get screen metrics used to setup camera for full screen resolution
            var metrics = new DisplayMetrics();

            viewFinder.Display.GetRealMetrics(metrics);
            Log.Debug(Tag, "Screen metrics: " + metrics);

            var screenAspectRatio = AspectRatio(metrics.WidthPixels, metrics.HeightPixels);

            Log.Debug(Tag, "Preview aspect ratio: " + screenAspectRatio);

            var rotation = viewFinder.Display.Rotation;

            // CameraProvider
            if (cameraProvider == null)
            {
                throw new Java.Lang.IllegalStateException("Camera initialization failed.");
            }

            // CameraSelector
            var cameraSelector = (new CameraSelector.Builder()).RequireLensFacing(lensFacing).Build();

            // Preview
            preview = new Preview.Builder()
                      // We request aspect ratio but no resolution
                      .SetTargetAspectRatio(screenAspectRatio)
                      // Set initial target rotation
                      .SetTargetRotation((int)rotation)
                      .Build();

            // ImageCapture
            imageCapture = new ImageCapture.Builder()
                           .SetCaptureMode(ImageCapture.CaptureModeMinimizeLatency)
                           // We request aspect ratio but no resolution to match preview config, but letting
                           // CameraX optimize for whatever specific resolution best fits our use cases
                           .SetTargetAspectRatio(screenAspectRatio)
                           // Set initial target rotation, we will have to call this again if rotation changes
                           // during the lifecycle of this use case
                           .SetTargetRotation((int)rotation)
                           .Build();

            // ImageAnalysis
            imageAnalyzer = new ImageAnalysis.Builder()
                            // We request aspect ratio but no resolution
                            .SetTargetAspectRatio(screenAspectRatio)
                            // Set initial target rotation, we will have to call this again if rotation changes
                            // during the lifecycle of this use case
                            .SetTargetRotation((int)rotation)
                            .Build();

            // The analyzer can then be assigned to the instance
            imageAnalyzer.SetAnalyzer(cameraExecutor, new LuminosityAnalyzer(
                                          (double luma) => {
                // Values returned from our analyzer are passed to the attached listener
                // We log image analysis results here - you should do something useful
                // instead!
                Log.Debug(Tag, "Average luminosity: " + luma);
            })
                                      );

            // Must unbind the use-cases before rebinding them
            cameraProvider.UnbindAll();

            try
            {
                // A variable number of use-cases can be passed here -
                // camera provides access to CameraControl & CameraInfo
                camera = cameraProvider.BindToLifecycle(
                    (ILifecycleOwner)this, cameraSelector, preview, imageCapture, imageAnalyzer);

                // Attach the viewfinder's surface provider to preview use case
                preview?.SetSurfaceProvider(viewFinder.CreateSurfaceProvider());
            }
            catch (Java.Lang.Exception exc)
            {
                Log.Error(Tag, "Use case binding failed: " + exc);
            }
        }