【问题标题】:ARKit planeDectection continues even after setting planeDetection as empty即使将 planeDetection 设置为空,ARKit planeDetection 也会继续
【发布时间】:2018-06-09 14:42:26
【问题描述】:

在我的应用程序中,我使用 ARKit 的委托方法来自动检测表面/平面:

  1. renderer(_ renderer: SCNSceneRenderer, didAdd node: SCNNode, for anchor: ARAnchor) {} 添加飞机。
  2. renderer(_ renderer: SCNSceneRenderer, didUpdate node: SCNNode, for anchor: ARAnchor) {} 更新飞机。
  3. renderer(_ renderer: SCNSceneRenderer, didRemove node: SCNNode, for anchor: ARAnchor) {} 删除飞机。

我的配置设置为启用水平面检测:

configuration?.planeDetection = .horizontal

这工作正常,我能够检测并创建正在检测表面的平面节点。

这里有两个问题:

  1. 根据 Apple docs,如果我想停止水平平面检测,我应该能够将 planeDetection 设置为 []。在我试图做的一个按钮中,我将 planeDetection 设置为空,但是在运行应用程序时,仍然在应用程序中检测到平面。意思是,renderer(didAdd: )renderer(didUpdate: ) 方法仍然可以运行。为了确保我什至打印了他们的结果,并且即使在禁用 planeDetection 之后它们也可以运行。 我做错了吗?随意停止我的renderer(didAdd: )renderer(didUpdate: ) 方法的可靠方法是什么?

  2. 有时会在同一位置检测到两个平面。有时,这两个平面会合并,但有时它们不会合并。 就最佳实践而言,如何避免这种情况?我尝试检测场景的平截头体中是否已经存在 planeNode,不要添加新平面,但这也会带来一些问题,尤其是在添加了一个平面,但后来应该在同一位置添加另一个平面,后者是一个委托功能正在更新。在这种情况下,甚至没有添加后者,因为前者仍在我的视锥中。希望这很清楚。 只是想知道如何最好地避免/避免这种情况?

渲染器方法的主体是通常的:

func renderer(_ renderer: SCNSceneRenderer, didAdd node: SCNNode, for anchor: ARAnchor) {
    guard let planeAnchor = anchor as? ARPlaneAnchor else { return }
    let plane = SCNPlane(width: CGFloat(planeAnchor.extent.x),
                         height: CGFloat(planeAnchor.extent.z))
    ...
}

非常感谢指针。

注意:

我目前考虑管理这两个问题的方式是 引入将由按钮更改的 Bool - 这将决定 renderer(didAdd: ) 工作或停止工作的地方。 (我不会使用 Bool on renderer(didUpdate: ) 因为它需要更新已经 检测到的飞机。此外,我将使用 frustum 逻辑,以便 在一个地方只检测到一架飞机。最后,我会追踪 我的飞机正在更新的数量,如果没有达到 阈值,比如说 5,我将删除所有那些 更新无法从现场达到 5。这可能会增加一些 用户体验的稳定性,但我强烈认为这将 增加了比用户想要的更多的复杂性和更多的约束 有。

我的想法是否正确?伙计们,这里迫切需要一些更好的逻辑。

【问题讨论】:

  • 我认为您需要在更改其配置后再次在会话中调用run()
  • 天哪!我怎么能忘记这样做 :( 非常感谢,就是这样。我打电话给run() 并且它有效。关于我问题的第二部分的任何想法?
  • 我不确定这是否是最佳做法,但我前几天就你的第二个问题写了一个答案,你可以看看:stackoverflow.com/questions/47980670/arkit-floating-planes/…
  • 看了一下,试试这个逻辑。同时,如果您可以将您的两个 cmets 和 post and answer 结合起来,我会检查一下,因为实际上这两个组合构成了一个很好的答案。再次感谢!

标签: ios swift arkit


【解决方案1】:

1) 更改ARSession 的配置后,您需要再次调用run(_:options:) 方法才能使其工作。

2) 我不确定这是否是最佳做法,但您可以尝试通过执行以下操作手动检查平面是否重叠:

  • 将您的平面投影到 xz 平面上。由于 ARKit 只支持水平表面检测,这应该相当容易。
  • 使用 2D 碰撞检测方法检查您的飞机是否发生碰撞。
  • 如果高于某个平面阈值的部分发生碰撞,则删除其中一个碰撞平面。您可能还想检查两个平面在 3D 中是否足够接近。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-09-02
    • 2012-08-17
    • 2021-08-05
    • 2017-03-29
    • 1970-01-01
    相关资源
    最近更新 更多