【visionOS】RealityViewでVision Proの画面上に3Dオブジェクトを表示させる
ということでRealityKitを使用すると3DオブジェクトをVision Pro上に表示させることができます。
またRealityKitのRealityViewを使用することでSwiftUIのView内にvisionOS 上に3Dオブジェクトを表示させられるので試してみます。
ドキュメントは以下です。
サンプルコードの通りModelEntityを使用して表示します。
とりあえず一番簡単に3Dオブジェクトを表示させてみたいのでMeshResourceのCreating a Boxを参考に試してみます。
import SwiftUI
import RealityKit
struct Sample2: View {
var body: some View {
VStack {
RealityView { content in
let box = ModelEntity(mesh: .generateBox(size: 0.1))
content.add(box)
}
}
}
}
たった数行で3Dオブジェクトを表示させることができました。
正方形以外表示させたい場合は'.generateBox(width: 0.2, height: 0.1, depth: 0.3)'で任意の辺の長さを定義できます。
3Dオブジェクトをタップをする
表示できたので3Dオブジェクトに対してタップして何かしらのアクションを行ってみます。
従来のSwiftUIではButtonもしくはonTapGestureで行うことができるので試してみます。
struct Sample2: View {
@State var flag = false
var body: some View {
VStack {
Text(flag ? "true" : "false")
.font(.extraLargeTitle)
Button(action: {
flag.toggle()
}, label: {
RealityView { content in
let box = ModelEntity(mesh: .generateBox(size: 0.1))
content.add(box)
}
})
RealityView { content in
let box = ModelEntity(mesh: .generateBox(size: 0.1))
content.add(box)
}
.onTapGesture {
flag.toggle()
}
}
}
}
Buttonはタップするとtrue/falseとテキストが変更しますがUIが変更されています。
onTapGestureは反応しません。
TapGestureに関してはRespond to interactions with RealityKit contentに記載されています。
実際にミニマムで検証したコードは以下の通りです。
RealityView { content in
let model = ModelEntity(mesh: .generateBox(size: 0.1))
model.components.set(InputTargetComponent())
model.components.set(CollisionComponent(shapes: [ShapeResource.generateBox(size: SIMD3<Float>(repeating: 0.1))]))
content.add(model)
}
.gesture(
SpatialTapGesture()
.targetedToAnyEntity()
.onEnded { _ in
flag.toggle()
}
)
これで3Dオブジェクトがタップされたことを検知することができます。
タップ機能を実装するにはInputTargetComponentとCollisionComponentを必ずcomponents.setにセットすることとSpatialTapGesture()もしくはTapGesture()に対してtargetedToAnyEntityもしくはtargetedToEntity(任意のEntityをターゲットにする場合に使用する)を追加する必要があります。
これで3Dオブジェクトがタップされたことを検知することができます。
いいねと思えたらよろしくお願いします😋