ARKitでオブジェクトの方向を求めたい
Swift4.0でARKitを使いたくて、簡単なARシューティングゲームを作ってみました。そのときに、的となるオブジェクトを見失った時にヒントととしてオブジェクトの方向を出すようにしたいと思って実装して見たところ、結構教育的て面白かったので記事にしてみます。
同じように方向を計算したいという場合は参考にしてください。
全体のコード
最初に全体のコードを先に載せてしまいます
https://github.com/kamata1729/AR_Buster
アプリの流れ
初めはRootViewController
に入り、STARTボタンを押してARViewController
に遷移し、ゲームが終了するとResultViewController
に入る。
ARViewController
では、下の図のようにオブジェクトがランダムな位置に出現してランダムに動くので、それを制限時間内にタップして消していくというゲームです。
今回は、主にこれの右下の矢印の部分の実装を解説します。
三次元の方向を二次元に射影して表現する
やりたいことは、カメラ(iPhone)からオブジェクトまでの3次元空間での方向を、iPhoneの二次元の画面上に射影して表現することです。そのためにはまず、オブジェクトの位置が記述される座標系を、絶対座標系$E$から、カメラ(iPhone)とともに動く座標系$E'$に座標変換する必要があります。
座標変換した後は、座標系$E'$上でカメラとオブジェクトの角度$\theta$は、
$\theta = \arctan \dfrac{y'_2 - y'_1}{x'_2 - x'_1}$
として求めることが可能です。
この部分の実装方法は以下のようになっています。
if let node = self.sceneView.scene.rootNode.childNodes.first {
if let camera = self.sceneView.pointOfView {
let invMat :SCNMatrix4 = SCNMatrix4Invert(camera.transform)
let x = node.position.x
let y = node.position.y
let z = node.position.z
let transPosition :SCNVector3 = SCNVector3(x: x*invMat.m11 + y*invMat.m21 + z*invMat.m31, y: x*invMat.m12 + y*invMat.m22 + z*invMat.m32, z: x*invMat.m13 + y*invMat.m23 + z*invMat.m33)
let angle = (-1) * atan2(transPosition.y - camera.position.y, transPosition.x - camera.position.x)
imageView.transform = CGAffineTransform(rotationAngle: CGFloat(angle))
}
}
1行目:オブジェクトを取得
2行目:カメラ(iPhone)を取得
3行目:
camera.transform
で、原点からカメラの位置への4×4の変換行列を取得する。
(4×4の変換行列について参考:https://qiita.com/kengo1008L/items/2d7319772e08f9465294)
これの逆行列をSCNMatrix4Invert
で計算する。(変換行列は直交行列なので逆行列は存在)
4~6行目:オブジェクトの絶対座標系$E$での座標$(x,y,z)^T$を取得
7行目:
先ほど計算した逆行列のうち、回転角に関係する3×3の成分を$(x,y,z)^T$にかけることで、カメラとともに動く座標系$E'$に変換
8行目:回転角を計算
9行目:矢印の画像をCGAffineTransform
で回転
camera.transform
を使って、カメラの座標系に座標変換することが肝です。方向を計算したいときは参考にしてみてください。
Author And Source
この問題について(ARKitでオブジェクトの方向を求めたい), 我々は、より多くの情報をここで見つけました https://qiita.com/kamata1729/items/37f514ba9265c04c185b著者帰属:元の著者の情報は、元のURLに含まれています。著作権は原作者に属する。
Content is automatically searched and collected through network algorithms . If there is a violation . Please contact us . We will adjust (correct author information ,or delete content ) as soon as possible .