Apple platformlarında AutoML tarafından eğitilmiş bir modelle görüntüleri etiketleyin.

AutoML Vision Edge'i kullanarak kendi modelinizi eğittikten sonra bu modeli uygulamanızda görüntüleri etiketlemek için kullanabilirsiniz.

AutoML Vision Edge'den eğitilen modelleri iki şekilde entegre edebilirsiniz. Modelin dosyalarını Xcode projenize kopyalayarak modeli gruplandırabilir veya Firebase'den dinamik olarak indirebilirsiniz.

Model paketleme seçenekleri
Uygulamanızda paket olarak sunuluyor
  • Model, paketin bir parçasıdır
  • Model, Apple cihaz çevrimdışı olsa bile hemen kullanılabilir
  • Firebase projesine gerek yoktur
Firebase ile barındırılan
  • Modeli Firebase Makine Öğrenimi'ne yükleyerek barındırın
  • Uygulama paketi boyutunu küçültür
  • Model istek üzerine indirilir
  • Uygulamanızı yeniden yayınlamadan model güncellemelerini aktarma
  • Firebase Remote Config ile kolay A/B testi
  • Firebase projesi gerekir

Başlamadan önce

  1. ML Kit kitaplıklarını Podfile'ınıza ekleyin:

    Bir modeli uygulamanızla gruplandırmak için:

    pod 'GoogleMLKit/ImageLabelingCustom'
    

    Firebase'den dinamik olarak model indirmek için LinkFirebase bağımlılığını ekleyin:

    pod 'GoogleMLKit/ImageLabelingCustom'
    pod 'GoogleMLKit/LinkFirebase'
    
  2. Projenizin kapsüllerini yükledikten veya güncelledikten sonra .xcworkspace kullanarak Xcode projenizi açın. ML Kit, Xcode 12.2 veya sonraki sürümlerde desteklenir.

  3. Model indirmek istiyorsanız henüz yapmadıysanız Firebase'i Android projenize eklediğinizden emin olun. Modeli paket haline getirirken bu işlem gerekli değildir.

1. Modeli yükleme

Yerel model kaynağını yapılandırma

Modeli uygulamanızla paket haline getirmek için:

  1. Modeli ve meta verilerini Firebase konsolundan indirdiğiniz zip arşivinden bir klasöre çıkarın:

    your_model_directory
      |____dict.txt
      |____manifest.json
      |____model.tflite
    

    Üç dosya da aynı klasörde olmalıdır. Dosyaları (dosya adları dahil) değişiklik yapmadan indirdiğinizde kullanmanızı öneririz.

  2. Klasörü Xcode projenize kopyalayın. Bu işlemi yaparken Klasör başvuruları oluştur'u seçmeyi unutmayın. Model dosyası ve meta veriler, uygulama paketine dahil edilir ve ML Kit tarafından kullanılabilir.

  3. Model manifest dosyasının yolunu belirterek LocalModel nesnesi oluşturun:

    Swift

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

    Objective-C

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

Firebase tarafından barındırılan bir model kaynağını yapılandırma

Uzaktan barındırılan modeli kullanmak için bir CustomRemoteModel nesnesi oluşturun ve modeli yayınlarken modele atadığınız adı belirtin:

Swift

// Initialize the model source with the name you assigned in
// the Firebase console.
let remoteModelSource = FirebaseModelSource(name: "your_remote_model")
let remoteModel = CustomRemoteModel(remoteModelSource: remoteModelSource)

Objective-C

// Initialize the model source with the name you assigned in
// the Firebase console.
MLKFirebaseModelSource *firebaseModelSource =
    [[MLKFirebaseModelSource alloc] initWithName:@"your_remote_model"];
MLKCustomRemoteModel *remoteModel =
    [[MLKCustomRemoteModel alloc] initWithRemoteModelSource:firebaseModelSource];

Ardından, indirmeye izin vermek istediğiniz koşulları belirterek model indirme görevini başlatın. Model cihazda yoksa veya modelin daha yeni bir sürümü varsa görev, modeli Firebase'den eşzamansız olarak indirir:

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] downloadRemoteModel:remoteModel
                                             conditions:downloadConditions];

Birçok uygulama, indirme görevini başlangıç kodlarında başlatır ancak modeli kullanmadan önce istediğiniz zaman bunu yapabilirsiniz.

Modelinizden görüntü etiketleyici oluşturma

Model kaynaklarınızı yapılandırdıktan sonra bu kaynakların birinden ImageLabeler nesnesi oluşturun.

Yalnızca yerel olarak paketlenmiş bir modeliniz varsa LocalModel nesnenizden bir etiketleyici oluşturmanız ve talep etmek istediğiniz güven puanı eşiğini yapılandırmanız yeterlidir (Modelinizi değerlendirme bölümüne bakın):

Swift

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

Objective-C

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

Uzaktan barındırılan bir modeliniz varsa çalıştırmadan önce modelin indirilip indirilmediğini kontrol etmeniz gerekir. Model indirme görevinin durumunu, model yöneticisinin isModelDownloaded(remoteModel:) yöntemini kullanarak kontrol edebilirsiniz.

Etiketleyiciyi çalıştırmadan önce bunu onaylamanız yeterlidir. Hem uzaktan barındırılan hem de yerel olarak paketlenmiş bir modeliniz varsa ImageLabeler öğesini örneklendirirken şu kontrolü gerçekleştirmek mantıklı olabilir: İndirildiyse uzak modelden, aksi takdirde yerel modelden bir etiketleyici oluşturun.

Swift

var options: CustomImageLabelerOptions
if (ModelManager.modelManager().isModelDownloaded(remoteModel)) {
  options = CustomImageLabelerOptions(remoteModel: remoteModel)
} else {
  options = CustomImageLabelerOptions(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

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

Yalnızca uzaktan barındırılan bir modeliniz varsa modelin indirildiğini onaylayana kadar modelle ilgili işlevleri (ör. kullanıcı arayüzünün bir kısmını devre dışı bırakma veya gizleme) devre dışı bırakmanız gerekir.

Varsayılan Bildirim Merkezi'ne gözlemciler ekleyerek model indirme durumunu öğrenebilirsiniz. İndirmeler biraz zaman alabileceğinden ve indirme işlemi tamamlandığında kaynak nesne serbest bırakılabileceği için gözlemci blokunda self için zayıf bir referans kullandığınızdan emin olun. Örnek:

Swift

NotificationCenter.default.addObserver(
    forName: .mlkitMLModelDownloadDidSucceed,
    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: .mlkitMLModelDownloadDidFail,
    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. Giriş resmini hazırlama

UIImage veya CMSampleBufferRef kullanarak VisionImage nesnesi oluşturun.

UIImage kullanıyorsanız şu adımları uygulayın:

  • UIImage ile bir VisionImage nesnesi oluşturun. Doğru .orientation değerini belirttiğinizden emin olun.

    Swift

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

    Objective-C

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

CMSampleBufferRef kullanıyorsanız şu adımları uygulayın:

  • CMSampleBufferRef arabelleğinde bulunan görüntü verilerinin yönünü belirtin.

    Resmin yönünü öğrenmek için:

    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 position == AVCaptureDevicePositionFront ? UIImageOrientationLeftMirrored
                                                          : UIImageOrientationRight;
    
        case UIDeviceOrientationLandscapeLeft:
          return position == AVCaptureDevicePositionFront ? UIImageOrientationDownMirrored
                                                          : UIImageOrientationUp;
        case UIDeviceOrientationPortraitUpsideDown:
          return position == AVCaptureDevicePositionFront ? UIImageOrientationRightMirrored
                                                          : UIImageOrientationLeft;
        case UIDeviceOrientationLandscapeRight:
          return position == AVCaptureDevicePositionFront ? UIImageOrientationUpMirrored
                                                          : UIImageOrientationDown;
        case UIDeviceOrientationUnknown:
        case UIDeviceOrientationFaceUp:
        case UIDeviceOrientationFaceDown:
          return UIImageOrientationUp;
      }
    }
          
  • CMSampleBufferRef nesnesini ve yönünü kullanarak bir VisionImage nesnesi oluşturun:

    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. Görüntü etiketleyiciyi çalıştırma

Eşzamansız olarak:

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<MLKImageLabel *> *_Nullable labels,
                   NSError *_Nullable error) {
        if (label.count == 0) {
            // Handle the error.
            return;
        }
        // Show results.
     }];

Eşzamanlı olarak:

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<MLKImageLabel *> *labels =
    [imageLabeler resultsInImage:image error:&error];
// Show results or handle the error.

4. Etiketli nesneler hakkında bilgi edinme

Görüntü etiketleme işlemi başarılı olursa bir ImageLabel dizisi döndürür. Her ImageLabel, resimde etiketlenen bir şeyi temsil eder. Her etiketin metin açıklamasını (TensorFlow Lite model dosyasının meta verilerinde varsa), güven puanını ve dizini alabilirsiniz. Örnek:

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;
}

Gerçek zamanlı performansı iyileştirmeye yönelik ipuçları

Görüntüleri gerçek zamanlı bir uygulamada etiketlemek istiyorsanız en iyi kare hızlarını elde etmek için şu yönergeleri uygulayın:

  • Algılayıcıya yapılan çağrıları hızlandırın. Algılayıcı çalışırken yeni bir video karesi kullanılabilir hale gelirse kareyi bırakın.
  • Algılayıcının çıkışını, giriş görüntüsünün üzerine grafik yerleştirmek için kullanıyorsanız önce sonucu alın, ardından resmi oluşturun ve tek bir adımda yer paylaşımı yapın. Böylece, her giriş karesi için görüntü yüzeyinde yalnızca bir kez oluşturma yaparsınız. Örnek için vitrin örnek uygulamasındaki previewOverlayView ve FIRDetectionOverlayView sınıflarına göz atın.