RealityKit – 如何从 USDZ 文件向加载的 ModelEntity 添加动作?
RealityKit – How to add motion to a loaded ModelEntity from USDZ file?
我已成功将 USDZ 文件加载到我的场景中。现在我想给 ModelEntity 添加动作。我添加了 PhysicsMotionComponent 但它不起作用。加载模型后,它像往常一样是静态的。没有动静。如何在 RealityKit 中给实体运动?
当我看到组件时,我看到组件已添加。但是实体没有动。我做错了什么?
我的代码:
import SwiftUI
import RealityKit
import ARKit
import Combine
struct ARViewContainer: UIViewRepresentable {
func makeUIView(context: Context) -> ARView {
let arVIew = ARView(frame: .zero)
context.coordinator.arVIew = arVIew
arVIew.session.delegate = context.coordinator
let config = ARWorldTrackingConfiguration()
arVIew.session.run(config, options: [.resetTracking,.removeExistingAnchors])
let anchorEntity = AnchorEntity()
loadASingleModel(name:"toy_biplane") { entity in
if let entity = entity {
let kinematics: PhysicsBodyComponent = .init(massProperties: .default,
material: nil,
mode: .kinematic)
let motion: PhysicsMotionComponent = .init(linearVelocity: [0.1 ,0, 0],
angularVelocity: [3, 3, 3])
entity.components.set(kinematics)
entity.components.set(motion)
anchorEntity.addChild(entity)
//anchorEntity.transform.matrix.columns.3.z = -1.0
arVIew.scene.anchors.append(anchorEntity)
print("Model Added: ",entity.name)
}else{
print("No entity avaible")
}
}
return arVIew
}
// MARK: - AsychLoading working
func loadASingleModel(name:String,completion:@escaping (_ model:ModelEntity?)->Void){
var cancellable:AnyCancellable?
cancellable = Entity.loadModelAsync(named:name)
.sink(receiveCompletion: { handler in
if case let .failure(error) = handler {
print("Unable to load a model due to error \(error)")
}
cancellable?.cancel()
completion(nil)
}, receiveValue: { [self] (model: ModelEntity?) in
if let model = model {
cancellable?.cancel()
print("Congrats! Model is successfully loaded!")
completion(model)
}
})
}
func updateUIView(_ uiView: ARView, context: Context) {
}
func makeCoordinator() -> Coordinator {
Coordinator(arViewContainer: self)
}
class Coordinator:NSObject{
var parent:ARViewContainer
var arVIew:ARView?
init(arViewContainer:ARViewContainer){
parent = arViewContainer
}
}
}
extension ARViewContainer.Coordinator:ARSessionDelegate{
func session(_ session: ARSession, didUpdate frame: ARFrame) {
}
}
添加到您的代码中 .generateCollisionShapes(recursive:)
每个参与者(实体)的实例方法,它不仅可以创建碰撞的形状,还可以让您模拟物理。
import SwiftUI
import RealityKit
struct ARViewContainer: UIViewRepresentable {
let boxx = ModelEntity(mesh: .generateBox(size: 0.5))
let ball = ModelEntity(mesh: .generateSphere(radius: 0.25))
let anchor = AnchorEntity()
func makeUIView(context: Context) -> ARView {
let arView = ARView(frame: .zero)
// BALL
ball.physicsBody = .init()
ball.physicsMotion = .init()
ball.physicsMotion?.linearVelocity = [10,0,0]
ball.position.x = -3
ball.generateCollisionShapes(recursive: true)
anchor.addChild(ball)
// BOX
boxx.physicsBody = .init()
boxx.physicsMotion = .init()
boxx.physicsMotion?.linearVelocity = [0,2,0]
boxx.generateCollisionShapes(recursive: true)
anchor.addChild(boxx)
// Anchor
anchor.position.z = -3
arView.scene.addAnchor(anchor)
return arView
}
func updateUIView(_ uiView: ARView, context: Context) { }
}
...
struct ContentView : View {
var body: some View {
return ARViewContainer().edgesIgnoringSafeArea(.all)
}
}
有关详细信息,请阅读 THIS post。
我已成功将 USDZ 文件加载到我的场景中。现在我想给 ModelEntity 添加动作。我添加了 PhysicsMotionComponent 但它不起作用。加载模型后,它像往常一样是静态的。没有动静。如何在 RealityKit 中给实体运动?
当我看到组件时,我看到组件已添加。但是实体没有动。我做错了什么?
我的代码:
import SwiftUI
import RealityKit
import ARKit
import Combine
struct ARViewContainer: UIViewRepresentable {
func makeUIView(context: Context) -> ARView {
let arVIew = ARView(frame: .zero)
context.coordinator.arVIew = arVIew
arVIew.session.delegate = context.coordinator
let config = ARWorldTrackingConfiguration()
arVIew.session.run(config, options: [.resetTracking,.removeExistingAnchors])
let anchorEntity = AnchorEntity()
loadASingleModel(name:"toy_biplane") { entity in
if let entity = entity {
let kinematics: PhysicsBodyComponent = .init(massProperties: .default,
material: nil,
mode: .kinematic)
let motion: PhysicsMotionComponent = .init(linearVelocity: [0.1 ,0, 0],
angularVelocity: [3, 3, 3])
entity.components.set(kinematics)
entity.components.set(motion)
anchorEntity.addChild(entity)
//anchorEntity.transform.matrix.columns.3.z = -1.0
arVIew.scene.anchors.append(anchorEntity)
print("Model Added: ",entity.name)
}else{
print("No entity avaible")
}
}
return arVIew
}
// MARK: - AsychLoading working
func loadASingleModel(name:String,completion:@escaping (_ model:ModelEntity?)->Void){
var cancellable:AnyCancellable?
cancellable = Entity.loadModelAsync(named:name)
.sink(receiveCompletion: { handler in
if case let .failure(error) = handler {
print("Unable to load a model due to error \(error)")
}
cancellable?.cancel()
completion(nil)
}, receiveValue: { [self] (model: ModelEntity?) in
if let model = model {
cancellable?.cancel()
print("Congrats! Model is successfully loaded!")
completion(model)
}
})
}
func updateUIView(_ uiView: ARView, context: Context) {
}
func makeCoordinator() -> Coordinator {
Coordinator(arViewContainer: self)
}
class Coordinator:NSObject{
var parent:ARViewContainer
var arVIew:ARView?
init(arViewContainer:ARViewContainer){
parent = arViewContainer
}
}
}
extension ARViewContainer.Coordinator:ARSessionDelegate{
func session(_ session: ARSession, didUpdate frame: ARFrame) {
}
}
添加到您的代码中 .generateCollisionShapes(recursive:)
每个参与者(实体)的实例方法,它不仅可以创建碰撞的形状,还可以让您模拟物理。
import SwiftUI
import RealityKit
struct ARViewContainer: UIViewRepresentable {
let boxx = ModelEntity(mesh: .generateBox(size: 0.5))
let ball = ModelEntity(mesh: .generateSphere(radius: 0.25))
let anchor = AnchorEntity()
func makeUIView(context: Context) -> ARView {
let arView = ARView(frame: .zero)
// BALL
ball.physicsBody = .init()
ball.physicsMotion = .init()
ball.physicsMotion?.linearVelocity = [10,0,0]
ball.position.x = -3
ball.generateCollisionShapes(recursive: true)
anchor.addChild(ball)
// BOX
boxx.physicsBody = .init()
boxx.physicsMotion = .init()
boxx.physicsMotion?.linearVelocity = [0,2,0]
boxx.generateCollisionShapes(recursive: true)
anchor.addChild(boxx)
// Anchor
anchor.position.z = -3
arView.scene.addAnchor(anchor)
return arView
}
func updateUIView(_ uiView: ARView, context: Context) { }
}
...
struct ContentView : View {
var body: some View {
return ARViewContainer().edgesIgnoringSafeArea(.all)
}
}
有关详细信息,请阅读 THIS post。