7
2

RealityKitをnonARモードで使ってみた

Last updated at Posted at 2022-08-18

RealityKitをnonARモードで使ってみた

RealityKitはAR表示を推しているFrameworkですが、CameraModeに.nonARがあったので、これを試してみました

リポジトリはコチラ↓です

作成したみたものがコチラ↓です

Xcode 15からReality Composerが利用できなくなったため、加筆修正しました

arモードとnonARモードで違う所

基本的にRealityKitはarモードでもnonARモードでも同じように扱うことができました
nonARモードで意識したのは下記の4点です、順番に取り扱って行きます

  1. ARViewをnonARで作成する
  2. カメラの追加
  3. Lightの追加
  4. Skyboxの設定
  5. これらを1つのAnchorに追加する

ARViewをnonARで作成する

cameraModeをnonARでARViewを作成します

let arView = ARView(frame: .zero, cameraMode: .nonAR, automaticallyConfigureSession: false)

USDZの読み込み

USDZファイルを読み込んでモデルを表示します
アニメーションがあれば、リピートで再生させます
Appleのサイトからダウンロードしてきました

let plane = try ModelEntity.loadModel(named: "toy_biplane_idle")
plane.availableAnimations.forEach {
    plane.playAnimation($0.repeat())
}

let worldAnchor = AnchorEntity(world: .zero)
worldAnchor.addChild(plane)
arView.scene.anchors.append(worldAnchor)

こちらが結果です
飛行機が表示されているようですが、イマイチわかりません🥺

カメラの追加

arモードではカメラの位置はデバイスの位置になるのですが、nonARモードでは手動でカメラを追加してあげる必要があります
PerspectiveCameraを使用します
適当にカメラの位置と向きを設定します

let camera = PerspectiveCamera()
camera.camera.fieldOfViewInDegrees = 60
camera.look(at: .zero, from: [1, 0.5, 1], relativeTo: nil)

worldAnchor.addChild(camera)

こちらが結果です
斜め上から見ているので分かりやすくはなりましたが、真っ暗でよくわかりません🥺

Lightの追加

真っ暗なので、Lightを追加します
LightはPerspectiveCamera、DirectionalLight、SpotLightの3種類があります
今回はDirectionalLightを配置しました

let directionalLight = DirectionalLight()
directionalLight.light.color = .white
directionalLight.light.intensity = 5000
directionalLight.look(at: .zero, from: .init(x: 0, y: 20, z: 5), relativeTo: nil)

worldAnchor.addChild(directionalLight)

こちらが結果です
飛行機は明るくなりましたが、背景が真っ暗で寂しいです🥺

Skyboxの設定

ARView.Environment.Background.skyboxを使って背景として設定します

  1. https://polyhaven.com/a/alps_fieldから全天球の画像をダウンロードします
  2. {任意の名前}.skybox というリファレンスフォルダを追加し、その中にダウンロードした画像を配置します
    image.png
  3. EnvironmentResource.load(named: "{任意の名前}") でロードして、backgroundに設定します
    * {任意の名前}.skybox というリファレンスフォルダがある場合、ビルド時に自動的にrealityenvファイルに変換され、アプリにバンドルされるようです
let skybox = try! EnvironmentResource.load(named: "alps_field_1k")
arView.environment.background = .skybox(skybox)

Swift Packageでは.skyboxを処理してくれなかったため、Swift Packageのみで設定する場合、オレオレSkyboxを作成して追加します

let skyboxTexture = try TextureResource.load(named: "alps_field_1k", in: .module)
var skyboxMaterial = UnlitMaterial()
skyboxMaterial.color = .init(texture: .init(skyboxTexture))
let skyboxComponent = ModelComponent(mesh: .generateSphere(radius: 1000), materials: [skyboxMaterial])

let skybox = Entity()
skybox.components.set(skyboxComponent)
skybox.scale *= .init(1, 1, -1)

worldAnchor.addChild(skybox)

こちらが結果です
全体的に明るくなってイイ感じです!

これらを1つのAnchorに追加する

これはワンポイントで、上でしれっとやっているのですが、カメラなど表示に必要なものを1つのAnchorに追加して、それを追加する必要があります
Anchorが別れているとカメラに反映されないので注意が必要でした

let worldAnchor = AnchorEntity(world: .zero)
worldAnchor.addChild(plane)
worldAnchor.addChild(camera)
worldAnchor.addChild(skybox)
worldAnchor.addChild(directionalLight)
arView.scene.anchors.append(worldAnchor)

その他

SceneEvents.Updateのタイミングでカメラを更新します

let len: Float = 0.8
var cameraRot: (yaw: Float, pitch: Float) = (yaw: 0, pitch: 0)

arView.scene
    .publisher(for: SceneEvents.Update.self)
    .sink { [weak self] (_: SceneEvents.Update) in
        self?.updateEvent()
    }
    .store(in: &cancellables)

func updateEvent() {
    camera.position = plane.position + .init(
        x: len * sin(cameraRot.yaw) * cos(cameraRot.pitch),
        y: len * sin(cameraRot.pitch),
        z: len * cos(cameraRot.yaw) * cos(cameraRot.pitch)
    )

    camera.look(
        at: plane.position,
        from: camera.position,
        relativeTo: nil
    )
}

おわりに

RealityKitをnonARで使ってみました
SkyboxやカメラなどnonARで使うためのような機能もありますが、Lighting Shaderが設定できないなど、微妙に痒い所に手が届かない点があり、nonARモードでガッツリ使うには用途が限定される印象でした
しかし、RoomPlanなどAppleはARに力が入っているようなので、Frameworkの機能の追加、拡張に期待したいですしていたのですが、Vision Proが始まりReality Composerが使えなくなり、悲しい気持ちになりましたw

7
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
7
2