ML Kit bietet zwei optimierte SDKs für die Posenerkennung.
SDK-Name | PoseDetection | PoseDetectionAccurate |
---|---|---|
Implementierung | Assets für Basisdetektoren sind beim Build statisch mit Ihrer Anwendung verknüpft. | Assets für genaue Detektoren sind beim Build statisch mit Ihrer App verknüpft. |
App-Größe | Bis zu 29,6 MB | Bis zu 33,2 MB |
Leistung | iPhone X: ~45 fps | iPhone X: ~29 fps |
Ausprobieren
- Probieren Sie die Beispiel-App aus, um ein Beispiel für die Verwendung dieser API zu sehen.
Hinweis
Fügen Sie die folgenden ML Kit-Pods in Ihre Podfile-Datei ein:
# If you want to use the base implementation: pod 'GoogleMLKit/PoseDetection', '3.2.0' # If you want to use the accurate implementation: pod 'GoogleMLKit/PoseDetectionAccurate', '3.2.0'
Nachdem Sie die Pods Ihres Projekts installiert oder aktualisiert haben, öffnen Sie Ihr Xcode-Projekt mit der
xcworkspace
. ML Kit wird in Xcode ab Version 13.2.1 unterstützt.
1. Instanz von PoseDetector
erstellen
Erstellen Sie zuerst eine Instanz von PoseDetector
und geben Sie optional die Detektoreinstellungen an, um eine Pose in einem Bild zu erkennen.
PoseDetector
Optionen
Erkennungsmodus
Das PoseDetector
funktioniert in zwei Erkennungsmodi. Wählen Sie unbedingt die Option aus, die zu Ihrem Anwendungsfall passt.
stream
(Standard)- Der Posendetektor erkennt zuerst die bekannteste Person auf dem Bild und führt dann die Posenerkennung durch. In nachfolgenden Frames wird die Personenerkennung nur dann ausgeführt, wenn die Person verdeckt wird oder nicht mehr mit hoher Zuverlässigkeit erkannt wird. Der Posendetektor versucht, die bekannteste Person zu verfolgen und ihre Pose in jeder Ableitung zurückzugeben. Dies reduziert die Latenz und sorgt für eine reibungslose Erkennung. Verwenden Sie diesen Modus, wenn Sie eine Pose in einem Videostream erkennen möchten.
singleImage
- Der Posendetektor erkennt eine Person und führt dann die Posenerkennung durch. Die Personenerkennung wird für jedes Bild ausgeführt, sodass die Latenz höher ist und es keine Personennachverfolgung gibt. Verwenden Sie diesen Modus, wenn Sie die Posenerkennung auf statischen Bildern verwenden oder wenn eine Nachverfolgung nicht erwünscht ist.
Geben Sie die Optionen für die Positionserkennung an:
Swift
// 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
Objective-C
// 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;
Rufen Sie abschließend eine Instanz von PoseDetector
ab. Übergeben Sie die angegebenen Optionen:
Swift
let poseDetector = PoseDetector.poseDetector(options: options)
Objective-C
MLKPoseDetector *poseDetector = [MLKPoseDetector poseDetectorWithOptions:options];
2. Eingabebild vorbereiten
Um Posen zu erkennen, gehen Sie für jedes Bild oder jeden Frame eines Videos wie folgt vor:
Wenn Sie den Streammodus aktiviert haben, müssen Sie VisionImage
-Objekte aus CMSampleBuffer
s erstellen.
Erstellen Sie mit UIImage
oder CMSampleBuffer
ein VisionImage
-Objekt.
Wenn du UIImage
verwendest, gehe so vor:
- Erstellen Sie mit der
UIImage
einVisionImage
-Objekt. Achte darauf, den richtigen.orientation
anzugeben.Swift
let image = VisionImage(image: UIImage) visionImage.orientation = image.imageOrientation
Objective-C
MLKVisionImage *visionImage = [[MLKVisionImage alloc] initWithImage:image]; visionImage.orientation = image.imageOrientation;
Wenn du CMSampleBuffer
verwendest, gehe so vor:
-
Geben Sie die Ausrichtung der Bilddaten an, die in
CMSampleBuffer
enthalten sind.So rufen Sie die Bildausrichtung ab:
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 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; } }
- Erstelle mit dem Objekt
CMSampleBuffer
und der Ausrichtung einVisionImage
-Objekt: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. Bild verarbeiten
Übergeben Sie die VisionImage
an eine der Bildverarbeitungsmethoden des Pose-Detektors. Sie können entweder die asynchrone process(image:)
-Methode oder die synchrone results()
-Methode verwenden.
So erkennen Sie Objekte synchron:
Swift
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.
Objective-C
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.
So erkennen Sie Objekte asynchron:
Swift
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. }
Objective-C
[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. }];
4. Informationen zur erkannten Pose abrufen
Wenn auf dem Bild eine Person erkannt wird, übergibt die Posenerkennungs-API entweder ein Array von Pose
-Objekten an den Abschluss-Handler oder gibt das Array zurück, je nachdem, ob Sie die asynchrone oder synchrone Methode aufgerufen haben.
Wenn sich die Person nicht vollständig im Bild befand, weist das Modell die fehlenden Markierungskoordinaten außerhalb des Frames zu und weist ihr niedrige InFrameConfidence-Werte zu.
Wenn keine Person gefunden wurde, ist das Array leer.
Swift
for pose in detectedPoses { let leftAnkleLandmark = pose.landmark(ofType: .leftAnkle) if leftAnkleLandmark.inFrameLikelihood > 0.5 { let position = leftAnkleLandmark.position } }
Objective-C
for (MLKPose *pose in detectedPoses) { MLKPoseLandmark *leftAnkleLandmark = [pose landmarkOfType:MLKPoseLandmarkTypeLeftAnkle]; if (leftAnkleLandmark.inFrameLikelihood > 0.5) { MLKVision3DPoint *position = leftAnkleLandmark.position; } }
Tipps zur Leistungsverbesserung
Die Qualität der Ergebnisse hängt von der Qualität des Eingabebilds ab:
- Damit das ML Kit die Pose genau erkennen kann, sollte die Person auf dem Bild durch genügend Pixeldaten repräsentiert sein. Für eine optimale Leistung sollte die Person mindestens 256 × 256 Pixel groß sein.
- Wenn Sie Posen in einer Echtzeitanwendung erkennen, sollten Sie auch die Gesamtabmessungen der Eingabebilder berücksichtigen. Kleinere Bilder können schneller verarbeitet werden. Um die Latenz zu verringern, sollten Sie Bilder mit geringerer Auflösung erfassen. Beachten Sie dabei jedoch die oben genannten Auflösungsanforderungen und achten Sie darauf, dass das Motiv so viel wie möglich auf dem Bild einnimmt.
- Ein schlechter Bildfokus kann sich auch auf die Genauigkeit auswirken. Wenn Sie keine akzeptablen Ergebnisse erhalten, bitten Sie den Nutzer, das Bild neu aufzunehmen.
Wenn Sie die Posenerkennung in einer Echtzeitanwendung verwenden möchten, beachten Sie die folgenden Richtlinien, um die besten Framerates zu erzielen:
- Verwende das PoseDetection SDK und den
stream
-Erkennungsmodus. - Nehmen Sie Bilder mit einer niedrigeren Auflösung auf. Beachten Sie jedoch auch die Anforderungen dieser API an die Bildabmessung.
- Verwenden Sie zum Verarbeiten von Videoframes die synchrone
results(in:)
API des Detektors. Rufen Sie diese Methode aus der Funktion captureOutput(_, didOutput:from:) von AVCaptureVideoDataOutputSampleBufferDelegate auf, um synchron Ergebnisse aus dem angegebenen Videoframe abzurufen. Belassen Sie das Feld alwaysDiscardsLateVideoFrames von AVCaptureVideoDataOutput auf „true“, um Aufrufe an den Detektor zu drosseln. Wenn ein neuer Videoframe verfügbar wird, während der Detektor ausgeführt wird, wird dieser gelöscht. - Wenn Sie die Ausgabe des Detektors verwenden, um Grafiken auf dem Eingabebild einzublenden, rufen Sie zuerst das Ergebnis aus dem ML Kit ab und rendern Sie dann das Bild und das Overlay in einem einzigen Schritt. Auf diese Weise rendern Sie für jeden verarbeiteten Eingabeframe nur einmal auf der Anzeigeoberfläche. Ein Beispiel hierfür finden Sie in der Showcase-Beispiel-App den Klassen previewOverlayView und MLKDetectionOverlayView.
Nächste Schritte
- Weitere Informationen zur Verwendung von Orientierungspunkten in Posen zum Klassifizieren von Posen finden Sie unter Tipps zur Körperklassifizierung.
- Im ML Kit-Schnellstartbeispiel auf GitHub finden Sie ein Beispiel für diese Verwendung der API.