iOS पर, AutoML से ट्रेन किए गए मॉडल की मदद से इमेज को लेबल करना

AutoML Vision Edge का इस्तेमाल करके, अपना मॉडल ट्रेन करने के बाद, इसका इस्तेमाल अपने ऐप्लिकेशन में इमेज को लेबल करने के लिए किया जा सकता है.

AutoML Vision Edge से ट्रेन किए गए मॉडल को इंटिग्रेट करने के दो तरीके हैं. मॉडल की फ़ाइलों को अपने Xcode प्रोजेक्ट में कॉपी करके, मॉडल को बंडल किया जा सकता है. इसके अलावा, इसे Firebase से डाइनैमिक तरीके से डाउनलोड किया जा सकता है.

मॉडल बंडल करने के विकल्प
आपके ऐप्लिकेशन में बंडल किया गया मॉडल
  • मॉडल, बंडल का हिस्सा है
  • मॉडल तुरंत उपलब्ध हो जाता है. भले ही, iOS डिवाइस ऑफ़लाइन हो
  • इसके लिए, Firebase प्रोजेक्ट की ज़रूरत नहीं होती
Firebase पर होस्ट किया गया मॉडल
  • मॉडल को Firebase Machine Learning पर अपलोड करके होस्ट करें
  • इससे ऐप्लिकेशन बंडल का साइज़ कम हो जाता है
  • मॉडल, मांग पर डाउनलोड किया जाता है
  • अपने ऐप्लिकेशन को फिर से पब्लिश किए बिना, मॉडल के अपडेट पुश करें
  • Firebase रिमोट कॉन्फ़िगरेशन की मदद से, A/B टेस्टिंग आसानी से की जा सकती है
  • इसके लिए, Firebase प्रोजेक्ट की ज़रूरत होती है

इसे आज़माएं

शुरू करने से पहले

1. अपने Podfile में, ML Kit की लाइब्रेरी शामिल करें:

अपने ऐप्लिकेशन के साथ मॉडल बंडल करने के लिए:
    pod 'GoogleMLKit/ImageLabelingAutoML'
    
Firebase से डाइनैमिक तरीके से मॉडल डाउनलोड करने के लिए, LinkFirebase डिपेंडेंसी जोड़ें:
    pod 'GoogleMLKit/ImageLabelingAutoML'
    pod 'GoogleMLKit/LinkFirebase'
    
2. अपने प्रोजेक्ट के पॉड इंस्टॉल या अपडेट करने के बाद, अपने Xcode प्रोजेक्ट को उसके .xcworkspaceकोड> का इस्तेमाल करके खोलें. ML Kit, Xcode के 13.2.1 या इससे नए वर्शन के साथ काम करता है. 3. अगर आपको कोई मॉडल डाउनलोड करना है, तो पक्का करें कि आपने अपने iOS प्रोजेक्ट में Firebase जोड़ा हो. अगर आपने ऐसा नहीं किया है, तो Firebase जोड़ें. मॉडल बंडल करने पर, इसकी ज़रूरत नहीं होती.

1. मॉडल लोड करना

लोकल मॉडल सोर्स कॉन्फ़िगर करना

मॉडल को अपने ऐप्लिकेशन के साथ बंडल करने के लिए:

1. Firebase कंसोल से डाउनलोड किए गए zip संग्रह से, मॉडल और उसके मेटाडेटा को किसी फ़ोल्डर में एक्सट्रैक्ट करें:
    your_model_directory
      |____dict.txt
      |____manifest.json
      |____model.tflite
    
तीनों फ़ाइलें एक ही फ़ोल्डर में होनी चाहिए. हमारा सुझाव है कि फ़ाइलों को डाउनलोड करने के बाद, उनमें कोई बदलाव न करें. इनमें फ़ाइल के नाम भी शामिल हैं.

2. फ़ोल्डर को अपने Xcode प्रोजेक्ट में कॉपी करें. ऐसा करते समय, फ़ोल्डर रेफ़रंस बनाएं को चुनना न भूलें. मॉडल फ़ाइल और मेटाडेटा ऐप्लिकेशन बंडल में शामिल हो जाएगा और ML Kit के लिए उपलब्ध होगा.

3. AutoMLImageLabelerLocalModel ऑब्जेक्ट बनाएं. इसके लिए, मॉडल की मेनिफ़ेस्ट फ़ाइल का पाथ तय करें:

Swift

guard let manifestPath = Bundle.main.path(
    forResource: "manifest",
    ofType: "json",
    inDirectory: "your_model_directory"
) else { return }
let localModel = AutoMLImageLabelerLocalModel(manifestPath: manifestPath)

Objective-C

NSString *manifestPath =
    [NSBundle.mainBundle pathForResource:@"manifest"
                                  ofType:@"json"
                             inDirectory:@"your_model_directory"];
MLKAutoMLImageLabelerLocalModel *localModel =
    [[MLKAutoMLImageLabelerLocalModel alloc] initWithManifestPath:manifestPath];

Firebase पर होस्ट किए गए मॉडल का सोर्स कॉन्फ़िगर करना

रिमोट तरीके से होस्ट किए गए मॉडल का इस्तेमाल करने के लिए, AutoMLImageLabelerRemoteModel ऑब्जेक्ट बनाएं. इसके लिए, मॉडल को पब्लिश करते समय दिया गया नाम तय करें:

Swift

let remoteModel = AutoMLImageLabelerRemoteModel(
    name: "your_remote_model"  // The name you assigned in
                               // the Firebase console.
)

Objective-C

MLKAutoMLImageLabelerRemoteModel *remoteModel =
    [[MLKAutoMLImageLabelerRemoteModel alloc]
        initWithName:@"your_remote_model"];  // The name you assigned in
                                             // the Firebase console.

इसके बाद, मॉडल डाउनलोड करने का टास्क शुरू करें. इसके लिए, वे शर्तें तय करें जिनके तहत डाउनलोड करने की अनुमति देनी है. अगर मॉडल डिवाइस पर नहीं है या मॉडल का नया वर्शन उपलब्ध है, तो टास्क, Firebase से मॉडल को एसिंक्रोनस तरीके से डाउनलोड करेगा:

Swift

let downloadConditions = ModelDownloadConditions(
  allowsCellularAccess: true,
  allowsBackgroundDownloading: true
)

let downloadProgress = ModelManager.modelManager().download(
  remoteModel,
  conditions: downloadConditions
)

Objective-C

MLKModelDownloadConditions *downloadConditions =
    [[MLKModelDownloadConditions alloc] initWithAllowsCellularAccess:YES
                                         allowsBackgroundDownloading:YES];

NSProgress *downloadProgress =
    [[MLKModelManager modelManager] downloadModel:remoteModel
                                       conditions:downloadConditions];

कई ऐप्लिकेशन, डाउनलोड करने का टास्क अपने इनिशियलाइज़ेशन कोड में शुरू करते हैं. हालांकि, मॉडल का इस्तेमाल करने से पहले, किसी भी समय ऐसा किया जा सकता है.

अपने मॉडल से इमेज लेबलर बनाना

मॉडल के सोर्स कॉन्फ़िगर करने के बाद, इनमें से किसी एक से ImageLabeler ऑब्जेक्ट बनाएं.

अगर आपके पास सिर्फ़ लोकल तरीके से बंडल किया गया मॉडल है, तो सिर्फ़ अपने AutoMLImageLabelerLocalModel ऑब्जेक्ट से लेबलर बनाएं और कॉन्फ़िडेंस स्कोर की वह थ्रेशोल्ड कॉन्फ़िगर करें जिसकी आपको ज़रूरत है (अपना मोड देखें:

Swift

let options = AutoMLImageLabelerOptions(localModel: localModel)
options.confidenceThreshold = NSNumber(value: 0.0)  // Evaluate your model in the Firebase console
                                                    // to determine an appropriate value.
let imageLabeler = ImageLabeler.imageLabeler(options: options)

Objective-C

MLKAutoMLImageLabelerOptions *options =
    [[MLKAutoMLImageLabelerOptions alloc] initWithLocalModel:localModel];
options.confidenceThreshold = @(0.0);  // Evaluate your model in the Firebase console
                                       // to determine an appropriate value.
MLKImageLabeler *imageLabeler =
    [MLKImageLabeler imageLabelerWithOptions:options];

अगर आपके पास रिमोट तरीके से होस्ट किया गया मॉडल है, तो आपको इसे चलाने से पहले यह देखना होगा कि यह डाउनलोड हो गया है या नहीं. मॉडल मैनेजर के isModelDownloaded(remoteModel:) तरीके का इस्तेमाल करके, मॉडल डाउनलोड करने के टास्क की स्थिति देखी जा सकती है.

हालांकि, लेबलर चलाने से पहले आपको सिर्फ़ इसकी पुष्टि करनी होती है. अगर आपके पास रिमोट तरीके से होस्ट किया गया मॉडल और लोकल तरीके से बंडल किया गया मॉडल, दोनों हैं, तो ImageLabeler को इंस्टैंशिएट करते समय, इस जांच को करना सही हो सकता है: अगर रिमोट मॉडल डाउनलोड हो गया है, तो उससे लेबलर बनाएं. अगर ऐसा नहीं है, तो लोकल मॉडल से लेबलर बनाएं.

Swift

var options: AutoMLImageLabelerOptions!
if (ModelManager.modelManager().isModelDownloaded(remoteModel)) {
  options = AutoMLImageLabelerOptions(remoteModel: remoteModel)
} else {
  options = AutoMLImageLabelerOptions(localModel: localModel)
}
options.confidenceThreshold = NSNumber(value: 0.0)  // Evaluate your model in the Firebase console
                                                    // to determine an appropriate value.
let imageLabeler = ImageLabeler.imageLabeler(options: options)

Objective-C

MLKAutoMLImageLabelerOptions *options;
if ([[MLKModelManager modelManager] isModelDownloaded:remoteModel]) {
  options = [[MLKAutoMLImageLabelerOptions alloc] initWithRemoteModel:remoteModel];
} else {
  options = [[MLKAutoMLImageLabelerOptions alloc] initWithLocalModel:localModel];
}
options.confidenceThreshold = @(0.0);  // Evaluate your model in the Firebase console
                                       // to determine an appropriate value.
MLKImageLabeler *imageLabeler =
    [MLKImageLabeler imageLabelerWithOptions:options];

अगर आपके पास सिर्फ़ रिमोट तरीके से होस्ट किया गया मॉडल है, तो मॉडल से जुड़ी सुविधाओं को बंद कर दें. जैसे, यूज़र इंटरफ़ेस (यूआई) के किसी हिस्से को धुंधला कर दें या छिपा दें. ऐसा तब तक करें, जब तक आपको यह पुष्टि न हो जाए कि मॉडल डाउनलोड हो गया है.

डिफ़ॉल्ट सूचना केंद्र में ऑब्ज़र्वर जोड़कर, मॉडल डाउनलोड करने की स्थिति देखी जा सकती है. ऑब्ज़र्वर ब्लॉक में self के लिए, कमज़ोर रेफ़रंस का इस्तेमाल करना न भूलें. ऐसा इसलिए, क्योंकि डाउनलोड होने में कुछ समय लग सकता है. साथ ही, डाउनलोड पूरा होने तक, ओरिजनल ऑब्जेक्ट को रिलीज़ किया जा सकता है. उदाहरण के लिए:

Swift

NotificationCenter.default.addObserver(
    forName: .mlkitModelDownloadDidSucceed,
    object: nil,
    queue: nil
) { [weak self] notification in
    guard let strongSelf = self,
        let userInfo = notification.userInfo,
        let model = userInfo[ModelDownloadUserInfoKey.remoteModel.rawValue]
            as? RemoteModel,
        model.name == "your_remote_model"
        else { return }
    // The model was downloaded and is available on the device
}

NotificationCenter.default.addObserver(
    forName: .mlkitModelDownloadDidFail,
    object: nil,
    queue: nil
) { [weak self] notification in
    guard let strongSelf = self,
        let userInfo = notification.userInfo,
        let model = userInfo[ModelDownloadUserInfoKey.remoteModel.rawValue]
            as? RemoteModel
        else { return }
    let error = userInfo[ModelDownloadUserInfoKey.error.rawValue]
    // ...
}

Objective-C

__weak typeof(self) weakSelf = self;

[NSNotificationCenter.defaultCenter
    addObserverForName:MLKModelDownloadDidSucceedNotification
                object:nil
                 queue:nil
            usingBlock:^(NSNotification *_Nonnull note) {
              if (weakSelf == nil | note.userInfo == nil) {
                return;
              }
              __strong typeof(self) strongSelf = weakSelf;

              MLKRemoteModel *model = note.userInfo[MLKModelDownloadUserInfoKeyRemoteModel];
              if ([model.name isEqualToString:@"your_remote_model"]) {
                // The model was downloaded and is available on the device
              }
            }];

[NSNotificationCenter.defaultCenter
    addObserverForName:MLKModelDownloadDidFailNotification
                object:nil
                 queue:nil
            usingBlock:^(NSNotification *_Nonnull note) {
              if (weakSelf == nil | note.userInfo == nil) {
                return;
              }
              __strong typeof(self) strongSelf = weakSelf;

              NSError *error = note.userInfo[MLKModelDownloadUserInfoKeyError];
            }];

2. इनपुट इमेज तैयार करना

VisionImage ऑब्जेक्ट बनाने के लिए, UIImage या CMSampleBuffer का इस्तेमाल करें.

अगर UIImage का इस्तेमाल किया जाता है, तो यह तरीका अपनाएं:

  • VisionImage ऑब्जेक्ट, UIImage की मदद से बनाएं. पक्का करें कि .orientation सही हो.

    Swift

    let image = VisionImage(image: UIImage)
    visionImage.orientation = image.imageOrientation

    Objective-C

    MLKVisionImage *visionImage = [[MLKVisionImage alloc] initWithImage:image];
    visionImage.orientation = image.imageOrientation;

अगर CMSampleBuffer का इस्तेमाल किया जाता है, तो यह तरीका अपनाएं:

  • ` CMSampleBuffer` में मौजूद इमेज डेटा का ओरिएंटेशन तय करें.

    इमेज का ओरिएंटेशन पाने के लिए:

    Swift

    func imageOrientation(
      deviceOrientation: UIDeviceOrientation,
      cameraPosition: AVCaptureDevice.Position
    ) -> UIImage.Orientation {
      switch deviceOrientation {
      case .portrait:
        return cameraPosition == .front ? .leftMirrored : .right
      case .landscapeLeft:
        return cameraPosition == .front ? .downMirrored : .up
      case .portraitUpsideDown:
        return cameraPosition == .front ? .rightMirrored : .left
      case .landscapeRight:
        return cameraPosition == .front ? .upMirrored : .down
      case .faceDown, .faceUp, .unknown:
        return .up
      }
    }
          

    Objective-C

    - (UIImageOrientation)
      imageOrientationFromDeviceOrientation:(UIDeviceOrientation)deviceOrientation
                             cameraPosition:(AVCaptureDevicePosition)cameraPosition {
      switch (deviceOrientation) {
        case UIDeviceOrientationPortrait:
          return cameraPosition == AVCaptureDevicePositionFront ? UIImageOrientationLeftMirrored
                                                                : UIImageOrientationRight;
    
        case UIDeviceOrientationLandscapeLeft:
          return cameraPosition == AVCaptureDevicePositionFront ? UIImageOrientationDownMirrored
                                                                : UIImageOrientationUp;
        case UIDeviceOrientationPortraitUpsideDown:
          return cameraPosition == AVCaptureDevicePositionFront ? UIImageOrientationRightMirrored
                                                                : UIImageOrientationLeft;
        case UIDeviceOrientationLandscapeRight:
          return cameraPosition == AVCaptureDevicePositionFront ? UIImageOrientationUpMirrored
                                                                : UIImageOrientationDown;
        case UIDeviceOrientationUnknown:
        case UIDeviceOrientationFaceUp:
        case UIDeviceOrientationFaceDown:
          return UIImageOrientationUp;
      }
    }
          
  • VisionImage ऑब्जेक्ट और ओरिएंटेशन का इस्तेमाल करके, CMSampleBuffer ऑब्जेक्ट बनाएं:

    Swift

    let image = VisionImage(buffer: sampleBuffer)
    image.orientation = imageOrientation(
      deviceOrientation: UIDevice.current.orientation,
      cameraPosition: cameraPosition)

    Objective-C

     MLKVisionImage *image = [[MLKVisionImage alloc] initWithBuffer:sampleBuffer];
     image.orientation =
       [self imageOrientationFromDeviceOrientation:UIDevice.currentDevice.orientation
                                    cameraPosition:cameraPosition];

3. इमेज लेबलर चलाना

एसिंक्रोनस तरीके से:

Swift

imageLabeler.process(image) { labels, error in
    guard error == nil, let labels = labels, !labels.isEmpty else {
        // Handle the error.
        return
    }
    // Show results.
}

Objective-C

[imageLabeler
    processImage:image
      completion:^(NSArray *_Nullable labels,
                   NSError *_Nullable error) {
        if (labels.count == 0) {
            // Handle the error.
            return;
        }
        // Show results.
     }];

सिंक्रोनस तरीके से:

Swift

var labels: [ImageLabel]
do {
    labels = try imageLabeler.results(in: image)
} catch let error {
    // Handle the error.
    return
}
// Show results.

Objective-C

NSError *error;
NSArray *labels =
    [imageLabeler resultsInImage:image error:&error];
// Show results or handle the error.

4. लेबल किए गए ऑब्जेक्ट के बारे में जानकारी पाना

अगर इमेज लेबल करने की प्रोसेस पूरी हो जाती है, तो यह ImageLabel का कलेक्शन दिखाता है. हर ImageLabel, इमेज में लेबल की गई किसी चीज़ को दिखाता है. हर लेबल का टेक्स्ट ब्यौरा (अगर TensorFlow Lite मॉडल फ़ाइल के मेटाडेटा में उपलब्ध है), कॉन्फ़िडेंस स्कोर, और इंडेक्स पाया जा सकता है. उदाहरण के लिए:

Swift

for label in labels {
  let labelText = label.text
  let confidence = label.confidence
  let index = label.index
}

Objective-C

for (MLKImageLabel *label in labels) {
  NSString *labelText = label.text;
  float confidence = label.confidence;
  NSInteger index = label.index;
}

रीयल-टाइम परफ़ॉर्मेंस को बेहतर बनाने के लिए सलाह

अगर आपको रीयल-टाइम ऐप्लिकेशन में इमेज को लेबल करना है, तो सबसे अच्छे फ़्रेमरेट पाने के लिए, इन दिशा-निर्देशों का पालन करें:

  • वीडियो फ़्रेम प्रोसेस करने के लिए, डिटेक्टर के results(in:) सिंक्रोनस एपीआई का इस्तेमाल करें. दिए गए वीडियो फ़्रेम से नतीजे सिंक्रोनस तरीके से पाने के लिए, इस तरीके को AVCaptureVideoDataOutputSampleBufferDelegate's captureOutput(_, didOutput:from:) फ़ंक्शन से कॉल करें. डिटेक्टर को कॉल करने की संख्या कम करने के लिए, AVCaptureVideoDataOutput के alwaysDiscardsLateVideoFrames को true के तौर पर सेट करें. अगर डिटेक्टर के चलने के दौरान, वीडियो का कोई नया फ़्रेम उपलब्ध होता है, तो उसे छोड़ दिया जाएगा.
  • अगर इनपुट इमेज पर ग्राफ़िक्स ओवरले करने के लिए, डिटेक्टर के आउटपुट का इस्तेमाल किया जाता है, तो पहले ML Kit से नतीजा पाएं. इसके बाद, इमेज रेंडर करें और एक ही चरण में ओवरले करें. ऐसा करने से, प्रोसेस किए गए हर इनपुट फ़्रेम के लिए, डिसप्ले सर्फ़ेस पर सिर्फ़ एक बार रेंडर किया जाता है. उदाहरण के लिए, ML Kit के क्विकस्टार्ट सैंपल में updatePreviewOverlayViewWithLastFrame देखें.