This document covers the steps you need to take to migrate your projects from
Google Mobile Vision (GMV) to ML Kit on iOS.

## Prerequisites

Before you start to migrate your code, be sure you meet these requirements:

- ML Kit supports Xcode 13.2.1 or later.
- ML Kit supports iOS version 15.5 or greater.
- ML Kit doesn't support 32-bit architectures (i386 and armv7). ML Kit does support 64-bit architectures (x86_64 and arm64).

## Update cocoapods

Update the dependencies for the ML Kit iOS cocoapods in your app's Podfile:

| API | GMV Pod | ML Kit Pod |
|---|---|---|
| Barcode scanning | `GoogleMobileVision/BarcodeDetector` | `GoogleMLKit/BarcodeScanning` |
| Face detection | `GoogleMobileVision/FaceDetector` | `GoogleMLKit/FaceDetection` |
| Text recognition | `GoogleMobileVision/TextDetector` | `GoogleMLKit/TextRecognition` |

## Overall API changes

These changes apply to all APIs:

- GMV's inference APIs take [`UIImage`](https://developer.apple.com/documentation/uikit/uiimage?language=objc) or [`CMSampleBufferRef`](https://developer.apple.com/documentation/coremedia/cmsamplebufferref?language=objc) as input. ML Kit wraps them inside an [`MLKVisionImage`](https://developers.google.com/ml-kit/reference/ios/mlkitvision/api/reference/Classes/MLKVisionImage.md.txt) and takes that as input.
- GMV uses [`NSDictionary`](https://developer.apple.com/documentation/foundation/nsdictionary?language=objc) to pass various detector options. ML Kit uses dedicated options classes for that purpose.
- GMV passes the detector type to the single [`GMVDetector`](https://developers.google.com/vision/ios/reference/interface_g_m_v_detector#a5dc29327e330df657df947033b97a50b) class when it creats a detector. ML Kit uses dedicated classes to create separate detector, scanner, and recognizer instances.
- GMV's APIs support synchronous detection only. ML Kit's inference APIs can be called synchronously and asynchronously.
- GMV extends [`AVCaptureVideoDataOutput`](https://developer.apple.com/documentation/avfoundation/avcapturevideodataoutput?language=objc) and provides a [multi-detector framework](https://developers.google.com/vision/ios/reference/interface_g_m_v_multi_data_output) for performing multiple detections at the same time. ML Kit doesn't provide such mechanisms, but the same functionality can be implemented by the developer if desired.

## API-specific changes

This section describes corresponding GMV and ML Kit classes and methods for each Vision API, and shows how to initialize the API.

### FaceDetector

Recode the initialization as shown in this example:

### GMV

```objective-c
NSDictionary *options = @{
    GMVDetectorFaceMode : @(GMVDetectorFaceAccurateMode),
    GMVDetectorFaceClassificationType : @(GMVDetectorFaceClassificationAll),
    GMVDetectorFaceLandmarkType : @(GMVDetectorFaceLandmarkAll)
};
GMVDetector *faceDetector =
    [GMVDetector detectorOfType:GMVDetectorTypeFace options:options];
```

### ML Kit

```objective-c
MLKFaceDetectorOptions *options = [[MLKFaceDetectorOptions alloc] init];
options.performanceMode = MLKFaceDetectorPerformanceModeAccurate;
options.classificationMode = MLKFaceDetectorClassificationModeAll;
options.landmarkMode = MLKFaceDetectorLandmarkModeAll;
MLKFaceDetector *faceDetector = [MLKFaceDetector faceDetectorWithOptions:options];
```

[`GMVDetector`](https://developers.google.com/vision/ios/reference/interface_g_m_v_detector) has two
different detection APIs. Both are synchronous operations:

```objective-c
- (nullable NSArray<__kindof GMVFeature *> *)
    featuresInImage:(UIImage *)image
            options:(nullable NSDictionary *)options;

- (nullable NSArray<__kindof GMVFeature *> *)
    featuresInBuffer:(CMSampleBufferRef)sampleBuffer
             options:(nullable NSDictionary *)options;
```

Replace [`GMVDetector`](https://developers.google.com/vision/ios/reference/interface_g_m_v_detector) with [`MLKFaceDetector`](https://developers.google.com/ml-kit/reference/ios/mlkitfacedetection/api/reference/Classes/MLKFaceDetector.md.txt).
The inference API can be called synchronously or asynchronously.

### Synchronous

```objective-c
- (nullable NSArray<MLKFace *> *)
    resultsInImage:(MLKVisionImage *)image
             error:(NSError **)error;
```

### Asynchronous

```objective-c
- (void)processImage:(MLKVisionImage *)image
    Completion:
        (MLKFaceDetectionCallback)completion
    NS_SWIFT_NAME(process(_:completion:));
```

Change the following classes, methods, and names:

| GMV | ML Kit |
|---|---|
| `GMVFaceFeature` | `MLKFace` |
| `GMVFaceContour` | `MLKFaceContour` |
| `GMVDetectorImageOrientation` | `MLKVisionImage.orientation` |
| `NSDictionary` of face detection options | `MLKFaceDetectorOptions` |
| `GMVDetectorFaceFastMode` | `Set MLKFaceDetectorOptions.performanceMode to MLKFaceDetectorPerformanceModeFast` |
| `GMVDetectorFaceAccurateMode` | `Set MLKFaceDetectorOptions.performanceMode to MLKFaceDetectorPerformanceModeAccurate` |
| `GMVDetectorFaceSelfieMode` | `Set MLKFaceDetectorOptions.contourMode to MLKFaceDetectorContourModeAll` |
| `GMVDetectorFaceLandmarkType` | `MLKFaceDetectorOptions.landmarkMode` |
| `GMVDetectorFaceLandmarkNone` | `Set MLKFaceDetectorOptions.landmarkMode to MLKFaceDetectorLandmarkModeNone` |
| `GMVDetectorFaceLandmarkAll` | `Set MLKFaceDetectorOptions.landmarkMode to MLKFaceDetectorLandmarkModeAll` |
| `GMVDetectorFaceLandmarkContour` | `Set MLKFaceDetectorOptions.contourMode to MLKFaceDetectorContourModeAll` |
| `GMVDetectorFaceClassificationType` | `MLKFaceDetectorOptions.classificationMode` |
| `GMVDetectorFaceClassificationNone` | `Set MLKFaceDetectorOptions.classificationMode to MLKFaceDetectorClassificationModeNone` |
| `GMVDetectorFaceClassificationAll` | `Set MLKFaceDetectorOptions.classificationMode to MLKFaceDetectorClassificationModeAll` |
| `GMVDetectorFaceTrackingEnabled` | `MLKFaceDetectorOptions.trackingEnabled` |
| `GMVDetectorProminentFaceOnly` | `Set MLKFaceDetectorOptions.contourMode to MLKFaceDetectorContourModeAll` |
| `GMVDetectorFaceMinSize` | `MLKFaceDetectorOptions.minFaceSize` |

### BarcodeDetector

Recode the initialization as shown in this example:

### GMV

```objective-c
NSDictionary *options = @{
    GMVDetectorBarcodeFormats : @(GMVDetectorBarcodeFormatCode128 |
                                  GMVDetectorBarcodeFormatQRCode)
};
GMVDetector *barcodeDetector =
    [GMVDetector detectorOfType:GMVDetectorTypeBarcode options:options];
```

### ML Kit

```objective-c
MLKBarcodeScannerOptions *options = [[MLKBarcodeScannerOptions alloc] init];
options.formats = MLKBarcodeFormatCode128 | MLKBarcodeFormatQRCode;
MLKBarcodeScanner *barcodeScanner =
    [MLKBarcodeScanner barcodeScannerWithOptions:options];
```

[`GMVDetector`](https://developers.google.com/vision/ios/reference/interface_g_m_v_detector) has two different detection APIs. Both are synchronous operations:

```objective-c
- (nullable NSArray<__kindof GMVFeature *> *)
    featuresInImage:(UIImage *)image
            options:(nullable NSDictionary *)options;

- (nullable NSArray<__kindof GMVFeature *> *)
    featuresInBuffer:(CMSampleBufferRef)sampleBuffer
             options:(nullable NSDictionary *)options;
```

Replace [`GMVDetector`](https://developers.google.com/vision/ios/reference/interface_g_m_v_detector) with
[`MLKBarcodeScanner`](https://developers.google.com/ml-kit/reference/ios/mlkitbarcodescanning/api/reference/Classes/MLKBarcodeScanner.md.txt).
The inference API can be called synchronously or asynchronously.

### Synchronous

```objective-c
- (nullable NSArray<MLKBarcode *> *)
    resultsInImage:(MLKVisionImage *)image
             error:(NSError **)error;
```

### Asynchronous

```objective-c
- (void)processImage:(MLKVisionImage *)image
    Completion:
        (MLKBarcodeScanningCallback)completion
    NS_SWIFT_NAME(process(_:completion:));
```

Change the following classes, methods, and names:

| GMV | ML Kit |
|---|---|
| `GMVDetectorImageOrientation` | `MLKVisionImage.orientation` |
| `NSDictionary` of barcode detector options | `MLKBarcodeScannerOptions` |
| `GMVDetectorBarcodeFormats` | `MLKBarcodeScannerOptions.formats` |
| `GMVBarcodeFeature` | `MLKBarcode` |
| `GMVBarcodeFeatureAddress` | `MLKBarcodeAddress` |
| `GMVBarcodeFeatureCalendarEvent` | `MLKBarcodeCalendarEvent` |
| `GMVBarcodeFeatureContactInfo` | `MLKBarcodeContactInfo` |
| `GMVBarcodeFeatureDriverLicense` | `MLKBarcodeDriverLicense` |
| `GMVBarcodeFeatureEmail` | `MLKBarcodeEmail` |
| `GMVBarcodeFeatureGeoPoint` | `MLKBarcodeGeoPoint` |
| `GMVBarcodeFeaturePersonName` | `MLKBarcodePersonName` |
| `GMVBarcodeFeaturePhone` | `MLKBarcodePhone` |
| `GMVBarcodeFeatureSMS` | `MLKBarcodeSMS` |
| `GMVBarcodeFeatureURLBookmark` | `MLKBarcodeURLBookmark` |
| `GMVBarcodeFeatureWiFi` | `MLKBarcodeWiFi` |

### TextRecognition

Recode the initialization as shown in this example:

### GMV

```objective-c
GMVDetector *textDetector =
    [GMVDetector detectorOfType:GMVDetectorTypeText options:nil];
```

### ML Kit

```objective-c
MLKTextRecognizer *textRecognizer = [MLKTextRecognizer textRecognizer];
```

[`GMVDetector`](https://developers.google.com/vision/ios/reference/interface_g_m_v_detector) has two
different detection APIs. Both are synchronous operations:

```objective-c
- (nullable NSArray<__kindof GMVFeature *> *)
    featuresInImage:(UIImage *)image
            options:(nullable NSDictionary *)options;

- (nullable NSArray<__kindof GMVFeature *> *)
    featuresInBuffer:(CMSampleBufferRef)sampleBuffer
             options:(nullable NSDictionary *)options;
```

Replace [`GMVDetector`](https://developers.google.com/vision/ios/reference/interface_g_m_v_detector) with
[`MLKTextRecognizer`](https://developers.google.com/ml-kit/reference/ios/mlkittextrecognition/api/reference/Classes/MLKTextRecognizer).
The inference API can be called synchronously or asynchronously.

### Synchronous

```objective-c
- (nullable MLKText *)
    resultsInImage:(MLKVisionImage *)image
             error:(NSError **)error;
```

### Asynchronous

```objective-c
- (void)processImage:(MLKVisionImage *)image
    Completion:
        (MLKTextRecognitionCallback)completion
    NS_SWIFT_NAME(process(_:completion:));
```

Change the following classes, methods, and names:

| GMV | ML Kit |
|---|---|
| `GMVDetectorImageOrientation` | `MLKVisionImage.orientation` |
| `GMVTextBlockFeature` | `MLKTextBlock` |
| `GMVTextElementFeature` | `MLKTextElement` |
| `GMVTextLineFeature` | `MLKTextLine` |

## Getting help

If you run into any issues, check out our [Community page](https://developers.google.com/ml-kit/community)
where we outline the channels available for getting in touch with us.