وظیفه آشکارساز شی به شما امکان می دهد حضور و مکان چندین کلاس از اشیاء را تشخیص دهید. به عنوان مثال، یک آشکارساز شی می تواند سگ ها را در یک تصویر پیدا کند. این دستورالعمل به شما نشان می دهد که چگونه از وظیفه آشکارساز شی در iOS استفاده کنید. نمونه کد شرح داده شده در این دستورالعمل ها در GitHub موجود است.
شما می توانید با مشاهده این نسخه نمایشی وب، این کار را در عمل مشاهده کنید. برای اطلاعات بیشتر در مورد قابلیتها، مدلها و گزینههای پیکربندی این کار، به نمای کلی مراجعه کنید.
نمونه کد
کد مثال MediaPipe Tasks یک پیاده سازی اساسی از یک برنامه Object Detector برای iOS است. این مثال از دوربین یک دستگاه iOS فیزیکی برای شناسایی مداوم اشیا استفاده میکند و همچنین میتواند از تصاویر و ویدیوهای گالری دستگاه برای شناسایی استاتیک اشیا استفاده کند.
میتوانید از برنامه بهعنوان نقطه شروع برای برنامه iOS خودتان استفاده کنید، یا هنگام تغییر یک برنامه موجود به آن مراجعه کنید. کد نمونه Object Detector در GitHub میزبانی می شود.
کد را دانلود کنید
دستورالعمل های زیر به شما نشان می دهد که چگونه با استفاده از ابزار خط فرمان git یک کپی محلی از کد مثال ایجاد کنید.
برای دانلود کد نمونه:
با استفاده از دستور زیر مخزن git را کلون کنید:
git clone https://github.com/google-ai-edge/mediapipe-samples
به صورت اختیاری، نمونه git خود را برای استفاده از پرداخت پراکنده پیکربندی کنید، بنابراین فقط فایلهای برنامه مثالی Object Detector را داشته باشید:
cd mediapipe git sparse-checkout init --cone git sparse-checkout set examples/object_detection/ios/
پس از ایجاد یک نسخه محلی از کد نمونه، می توانید کتابخانه وظایف MediaPipe را نصب کنید، پروژه را با استفاده از Xcode باز کنید و برنامه را اجرا کنید. برای دستورالعملها، به راهنمای راهاندازی برای iOS مراجعه کنید.
اجزای کلیدی
فایل های زیر حاوی کد حیاتی برای مثال برنامه Object Detector هستند:
- ObjectDetectorService.swift : آشکارساز را اولیه می کند، انتخاب مدل را مدیریت می کند و استنتاج را روی داده های ورودی اجرا می کند.
- CameraViewController.swift : رابط کاربری را برای حالت ورودی تغذیه زنده دوربین پیادهسازی میکند و نتایج تشخیص را به تصویر میکشد.
- MediaLibraryViewController.swift : رابط کاربری را برای حالت ورودی تصویر ثابت و فایل ویدیویی پیادهسازی میکند و نتایج تشخیص را به تصویر میکشد.
راه اندازی
این بخش مراحل کلیدی را برای تنظیم محیط توسعه و پروژه های کد برای استفاده از Object Detector شرح می دهد. برای اطلاعات کلی در مورد تنظیم محیط توسعه خود برای استفاده از وظایف MediaPipe، از جمله الزامات نسخه پلت فرم، به راهنمای راه اندازی برای iOS مراجعه کنید.
وابستگی ها
Object Detector از کتابخانه MediaPipeTasksVision
استفاده می کند که باید با استفاده از CocoaPods نصب شود. این کتابخانه با هر دو برنامه Swift و Objective-C سازگار است و نیازی به تنظیمات زبان خاصی ندارد.
برای دستورالعملهای نصب CocoaPods در macOS، به راهنمای نصب CocoaPods مراجعه کنید. برای دستورالعملهای نحوه ایجاد یک Podfile
با پادهای لازم برای برنامه خود، به استفاده از CocoaPods مراجعه کنید.
با استفاده از کد زیر، MediaPipeTasksVision pod را در Podfile
اضافه کنید:
target 'MyObjectDetectorApp' do
use_frameworks!
pod 'MediaPipeTasksVision'
end
اگر برنامه شما شامل اهداف تست واحد است، برای اطلاعات بیشتر در مورد راهاندازی Podfile
، به راهنمای تنظیم برای iOS مراجعه کنید.
مدل
وظیفه MediaPipe Object Detector به یک مدل آموزش دیده نیاز دارد که با این کار سازگار باشد. برای اطلاعات بیشتر در مورد مدلهای آموزشدیده موجود برای آشکارساز شی، به بخش مدلهای نمای کلی کار مراجعه کنید.
یک مدل را انتخاب و دانلود کنید و آن را با استفاده از Xcode به فهرست پروژه خود اضافه کنید. برای دستورالعملهایی درباره نحوه افزودن فایلها به پروژه Xcode، به مدیریت فایلها و پوشهها در پروژه Xcode خود مراجعه کنید.
از ویژگی BaseOptions.modelAssetPath
برای تعیین مسیر مدل در بسته نرم افزاری خود استفاده کنید. برای مثال کد، بخش بعدی را ببینید.
کار را ایجاد کنید
می توانید وظیفه آشکارساز شی را با فراخوانی یکی از اولیه سازهای آن ایجاد کنید. آغازگر ObjectDetector(options:)
مقادیری را برای گزینه های پیکربندی از جمله حالت اجرا، محل نام نمایشی، حداکثر تعداد نتایج، آستانه اطمینان، لیست مجاز دسته ها و فهرست رد تنظیم می کند.
اگر به یک آشکارساز شی که با گزینه های پیکربندی سفارشی راه اندازی شده است نیاز ندارید، می توانید از مقداردهی اولیه ObjectDetector(modelPath:)
برای ایجاد یک آشکارساز شی با گزینه های پیش فرض استفاده کنید. برای اطلاعات بیشتر درباره گزینههای پیکربندی، به نمای کلی پیکربندی مراجعه کنید.
وظیفه آشکارساز شی از 3 نوع داده ورودی پشتیبانی می کند: تصاویر ثابت، فایل های ویدیویی و پخش جریانی ویدیویی زنده. به طور پیش فرض، ObjectDetector(modelPath:)
یک کار را برای تصاویر ثابت مقداردهی اولیه می کند. اگر میخواهید کار شما برای پردازش فایلهای ویدیویی یا پخش جریانی زنده ویدیویی اولیه شود، از ObjectDetector(options:)
برای مشخص کردن حالت اجرای ویدیو یا پخش زنده استفاده کنید. حالت پخش زنده همچنین به گزینه پیکربندی objectDetectorLiveStreamDelegate
اضافی نیاز دارد که به Object Detector امکان می دهد نتایج تشخیص را به صورت ناهمزمان به نماینده ارائه دهد.
برای مشاهده نحوه ایجاد کار و اجرای استنتاج، برگه مربوط به حالت در حال اجرا خود را انتخاب کنید.
سویفت
تصویر
import MediaPipeTasksVision let modelPath = Bundle.main.path(forResource: "model", ofType: "tflite") let options = ObjectDetectorOptions() options.baseOptions.modelAssetPath = modelPath options.runningMode = .image options.maxResults = 5 let objectDetector = try ObjectDetector(options: options)
ویدئو
import MediaPipeTasksVision let modelPath = Bundle.main.path(forResource: "model", ofType: "tflite") let options = ObjectDetectorOptions() options.baseOptions.modelAssetPath = modelPath options.runningMode = .video options.maxResults = 5 let objectDetector = try ObjectDetector(options: options)
پخش زنده
import MediaPipeTasksVision // Class that conforms to the `ObjectDetectorLiveStreamDelegate` protocol and // implements the method that the object detector calls once it // finishes performing detection on each input frame. class ObjectDetectorResultProcessor: NSObject, ObjectDetectorLiveStreamDelegate { func objectDetector( _ objectDetector: ObjectDetector, didFinishDetection objectDetectionResult: ObjectDetectorResult?, timestampInMilliseconds: Int, error: Error?) { // Process the detection result or errors here. } } let modelPath = Bundle.main.path(forResource: "model", ofType: "tflite") let options = ObjectDetectorOptions() options.baseOptions.modelAssetPath = modelPath options.runningMode = .liveStream options.maxResults = 5 // Assign an object of the class to the `objectDetectorLiveStreamDelegate` // property. let processor = ObjectDetectorResultProcessor() options.objectDetectorLiveStreamDelegate = processor let objectDetector = try ObjectDetector(options: options)
هدف-C
تصویر
@import MediaPipeTasksVision; NSString *modelPath = [[NSBundle mainBundle] pathForResource:@"model" ofType:@"tflite"]; MPPObjectDetectorOptions *options = [[MPPObjectDetectorOptions alloc] init]; options.baseOptions.modelAssetPath = modelPath; options.runningMode = MPPRunningModeImage; options.maxResults = 5; MPPObjectDetector *objectDetector = [[MPPObjectDetector alloc] initWithOptions:options error:nil];
ویدئو
@import MediaPipeTasksVision; NSString *modelPath = [[NSBundle mainBundle] pathForResource:@"model" ofType:@"tflite"]; MPPObjectDetectorOptions *options = [[MPPObjectDetectorOptions alloc] init]; options.baseOptions.modelAssetPath = modelPath; options.runningMode = MPPRunningModeVideo; options.maxResults = 5; MPPObjectDetector *objectDetector = [[MPPObjectDetector alloc] initWithOptions:options error:nil];
پخش زنده
@import MediaPipeTasksVision; // Class that conforms to the `ObjectDetectorLiveStreamDelegate` protocol and // implements the method that the object detector calls once it // finishes performing detection on each input frame. @interface APPObjectDetectorResultProcessor : NSObject@end @implementation MPPObjectDetectorResultProcessor - (void)objectDetector:(MPPObjectDetector *)objectDetector didFinishDetectionWithResult:(MPPObjectDetectorResult *)ObjectDetectorResult timestampInMilliseconds:(NSInteger)timestampInMilliseconds error:(NSError *)error { // Process the detection result or errors here. } @end NSString *modelPath = [[NSBundle mainBundle] pathForResource:@"model" ofType:@"tflite"]; MPPObjectDetectorOptions *options = [[MPPObjectDetectorOptions alloc] init]; options.baseOptions.modelAssetPath = modelPath; options.runningMode = MPPRunningModeLiveStream; options.maxResults = 5; // Assign an object of the class to the `objectDetectorLiveStreamDelegate` // property. APPObjectDetectorResultProcessor *processor = [APPObjectDetectorResultProcessor new]; options.objectDetectorLiveStreamDelegate = processor; MPPObjectDetector *objectDetector = [[MPPObjectDetector alloc] initWithOptions:options error:nil];
گزینه های پیکربندی
این کار دارای گزینه های پیکربندی زیر برای برنامه های iOS است:
نام گزینه | توضیحات | محدوده ارزش | مقدار پیش فرض |
---|---|---|---|
runningMode | حالت اجرا را برای کار تنظیم می کند. سه حالت وجود دارد: IMAGE: حالت برای ورودی های تک تصویر. VIDEO: حالت برای فریم های رمزگشایی شده یک ویدیو. LIVE_STREAM: حالت پخش زنده داده های ورودی، مانند دوربین. در این حالت، resultListener باید فراخوانی شود تا شنونده ای را برای دریافت نتایج به صورت ناهمزمان تنظیم کند. | { RunningMode.image, RunningMode.video, RunningMode.liveStream } | RunningMode.image |
displayNamesLocales | زبان برچسبها را برای استفاده برای نامهای نمایشی ارائه شده در فراداده مدل کار، در صورت وجود، تنظیم میکند. پیش فرض برای انگلیسی en است. با استفاده از TensorFlow Lite Metadata Writer API میتوانید برچسبهای محلی را به ابرداده یک مدل سفارشی اضافه کنید. | کد محلی | en |
maxResults | حداکثر تعداد اختیاری نتایج تشخیص با امتیاز بالا را برای بازگشت تنظیم می کند. | هر عدد مثبت | -1 (همه نتایج برگردانده می شوند) |
scoreThreshold | آستانه امتیاز پیشبینی را تنظیم میکند که بر آستانه ارائهشده در فراداده مدل (در صورت وجود) لغو میشود. نتایج زیر این مقدار رد می شوند. | هر شناور | تنظیم نشده است |
categoryAllowlist | فهرست اختیاری نامهای دستهبندی مجاز را تنظیم میکند. اگر خالی نباشد، نتایج تشخیصی که نام دسته آنها در این مجموعه نیست فیلتر میشوند. نامهای دستهبندی تکراری یا ناشناخته نادیده گرفته میشوند. این گزینه با categoryDenylist منحصر به فرد است و از هر دو نتیجه در یک خطا استفاده می کند. | هر رشته | تنظیم نشده است |
categoryDenylist | فهرست اختیاری نامهای دستههایی را که مجاز نیستند را تنظیم میکند. اگر خالی نباشد، نتایج تشخیصی که نام دسته آنها در این مجموعه است، فیلتر میشوند. نامهای دستهبندی تکراری یا ناشناخته نادیده گرفته میشوند. این گزینه با categoryAllowlist منحصر به فرد است و از هر دو نتیجه در خطا استفاده می کند. | هر رشته | تنظیم نشده است |
پیکربندی پخش زنده
هنگامی که حالت اجرا روی پخش مستقیم تنظیم می شود، آشکارساز شیء به گزینه پیکربندی اضافی objectDetectorLiveStreamDelegate
نیاز دارد، که آشکارساز را قادر می سازد تا نتایج تشخیص را به صورت ناهمزمان ارائه دهد. نماینده متد objectDetector(_objectDetector:didFinishDetection:timestampInMilliseconds:error:)
پیاده سازی می کند، که Object Detector پس از پردازش نتیجه تشخیص برای هر فریم، آن را فراخوانی می کند.
نام گزینه | توضیحات | محدوده ارزش | مقدار پیش فرض |
---|---|---|---|
objectDetectorLiveStreamDelegate | آشکارساز شی را فعال می کند تا نتایج تشخیص را به صورت ناهمزمان در حالت پخش زنده دریافت کند. کلاسی که نمونه آن روی این ویژگی تنظیم شده است باید متد objectDetector(_:didFinishDetection:timestampInMilliseconds:error:) پیاده سازی کند. | قابل اجرا نیست | تنظیم نشده است |
داده ها را آماده کنید
قبل از ارسال آن به Object Detector باید تصویر یا فریم ورودی را به یک شی MPImage
تبدیل کنید. MPImage
از انواع فرمت های تصویر iOS پشتیبانی می کند و می تواند از آنها در هر حالت در حال اجرا برای استنتاج استفاده کند. برای اطلاعات بیشتر در مورد MPImage
، به MPImage API مراجعه کنید.
یک قالب تصویر iOS را بر اساس مورد استفاده خود و حالت اجرای مورد نیاز برنامه خود انتخاب کنید. MPImage
فرمتهای تصویر UIImage
، CVPixelBuffer
، و CMSampleBuffer
را میپذیرد.
تصویر UII
فرمت UIImage
برای حالتهای اجرای زیر مناسب است:
تصاویر: تصاویر از یک بسته نرم افزاری، گالری کاربر یا سیستم فایل فرمت شده به عنوان تصاویر
UIImage
را می توان به یک شیMPImage
تبدیل کرد.ویدیوها: از AVAssetImageGenerator برای استخراج فریم های ویدیو به فرمت CGImage استفاده کنید، سپس آنها را به تصاویر
UIImage
تبدیل کنید.
سویفت
// Load an image on the user's device as an iOS `UIImage` object. // Convert the `UIImage` object to a MediaPipe's Image object having the default // orientation `UIImage.Orientation.up`. let image = try MPImage(uiImage: image)
هدف-C
// Load an image on the user's device as an iOS `UIImage` object. // Convert the `UIImage` object to a MediaPipe's Image object having the default // orientation `UIImageOrientationUp`. MPImage *image = [[MPPImage alloc] initWithUIImage:image error:nil];
این مثال یک MPImage
با جهت پیشفرض UIImage.Orientation.Up مقداردهی اولیه میکند. می توانید یک MPImage
با هر یک از مقادیر UIImage.Orientation پشتیبانی شده مقداردهی کنید. آشکارساز شی از جهت گیری های آینه ای مانند .upMirrored
، .downMirrored
، .leftMirrored
، .rightMirrored
پشتیبانی نمی کند.
برای اطلاعات بیشتر در مورد UIImage
، به UIImage Apple Developer Documentation مراجعه کنید.
CVPixelBuffer
فرمت CVPixelBuffer
برای برنامه هایی که فریم تولید می کنند و از چارچوب CoreImage iOS برای پردازش استفاده می کنند، مناسب است.
فرمت CVPixelBuffer
برای حالتهای اجرای زیر مناسب است:
تصاویر: برنامههایی که تصاویر
CVPixelBuffer
پس از مدتی پردازش با استفاده از چارچوبCoreImage
iOS تولید میکنند، میتوانند در حالت اجرای تصویر به Object Detector ارسال شوند.فیلمها: فریمهای ویدیو را میتوان برای پردازش به فرمت
CVPixelBuffer
تبدیل کرد و سپس در حالت ویدیو به آشکارساز شی ارسال کرد.پخش زنده: برنامه هایی که از دوربین iOS برای تولید فریم استفاده می کنند ممکن است قبل از ارسال به Object Detector در حالت پخش زنده به فرمت
CVPixelBuffer
برای پردازش تبدیل شوند.
سویفت
// Obtain a CVPixelBuffer. // Convert the `CVPixelBuffer` object to a MediaPipe's Image object having the default // orientation `UIImage.Orientation.up`. let image = try MPImage(pixelBuffer: pixelBuffer)
هدف-C
// Obtain a CVPixelBuffer. // Convert the `CVPixelBuffer` object to a MediaPipe's Image object having the // default orientation `UIImageOrientationUp`. MPImage *image = [[MPPImage alloc] initWithUIImage:image error:nil];
برای اطلاعات بیشتر در مورد CVPixelBuffer
، به مستندات توسعه دهنده Apple CVPixelBuffer مراجعه کنید.
CMSampleBuffer
فرمت CMSampleBuffer
نمونههای رسانهای از یک نوع رسانه یکنواخت را ذخیره میکند و برای حالت پخش زنده مناسب است. قابهای زنده دوربینهای iOS بهصورت ناهمزمان در قالب CMSampleBuffer
توسط iOS AVCaptureVideoDataOutput ارائه میشوند.
سویفت
// Obtain a CMSampleBuffer. // Convert the `CMSampleBuffer` object to a MediaPipe's Image object having the default // orientation `UIImage.Orientation.up`. let image = try MPImage(sampleBuffer: sampleBuffer)
هدف-C
// Obtain a `CMSampleBuffer`. // Convert the `CMSampleBuffer` object to a MediaPipe's Image object having the // default orientation `UIImageOrientationUp`. MPImage *image = [[MPPImage alloc] initWithSampleBuffer:sampleBuffer error:nil];
برای اطلاعات بیشتر در مورد CMSampleBuffer
، به مستندات توسعه دهنده Apple CMSampleBuffer مراجعه کنید.
وظیفه را اجرا کنید
برای اجرای Object Detector، از متد detect()
مخصوص حالت در حال اجرا اختصاص داده شده استفاده کنید:
- تصویر ثابت:
detect(image:)
- ویدیو:
detect(videoFrame:timestampInMilliseconds:)
- پخش زنده:
detectAsync(image:)
نمونههای کد زیر نمونههای اساسی از نحوه اجرای Object Detector در این حالتهای مختلف اجرا را نشان میدهند:
سویفت
تصویر
let objectDetector.detect(image:image)
ویدئو
let objectDetector.detect(videoFrame:image)
پخش زنده
let objectDetector.detectAsync(image:image)
هدف-C
تصویر
MPPObjectDetectorResult *result = [objectDetector detectInImage:image error:nil];
ویدئو
MPPObjectDetectorResult *result = [objectDetector detectInVideoFrame:image timestampInMilliseconds:timestamp error:nil];
پخش زنده
BOOL success = [objectDetector detectAsyncInImage:image timestampInMilliseconds:timestamp error:nil];
مثال کد Object Detector پیاده سازی هر یک از این حالت ها را با جزئیات بیشتر detect(image:)
، detect(videoFrame:)
و detectAsync(image:)
نشان می دهد. کد مثال به کاربر اجازه می دهد تا بین حالت های پردازشی که ممکن است برای مورد استفاده شما مورد نیاز نباشد جابجا شود.
به موارد زیر توجه کنید:
هنگام اجرا در حالت ویدیو یا حالت پخش زنده، باید مهر زمانی فریم ورودی را نیز به وظیفه آشکارساز شی ارائه دهید.
هنگامی که در حالت تصویر یا ویدیو اجرا می شود، وظیفه آشکارساز شی، رشته فعلی را مسدود می کند تا زمانی که پردازش تصویر یا فریم ورودی به پایان برسد. برای جلوگیری از مسدود کردن رشته فعلی، پردازش را در یک رشته پسزمینه با استفاده از چارچوبهای iOS Dispatch یا NSOperation انجام دهید.
هنگامی که در حالت پخش زنده اجرا می شود، وظیفه آشکارساز شی بلافاصله برمی گردد و رشته فعلی را مسدود نمی کند. پس از پردازش هر فریم ورودی، متد
objectDetector(_objectDetector:didFinishDetection:timestampInMilliseconds:error:)
با نتیجه تشخیص فراخوانی می کند. Object Detector این روش را به صورت ناهمزمان در یک صف پخش سریال اختصاصی فراخوانی می کند. برای نمایش نتایج در رابط کاربری، پس از پردازش نتایج، نتایج را به صف اصلی ارسال کنید. اگر تابعdetectAsync
زمانی فراخوانی شود که وظیفه آشکارساز شی مشغول پردازش فریم دیگری است، آشکارساز شی فریم ورودی جدید را نادیده می گیرد.
کنترل و نمایش نتایج
پس از اجرای استنتاج، وظیفه آشکارساز شی یک شی ObjectDetectorResult
را برمی گرداند که اشیایی را که در تصویر ورودی پیدا کرده است، توصیف می کند.
شکل زیر نمونه ای از داده های خروجی از این کار را نشان می دهد:
ObjectDetectorResult:
Detection #0:
Box: (x: 355, y: 133, w: 190, h: 206)
Categories:
index : 17
score : 0.73828
class name : dog
Detection #1:
Box: (x: 103, y: 15, w: 138, h: 369)
Categories:
index : 17
score : 0.73047
class name : dog
تصویر زیر تصویری از خروجی کار را نشان می دهد:
کد مثالی Object Detector نحوه نمایش نتایج تشخیص برگشتی از کار را نشان می دهد، برای جزئیات به مثال کد مراجعه کنید.