ios - 如何从 VNFaceObservation 边界框(Vision + ARKit)正确平移 X 轴

标签 ios swift computer-vision arkit apple-vision

我正在使用 ARKit 和 Vision,遵循 Apple 的示例项目“通过 ARKit 实时使用视觉”。所以我不会设置相机,因为 ARKit 会帮我处理。

使用 Vision 的 VNDetectFaceRectanglesRequest,我能够取回 VNFaceObservation 对象的集合。

按照各种在线指南,我能够将 VNFaceObservation 的边界框转换为可以在 ViewController 的 UIView 上使用的边界框。

当放置在 ARKit 中的 UIView 上时,Y 轴是正确的,但 X 轴完全关闭且不准确。

// face is an instance of VNFaceObservation  
let transform = CGAffineTransform(scaleX: 1, y: -1).translatedBy(x: 0, y: -view.frame.height)  
let translate = CGAffineTransform.identity.scaledBy(x: view.frame.width, y: view.frame.height)  
let rect = face.boundingBox.applying(translate).applying(transform)  

在屏幕上(在 ARKit/UIKit 中)显示边界框以使 X 和 Y 轴与检测到的面部矩形正确匹配的正确方法是什么?我无法使用self.cameraLayer.layerRectConverted(fromMetadataOutputRect: transformedRect)因为我没有使用 AVCaptureSession。


更新:进一步深入研究,相机的图像为 1920 x 1440。其中大部分不会显示在 ARKit 的屏幕空间上。 iPhone XS 屏幕为 375 x 812 点。

获得 Vision 的观察边界框后,我将其转换为适合当前 View (375 x 812)。这是行不通的,因为实际宽度似乎是 500(左侧和右侧超出了屏幕 View )。我该怎么办CGAffineTransform 375x812 的 CGRect 边界框(看起来像 500x812,完全猜测)?

最佳答案

这里缺少的关键部分是 ARFrame 的 displayTransform(for:viewportSize:)。您可以阅读它的文档 here .

此函数将为给定的帧和视口(viewport)大小(显示图像和边界框的 View 的 CGRect)生成适当的变换。

func visionTransform(frame: ARFrame, viewport: CGRect) -> CGAffineTransform {
    let orientation = UIApplication.shared.statusBarOrientation
    let transform = frame.displayTransform(for: orientation,
                                           viewportSize: viewport.size)
    let scale = CGAffineTransform(scaleX: viewport.width,
                                  y: viewport.height)

    var t = CGAffineTransform()
    if orientation.isPortrait {
        t = CGAffineTransform(scaleX: -1, y: 1)
        t = t.translatedBy(x: -viewport.width, y: 0)
    } else if orientation.isLandscape {
        t = CGAffineTransform(scaleX: 1, y: -1)
        t = t.translatedBy(x: 0, y: -viewport.height)
    }

    return transform.concatenating(scale).concatenating(t)
}

然后您可以像这样使用它:

let transform = visionTransform(frame: yourARFrame, viewport: yourViewport)
let rect = face.boundingBox.applying(transform)

关于ios - 如何从 VNFaceObservation 边界框(Vision + ARKit)正确平移 X 轴,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54061482/

相关文章:

computer-vision - track和tracklet在tracking上有什么区别?

opencv - 查找 ORB 特征描述符之间的汉明距离

image - 如何删除图像中的非条形码区域? - MATLAB

ios - 以编程方式向 UITableview 添加 header

ios - 从 appdelegate 设置 UIViewController 委托(delegate)

ios - 如何在 Swift 中使用 Codable 协议(protocol)进行解码时进行区分?

ios - 幽灵 View Controller

iOS - 如何在 View Controller 中设置导航栏项目?

ios - 以编程方式在 Sprite 的框架内创建一个区域

ios - 标签栏可以包含 "play"按钮吗