Realitykit - How to Add Motion to a Loaded Modelentity from Usdz File

RealityKit – How to add motion to a loaded ModelEntity from USDZ file?

Add to your code .generateCollisionShapes(recursive:) instance method for every participant (entity) that not only creates collision's shapes but also allows you to simulate physics.

Sample Image

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)
}
}

For more details, read THIS post.

Applying Physics on USDZ model in RealityKit

Use generateCollisionShapes() instance method to activate physics and run collisions detection:

func makeUIView(context: Context) -> ARView {

let arView = ARView(frame: .zero)

let robot = try! Entity.loadAnchor(named: "robot")
robot.scale = [0.03, 0.03, 0.03]
let headEntity = robot.findEntity(named: "vintage_robot_animRig_model_head")

robot.generateCollisionShapes(recursive: true)

let physics = PhysicsBodyComponent(massProperties: .default,
material: .default,
mode: .dynamic)
headEntity?.components.set(physics)
arView.scene.anchors.append(robot)

return arView
}

Importing and animating multiple .usdz objects in RealityKit

In RealityKit API to play animation contained in .usdz file you could use the following code:

let cow = try ModelEntity.load(named: "cow")
let horse = try ModelEntity.load(named: "horse")

cow.position.x = -1.0
horse.position.x = 1.0

let anchor = AnchorEntity()
cow.setParent(anchor)
horse.setParent(anchor)
arView.scene.anchors.append(anchor)

let cowAnimationResource = cow.availableAnimations[0]
let horseAnimationResource = horse.availableAnimations[0]

cow.playAnimation(cowAnimationResource.repeat(duration: .infinity),
transitionDuration: 1.25,
startsPaused: false)

horse.playAnimation(horseAnimationResource.repeat(duration: .infinity),
transitionDuration: 0.75,
startsPaused: false)

It's a pity but in RealityKit 2.0 you can play only first animation placed inside your file – other ones are unavailable at the moment.

RealityKit – Grab children from USDZ file by name

Use findEntity(named:) instance method to recursively get any descendant entity by its name.

func findEntity(named name: String) -> Entity?

.rcproject scene

let boxAnchor = try! Experience.loadBox()
arView.scene.anchors.append(boxAnchor)

print(boxAnchor)

let entity = boxAnchor.findEntity(named: "Steel Box")
entity?.scale *= 7

.usdz model

let model = try! ModelEntity.load(named: "model.usdz")
let anchor = AnchorEntity(world: [0,0,-1])
anchor.addChild(model)
arView.scene.anchors.append(anchor)

print(model)

let entity = model.findEntity(named: "teapot")
entity?.scale /= 33

P. S.

Unfortunately, not all entities in .usdz or .rcproject have names by default.

So, you must give all the required names to entities to use this method.



Related Topics



Leave a reply



Submit