新闻资讯

新闻资讯 行业动态

clone 与 flattenedClone使用时的注意事项

编辑:008     时间:2020-02-26

需要注意的是,原始的 node 和 clone 得到的 node2 其实是共用一个 geometry 对象的,同时也共用了所有的材质和贴图;flattenedClone 后得到的 node3 虽然生成了合并后的 geometry,但是仍然和前两个共用了材质和贴图,即它们的 geometry?.firstMaterial 是同一个对象。


这就导致了两个问题:

  • 当试图改变复制出来的 node 的材质或颜色时,三者会同时改变;
  • flattenedClone 时,内部结构复杂的 node(比如内部有多个子 node,子 node 有自己的 geometry),所有子 geometry 被合并,但材质贴图无法自动合并,会保留最外层或第一个子node 的材质;

比如下图这个模型:


因此,模型有多个部件,材质与贴图需要专门处理,使用 flattenedClone 应慎重。

但是第一个问题我们是可以通过简单的代码来处理的:

let node = scene.rootNode.childNode(withName: "ship", recursively: true)
node?.simdPosition = simd_float3(0, 0, -0.5)
scene.rootNode.addChildNode(node!) let node2 = node?.clone()
node2?.simdPosition = simd_float3(0.5, 0, -0.5)
scene.rootNode.addChildNode(node2!) // 找到真正有 geometry 的子 node let shipMesh = node?.childNodes.first // copy 这个 geometry 给自己对应的子 node 赋值 node2?.childNodes.first?.geometry = shipMesh?.geometry?.copy() as? SCNGeometry // 新建一个 SCNMaterial 对象 node2?.childNodes.first?.geometry?.firstMaterial = SCNMaterial() // 改变 geometry 的材质颜色 node2?.childNodes.first?.geometry?.firstMaterial?.diffuse.contents = UIColor.red let node3 = node?.flattenedClone()
node3?.simdPosition = simd_float3(1, 0, -0.5)
scene.rootNode.addChildNode(node3!) // geometry 已经不是同一个了,无需再 copy,但仍需创建新的 SCNMaterial 对象 node3?.geometry?.firstMaterial = SCNMaterial()
node3?.geometry?.firstMaterial?.diffuse.contents = UIColor.green 

只需要将 geometry 也 copy 一份,并赋值到对应的 clone 出的 node 下面,并新建一个SCNMaterial对象就可以改变材质和颜色了。



原文链接:https://juejin.im/post/5e532421e51d4526d05952cf
郑重声明:本文版权归原作者所有,转载文章仅为传播更多信息之目的,如作者信息标记有误,请第一时间联系我们修改或删除,多谢。

回复列表

相关推荐