رصد الكائنات وتتبُّعها باستخدام حزمة تعلُّم الآلة على أجهزة iOS

يمكنك استخدام مجموعة أدوات تعلُّم الآلة لرصد العناصر وتتبُّعها على مستوى إطارات الفيديو.

عند تمرير صور ML Kit، يعرض كل صورة قائمة يتم رصد ما يصل إلى خمسة أشياء وتحديد موضعها في الصورة. عند الكشف الكائنات في مجموعات بث الفيديو، فكل كائن له معرّف يمكنك استخدامه لتتبع كائن عبر الصور. ويمكنك أيضًا اختياريًا تفعيل الكائن التقريبي. الذي يصنف الكائنات بأوصاف فئات واسعة.

قبل البدء

  1. إذا لم يسبق لك إضافة Firebase إلى تطبيقك، يمكنك إجراء ذلك من خلال اتّباع الخطوات الأولى في دليل البدء.
  2. تضمين مكتبات ML Kit في Podfile:
    pod 'Firebase/MLVision', '6.25.0'
    pod 'Firebase/MLVisionObjectDetection', '6.25.0'
    
    بعد تثبيت مجموعات مشروعك الصغيرة أو تحديثها، احرص على فتح ملف Xcode باستخدام .xcworkspace.
  3. في تطبيقك، استورد Firebase:

    Swift

    import Firebase

    Objective-C

    @import Firebase;

1- ضبط أداة رصد الكائنات

لبدء رصد العناصر وتتبُّعها، أنشئ أولاً مثيلاً VisionObjectDetector، بشكل اختياري، تحديد أي إعدادات أداة رصد تريد عن الوضع الافتراضي.

  1. ضبط أداة رصد العناصر لحالة الاستخدام من خلال عنصر VisionObjectDetectorOptions. يمكنك تغيير ما يلي الإعدادات:

    إعدادات ميزة "رصد الأجسام"
    وضع الكشف .stream (الخيار التلقائي) | .singleImage

    في وضع البث (التلقائي)، تعمل أداة رصد الكائنات بدرجات حرارة منخفضة جدًا وقت الاستجابة، ولكنه قد يؤدي إلى نتائج غير مكتملة (مثل المربعات أو الفئة) في الاستدعاءات القليلة الأولى أداة الكشف. في وضع البث أيضًا، تخصص أداة الكشف عن معرّفات للكائنات، والتي يمكنك استخدامها لتتبع الكائنات عبر الإطارات. يمكنك استخدام هذا الوضع إذا أردت تتبُّع العناصر أو عند الاستجابة السريعة. مهم، كما هو الحال عند معالجة مقاطع الفيديو المضمنة في الواقع الوقت.

    في وضع الصورة الواحدة، تنتظر أداة رصد الأجسام حتى يتم رصد مربع إحاطة الكائن و (في حالة تمكين التصنيف) قبل عرض نتيجة. وبالتالي، من المحتمل أن يكون وقت استجابة الرصد أعلى. أيضًا، في صورة واحدة لا يتم تعيين أرقام تعريف التتبع. استخدام هذا الوضع في حال وقت الاستجابة ليس بالغ الأهمية ولا تريد التعامل مع نتائجك.

    اكتشِف عناصر متعددة وتتبَّعها false (الخيار التلقائي) | true

    ما إذا كان سيتم رصد وتتبع ما يصل إلى خمسة عناصر أو أكثرها فقط كائن بارز (الافتراضي).

    تصنيف العناصر false (الخيار التلقائي) | true

    تحديد ما إذا كان سيتم تصنيف العناصر المرصودة إلى فئات تقريبية أو لا. عند تفعيل هذه الميزة، تصنِّف أداة رصد الكائنات العناصر في الفئات التالية: سلع أزياء، طعام، سلع منزلية وأماكن ونباتات وغير معروفة.

    تم تحسين واجهة برمجة التطبيقات لمراقبة الكائنات وتتبّعها لاستخدام هذين العنصرين الأساسيين الحالات:

    • الرصد المباشر للجسم الأكثر بروزًا في الكاميرا وتتبُّعه عدسة الكاميرا
    • رصد كائنات متعدّدة في صورة ثابتة

    لضبط واجهة برمجة التطبيقات لحالات الاستخدام هذه:

    Swift

    // Live detection and tracking
    let options = VisionObjectDetectorOptions()
    options.detectorMode = .stream
    options.shouldEnableMultipleObjects = false
    options.shouldEnableClassification = true  // Optional
    
    // Multiple object detection in static images
    let options = VisionObjectDetectorOptions()
    options.detectorMode = .singleImage
    options.shouldEnableMultipleObjects = true
    options.shouldEnableClassification = true  // Optional
    

    Objective-C

    // Live detection and tracking
    FIRVisionObjectDetectorOptions *options = [[FIRVisionObjectDetectorOptions alloc] init];
    options.detectorMode = FIRVisionObjectDetectorModeStream;
    options.shouldEnableMultipleObjects = NO;
    options.shouldEnableClassification = YES;  // Optional
    
    // Multiple object detection in static images
    FIRVisionObjectDetectorOptions *options = [[FIRVisionObjectDetectorOptions alloc] init];
    options.detectorMode = FIRVisionObjectDetectorModeSingleImage;
    options.shouldEnableMultipleObjects = YES;
    options.shouldEnableClassification = YES;  // Optional
    
  2. الحصول على نسخة افتراضية من FirebaseVisionObjectDetector:

    Swift

    let objectDetector = Vision.vision().objectDetector()
    
    // Or, to change the default settings:
    let objectDetector = Vision.vision().objectDetector(options: options)
    

    Objective-C

    FIRVisionObjectDetector *objectDetector = [[FIRVision vision] objectDetector];
    
    // Or, to change the default settings:
    FIRVisionObjectDetector *objectDetector = [[FIRVision vision] objectDetectorWithOptions:options];
    

2- تشغيل أداة رصد الكائنات

لرصد العناصر وتتبُّعها، يُرجى اتّباع الخطوات التالية لكل صورة أو إطار فيديو. في حال تفعيل وضع البث، يجب إنشاء VisionImage عناصر من CMSampleBufferRef

  1. إنشاء عنصر VisionImage باستخدام UIImage أو CMSampleBufferRef

    لاستخدام UIImage:

    1. إذا لزم الأمر، يمكنك تدوير الصورة لتكون imageOrientation الموقع هو .up.
    2. إنشاء عنصر VisionImage باستخدام عنصر التدوير الذي تم تدويره بشكل صحيح UIImage عدم تحديد أي بيانات وصفية حول عرض الإعلانات بالتناوب - البيانات التلقائية القيمة، .topLeft،.

      Swift

      let image = VisionImage(image: uiImage)

      Objective-C

      FIRVisionImage *image = [[FIRVisionImage alloc] initWithImage:uiImage];

    لاستخدام CMSampleBufferRef:

    1. أنشئ كائن VisionImageMetadata يحدّد اتجاه بيانات الصورة الواردة في المخزن المؤقت CMSampleBufferRef

      للحصول على اتجاه الصورة:

      Swift

      func imageOrientation(
          deviceOrientation: UIDeviceOrientation,
          cameraPosition: AVCaptureDevice.Position
          ) -> VisionDetectorImageOrientation {
          switch deviceOrientation {
          case .portrait:
              return cameraPosition == .front ? .leftTop : .rightTop
          case .landscapeLeft:
              return cameraPosition == .front ? .bottomLeft : .topLeft
          case .portraitUpsideDown:
              return cameraPosition == .front ? .rightBottom : .leftBottom
          case .landscapeRight:
              return cameraPosition == .front ? .topRight : .bottomRight
          case .faceDown, .faceUp, .unknown:
              return .leftTop
          }
      }

      Objective-C

      - (FIRVisionDetectorImageOrientation)
          imageOrientationFromDeviceOrientation:(UIDeviceOrientation)deviceOrientation
                                 cameraPosition:(AVCaptureDevicePosition)cameraPosition {
        switch (deviceOrientation) {
          case UIDeviceOrientationPortrait:
            if (cameraPosition == AVCaptureDevicePositionFront) {
              return FIRVisionDetectorImageOrientationLeftTop;
            } else {
              return FIRVisionDetectorImageOrientationRightTop;
            }
          case UIDeviceOrientationLandscapeLeft:
            if (cameraPosition == AVCaptureDevicePositionFront) {
              return FIRVisionDetectorImageOrientationBottomLeft;
            } else {
              return FIRVisionDetectorImageOrientationTopLeft;
            }
          case UIDeviceOrientationPortraitUpsideDown:
            if (cameraPosition == AVCaptureDevicePositionFront) {
              return FIRVisionDetectorImageOrientationRightBottom;
            } else {
              return FIRVisionDetectorImageOrientationLeftBottom;
            }
          case UIDeviceOrientationLandscapeRight:
            if (cameraPosition == AVCaptureDevicePositionFront) {
              return FIRVisionDetectorImageOrientationTopRight;
            } else {
              return FIRVisionDetectorImageOrientationBottomRight;
            }
          default:
            return FIRVisionDetectorImageOrientationTopLeft;
        }
      }

      بعد ذلك، أنشئ كائن البيانات الوصفية:

      Swift

      let cameraPosition = AVCaptureDevice.Position.back  // Set to the capture device you used.
      let metadata = VisionImageMetadata()
      metadata.orientation = imageOrientation(
          deviceOrientation: UIDevice.current.orientation,
          cameraPosition: cameraPosition
      )

      Objective-C

      FIRVisionImageMetadata *metadata = [[FIRVisionImageMetadata alloc] init];
      AVCaptureDevicePosition cameraPosition =
          AVCaptureDevicePositionBack;  // Set to the capture device you used.
      metadata.orientation =
          [self imageOrientationFromDeviceOrientation:UIDevice.currentDevice.orientation
                                       cameraPosition:cameraPosition];
    2. إنشاء عنصر VisionImage باستخدام عنصر CMSampleBufferRef والبيانات الوصفية بالتناوب:

      Swift

      let image = VisionImage(buffer: sampleBuffer)
      image.metadata = metadata

      Objective-C

      FIRVisionImage *image = [[FIRVisionImage alloc] initWithBuffer:sampleBuffer];
      image.metadata = metadata;
  2. نقْل VisionImage إلى إحدى عمليات معالجة الصور لأداة رصد الأجسام الطرق. يمكنك استخدام إما طريقة process(image:) غير المتزامنة أو طريقة results() متزامنة.

    لرصد العناصر بشكل غير متزامن:

    Swift

    objectDetector.process(image) { detectedObjects, error in
      guard error == nil else {
        // Error.
        return
      }
      guard let detectedObjects = detectedObjects, !detectedObjects.isEmpty else {
        // No objects detected.
        return
      }
    
      // Success. Get object info here.
      // ...
    }
    

    Objective-C

    [objectDetector processImage:image
                      completion:^(NSArray<FIRVisionObject *> * _Nullable objects,
                                   NSError * _Nullable error) {
                        if (error == nil) {
                          return;
                        }
                        if (objects == nil | objects.count == 0) {
                          // No objects detected.
                          return;
                        }
    
                        // Success. Get object info here.
                        // ...
                      }];
    

    لرصد العناصر بشكل متزامن:

    Swift

    var results: [VisionObject]? = nil
    do {
      results = try objectDetector.results(in: image)
    } catch let error {
      print("Failed to detect object with error: \(error.localizedDescription).")
      return
    }
    guard let detectedObjects = results, !detectedObjects.isEmpty else {
      print("Object detector returned no results.")
      return
    }
    
    // ...
    

    Objective-C

    NSError *error;
    NSArray<FIRVisionObject *> *objects = [objectDetector resultsInImage:image
                                                                   error:&error];
    if (error == nil) {
      return;
    }
    if (objects == nil | objects.count == 0) {
      // No objects detected.
      return;
    }
    
    // Success. Get object info here.
    // ...
    
  3. إذا نجح الاتصال بمعالج الصور، فهو إما يجتاز قائمة VisionObject إلى معالج الإكمال أو يتم عرض القائمة، بناءً على سواء استدعيت الطريقة غير المتزامنة أم المتزامنة.

    يحتوي كل VisionObject على السمات التالية:

    frame علامة CGRect تشير إلى موضع العنصر في .
    trackingID عدد صحيح يعرّف العنصر عبر الصور. أغنية واحدة وضع الصور.
    classificationCategory الفئة التقريبية للعنصر. وإذا لم تتعرّف أداة رصد الكائنات على يكون التصنيف مفعّلاً، يكون التصنيف دائمًا .unknown.
    confidence قيمة الثقة لتصنيف العنصر. إذا كان الكائن أنّ التصنيف لم يكُن تصنيفًا في أداة الرصد، أو أنّ العنصر مصنفة على أنها غير معروفة، وهذا هو nil.

    Swift

    // detectedObjects contains one item if multiple object detection wasn't enabled.
    for obj in detectedObjects {
      let bounds = obj.frame
      let id = obj.trackingID
    
      // If classification was enabled:
      let category = obj.classificationCategory
      let confidence = obj.confidence
    }
    

    Objective-C

    // The list of detected objects contains one item if multiple
    // object detection wasn't enabled.
    for (FIRVisionObject *obj in objects) {
      CGRect bounds = obj.frame;
      if (obj.trackingID) {
        NSInteger id = obj.trackingID.integerValue;
      }
    
      // If classification was enabled:
      FIRVisionObjectCategory category = obj.classificationCategory;
      float confidence = obj.confidence.floatValue;
    }
    

تحسين سهولة الاستخدام والأداء

لتقديم أفضل تجربة للمستخدم، يُرجى اتّباع الإرشادات التالية في تطبيقك:

  • يعتمد نجاح رصد العناصر على التعقيد البصري للكائن. أغراض ذات عدد صغير من الميزات المرئية قد تحتاج إلى شغل جزء أكبر من عن الصورة المراد رصدها. يجب عليك تقديم إرشادات للمستخدمين حول التقاط مدخلاً يتناسب جيدًا مع نوع العناصر التي تريد رصدها.
  • عند استخدام التصنيف، إذا كنت تريد رصد الأجسام التي لا تسقط بوضوح في الفئات المعتمدة، وتنفيذ معالجة خاصة للفئات الأخرى.

يمكنك أيضًا الاطّلاع على [تطبيق عرض التصميم المتعدد الأبعاد لمجموعة أدوات تعلّم الآلة][showcase-link]{: .external } و التصميم المتعدد الأبعاد مجموعة أنماط الميزات المستنِدة إلى تعلُّم الآلة:

عند استخدام وضع البث في تطبيق في الوقت الفعلي، اتّبِع الإرشادات التالية وتحقيق أفضل معدلات عرض الإطارات:

  • يجب عدم استخدام ميزة رصد الكائنات المتعددة في وضع البث، إذ لا تسمح معظم الأجهزة بذلك قادرًا على إنتاج معدلات إطارات مناسبة.

  • يمكنك إيقاف التصنيف إذا لم تكن بحاجة إليه.

  • التحكُّم في المكالمات الواردة إلى أداة الرصد. إذا أصبح إطار فيديو جديد المتاح أثناء تشغيل أداة الكشف، أفلِت الإطار.
  • إذا كنت تستخدم ناتج أداة الكشف لتراكب الرسومات على الصورة المدخلة، والحصول أولاً على النتيجة من ML Kit، ثم عرض الصورة وتراكبها في خطوة واحدة. ومن خلال القيام بذلك، يمكنك العرض على سطح الشاشة مرة واحدة فقط لكل إطار إدخال اطّلع على previewOverlayView وFIRDetectionOverlayView الفئات في نموذج تطبيق العرض كمثال.