如何保持 ARKit SCNNode 就位

2024-02-07

嘿,我正在想办法。如何保持简单节点的位置。当我在 ARKit 中绕着它走动时

Code:

 func renderer(_ renderer: SCNSceneRenderer, didAdd node: SCNNode, for anchor: ARAnchor) {

    if let planeAnchor = anchor as? ARPlaneAnchor {

    if planeDetected == false { // Bool only allows 1 plane to be added
            planeDetected = true
        self.addPlane(node: node, anchor: planeAnchor)
    }

    }
}

这会添加 SCNNode

    func addPlane(node: SCNNode, anchor: ARPlaneAnchor) {

    // We add the anchor plane here

    let showDebugVisuals = Bool()
    let plane = Plane(anchor, showDebugVisuals)
    planes[anchor] = plane
    node.addChildNode(plane)



    // We add our custom SCNNode here 

    let scene = SCNScene(named: "art.scnassets/PlayerModel.scn")!
    let Body = scene.rootNode.childNode(withName: "Body", recursively: true)!

    Body.position = SCNVector3.positionFromTransform(anchor.transform)
    Body.movabilityHint = .movable
    wrapperNode.position = SCNVector3.positionFromTransform(anchor.transform)

    wrapperNode.addChildNode(Body)

    scnView.scene.rootNode.addChildNode(wrapperNode)

我尝试添加一个平面/锚节点并将“主体”节点放入其中,但它仍然会移动。我想这可能与更新功能有关。

 func renderer(_ renderer: SCNSceneRenderer, didUpdate node: SCNNode, for anchor: ARAnchor) {
 }

Or最有可能的是位置设置

wrapperNode.position = SCNVector3.positionFromTransform(anchor.transform)

我查看了互联网上的每个源/项目文件/视频,没有人对这个简单的问题有简单的解决方案。


这里可能发生两种“移动”。


一是 ARKit 不断完善对设备在现实世界中的位置如何映射到您放置虚拟内容的抽象坐标空间的估计。例如,假设您将一个虚拟对象放置在(0, 0, -0.5),然后将设备向左移动 10 厘米。仅当 ARKit 精确跟踪移动时,虚拟对象才会看起来锚定在物理空间中。但视觉惯性里程计并不是一门精确的科学,因此 ARKit 可能会认为您向左移动了 10.5 厘米——在这种情况下,您的虚拟对象看起来会向右“滑动”5 毫米,尽管它ARKit/SceneKit 坐标空间中的位置保持不变。

对此你真的无能为力,只能希望苹果制造出配备更好传感器、更好摄像头或更好 CPU/GPU 的设备,并提高世界追踪的科学性。 (在时间充裕的情况下,这可能是一个安全的选择,尽管这可能对您当前的项目没有帮助。)


由于您还要处理平面检测,因此还有另一个问题。 ARKit 不断完善对检测到的飞机位置的估计。因此,即使飞机的现实世界位置没有改变,它在 ARKit/SceneKit 坐标空间中的位置却发生了变化。

这种移动通常是一件好事 - 如果您希望虚拟对象看起来锚定到现实世界的表面,您需要确定该表面的位置。当平面检测更加确定表面的位置时,您会看到一些移动,但不久之后,当您移动相机时,对于平面锚定的虚拟对象,您应该会看到比那些仅漂浮在世界中的虚拟对象更少的“滑动”空间。


但是,在您的代码中,您没有利用平面检测来使自定义内容(来自“PlayerModel.scn”)粘附到平面锚点:

wrapperNode.position = SCNVector3.positionFromTransform(anchor.transform)
wrapperNode.addChildNode(Body)
scnView.scene.rootNode.addChildNode(wrapperNode)

这段代码使用了initial平面锚点到位置的位置wrapperNode在世界空间中(因为您将其设为根节点的子节点)。如果你改为wrapperNode平面锚节点的子节点(您在renderer(_:didAdd:for:)),当 ARKit 完善对飞机位置的估计时,它将保持附着在飞机上。最初,您会得到更多的移动,但随着平面检测“稳定”,您的虚拟对象将“滑动”得更少。

(当你使节点成为平面的子节点时,你不需要设置它的位置 - 位置为零意味着它就在平面所在的位置。不管怎样,你只需要设置它相对于平面的位置 - 即上方/下方/沿线多远。)

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

如何保持 ARKit SCNNode 就位 的相关文章

随机推荐

  • Java什么时候调用垃圾收集器

    我读了很多关于 Java 堆的文章 我看到如果我们得到 java lang OutOfMemoryError 我们应该增加 Xmx 来解决这个问题 for e g java Xmx2048m Xms256m 这会将 Java 使用的堆内存增
  • 在 Windows 上安装 PG Gem 时出错

    我使用 XAMPP 作为 PostgreSQL 9 3 的安装文件夹 C xampp pgsql 9 3 现在我尝试使用该目录作为参考来安装 PostgreSQL gem gem install pg with pg include C x
  • R 中的“抖动”函数有什么作用?

    根据文档 http astrostatistics psu edu su07 R html base html jitter html 的解释为jitter函数是 向数字向量添加少量噪声 这是什么意思 是否有一个随机数与向量中的每个数字相关
  • 使用 Tkinter 中的按钮终止线程

    在我的 GUI 代码中 我尝试通过单击一个按钮来同时运行循环 1 和循环 2 因此 我用了Thread为了达成这个 但我也尝试通过单击另一个按钮来阻止它 但失败了 在stackoverflow上搜索后发现没有直接杀死的方法Thread 这是
  • Rails 4:f.select 返回字符串而不是整数

    我有用户注册表格 用户必须通过选择选项选择他的国家 地区 当我提交表单时 我收到错误 Country 70309119520500 Expected got String 8039220 请帮助我如何将字符串转换为整数 以便我可以在数据库中
  • OpenGL ES 中使用的 3d 立方体的法线是什么?

    我有一个立方体定义为 float vertices Vertices according to faces 1 0f 1 0f 1 0f Vertex 0 1 0f 1 0f 1 0f v1 1 0f 1 0f 1 0f v2 1 0f 1
  • Visual Studio 2010 中的编程数据断点

    我一直在尝试使用编程数据断点 就像CBreakpoint http www morearty com code breakpoint 例如 通过使用SetThreadContext http msdn microsoft com en us
  • 使用 selenium2library 和 Robot Framework 验证页面中是否存在 2 个文本中的一个文本

    我想测试页面是否包含 TEXT1 或 TEXT2 页面应包含 TEXT1 或 TEXT2 有什么建议我该怎么做 目前我只能检查一篇文本 您可以使用 Page Should Contain Element http rtomac github
  • 列向量与行意味着——与 std::accumulate?

    为了尽可能地懒惰 我在矩阵中读为 vector lt vector
  • 除了动态参数和可选参数之外,C# 4.0 还有哪些新功能?

    所以 C 4 0 昨天出来了 它引入了备受争议的dynamic关键字 命名参数和可选参数 较小的改进是隐含的ref识别 COM 方法上的索引属性和默认属性 逆变和协变 实际上是 NET CLR 功能 不仅仅是 C 以及 真的是这样吗 是dy
  • 找出 Uneaten Leaves 算法错误

    我在面试挑战中遇到了这个问题 K 条毛毛虫正在吃掉 N 片叶子 每条毛毛虫 以独特的顺序从一片叶子落到另一片叶子 所有毛毛虫都开始 在位置 0 处的树枝上 并落在位置之间的叶子上 1 和 N 每条毛毛虫 j 都有一个关联的跳跃数 Aj A
  • 由于延迟加载而使用 Pony ORM 的 DatabaseSessionIsOver?

    我正在使用 Pony ORM 作为烧瓶解决方案 并且遇到了以下问题 考虑以下 db session def get orders of the week self user date q select o for o in Order fo
  • 同步块和监视器对象

    您好 有人可以解释一下下面的代码中的同步代码是否会限制对线程的访问 如果是的话 它与我们使用 this 而不是 msg 作为监视对象有什么不同 public void display String msg synchronized msg
  • 使用 C 中的 GLib/GIO 从 Web 获取文件

    我应该使用什么函数使用 GLib GIO 库从网络获取文件 如果我的文件来自 gchar path http xxx yyyServer sharing temp txt 我应该怎么做才能下载它 对于本地文件 我只使用 fopen 和 fr
  • 理解Python内存分配和释放

    我最近遇到本文 http deeplearning net software theano tutorial python memory management html关于python内存分配 在这个页面中 它描述了 python 的内存使
  • 在 R 中进行矩阵乘法时的非一致性数组

    我正在尝试在 R 中实现内核岭回归 公式为 alpha lt lambda I K 1 y 拉姆达 0 1 I 与 K 大小相同的单位矩阵 y 是与 K 具有相同行数的特征向量 所以我在 R 中尝试了这个 I lt diag nrow df
  • 如何将 AWS Glue 作业的输出返回到调用 Step Function 工作流程?

    AWS Step Functions 允许调用 AWS Glue 作业 如下所述 https docs aws amazon com step functions latest dg connect glue html https docs
  • 合并冲突解决

    当 Git 中出现合并冲突时 如下所示的垃圾会被插入到冲突的文件中 三个问题 你如何阅读这些注释 解决这些合并冲突时可以使用哪些策略 是否有适用于 Mac 的 GUI 工具知道如何读取这些文件并并排显示两个版本 以便更轻松地解决问题 注意
  • 如何从 Composer 中全局删除包?

    我运行此命令进行全局安装PHPUnit composer global require phpunit phpunit 3 7 现在我想全局卸载PHPUnit 有任何想法吗 要删除全局安装的包 请运行 composer global rem
  • 如何保持 ARKit SCNNode 就位

    嘿 我正在想办法 如何保持简单节点的位置 当我在 ARKit 中绕着它走动时 Code func renderer renderer SCNSceneRenderer didAdd node SCNNode for anchor ARAnc