我正在寻找一种方法来将SCNNodes的枢轴(从导入Collada文件获得)设置为其质心(或其边界框的中心)。
我得到了中心
SCNVector3 center;
CGFloat radius;
[node getBoundingSphereCenter:¢er radius:&radius];
但是,当我尝试将节点的枢轴(相对于中心的3D向量为4D向量)设置为中心时,节点的位置也会更改。
node.pivot = SCNMatrix4MakeTranslation(center.x,center.y,center.z);
我该如何抵消这一运动-分别。如何仅更改节点的枢轴而不影响其在空间中的位置?
还是有一种方法(不使用其他空节点)在Interface Builder中完成?
最佳答案
此处也询问了同样的问题Is it normal for an SCNNode pivot to change the nodes position? ...,但是在网上搜索了几个小时之后,我找不到该问题的任何编码解决方案。这是,它如何在不移动节点的情况下使节点的轴心居中。
因此,最后,我将大部分时间用在下面的此编码答案上。
我发现,局部轴的方向决定了对校正因子进行减还是加。
在下面骑这辆自行车。右踏板曲柄枢轴z轴(蓝色)指向上方,而另一张照片中,左踏板曲柄枢轴z轴(蓝色)指向下方。这些轴不同的原因是当人们在SketchUp中绘制自行车模型时,他们只是复制了第一把踏板曲柄并将其翻转到另一侧。因此,不幸的是,获得具有特定枢轴方向和位置的进口DAE模型是很常见的!
func centerPivotWithOutMoving(for node: SCNNode) -> SCNNode {
let initialPos = activeNode.presentation.position
var min = SCNVector3Zero
var max = SCNVector3Zero
node.__getBoundingBoxMin(&min, max: &max)
node.pivot = SCNMatrix4MakeTranslation(
min.x + (max.x - min.x)/2,
min.y + (max.y - min.y)/2,
min.z + (max.z - min.z)/2
)
let correctX = Float(min.x + (max.x - min.x)/2)
let correctY = Float(min.y + (max.y - min.y)/2)
let correctZ = Float(min.z + (max.z - min.z)/2)
if node.convertVector(SCNVector3(0,0,1), from: parentNode).z < 0 {
// if blue local z-axis is pointing downwards
node.position = SCNVector3(initialPos.x - correctX, initialPos.y - correctY, initialPos.z - correctZ)
} else {
// if blue local z-axis is pointing upwards
node.position = SCNVector3(initialPos.x + correctX, initialPos.y + correctY, initialPos.z + correctZ)
}
return node
}
我只在上面显示的两个不同的z轴方向上测试了上面的代码,完整的代码也必须使用这两个条件处理x,y轴。
node.convertVector(SCNVector3(0,1,0), from: parentNode).z < 0
node.convertVector(SCNVector3(1,0,0), from: parentNode).z < 0
如果有更好的方法可以...请分享?