将 ARFaceAnchor 从左手坐标系翻转到右手坐标系 [英] Flip ARFaceAnchor from left-handed to right-handed coordinate system
问题描述
通过打印 faceAnchor.transform.columns.3
进行一些测试后,深入研究:
正x方向指向观察者的右侧(即人脸自己的左侧),正y方向指向上方(相对于人脸本身,而不是世界),正z方向指向观察者的外侧面对(面向观众)
Sarasvati 给出了进行转型的建议:
func faceAnchorPoseToRHS(_ mat: float4x4) ->浮动4x4 {让更正Pos = float4(x: mat.columns.3.x, y: mat.columns.3.y, z: -mat.columns.3.z, w: 1)让 quat = simd_quatf(mat)让 newQuat = simd_quatf(角度:-quat.angle,轴:float3(quat.axis.x,quat.axis.y,-quat.axis.z))var newPose = float4x4(newQuat)newPose.columns.3 = CorrectPos返回新姿势}
基于 Andy Fedoroff 的更新:
extension ViewController: ARSCNViewDelegate {func renderer(_ renderer: SCNSceneRenderer, didAdd node: SCNNode, for anchor: ARAnchor) {守卫让 faceAnchor = 锚定为?ARFaceAnchor else { return }currentFaceAnchor = faceAnchor如果 node.childNodes.isEmpty,让 contentNode = selectedContentController.renderer(renderer, nodeFor: faceAnchor) {node.addChildNode(contentNode)}selectedContentController.session = sceneView?.sessionselectedContentController.sceneView = 场景视图}///- 标签:ARFaceGeometryUpdatefunc renderer(_ renderer: SCNSceneRenderer, didUpdate node: SCNNode, for anchor: ARAnchor) {守卫锚== currentFaceAnchor,让 contentNode = selectedContentController.contentNode,contentNode.parent == 节点否则{返回}sceneView.session.currentFrame!.anchors.first!.transform打印(currentFaceAnchor!.transform.columns.3)selectedContentController.session = sceneView?.sessionselectedContentController.sceneView = 场景视图selectedContentController.renderer(renderer, didUpdate: contentNode, for: anchor)}}
但是,我打印了 faceAnchor.transform.columns.3
并使用 True Depth 相机获得了 z 底片.下面显示 x,y,z,w 轴:
关于如何更正 z 轴的任何建议?提前谢谢您
首先,让我们看看默认矩阵值是什么.
身份矩阵
这是一个带有默认值的 Identity 4x4 矩阵
.
如果您需要有关 4x4 矩阵
元素的更多信息,请阅读
正+cos(a)
:
┌ ┐|cos -sin 0 0 ||sin cos 0 0 ||0 0 1 0 ||0 0 0 1 |└ ┘
这是一个负 Z 旋转表达式 (CW).
负-cos(a)
:
┌ ┐|-cos -sin 0 0 ||sin-cos 0 0 ||0 0 1 0 ||0 0 0 1 |└ ┘
After some testings by printing faceAnchor.transform.columns.3
, digging in SO: ARFaceAnchor have negative Z position? and Apple's documentation: ARFaceAnchor, I realized that the z axis is actually flipped and it is not the right-handed coordinate system as in the documentation. The ARFaceAnchor claims the coordinate:
the positive x direction points to the viewer’s right (that is, the face’s own left), the positive y direction points up (relative to the face itself, not to the world), and the positive z direction points outward from the face (toward the viewer)
Sarasvati has given a suggestion on doing the transformation:
func faceAnchorPoseToRHS(_ mat: float4x4) -> float4x4 {
let correctedPos = float4(x: mat.columns.3.x, y: mat.columns.3.y, z: -mat.columns.3.z, w: 1)
let quat = simd_quatf(mat)
let newQuat = simd_quatf(angle: -quat.angle, axis: float3(quat.axis.x, quat.axis.y, -quat.axis.z))
var newPose = float4x4(newQuat)
newPose.columns.3 = correctedPos
return newPose
}
Updates based on Andy Fedoroff:
extension ViewController: ARSCNViewDelegate {
func renderer(_ renderer: SCNSceneRenderer, didAdd node: SCNNode, for anchor: ARAnchor) {
guard let faceAnchor = anchor as? ARFaceAnchor else { return }
currentFaceAnchor = faceAnchor
if node.childNodes.isEmpty, let contentNode = selectedContentController.renderer(renderer, nodeFor: faceAnchor) {
node.addChildNode(contentNode)
}
selectedContentController.session = sceneView?.session
selectedContentController.sceneView = sceneView
}
/// - Tag: ARFaceGeometryUpdate
func renderer(_ renderer: SCNSceneRenderer, didUpdate node: SCNNode, for anchor: ARAnchor) {
guard anchor == currentFaceAnchor,
let contentNode = selectedContentController.contentNode,
contentNode.parent == node
else { return }
sceneView.session.currentFrame!.anchors.first!.transform
print(currentFaceAnchor!.transform.columns.3)
selectedContentController.session = sceneView?.session
selectedContentController.sceneView = sceneView
selectedContentController.renderer(renderer, didUpdate: contentNode, for: anchor)
}
}
However, I printed faceAnchor.transform.columns.3
and obtained the z negative with True Depth camera. Below show x,y,z,w axis:
Any suggestions on how to correct the z-axis? Thank you in advance
At first, let's see what a default matrix values are.
Identity matrix
Here's an Identity 4x4 matrix
with default values.
If you need additional info on elements of 4x4 matrices
read this post.
// 0 1 2 3
┌ ┐
| 1 0 0 0 | x
| 0 1 0 0 | y
| 0 0 1 0 | z
| 0 0 0 1 |
└ ┘
Position Mirroring
To flip entity's Z axis
and X axis
, in order to reorient axis from Face tracking environment to World tracking environment, use the following form of 4x4 transform matrix
.
// 0 1 2 3
┌ ┐
| -1 0 0 0 | x
| 0 1 0 0 | y
| 0 0 -1 0 | z
| 0 0 0 1 |
└ ┘
Rotation Mirroring
In 4x4 transform matrices
rotation is a combination of scale and skew
. To choose a right rotation's direction, clockwise (CW) or counter-clockwise (CCW) use +
or -
for cos
expressions.
Here's a positive Z rotation expression (CCW).
Positive +cos(a)
:
┌ ┐
| cos -sin 0 0 |
| sin cos 0 0 |
| 0 0 1 0 |
| 0 0 0 1 |
└ ┘
And here's a negative Z rotation expression (CW).
Negative -cos(a)
:
┌ ┐
|-cos -sin 0 0 |
| sin -cos 0 0 |
| 0 0 1 0 |
| 0 0 0 1 |
└ ┘
这篇关于将 ARFaceAnchor 从左手坐标系翻转到右手坐标系的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!