Xamarin.forms iOS take image using camera natively

In my xamarin.forms app, I implemented overlay for native camera.

enter image description here

What I am trying to do is take image and check whether the image contains

  • Single face, multiple face and no face.

I implemented this successfully on android after a long period of time.For face detection I used Camera.IFaceDetectionListener. Currently I am stuck on iOS part.
In iOS I can currently open camera in my custom preview. But I don’t know how to take photo. and also like android is there any method for checking faces in IOS?

Created a custom view for camera in Shared folder

public  class CameraPreview : View
    {
        public static readonly BindableProperty CameraProperty = BindableProperty.Create(
          propertyName: "Camera",
          returnType: typeof(CameraOptions),
          declaringType: typeof(CameraPreview),
          defaultValue: CameraOptions.Front);

        public CameraOptions Camera
        {
            get { return (CameraOptions)GetValue(CameraProperty); }
            set { SetValue(CameraProperty, value); }
        }
        public CameraPreview()
        {

        }
    }

Camera Page.xaml

 <Grid x:Name="CameraGrid">
   <local1:CameraPreview  x:Name="CameraPreview"  HorizontalOptions="FillAndExpand" VerticalOptions="FillAndExpand" Camera="Front"/>
        </Grid>

I am using MessegingCenter for capturing image from shared page

MessagingCenter.Send<Camera_Popup>(this, "CaptureClick");

My CameraPreviewRenderer in iOS

 public class CameraPreviewRenderer : ViewRenderer<CameraPreview, UICameraPreview>, IAVCaptureMetadataOutputObjectsDelegate
  {
    UICameraPreview uiCameraPreview;

    public AVCaptureSession CaptureSession { get; private set; }

    public AVCaptureStillImageOutput CaptureOutput { get; set; }

    public bool IsPreviewing { get; set; }
    protected override void OnElementChanged(ElementChangedEventArgs<CameraPreview> e)
    {
      base.OnElementChanged(e);

      if (e.OldElement != null)
      {
        // Unsubscribe
        uiCameraPreview.Tapped -= OnCameraPreviewTapped;
      }
      if (e.NewElement != null)
      {
        if (Control == null)
        {
          uiCameraPreview = new UICameraPreview(e.NewElement.Camera);
          SetNativeControl(uiCameraPreview);
          MessagingCenter.Subscribe<Camera_Popup>(this, "CaptureClick", async (sender) =>
          {
            try
            {

              var data = new AVCaptureMetadataOutputObjectsDelegate();
              await Task.Run(() => takephoto());
            }
            catch (Exception ex)
            {
              return;
            }

          });
        }
        MessagingCenter.Subscribe<Camera_Popup>(this, "RetryClick", (sender) =>
        {
          Device.BeginInvokeOnMainThread(() =>
          {
            uiCameraPreview.CaptureSession.StartRunning();
            uiCameraPreview.IsPreviewing = true;
          });
        });
        MessagingCenter.Subscribe<Camera_Popup>(this, "FlipClick", (sender) =>
        {
          try
          {
            var devicePosition = uiCameraPreview.captureDeviceInput.Device.Position;
            if (devicePosition == AVCaptureDevicePosition.Front)
            {
              devicePosition = AVCaptureDevicePosition.Back;
            }
            else
            {
              devicePosition = AVCaptureDevicePosition.Front;
            }
            uiCameraPreview.device = uiCameraPreview.videoDevices.FirstOrDefault(d => d.Position == devicePosition);
            uiCameraPreview.CaptureSession.BeginConfiguration();
            uiCameraPreview.CaptureSession.RemoveInput(uiCameraPreview.captureDeviceInput);
            uiCameraPreview.captureDeviceInput = AVCaptureDeviceInput.FromDevice(uiCameraPreview.device);
            uiCameraPreview.CaptureSession.AddInput(uiCameraPreview.captureDeviceInput);
            uiCameraPreview.CaptureSession.CommitConfiguration();

          }
          catch (Exception ex)
          {
            var abc = ex.InnerException.Message;
          }

        });
        uiCameraPreview.Tapped += OnCameraPreviewTapped;
      }
    }
   
    public async Task takephoto()
    {
       try
     {
        // How to take photo and preview?

      }
      catch(Exception ex)
            {

            }
        }

     
    void OnCameraPreviewTapped(object sender, EventArgs e)
    {
      if (uiCameraPreview.IsPreviewing)
      {
        uiCameraPreview.CaptureSession.StopRunning();
        uiCameraPreview.IsPreviewing = false;
      }
      else
      {
        uiCameraPreview.CaptureSession.StartRunning();
        uiCameraPreview.IsPreviewing = true;
      }
    }

    protected override void Dispose(bool disposing)
    {
      if (disposing)
      {
        Control.CaptureSession.Dispose();
        Control.Dispose();
      }
      base.Dispose(disposing);
    }
  }

My UICameraPreview

public class UICameraPreview : UIView
    {
        AVCaptureVideoPreviewLayer previewLayer;
        public AVCaptureDevice[] videoDevices;
        CameraOptions cameraOptions;
        public AVCaptureStillImageOutput stillImageOutput;
        public AVCaptureDeviceInput captureDeviceInput;
        public AVCaptureDevice device;

        public event EventHandler<EventArgs> Tapped;

        public AVCaptureSession CaptureSession { get; set; }

        public bool IsPreviewing { get; set; }

        public UICameraPreview(CameraOptions options)
        {
            cameraOptions = options;
            IsPreviewing = false;
            Initialize();
        }

        public override void LayoutSubviews()
        {
            base.LayoutSubviews();

            if (previewLayer != null)
                previewLayer.Frame = Bounds;
        }

        public override void TouchesBegan(NSSet touches, UIEvent evt)
        {
            base.TouchesBegan(touches, evt);
            OnTapped();
        }

        protected virtual void OnTapped()
        {
            var eventHandler = Tapped;
            if (eventHandler != null)
            {
                eventHandler(this, new EventArgs());
            }
        }

        void Initialize()
        {
            CaptureSession = new AVCaptureSession();
            previewLayer = new AVCaptureVideoPreviewLayer(CaptureSession)
            {
                Frame = Bounds,
                VideoGravity = AVLayerVideoGravity.ResizeAspectFill
            };

            videoDevices = AVCaptureDevice.DevicesWithMediaType(AVMediaType.Video);
            var cameraPosition = (cameraOptions == CameraOptions.Front) ? AVCaptureDevicePosition.Front : AVCaptureDevicePosition.Back;
            device = videoDevices.FirstOrDefault(d => d.Position == cameraPosition);

            if (device == null)
            {
                return;
            }

            NSError error;
            captureDeviceInput = new AVCaptureDeviceInput(device, out error);
            CaptureSession.AddInput(captureDeviceInput);

            var dictionary = new NSMutableDictionary();
            dictionary[AVVideo.CodecKey] = new NSNumber((int)AVVideoCodec.JPEG);
            stillImageOutput = new AVCaptureStillImageOutput()
            {
                OutputSettings = new NSDictionary()
            };
            CaptureSession.AddOutput(stillImageOutput);
            Layer.AddSublayer(previewLayer);
            CaptureSession.StartRunning();
            IsPreviewing = true;
        }
    }

How can I take image and preview it? Is there any method available for checking face available or not?
Any help is really appreciated.

Source: Xamarin.ios Questions