我已经搜索了所有的文档,可能只是缺少一些非常重要的东西.像iPad Pro那样的前置True Depth摄像头是否可以使用光线投射?

我目前正在做一个应用程序,我在ARFaceTrackingConfiguration中,从屏幕中心进行简单的光线投射没有产生结果.

在World Configuration中使用后置摄像头的相同代码正在产生结果.这段代码是直接从文档中获取的.

let raycastQuery: ARRaycastQuery? = sceneView.raycastQuery(
                                                      from: sceneView.center,
                                                  allowing: .estimatedPlane,
                                                 alignment: .any)

let rayresults: [ARRaycastResult] = sceneView.session.raycast(raycastQuery!)
print(rayresults)

给出背景模糊的人脸跟踪深度图的例子,我的理解是,前置摄像头的深度数据基本上与后置摄像头相同,只是可用的总深度距离较小.

由于此代码在后置相机上返回结果集,但在前置相机上不返回结果,我想知道这是否与光线的方向有关?对于前置摄影机,如果支持rayCast,可能需要将光线投射到负z方向?但我在那里并没有取得成功.

该项目的目标是能够在3D空间中获得2点之间的距离,但使用前置摄像头而不是后置摄像头.

谢谢你纠正我的错误!我很感激.

推荐答案

ARFaceTrackingConfig的命中测试

显然,基于World跟踪配置的用于检测到的飞机的ARKit光线投射方法不适用于人脸跟踪场景.在您的情况下,您需要使用SceneKit的命中测试.对于命中测试,你不能使用estimatedPlane,你需要canonical face mask.当使用前置摄像头时,XZ坐标是绝对正确的--XZ平面是mirrored.同样值得注意的是,这款相机的红外TrueDepth传感器在10到mirrored厘米的距离内"工作".ARFaceAnchor仅在此范围内生成.

在iPad Pro上的Swift Playgrounds应用中运行此代码.

import ARKit
import SceneKit
import PlaygroundSupport

class ViewController : UIViewController {
    var sceneView = ARSCNView(frame: .zero)
    
    override func viewDidLoad() {
        super.viewDidLoad()
        self.view = self.sceneView
        sceneView.delegate = self
        sceneView.scene = SCNScene()
        
        let config = ARFaceTrackingConfiguration()
        config.maximumNumberOfTrackedFaces = 1
        sceneView.session.run(config)
    }
}

extension ViewController {       
    override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {
        let location: CGPoint? = touches.first?.location(in: sceneView)
                                            
        var hitTestOptions = [SCNHitTestOption: Any]()
        hitTestOptions[.boundingBoxOnly] = true
                                            
        let hitTestResults: [SCNHitTestResult] = sceneView.hitTest(location!, 
                                                   options: hitTestOptions)
                    
        guard let hit = hitTestResults.first else { return }
                                        
        let sphere = SCNNode(geometry: SCNSphere(radius: 0.005))
        sphere.simdPosition = hit.simdWorldCoordinates
        sceneView.scene.rootNode.addChildNode(sphere)            
    }
}

extension ViewController : ARSCNViewDelegate {
    func renderer(_ renderer: SCNSceneRenderer, nodeFor anchor: ARAnchor) -> SCNNode? {
        let faceGeo = ARSCNFaceGeometry(device: sceneView.device!)
        let node = SCNNode(geometry: faceGeo)
        node.geometry?.firstMaterial?.lightingModel = .physicallyBased
        node.geometry?.firstMaterial?.diffuse.contents = UIColor.green
        return node
    }
    func renderer(_ renderer: SCNSceneRenderer, didUpdate node: SCNNode,
                                                    for anchor: ARAnchor) {    
        if let faceAnchor = anchor as? ARFaceAnchor,
           let faceGeo = node.geometry as? ARSCNFaceGeometry {
            faceGeo.update(from: faceAnchor.geometry)
        }
    }
}

PlaygroundPage.current.needsIndefiniteExecution = true
PlaygroundPage.current.liveView = ViewController()

Swift相关问答推荐

如何在Swift中获得与Python相同的HMAC—SHA512签名?

如何在realityKit中反转USDZ动画

有没有一种方法可以迭代可编码的代码(例如,JSON解析中的每一项)?

仅使用@MainActor注释类的部分时的并发问题

SWIFT:使字典数组值可变

根据其属性组合 2 个模型以在 Swift 中创建另一个模型

列表不显示信息

数组中某些元素的总和

快速更改tableView中的数据

SwiftUI:当先前的视图列表更改时,NavigationView 详细视图会弹出回栈

无法增加系统镜像的大小

Reality Composer Tap Trigger 问题

如何防止 UITableViewCell 移动(Swift 5)

Alamofire 会自动存储 cookie 吗?

Xcode 6 中的嵌入式内容包含 Swift 代码构建设置有什么作用?

在 Xcode 中自动实现 Swift 协议方法

Swift 覆盖实例变量

Swift :如何在一组字符之后得到所有东西

如何在 Swift 中将 NSURL 转换为字符串

从 Swift 初始化程序调用方法