Skip to content

Commit

Permalink
add delegate to face detector (#353)
Browse files Browse the repository at this point in the history
  • Loading branch information
st-tuanmai authored Mar 25, 2024
1 parent 252a41d commit 644b31e
Show file tree
Hide file tree
Showing 10 changed files with 131 additions and 47 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
7F7641A72A74865000DDCE4E /* testImg.jpeg in Resources */ = {isa = PBXBuildFile; fileRef = BFCF187A2A43E0F200D64FA6 /* testImg.jpeg */; };
A62955674D0B99A7D0E9C379 /* libPods-FaceDetectorTests.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 4CD418693247CFB204F2604A /* libPods-FaceDetectorTests.a */; };
BFCDADF02A9DD64200EC4371 /* DefaultConstants.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFCDADE22A9DD64200EC4371 /* DefaultConstants.swift */; };
BFCDADF12A9DD64200EC4371 /* InferenceConfigManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFCDADE32A9DD64200EC4371 /* InferenceConfigManager.swift */; };
BFCDADF12A9DD64200EC4371 /* InferenceConfigurationManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFCDADE32A9DD64200EC4371 /* InferenceConfigurationManager.swift */; };
BFCDADF22A9DD64200EC4371 /* CameraFeedService.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFCDADE52A9DD64200EC4371 /* CameraFeedService.swift */; };
BFCDADF32A9DD64200EC4371 /* FaceDetectorService.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFCDADE62A9DD64200EC4371 /* FaceDetectorService.swift */; };
BFCDADF52A9DD64200EC4371 /* MediaLibraryViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = BFCDADE92A9DD64200EC4371 /* MediaLibraryViewController.swift */; };
Expand Down Expand Up @@ -44,7 +44,7 @@
7F7641A92A74869900DDCE4E /* download_models.sh */ = {isa = PBXFileReference; lastKnownFileType = text.script.sh; path = download_models.sh; sourceTree = "<group>"; };
BB9395FBA7FB71903009034C /* Pods-FaceDetectorTests.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-FaceDetectorTests.debug.xcconfig"; path = "Target Support Files/Pods-FaceDetectorTests/Pods-FaceDetectorTests.debug.xcconfig"; sourceTree = "<group>"; };
BFCDADE22A9DD64200EC4371 /* DefaultConstants.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = DefaultConstants.swift; sourceTree = "<group>"; };
BFCDADE32A9DD64200EC4371 /* InferenceConfigManager.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = InferenceConfigManager.swift; sourceTree = "<group>"; };
BFCDADE32A9DD64200EC4371 /* InferenceConfigurationManager.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = InferenceConfigurationManager.swift; sourceTree = "<group>"; };
BFCDADE52A9DD64200EC4371 /* CameraFeedService.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CameraFeedService.swift; sourceTree = "<group>"; };
BFCDADE62A9DD64200EC4371 /* FaceDetectorService.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = FaceDetectorService.swift; sourceTree = "<group>"; };
BFCDADE92A9DD64200EC4371 /* MediaLibraryViewController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MediaLibraryViewController.swift; sourceTree = "<group>"; };
Expand Down Expand Up @@ -120,7 +120,7 @@
isa = PBXGroup;
children = (
BFCDADE22A9DD64200EC4371 /* DefaultConstants.swift */,
BFCDADE32A9DD64200EC4371 /* InferenceConfigManager.swift */,
BFCDADE32A9DD64200EC4371 /* InferenceConfigurationManager.swift */,
);
path = Configs;
sourceTree = "<group>";
Expand Down Expand Up @@ -379,7 +379,7 @@
BFCDADF32A9DD64200EC4371 /* FaceDetectorService.swift in Sources */,
BFCDADF82A9DD64200EC4371 /* CameraViewController.swift in Sources */,
BFCF18342A415B9300D64FA6 /* SceneDelegate.swift in Sources */,
BFCDADF12A9DD64200EC4371 /* InferenceConfigManager.swift in Sources */,
BFCDADF12A9DD64200EC4371 /* InferenceConfigurationManager.swift in Sources */,
BFCDADFA2A9DD64200EC4371 /* OverlayView.swift in Sources */,
BFCDADF22A9DD64200EC4371 /* CameraFeedService.swift in Sources */,
BFCDADF52A9DD64200EC4371 /* MediaLibraryViewController.swift in Sources */,
Expand Down
47 changes: 45 additions & 2 deletions examples/face_detector/ios/FaceDetector/Base.lproj/Main.storyboard
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
<?xml version="1.0" encoding="UTF-8"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="21701" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES" initialViewController="52l-qN-uG0">
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="32700.99.1234" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES" initialViewController="52l-qN-uG0">
<device id="retina6_12" orientation="portrait" appearance="light"/>
<dependencies>
<deployment identifier="iOS"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="21679"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="22684"/>
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
<capability name="System colors in document resources" minToolsVersion="11.0"/>
<capability name="UIMenu" message="Requires Xcode 11 or later." minToolsVersion="11.0" requiredIntegratedClassName="UICommandDiff"/>
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
</dependencies>
<scenes>
Expand Down Expand Up @@ -206,6 +207,44 @@
<nil key="textColor"/>
<nil key="highlightedColor"/>
</label>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="nRu-cG-Fy4">
<rect key="frame" x="0.0" y="176.66666666666666" width="393" height="32"/>
<subviews>
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Delegate" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="7vU-t5-LVI">
<rect key="frame" x="16" y="7.3333333333333428" width="58" height="17"/>
<fontDescription key="fontDescription" type="system" pointSize="14"/>
<nil key="textColor"/>
<nil key="highlightedColor"/>
</label>
<button opaque="NO" contentMode="scaleToFill" showsMenuAsPrimaryAction="YES" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="system" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="FiN-El-KVZ">
<rect key="frame" x="353" y="0.0" width="24" height="32"/>
<color key="backgroundColor" red="0.0" green="0.49803921569999998" blue="0.5450980392" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<constraints>
<constraint firstAttribute="height" constant="32" id="ZSW-M2-eKC"/>
</constraints>
<color key="tintColor" white="0.0" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
<menu key="menu" id="oF2-hQ-zDM">
<children>
<command title="item1" id="TKP-RH-SiW"/>
<command title="item2" id="cJE-0O-pyI"/>
</children>
</menu>
<buttonConfiguration key="configuration" style="plain"/>
<userDefinedRuntimeAttributes>
<userDefinedRuntimeAttribute type="string" keyPath="layer.cornerRadius" value="8"/>
</userDefinedRuntimeAttributes>
</button>
</subviews>
<color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
<constraints>
<constraint firstItem="FiN-El-KVZ" firstAttribute="top" secondItem="nRu-cG-Fy4" secondAttribute="top" id="9Sa-fI-gtK"/>
<constraint firstItem="FiN-El-KVZ" firstAttribute="leading" relation="greaterThanOrEqual" secondItem="7vU-t5-LVI" secondAttribute="trailing" id="FJY-qx-gTm"/>
<constraint firstItem="7vU-t5-LVI" firstAttribute="leading" secondItem="nRu-cG-Fy4" secondAttribute="leading" constant="16" id="XjJ-IN-6GZ"/>
<constraint firstItem="7vU-t5-LVI" firstAttribute="centerY" secondItem="FiN-El-KVZ" secondAttribute="centerY" id="bAt-tP-n2q"/>
<constraint firstAttribute="trailing" secondItem="FiN-El-KVZ" secondAttribute="trailing" constant="16" id="ba7-C4-rMo"/>
<constraint firstAttribute="bottom" secondItem="FiN-El-KVZ" secondAttribute="bottom" id="c2a-aM-LzC"/>
</constraints>
</view>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="tZo-oH-ToE">
<rect key="frame" x="0.0" y="0.0" width="393" height="1"/>
<color key="backgroundColor" red="0.070588235289999995" green="0.70980392160000005" blue="0.79607843140000001" alpha="0.84705882349999995" colorSpace="calibratedRGB"/>
Expand All @@ -221,10 +260,12 @@
<constraint firstItem="0nH-Zx-p69" firstAttribute="leading" secondItem="s05-yK-gXh" secondAttribute="trailing" constant="4" id="Bda-ye-Je2"/>
<constraint firstItem="cRO-ho-FXh" firstAttribute="centerY" secondItem="d2C-9O-82c" secondAttribute="centerY" id="MKa-V2-38z"/>
<constraint firstItem="0Hl-aV-l7w" firstAttribute="leading" secondItem="AOI-Gh-SLK" secondAttribute="leading" id="OQf-RZ-3g1"/>
<constraint firstItem="nRu-cG-Fy4" firstAttribute="leading" secondItem="AOI-Gh-SLK" secondAttribute="leading" id="OqS-hg-kEr"/>
<constraint firstItem="0nH-Zx-p69" firstAttribute="trailing" secondItem="cRO-ho-FXh" secondAttribute="trailing" id="S6M-bn-pkr"/>
<constraint firstItem="tZo-oH-ToE" firstAttribute="leading" secondItem="AOI-Gh-SLK" secondAttribute="leading" id="SpH-HP-7sh"/>
<constraint firstItem="0nH-Zx-p69" firstAttribute="trailing" secondItem="7MT-s0-Gcl" secondAttribute="trailing" id="TTU-rx-1TT"/>
<constraint firstItem="7MT-s0-Gcl" firstAttribute="top" secondItem="0nH-Zx-p69" secondAttribute="bottom" constant="12" id="VZ7-YN-QtR"/>
<constraint firstAttribute="trailing" secondItem="nRu-cG-Fy4" secondAttribute="trailing" id="XyY-G0-mqn"/>
<constraint firstItem="iaZ-s2-My0" firstAttribute="leading" secondItem="AOI-Gh-SLK" secondAttribute="leading" constant="16" id="a2w-hd-0Jy"/>
<constraint firstItem="cRO-ho-FXh" firstAttribute="leading" relation="greaterThanOrEqual" secondItem="d2C-9O-82c" secondAttribute="trailing" id="aYp-dR-YLG"/>
<constraint firstItem="s05-yK-gXh" firstAttribute="leading" relation="greaterThanOrEqual" secondItem="iaZ-s2-My0" secondAttribute="trailing" id="axL-QV-mDy"/>
Expand All @@ -236,6 +277,7 @@
<constraint firstItem="d2C-9O-82c" firstAttribute="top" secondItem="0Hl-aV-l7w" secondAttribute="bottom" constant="12" id="mcI-24-pk6"/>
<constraint firstItem="iaZ-s2-My0" firstAttribute="centerY" secondItem="0nH-Zx-p69" secondAttribute="centerY" id="o81-hG-imF"/>
<constraint firstItem="iaZ-s2-My0" firstAttribute="top" secondItem="d2C-9O-82c" secondAttribute="bottom" constant="26" id="pPe-bR-0qO"/>
<constraint firstItem="nRu-cG-Fy4" firstAttribute="top" secondItem="7MT-s0-Gcl" secondAttribute="bottom" constant="12" id="q0O-NW-Vg1"/>
<constraint firstItem="0Hl-aV-l7w" firstAttribute="top" secondItem="AOI-Gh-SLK" secondAttribute="top" id="rl8-eu-Q06"/>
<constraint firstAttribute="trailing" secondItem="tZo-oH-ToE" secondAttribute="trailing" id="xSe-Ss-8WB"/>
<constraint firstItem="tZo-oH-ToE" firstAttribute="top" secondItem="AOI-Gh-SLK" secondAttribute="top" id="yoR-Hn-w9J"/>
Expand All @@ -255,6 +297,7 @@
</view>
<navigationItem key="navigationItem" id="BIS-1q-gQH"/>
<connections>
<outlet property="delegateButton" destination="FiN-El-KVZ" id="tQD-B4-WXx"/>
<outlet property="inferenceTimeLabel" destination="cRO-ho-FXh" id="E3e-km-74r"/>
<outlet property="inferenceTimeNameLabel" destination="d2C-9O-82c" id="O7p-Pr-lsE"/>
<outlet property="minDetectionConfidenceStepper" destination="0nH-Zx-p69" id="HHj-CU-SVz"/>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@

import Foundation
import UIKit
import MediaPipeTasksVision

// MARK: Define default constants
struct DefaultConstants {
Expand All @@ -34,4 +35,5 @@ struct DefaultConstants {
static let ovelayColor = UIColor(red: 0, green: 127/255.0, blue: 139/255.0, alpha: 1)
static let displayFont = UIFont.systemFont(ofSize: 14.0, weight: .medium)
static let modelPath: String? = Bundle.main.path(forResource: "blaze_face_short_range", ofType: "tflite")
static let delegate: Delegate = .CPU
}
Original file line number Diff line number Diff line change
Expand Up @@ -13,12 +13,13 @@
// limitations under the License.

import Foundation
import MediaPipeTasksVision

/**
* Singleton storing the configs needed to initialize an MediaPipe Tasks object and run inference.
* Controllers can observe the `InferenceConfigManager.notificationName` for any changes made by the user.
*/
class InferenceConfigManager: NSObject {
class InferenceConfigurationManager: NSObject {
var modelPath: String? = DefaultConstants.modelPath

var minSuppressionThreshold: Float = DefaultConstants.minSuppressionThreshold {
Expand All @@ -29,13 +30,17 @@ class InferenceConfigManager: NSObject {
didSet { postConfigChangedNotification() }
}

static let sharedInstance = InferenceConfigManager()
var delegate: Delegate = DefaultConstants.delegate {
didSet { postConfigChangedNotification() }
}

static let sharedInstance = InferenceConfigurationManager()

static let notificationName = Notification.Name.init(rawValue: "com.google.mediapipe.inferenceConfigChanged")

private func postConfigChangedNotification() {
NotificationCenter.default
.post(name: InferenceConfigManager.notificationName, object: nil)
.post(name: InferenceConfigurationManager.notificationName, object: nil)
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -46,15 +46,17 @@ class FaceDetectorService: NSObject {
private(set) var runningMode = RunningMode.image
private var minDetectionConfidence: Float = 0.5
private var minSuppressionThreshold: Float = 0.5
var modelPath: String
private var modelPath: String
private var delegate: Delegate

// MARK: - Custom Initializer
private init?(modelPath: String?, minDetectionConfidence: Float, minSuppressionThreshold: Float, runningMode:RunningMode) {
private init?(modelPath: String?, minDetectionConfidence: Float, minSuppressionThreshold: Float, runningMode:RunningMode, delegate: Delegate) {
guard let modelPath = modelPath else { return nil }
self.modelPath = modelPath
self.minDetectionConfidence = minDetectionConfidence
self.minSuppressionThreshold = minSuppressionThreshold
self.runningMode = runningMode
self.delegate = delegate
super.init()

createFaceDetector()
Expand All @@ -63,9 +65,10 @@ class FaceDetectorService: NSObject {
private func createFaceDetector() {
let faceDetectorOptions = FaceDetectorOptions()
faceDetectorOptions.runningMode = runningMode
faceDetectorOptions.minDetectionConfidence = self.minDetectionConfidence
faceDetectorOptions.minSuppressionThreshold = self.minSuppressionThreshold
faceDetectorOptions.minDetectionConfidence = minDetectionConfidence
faceDetectorOptions.minSuppressionThreshold = minSuppressionThreshold
faceDetectorOptions.baseOptions.modelAssetPath = modelPath
faceDetectorOptions.baseOptions.delegate = delegate
if runningMode == .liveStream {
faceDetectorOptions.faceDetectorLiveStreamDelegate = self
}
Expand All @@ -82,12 +85,14 @@ class FaceDetectorService: NSObject {
modelPath: String?,
minDetectionConfidence: Float,
minSuppressionThreshold: Float,
videoDelegate: FaceDetectorServiceVideoDelegate?) -> FaceDetectorService? {
videoDelegate: FaceDetectorServiceVideoDelegate?,
delegate: Delegate) -> FaceDetectorService? {
let faceDetectorService = FaceDetectorService(
modelPath: modelPath,
minDetectionConfidence: minDetectionConfidence,
minSuppressionThreshold: minSuppressionThreshold,
runningMode: .video)
runningMode: .video,
delegate: delegate)
faceDetectorService?.videoDelegate = videoDelegate

return faceDetectorService
Expand All @@ -97,12 +102,14 @@ class FaceDetectorService: NSObject {
modelPath: String?,
minDetectionConfidence: Float,
minSuppressionThreshold: Float,
liveStreamDelegate: FaceDetectorServiceLiveStreamDelegate?) -> FaceDetectorService? {
liveStreamDelegate: FaceDetectorServiceLiveStreamDelegate?,
delegate: Delegate) -> FaceDetectorService? {
let faceDetectorService = FaceDetectorService(
modelPath: modelPath,
minDetectionConfidence: minDetectionConfidence,
minSuppressionThreshold: minSuppressionThreshold,
runningMode: .liveStream)
runningMode: .liveStream,
delegate: delegate)
faceDetectorService?.liveStreamDelegate = liveStreamDelegate

return faceDetectorService
Expand All @@ -111,12 +118,14 @@ class FaceDetectorService: NSObject {
static func stillImageDetectorService(
modelPath: String?,
minDetectionConfidence: Float,
minSuppressionThreshold: Float) -> FaceDetectorService? {
minSuppressionThreshold: Float,
delegate: Delegate) -> FaceDetectorService? {
let faceDetectorService = FaceDetectorService(
modelPath: modelPath,
minDetectionConfidence: minDetectionConfidence,
minSuppressionThreshold: minSuppressionThreshold,
runningMode: .image)
runningMode: .image,
delegate: delegate)

return faceDetectorService
}
Expand Down
Loading

0 comments on commit 644b31e

Please sign in to comment.