Przewodnik po wykrywaniu obiektów w iOS

Zadanie Wykrywacz obiektów umożliwia wykrywanie obecności i lokalizacji wielu klas obiektów. Wykrywacz obiektów może na przykład zlokalizować psy w . Te instrukcje pokazują, jak korzystać z zadania Wykrywacz obiektów w systemie iOS. przykładowy kod opisany w tych instrukcjach jest dostępny na GitHub.

Aby zobaczyć, jak działa to zadanie, wejdź na tę stronę wersji demonstracyjnej. Dla: więcej informacji o możliwościach, modelach i opcjach konfiguracji tego zadania, zobacz Przegląd.

Przykładowy kod

Przykładowy kod MediaPipe Tasks to podstawowa implementacja obiektu Aplikacja do wykrywania treści na iOS. W tym przykładzie użyto aparatu w fizycznym urządzeniu z iOS, stale wykrywają obiekty, a także mogą używać obrazów i filmów z urządzenia do statycznego wykrywania obiektów.

Możesz użyć tej aplikacji jako punktu wyjścia dla własnej aplikacji na iOS lub skorzystać z niej podczas modyfikowania istniejącej aplikacji. Przykładowy kod wykrywania obiektów jest hostowany GitHub

Pobieranie kodu

Poniżej znajdziesz instrukcje tworzenia lokalnej kopii przykładu. za pomocą narzędzia wiersza poleceń git.

Aby pobrać przykładowy kod:

  1. Sklonuj repozytorium git za pomocą tego polecenia:

    git clone https://github.com/google-ai-edge/mediapipe-samples
    
  2. Opcjonalnie możesz skonfigurować instancję git tak, aby wykorzystywała rozproszony proces płatności, aby Tylko pliki przykładowej aplikacji Wykrywacz obiektów:

    cd mediapipe
    git sparse-checkout init --cone
    git sparse-checkout set examples/object_detection/ios/
    

Po utworzeniu lokalnej wersji przykładowego kodu możesz zainstalować w bibliotece zadań MediaPipe, otwórz projekt za pomocą Xcode i uruchom aplikację. Dla: instrukcje znajdziesz w Przewodniku po konfiguracji na iOS.

Kluczowe elementy

Poniższe pliki zawierają kluczowy kod z przykładowego narzędzia do wykrywania obiektów aplikacja:

Konfiguracja

W tej sekcji opisujemy najważniejsze czynności związane z konfigurowaniem środowiska programistycznego oraz w projektach kodu, w których mają być używane detektor obiektów. Ogólne informacje o konfigurowaniu środowisko programistyczne do używania zadań MediaPipe, w tym wersja platformy wymagania znajdziesz w przewodniku konfiguracji dla iOS.

Zależności

Wykrywacz obiektów używa biblioteki MediaPipeTasksVision, którą należy zainstalować za pomocą CocoaPods. Biblioteka jest zgodna z aplikacjami Swift i Objective-C. i nie wymaga żadnej dodatkowej konfiguracji.

Instrukcje instalowania CocoaPods w macOS znajdziesz w CocoaPods przewodnik instalacji. Aby dowiedzieć się, jak utworzyć Podfile z podami niezbędnymi dla Twojego aplikacji można znaleźć w sekcji Korzystanie CocoaPods.

Dodaj pod MediaPipeTasksVision w tabeli Podfile przy użyciu tego kodu:

target 'MyObjectDetectorApp' do
  use_frameworks!
  pod 'MediaPipeTasksVision'
end

Jeśli Twoja aplikacja zawiera cele testów jednostkowych, zapoznaj się z przewodnikiem po konfiguracji iOS, gdzie znajdziesz dodatkowe informacje o konfigurowaniu Podfile.

Model

Zadanie wykrywania obiektów MediaPipe wymaga wytrenowanego modelu, który jest zgodny w tym zadaniu. Aby uzyskać więcej informacji o dostępnych wytrenowanych modelach dla Wykrywacz obiektów, zobacz omówienie zadania Modele .

Wybierz i pobierz model, a następnie dodaj go do katalogu projektu za pomocą Xcode. Instrukcje dodawania plików do projektu Xcode znajdziesz w sekcji Zarządzanie pliki i foldery w Xcode projekt.

Użyj właściwości BaseOptions.modelAssetPath, aby określić ścieżkę do modelu w pakiecie aplikacji. Przykładowy kod znajdziesz w następnej sekcji.

Tworzenie zadania

Zadanie Wykrywacz obiektów możesz utworzyć, wywołując jeden z jego inicjatorów. Inicjator ObjectDetector(options:) ustawia wartości opcji konfiguracji w tym tryb biegania, ustawienia regionalne wyświetlanych nazw, maksymalna liczba wyników, poziom ufności próg, listę dozwolonych kategorii i listę odrzuconych.

Jeśli nie potrzebujesz wykrywacza obiektów zainicjowanego z niestandardową konfiguracją możesz użyć inicjatora ObjectDetector(modelPath:) do utworzenia Wykrywacz obiektów z opcjami domyślnymi. Więcej informacji o konfiguracji Więcej informacji znajdziesz w artykule Omówienie konfiguracji.

Zadanie Wykrywacz obiektów obsługuje 3 typy danych wejściowych: nieruchome obrazy i pliki wideo i transmisje wideo na żywo. Domyślnie ObjectDetector(modelPath:) inicjuje dla nieruchomych obrazów. Jeśli chcesz, aby zadanie zostało zainicjowane do przetworzenia filmu plików lub transmisji wideo na żywo, użyj właściwości ObjectDetector(options:), aby określić wideo. czy w trybie biegowym transmisji na żywo. Tryb transmisji na żywo wymaga również dodatkowych objectDetectorLiveStreamDelegate, która włącza Wykrywacz obiektów, który asynchronicznie dostarcza wyniki wykrywania do przedstawiciela.

Wybierz kartę odpowiadającą Twojemu trybowi biegowemu, aby zobaczyć, jak utworzyć zadanie i prowadź wnioskowanie.

Swift

Obraz

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)
    

Wideo

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)
    

transmisja na żywo

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)
    

Objective-C

Obraz

@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];
    

Wideo

@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];
    

transmisja na żywo

@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];
    

Opcje konfiguracji

To zadanie zawiera te opcje konfiguracji aplikacji na iOS:

Nazwa opcji Opis Zakres wartości Wartość domyślna
runningMode Ustawia tryb działania zadania. Są trzy tryby:

IMAGE: tryb wprowadzania pojedynczego obrazu.

WIDEO: tryb zdekodowanych klatek filmu.

LIVE_STREAM: tryb transmisji danych wejściowych na przykład z kamery. W tym trybie detektor wyników musi mieć wartość wywołano, aby skonfigurować detektor i otrzymywać wyniki asynchronicznie.
{RunningMode.image, RunningMode.video, RunningMode.liveStream} RunningMode.image
displayNamesLocales Ustawia język etykiet, które mają być używane w przypadku nazw wyświetlanych w kolumnie metadane modelu zadania, jeśli są dostępne. Wartość domyślna to en dla Angielski. Do metadanych modelu niestandardowego możesz dodać zlokalizowane etykiety za pomocą interfejsu TensorFlow Lite Metadata Writer API. Kod języka en
maxResults Ustawia opcjonalną maksymalną liczbę wyników wykrywania na . Dowolne liczby dodatnie -1 (zostaną zwrócone wszystkie wyniki)
scoreThreshold Ustawia próg wyniku prognozy, który zastępuje próg podany w polu metadane modelu (jeśli występują). Wyniki poniżej tej wartości zostały odrzucone. Dowolna liczba zmiennoprzecinkowa Nie ustawiono
categoryAllowlist Ustawia opcjonalną listę dozwolonych nazw kategorii. Jeśli pole nie jest puste, wyniki wykrywania, których nazwa kategorii nie znajduje się w tym zestawie, zostaną zostały odfiltrowane. Zduplikowane lub nieznane nazwy kategorii są ignorowane. Ta opcja nie działa z usługą categoryDenylist i korzysta z funkcji skutkuje to błędem. Dowolne ciągi Nie ustawiono
categoryDenylist Ustawia opcjonalną listę nazw kategorii, które nie są dozwolone. Jeśli niepuste, wyniki wykrywania, których nazwa kategorii znajduje się w tym zbiorze, zostaną odfiltrowane na zewnątrz. Zduplikowane lub nieznane nazwy kategorii są ignorowane. Ta opcja jest wzajemna tylko w polu categoryAllowlist, co spowoduje błąd. Dowolne ciągi Nie ustawiono

Konfiguracja transmisji na żywo

Gdy tryb działania jest ustawiony na transmisję na żywo, detektor obiektów wymaga parametru dodatkową opcję konfiguracji objectDetectorLiveStreamDelegate, która umożliwia detektorowi asynchroniczne dostarczanie wyników wykrywania. Delegat stosuje objectDetector(_objectDetector:didFinishDetection:timestampInMilliseconds:error:) która jest wywoływana przez Wykrywacz obiektów po przetworzeniu wyniku wykrywania każdej klatki.

Nazwa opcji Opis Zakres wartości Wartość domyślna
objectDetectorLiveStreamDelegate Włącza narzędzie do wykrywania obiektów na asynchroniczne otrzymywanie wyników wykrywania w w trybie transmisji na żywo. Klasa, której instancja jest ustawiona na tę właściwość, musi zastosuj objectDetector(_:didFinishDetection:timestampInMilliseconds:error:) . Nie dotyczy Nie ustawiono

Przygotuj dane

Musisz przekonwertować obraz lub ramkę wejściową na obiekt MPImage przed i przekazać go do wykrywania obiektów. MPImage obsługuje różne typy obrazów z iOS formatów i używać ich w dowolnym trybie działania do wnioskowania. Więcej informacje na temat marki MPImage znajdziesz w Interfejs MPImage API

Wybierz format obrazu na iOS na podstawie swojego przypadku użycia i trybu uruchamiania wymagane jest zgłoszenie.MPImage akceptuje UIImage, CVPixelBuffer i CMSampleBuffer Formaty obrazów w iOS.

UIImage

Format UIImage sprawdza się w tych trybach biegu:

  • Obrazy: obrazy z pakietu aplikacji, galerii użytkownika lub systemu plików w formacie Obrazy (UIImage) można przekonwertować na obiekt MPImage.

  • Filmy: użyj narzędzia AVAssetImageGenerator. aby wyodrębnić klatki wideo do CGImage a potem przekonwertuj je na UIImage obrazy.

Swift

// 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)
    

Objective-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];
    

Ten przykład inicjuje MPImage z domyślną wartością UIImage.Orientation.Up orientacji ekranu. Możesz zainicjować MPImage przy użyciu dowolnej z obsługiwanych UIImage.Orientation . Wykrywacz obiektów nie obsługuje lustrzanych orientacji, takich jak .upMirrored, .downMirrored, .leftMirrored, .rightMirrored.

Więcej informacji o UIImage znajdziesz na stronie UIImage dla deweloperów Apple Dokumentacja.

CVPixelBuffer

Format CVPixelBuffer sprawdza się w przypadku aplikacji generujących ramki. i zastosuj CoreImage na iOS platformy przetwarzania danych.

Format CVPixelBuffer sprawdza się w tych trybach biegu:

  • Obrazy: aplikacje, które po przetworzeniu generują CVPixelBuffer obrazy. za pomocą platformy CoreImage systemu iOS można wysłać do w trybie uruchamiania obrazu.

  • Filmy: klatki wideo można konwertować do formatu CVPixelBuffer dla a następnie przesłany do Wykrywacza obiektów w trybie wideo.

  • transmisja na żywo: aplikacje korzystające z aparatu w iOS do generowania klatek mogą być konwertowane w formacie CVPixelBuffer do przetworzenia przed wysłaniem do Wykrywacz obiektów w trybie transmisji na żywo.

Swift

// 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)
    

Objective-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];
    

Więcej informacji o CVPixelBuffer znajdziesz tutaj: CVPixelBuffer Apple Dla programistów Dokumentacja.

CMSampleBuffer

Format CMSampleBuffer przechowuje próbki multimediów jednolitego typu mediów i jest co sprawdza się w trybie biegowym transmisji na żywo. Klatki na żywo z aparatów z iOS są asynchronicznie dostarczone w formacie CMSampleBuffer przez iOS AVCaptureVideoDataOutput.

Swift

// 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)
    

Objective-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];
    

Więcej informacji o CMSampleBuffer znajdziesz tutaj: CMSampleBuffer Apple Dla programistów Dokumentacja.

Uruchamianie zadania

Aby uruchomić Wykrywacz obiektów, użyj metody detect() specyficznej dla przypisanej tryb działania:

  • Zdjęcie: detect(image:)
  • Film: detect(videoFrame:timestampInMilliseconds:)
  • transmisja na żywo: detectAsync(image:)

Poniżej znajdziesz przykładowy kod pokazujący, jak uruchomić Wykrywacz obiektów w różnych trybach:

Swift

Obraz

let objectDetector.detect(image:image)
    

Wideo

let objectDetector.detect(videoFrame:image)
    

transmisja na żywo

let objectDetector.detectAsync(image:image)
    

Objective-C

Obraz

MPPObjectDetectorResult *result = [objectDetector detectInImage:image error:nil];
    

Wideo

MPPObjectDetectorResult *result = [objectDetector detectInVideoFrame:image          timestampInMilliseconds:timestamp error:nil];
    

transmisja na żywo

BOOL success = [objectDetector detectAsyncInImage:image
                          timestampInMilliseconds:timestamp
                                            error:nil];
    

Przykładowy kod wykrywania obiektów pokazuje implementacje każdego z tych trybów więcej szczegółów: detect(image:), detect(videoFrame:) i detectAsync(image:) Przykładowy kod pozwala użytkownikowi przełączać się między tryby przetwarzania, które mogą nie być wymagane w Twoim przypadku użycia.

Pamiętaj:

  • Korzystając z trybu wideo lub transmisji na żywo, musisz też podać: sygnatura czasowa ramki wejściowej zadania Wykrywacz obiektów.

  • W trybie obrazu lub filmu zadanie Wykrywacz obiektów blokuje w bieżącym wątku aż do zakończenia przetwarzania obrazu lub ramki wejściowej. Do unikaj blokowania bieżącego wątku, uruchamiaj przetwarzanie w tle w iOS na iOS Dispatch lub NSOperation zasad.

  • W przypadku działania w trybie transmisji na żywo zadanie Wykrywacz obiektów jest natychmiast przywracane i nie blokuje bieżącego wątku. Wywołuje on metodę objectDetector(_objectDetector:didFinishDetection:timestampInMilliseconds:error:) z wynikiem wykrywania po przetworzeniu każdej ramki wejściowej. Wykrywacz obiektów asynchronicznie wywołuje tę metodę w dedykowanym kolejki wysyłki. Aby wyświetlić wyniki w interfejsie, użyj polecenia do głównej kolejki po przetworzeniu wyników. Jeśli detectAsync jest wywoływana, gdy zadanie Wykrywacz obiektów jest zajęte przetwarzaniem innej , detektor obiektów zignoruje nową ramkę wejściową.

Obsługa i wyświetlanie wyników

Po uruchomieniu wnioskowania zadanie Wykrywacz obiektów zwraca błąd ObjectDetectorResult opisujący obiekty znalezione na obrazie wejściowym.

Poniżej znajdziesz przykładowe dane wyjściowe tego zadania:

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

Ten obraz przedstawia wizualizację danych wyjściowych zadania:

Przykładowy kod wykrywania obiektów pokazuje, jak wyświetlić wyniki wykrywania zwróconych przez zadanie, szczegółowe informacje znajdziesz w przykładowym kodzie.