Warhol

Swift Package Manager Carthage CocoaPods PRs Welcome Medium: @toupper

欢迎使用 Warhol — 一个用 Swift 编写的库,可以轻松实现 iOS 上的面部检测和顶部绘制。

Warhol 充当 Apple Vision Framework 的包装器,从相机或图像中检测面部特征,并在您自己的坐标中提供这些元素的位置,以便您可以轻松地在顶部绘制。忘记复杂的 Vision 或 AVFoundation 框架,只需处理封装了特征坐标的 Warhol Face View Model 类即可。

功能特点

系统要求

安装

CocoaPods

您可以使用 CocoaPods 安装 Warhol,方法是将其添加到您的 Podfile

platform :ios, '11.0'
use_frameworks!
pod 'Warhol'

为了获得完整益处,请在您使用的任何地方导入 Warhol

import Warhol

Carthage

Carthage 是一个去中心化的依赖管理器,它可以构建您的依赖项并为您提供二进制框架。要使用 Carthage 将 Alamofire 集成到您的 Xcode 项目中,请在您的 Cartfile 中指定它

github "toupper/Warhol" ~> 0.2.0

Swift Package Manager

Swift Package Manager 是一个用于自动化 Swift 代码分发的工具,并已集成到 swift 编译器中。它尚处于早期开发阶段,但 Alamofire 确实支持在受支持的平台上使用它。

一旦您设置好 Swift 包,添加 Warhol 作为依赖项就像将其添加到您的 Package.swiftdependencies 值中一样简单。

dependencies: [
    .package(url: "https://github.com/toupper/Warhol.git", .upToNextMajor(from: "0.2.0"))
]

手动

您也可以手动将 Warhol 集成到您的项目中。

嵌入式框架

使用示例

来自相机,在顶部绘制

在您要使用的文件中导入 Warhol。创建 CameraFaceDetectionViewController 的实例,并将您要绘制的视图分配给前者的 cameraFrontView 属性。然后您可以呈现视图控制器

import Warhol

let cameraViewController = CameraFaceDetectionViewController()
let faceView = FaceView()
faceView.backgroundColor = .clear
cameraViewController.cameraFrontView = faceView
present(cameraViewController, animated: true, completion: nil)

为了进行绘制,我们应该创建一个符合 Warhol 协议 FaceView 的 UIView 子类。然后我们可以在它们的 func draw(_ rect: CGRect) 函数中进行绘制。每当 Warhol 检测到面部变化时,它都会在视图上调用 setNeedsDisplay(),以便它可以触发绘制过程

import Warhol

final class FaceView: UIView, CameraFrontView {
  var viewModel: FaceViewModel?

  override func draw(_ rect: CGRect) {
    guard let context = UIGraphicsGetCurrentContext(),
          let viewModel = viewModel else {
      return
    }

    context.saveGState()

    defer {
      context.restoreGState()
    }

    context.addRect(viewModel.boundingBox)

    ...

来自相机,在面部特征上添加图像

FaceLayouts

如果您想在每个面部特征的顶部添加图像,您必须创建一个 FaceLayout 对象,为要绘制的每种面部地标类型定义一个 ImageLayout 对象。您可以为每个特征设置所需的偏移量和尺寸比率。一旦您有了它,您应该将其传递给 CameraFaceDetectionViewController 的 faceLayout 属性。请注意,如果您这样做,cameraFrontView 属性将被覆盖

let cameraViewController = CameraFaceDetectionViewController()

let leftEye = ImageLayout(image: UIImage(named: "leftEye")!, sizeRatio: SizeRatio(width: 1, height: 4))
let rightEye = ImageLayout(image: UIImage(named: "rightEye")!, sizeRatio: SizeRatio(width: 1, height: 4))
let nose = ImageLayout(image: UIImage(named: "nose")!)

let faceLayout = FaceLayout(landmarkLayouts: [.leftEye: leftEye,
                                                  .rightEye: rightEye,
                                                  .nose: nose])
cameraViewController.faceLayout = faceLayout

present(cameraViewController, animated: true, completion: nil)

除此之外,您可以实现 CameraFaceDetectionDelegate 协议来响应面部检测中的任何变化。当您不想在顶部绘制,而只想获取面部特征(地标)坐标时,这可能很方便。这些都封装在给定的参数 FaceViewModel 中。

来自图像

为了检测面部特征并在顶部绘制,我们应该将描绘面部的 UIImageView 传递给 sdk,并传递一个闭包,我们在闭包中在图像顶部绘制

import Warhol

imageView.image = UIImage(named: "Face")
Warhol.drawLandmarks(from: imageView,
                     draw: { (viewModel, context)  in
                      // draw with CGContext
                     },
                     error: {_ in })

如果您不想修改传递的图像,而是想生成一个新的 UIImageView 实例,请使用 drawLandmarksInNewImage

imageView.image = UIImage(named: "Face")
Warhol.drawLandmarksInNewImage(from: imageView,
                               draw: { (viewModel, context)  in
                                  self.draw(viewModel: viewModel, in: context)
                               },
                               completion: { newImage in
                                  self.newImageView.image = newImage
                               },
                               error: {_ in })

贡献

我们非常欢迎您为 Warhol 做出贡献,请查看 LICENSE 文件以获取更多信息。

鸣谢

César Vargas Casaseca 充满爱意地创建和维护。您可以在 Medium 上关注我 @toupper 以获取项目更新、版本发布和更多故事。

许可证

Warhol 在 MIT 许可证下发布。有关详细信息,请查看 LICENSE