WWDC2017 Introducing ARKit まとめ
iOS11の大きなウリの一つ、ARKitのセッションです。
動画はこちら
Introducing ARKit
ARとは?
- Virtualな物体をPhysicalな世界に配置すること
- ポケモンGOを始めとするデモ
ARKit
概要
3つの機能がある
Unityに組み込まれている
API概要
ProcessingとRenderingに分かれる
- RenderingがMetalやSceneKit
- ProcessingがAR-Kit
- 内部でAVFoundationやCoreMotionを用いる
ARKit
ARSessionConfiguration
if ARWorldTrackingSessionConfiguration.isSupported { configuration = ARWorldTrackingSessionConfiguration() } else { configuration = ARSessionConfiguration() }
** ARSession
* ARプロセスの管理
* run
/ pause
など
* ARSessionDelegate
で更新された ARFrame を受け取る
** ARFrame * ARレンダリングに必要な情報がある * カメラ画像 * トラッキング情報 * Scene情報 * ARAnchor * 実世界のポジション * ARSessionに追加/削除する
Traking
ARKitは座標だけでなく、「実世界の距離」も計測する
- セッション開始時点からの位置になる
- カメラから複数の特徴点を抽出、その位置差分で位置を出す
- 加速度センサも活用している
サンプルコード
let session = ARSession() session.delegate = self let configuration = ARWorldTrackingSessionConfiguration() sesison.run(configuration)
- ARCamera
- 仮想的なカメラ情報を提供するオブジェクト
- Transform/TrackingState/Camera intrinsics
Demo
デモで気になったクラスをピックアップ
- ARSCNView : ARシーンレンダリングの便利クラス
- SceneKitをはめることができる
arScnView.scene = scnView
- UITapGestureでタップ判定可能
- ARSCNView : ARシーンレンダリングの便利クラス
タップでスクリーンキャプチャを画像としてSceneに追加するサンプル
func handleTap(...) { guard let currentFrame = sceneView.session.currentFrame else { return } //キャプチャした平面Object作成 let imagePlane = SCNPlane(width: sceneView.bounds.width / 6000, height: sceneView.bounds.height / 6000) imgPlane.firstMaterial?.diffuse.contents = sceneView.snapshot() imgPlane.firstMaterial?.lightingModel = .constant //シーンに追加 let planeNode = SCNNode(geometry: imagePlane) sceneView.scene.rootNode.addChildNode(planeNode) //カメラの10cm先に配置 var translation = matrix_identity_float4x4 translation.column.3.z = -0.1 planeNode.simdTransform = matrix_multiply(currentFrame.camera.transform, translation) }
Trackingの品質
カメラの環境に大きく左右される
Trackingの状態
func session(.., cameraDidChangeTrackingState camera: ARCamera) { if case .limited(let reason) = camera.trackingState { ... } }
func sessionWasInterrupted(...) { showOverlay() } func sessionInterruptionEnded(...) { hideOverlay() //必要に応じAR処理を再開 }
Scene Understanding
バーチャルな物体を配置するときに必要な情報のこと
- 平面検出
- ヒットテスト
- 光量推定
平面検出
- テーブルのような水平面を検出できる
- 複数のフレーム情報から計算する
- 広さを測定できる
- 面をマージできる
- ARWorldTrackingSessionConfigurationの
planeDetection
を使う- 現状、
.horizontal
しか値がない模様
- 現状、
ARPlaneAnchor
- 平面が検出されるとDelegateが呼び出される?
- 3軸回転、中央、広さを保持している
HitTest
- カメラからのみた特定の直線が実世界平面のどこに位置するかを調べる
- 4つの種類がある
- Existing Plane Using Extent: 平面の位置/広さを考慮したヒット位置
- Existing Plane : 平面の広さが無限とした場合のヒット位置
- Estimated Plane : まだ平面が検出されてないときに使う
- Feature Point : 面が小さいときに用いる(イレギュラーなケースらしい)
- 画面の座標ベースでテスト可能(0,0が左上、1,1が右下)
光量推定
- 画像ベースの光量推定
- 1000ルーメンがデフォルト
- Configurationで設定する
構成
SceneKit/SpriteKit/Metalのいずれか
SceneKit
- ARSCNView
- カメラ画像を表示する
- SCNCameraが人にあわせ移動する
- 自動でLightingされる
- SCNNode が ARAncher にマップされる
SpriteKit
- ARSKView
- SKNode が ARAnchor にマップされる
- SpriteKitは2D描画用
- 物理計算にテーブルを使うなどが出来る(?)
Metal
- カスタムレンダリングに用いる
SceneKitで配置するだけで動くのは良さそうですね。3Dはあまり経験がないので厳しいと思っていたのですが、結構簡単にできそうでちょっと興味わいてきました