iOS-এ ML Kit-এর সাহায্যে পোজ শনাক্ত করুন

এমএল কিট পোজ সনাক্তকরণের জন্য দুটি অপ্টিমাইজড এসডিকে সরবরাহ করে।

SDK নাম ভঙ্গি সনাক্তকরণ ভঙ্গি সনাক্তকরণ সঠিক
বাস্তবায়ন বেস ডিটেক্টরের সম্পদগুলি তৈরির সময় আপনার অ্যাপের সাথে স্ট্যাটিক্যালি লিঙ্ক করা থাকে। নির্ভুল সনাক্তকারীর সম্পদগুলি তৈরির সময় আপনার অ্যাপের সাথে স্ট্যাটিক্যালি লিঙ্ক করা হয়।
অ্যাপের আকার ২৯.৬ এমবি পর্যন্ত ৩৩.২ এমবি পর্যন্ত
কর্মক্ষমতা আইফোন এক্স: ~৪৫ এফপিএস আইফোন এক্স: ~২৯ এফপিএস

চেষ্টা করে দেখো

শুরু করার আগে

  1. আপনার পডফাইলে নিম্নলিখিত ML কিট পডগুলি অন্তর্ভুক্ত করুন:

    # If you want to use the base implementation:
    pod 'GoogleMLKit/PoseDetection', '8.0.0'
    
    # If you want to use the accurate implementation:
    pod 'GoogleMLKit/PoseDetectionAccurate', '8.0.0'
    
  2. আপনার প্রোজেক্টের পড ইনস্টল বা আপডেট করার পর, আপনার Xcode প্রোজেক্টটি xcworkspace ব্যবহার করে খুলুন। ML Kit Xcode সংস্করণ 13.2.1 বা তার উচ্চতর সংস্করণে সমর্থিত।

১. PoseDetector এর একটি উদাহরণ তৈরি করুন

একটি ছবিতে একটি ভঙ্গি সনাক্ত করতে, প্রথমে PoseDetector এর একটি উদাহরণ তৈরি করুন এবং ঐচ্ছিকভাবে ডিটেক্টর সেটিংস নির্দিষ্ট করুন।

PoseDetector বিকল্পগুলি

সনাক্তকরণ মোড

PoseDetector দুটি সনাক্তকরণ মোডে কাজ করে। আপনার ব্যবহারের ক্ষেত্রে মেলে এমন একটি বেছে নেওয়ার বিষয়ে নিশ্চিত হন।

stream (ডিফল্ট)
পোজ ডিটেক্টর প্রথমে ছবির সবচেয়ে বিশিষ্ট ব্যক্তিকে সনাক্ত করবে এবং তারপর পোজ ডিটেকশন চালাবে। পরবর্তী ফ্রেমগুলিতে, ব্যক্তি-সনাক্তকরণের ধাপটি পরিচালিত হবে না যদি না ব্যক্তিটি অস্পষ্ট হয়ে যায় বা উচ্চ আত্মবিশ্বাসের সাথে আর সনাক্ত করা না যায়। পোজ ডিটেক্টর সর্বাধিক বিশিষ্ট ব্যক্তিকে ট্র্যাক করার চেষ্টা করবে এবং প্রতিটি অনুমানে তাদের পোজ ফিরিয়ে দেবে। এটি লেটেন্সি হ্রাস করে এবং সনাক্তকরণকে মসৃণ করে। যখন আপনি একটি ভিডিও স্ট্রিমে পোজ সনাক্ত করতে চান তখন এই মোডটি ব্যবহার করুন।
singleImage
পোজ ডিটেক্টর একজন ব্যক্তিকে সনাক্ত করবে এবং তারপর পোজ ডিটেকশন চালাবে। প্রতিটি ছবির জন্য ব্যক্তি-সনাক্তকরণ ধাপটি চলবে, তাই ল্যাটেন্সি বেশি হবে এবং কোনও ব্যক্তি-ট্র্যাকিং থাকবে না। স্ট্যাটিক ছবিতে বা যেখানে ট্র্যাকিং পছন্দসই নয় সেখানে পোজ ডিটেকশন ব্যবহার করার সময় এই মোডটি ব্যবহার করুন।

পোজ ডিটেক্টর বিকল্পগুলি নির্দিষ্ট করুন:

সুইফট

// Base pose detector with streaming, when depending on the PoseDetection SDK
let options = PoseDetectorOptions()
options.detectorMode = .stream

// Accurate pose detector on static images, when depending on the
// PoseDetectionAccurate SDK
let options = AccuratePoseDetectorOptions()
options.detectorMode = .singleImage

অবজেক্টিভ-সি

// Base pose detector with streaming, when depending on the PoseDetection SDK
MLKPoseDetectorOptions *options = [[MLKPoseDetectorOptions alloc] init];
options.detectorMode = MLKPoseDetectorModeStream;

// Accurate pose detector on static images, when depending on the
// PoseDetectionAccurate SDK
MLKAccuratePoseDetectorOptions *options =
    [[MLKAccuratePoseDetectorOptions alloc] init];
options.detectorMode = MLKPoseDetectorModeSingleImage;

অবশেষে, PoseDetector এর একটি উদাহরণ পান। আপনার নির্দিষ্ট করা বিকল্পগুলি পাস করুন:

সুইফট

let poseDetector = PoseDetector.poseDetector(options: options)

অবজেক্টিভ-সি

MLKPoseDetector *poseDetector =
    [MLKPoseDetector poseDetectorWithOptions:options];

2. ইনপুট ইমেজ প্রস্তুত করুন

ভঙ্গি সনাক্ত করতে, প্রতিটি ছবি বা ভিডিওর ফ্রেমের জন্য নিম্নলিখিতগুলি করুন। যদি আপনি স্ট্রিম মোড সক্ষম করে থাকেন, তাহলে আপনাকে CMSampleBuffer থেকে VisionImage অবজেক্ট তৈরি করতে হবে।

UIImage অথবা CMSampleBuffer ব্যবহার করে একটি VisionImage অবজেক্ট তৈরি করুন।

আপনি যদি UIImage ব্যবহার করেন, তাহলে এই পদক্ষেপগুলি অনুসরণ করুন:

  • UIImage ব্যবহার করে একটি VisionImage অবজেক্ট তৈরি করুন। সঠিক .orientation উল্লেখ করতে ভুলবেন না।

    সুইফট

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

    অবজেক্টিভ-সি

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

আপনি যদি CMSampleBuffer ব্যবহার করেন, তাহলে এই পদক্ষেপগুলি অনুসরণ করুন:

  • CMSampleBuffer এ থাকা চিত্রের ডেটার ওরিয়েন্টেশন নির্দিষ্ট করুন।

    ছবির ওরিয়েন্টেশন পেতে:

    সুইফট

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

    অবজেক্টিভ-সি

    - (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;
      }
    }
          
  • CMSampleBuffer অবজেক্ট এবং ওরিয়েন্টেশন ব্যবহার করে একটি VisionImage অবজেক্ট তৈরি করুন:

    সুইফট

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

    অবজেক্টিভ-সি

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

৩. ছবিটি প্রক্রিয়া করুন

VisionImage পোজ ডিটেক্টরের ইমেজ প্রসেসিং পদ্ধতিগুলির একটিতে পাস করুন। আপনি হয় অ্যাসিঙ্ক্রোনাস process(image:) পদ্ধতি অথবা সিঙ্ক্রোনাস results() পদ্ধতি ব্যবহার করতে পারেন।

সিঙ্ক্রোনাসভাবে বস্তু সনাক্ত করতে:

সুইফট

var results: [Pose]
do {
  results = try poseDetector.results(in: image)
} catch let error {
  print("Failed to detect pose with error: \(error.localizedDescription).")
  return
}
guard let detectedPoses = results, !detectedPoses.isEmpty else {
  print("Pose detector returned no results.")
  return
}

// Success. Get pose landmarks here.

অবজেক্টিভ-সি

NSError *error;
NSArray *poses = [poseDetector resultsInImage:image error:&error];
if (error != nil) {
  // Error.
  return;
}
if (poses.count == 0) {
  // No pose detected.
  return;
}

// Success. Get pose landmarks here.

অ্যাসিঙ্ক্রোনাসভাবে বস্তু সনাক্ত করতে:

সুইফট

poseDetector.process(image) { detectedPoses, error in
  guard error == nil else {
    // Error.
    return
  }
  guard !detectedPoses.isEmpty else {
    // No pose detected.
    return
  }

  // Success. Get pose landmarks here.
}

অবজেক্টিভ-সি

[poseDetector processImage:image
                completion:^(NSArray * _Nullable poses,
                             NSError * _Nullable error) {
                    if (error != nil) {
                      // Error.
                      return;
                    }
                    if (poses.count == 0) {
                      // No pose detected.
                      return;
                    }

                    // Success. Get pose landmarks here.
                  }];

৪. সনাক্ত করা ভঙ্গি সম্পর্কে তথ্য পান

যদি ছবিতে কোনও ব্যক্তিকে শনাক্ত করা হয়, তাহলে পোজ ডিটেকশন API হয় Pose অবজেক্টের একটি অ্যারে কমপ্লিশন হ্যান্ডলারে পাঠায় অথবা অ্যারেটি ফেরত দেয়, এটি নির্ভর করে আপনি অ্যাসিঙ্ক্রোনাস নাকি সিঙ্ক্রোনাস পদ্ধতিটি কল করেছেন তার উপর।

যদি ব্যক্তিটি ছবির ভেতরে সম্পূর্ণরূপে না থাকে, তাহলে মডেলটি ফ্রেমের বাইরে অনুপস্থিত ল্যান্ডমার্ক স্থানাঙ্কগুলি নির্ধারণ করে এবং তাদের কম InFrameConfidence মান দেয়।

যদি কোনও ব্যক্তি সনাক্ত না হয় তবে অ্যারে খালি থাকে।

সুইফট

for pose in detectedPoses {
  let leftAnkleLandmark = pose.landmark(ofType: .leftAnkle)
  if leftAnkleLandmark.inFrameLikelihood > 0.5 {
    let position = leftAnkleLandmark.position
  }
}

অবজেক্টিভ-সি

for (MLKPose *pose in detectedPoses) {
  MLKPoseLandmark *leftAnkleLandmark =
      [pose landmarkOfType:MLKPoseLandmarkTypeLeftAnkle];
  if (leftAnkleLandmark.inFrameLikelihood > 0.5) {
    MLKVision3DPoint *position = leftAnkleLandmark.position;
  }
}

কর্মক্ষমতা উন্নত করার টিপস

আপনার ফলাফলের মান ইনপুট ছবির মানের উপর নির্ভর করে:

  • ML Kit সঠিকভাবে ভঙ্গি সনাক্ত করতে, ছবিতে থাকা ব্যক্তিকে পর্যাপ্ত পিক্সেল ডেটা দ্বারা প্রতিনিধিত্ব করতে হবে; সর্বোত্তম পারফরম্যান্সের জন্য, বিষয়বস্তু কমপক্ষে 256x256 পিক্সেল হওয়া উচিত।
  • যদি আপনি রিয়েল-টাইম অ্যাপ্লিকেশনে পোজ শনাক্ত করেন, তাহলে আপনি ইনপুট ইমেজের সামগ্রিক মাত্রাও বিবেচনা করতে পারেন। ছোট ছবিগুলি দ্রুত প্রক্রিয়া করা যেতে পারে, তাই লেটেন্সি কমাতে, কম রেজোলিউশনে ছবিগুলি ক্যাপচার করুন, তবে উপরের রেজোলিউশনের প্রয়োজনীয়তাগুলি মনে রাখবেন এবং নিশ্চিত করুন যে সাবজেক্টটি যতটা সম্ভব ছবির বেশির ভাগ অংশ দখল করে।
  • ছবির দুর্বল ফোকাসও নির্ভুলতার উপর প্রভাব ফেলতে পারে। যদি আপনি গ্রহণযোগ্য ফলাফল না পান, তাহলে ব্যবহারকারীকে ছবিটি পুনরায় ধারণ করতে বলুন।

আপনি যদি রিয়েল-টাইম অ্যাপ্লিকেশনে পোজ ডিটেকশন ব্যবহার করতে চান, তাহলে সেরা ফ্রেমরেট অর্জনের জন্য এই নির্দেশিকাগুলি অনুসরণ করুন:

  • বেস PoseDetection SDK এবং stream সনাক্তকরণ মোড ব্যবহার করুন।
  • কম রেজোলিউশনে ছবি তোলার কথা বিবেচনা করুন। তবে, এই API-এর ছবির মাত্রার প্রয়োজনীয়তাগুলিও মনে রাখবেন।
  • ভিডিও ফ্রেম প্রক্রিয়াকরণের জন্য, ডিটেক্টরের results(in:) সিঙ্ক্রোনাস API ব্যবহার করুন। প্রদত্ত ভিডিও ফ্রেম থেকে সিঙ্ক্রোনাসভাবে ফলাফল পেতে AVCaptureVideoDataOutputSampleBufferDelegate এর captureOutput(_, didOutput:from:) ফাংশন থেকে এই পদ্ধতিটি কল করুন। ডিটেক্টরে থ্রোটল কলের জন্য AVCaptureVideoDataOutput এর alwaysDiscardsLateVideoFrames কে সত্য হিসাবে রাখুন। ডিটেক্টর চলাকালীন যদি একটি নতুন ভিডিও ফ্রেম উপলব্ধ হয়, তবে এটি বাদ দেওয়া হবে।
  • যদি আপনি ইনপুট ছবিতে গ্রাফিক্স ওভারলে করার জন্য ডিটেক্টরের আউটপুট ব্যবহার করেন, তাহলে প্রথমে ML Kit থেকে ফলাফলটি পান, তারপর একটি ধাপে ছবিটি রেন্ডার করুন এবং ওভারলে করুন। এটি করার মাধ্যমে, আপনি প্রতিটি প্রক্রিয়াজাত ইনপুট ফ্রেমের জন্য শুধুমাত্র একবার ডিসপ্লে সারফেসে রেন্ডার করবেন। উদাহরণের জন্য শোকেস নমুনা অ্যাপে previewOverlayView এবং MLKDetectionOverlayView ক্লাসগুলি দেখুন।

পরবর্তী পদক্ষেপ