Post

Replies

Boosts

Views

Activity

Reply to SwiftData ModelContext Pollution with Multiple ModelContainers and Schemas
@joadan yes, the application crashes as well. The below view will terminated the app if you attempt to save a local item. struct ContentView: View { @State private var localId: Int = 0 @State private var localCount: Int = 0 @State private var remoteId: Int = 0 @State private var remoteCount: Int = 0 private var localContainer: ModelContainer private var remoteContainer: ModelContainer private let log = Logger() init() { localContainer = { do { let schema = Schema(versionedSchema: LocalSchema.self) let config = ModelConfiguration("local", schema: schema, isStoredInMemoryOnly: true, allowsSave: true, cloudKitDatabase: .none) return try ModelContainer(for: schema, configurations: config) } catch { fatalError("could not create local store") } }() remoteContainer = { do { let schema = Schema(versionedSchema: RemoteSchema.self) let config = ModelConfiguration("remote", schema: schema, isStoredInMemoryOnly: true, allowsSave: true, cloudKitDatabase: .none) return try ModelContainer(for: schema, configurations: config) } catch { fatalError("could not create remote store") } }() } var body: some View { HStack { VStack { Text("\(localCount)") Button("Save Local") { do { log.info("save local") localId += 1 let context = ModelContext(localContainer) let item = LocalSchema.Item(title: "local: \(localId)", created: .now, modified: .now) context.insert(item) try context.save() localCount = try context.fetchCount(FetchDescriptor<LocalSchema.Item>()) } catch { log.error("\(error.localizedDescription)") } } } VStack { Text("\(remoteCount)") Button("Save Remote") { do { log.info("save remote") remoteId += 1 let context = ModelContext(remoteContainer) let item = RemoteSchema.Item(title: "remote: \(remoteId)", created: .now, modified: .now, origin: "from space") context.insert(item) try context.save() remoteCount = try context.fetchCount(FetchDescriptor<RemoteSchema.Item>()) } catch { log.error("\(error.localizedDescription)") } } } } } }
Mar ’26
Reply to How to detect which entity was tapped?
Do the entities that you want to drag have colliders and InputTargetComponents? If so you can use the entity value on the tap and drag gesture directly. TargetedToAnyEntity requires an input target component to trigger. The below lets you tap on a box to change the material and drag a box to a different location. I believe both Tap and Drag gestures have a hitTest method that you can use as well. import SwiftUI import RealityKit struct ContentView: View { @State var root: Entity = Entity() @GestureState private var isDragging: Bool = false var body: some View { ZStack(alignment: .bottom) { RealityView { content in content.add(root) for idx in 0...3 { let ball = ModelEntity(mesh: .generateBox(size: 0.1), materials: [SimpleMaterial(color: .blue, isMetallic: false)]) ball.generateCollisionShapes(recursive: true) ball.components.set(InputTargetComponent()) ball.position.y = 0.3 * Float(idx) root.addChild(ball) } } Button("Reset") { for entity in root.children { guard entity.components.has(InputTargetComponent.self) else { continue } entity .components[ModelComponent.self]?.materials = [ SimpleMaterial(color: .blue, isMetallic: false) ] } } } .gesture(TapGesture().targetedToAnyEntity().onEnded{ tap in tap.entity .components[ModelComponent.self]?.materials = [ SimpleMaterial(color: .green, isMetallic: false) ] }) .gesture(DragGesture(coordinateSpace: .global) .targetedToAnyEntity().updating($isDragging) { value, state, _ in if let location3d = value.unproject(value.location, from: .global, to: .scene) { value.entity.setPosition(location3d, relativeTo: root) } }) } } #Preview { ContentView() }
Topic: Graphics & Games SubTopic: RealityKit Tags:
Aug ’25
Reply to ARKit Planes do not appear where expected on visionOS
You can use simple planes if you want but you have to account for the fact that the anchor is not necessarily the center of the plane. You will still get a "bounding box" style representation and there may be some over/under lap but it should be much closer to what you were expecting. Something like the following should work for you on both vertical and horizontal planes. The relevant line is the setTransformationMatrix entity.setTransformMatrix( anchor.originFromAnchorTransform * anchor.geometry.extent.anchorFromExtentTransform, relativeTo: nil) if generateSimplifiedPlanes { let mesh: MeshResource = try! await MeshResource.generatePlane( width: anchor.geometry.extent.width, height: anchor.geometry.extent.height) modelEntity.model?.mesh = mesh modelEntity.collision?.shapes = [try! await ShapeResource.generateStaticMesh(from: mesh)] entity.setTransformMatrix( anchor.originFromAnchorTransform * anchor.geometry.extent.anchorFromExtentTransform, relativeTo: nil) } else { let shape: ShapeResource = try! await ShapeResource.generateStaticMesh( positions: anchor.geometry.meshVertices.asSIMD3(ofType: Float.self), faceIndices: anchor.geometry.meshFaces.asUInt16Array()) modelEntity.collision?.shapes = [shape] modelEntity.model?.mesh = planeAnchorToMeshResource(anchor) entity.transform = Transform(matrix: anchor.originFromAnchorTransform) } Notes: It appears that the extent is always defined on a vertical plane so if you apply anchorFromExtentTransform you always want to use a vertical plane. This is rough code from a while ago and I haven't checked to see if there are newer/easier ways to do this.
Apr ’25
Reply to SwiftData ModelContext Pollution with Multiple ModelContainers and Schemas
OK. Thank you for the reply @DTS Engineer . I'll namespace the conflicting model for now. Hopefully it won't be too difficult to migrate to the proper fix, if one is provided.
Replies
Boosts
Views
Activity
Mar ’26
Reply to SwiftData ModelContext Pollution with Multiple ModelContainers and Schemas
@joadan yes, the application crashes as well. The below view will terminated the app if you attempt to save a local item. struct ContentView: View { @State private var localId: Int = 0 @State private var localCount: Int = 0 @State private var remoteId: Int = 0 @State private var remoteCount: Int = 0 private var localContainer: ModelContainer private var remoteContainer: ModelContainer private let log = Logger() init() { localContainer = { do { let schema = Schema(versionedSchema: LocalSchema.self) let config = ModelConfiguration("local", schema: schema, isStoredInMemoryOnly: true, allowsSave: true, cloudKitDatabase: .none) return try ModelContainer(for: schema, configurations: config) } catch { fatalError("could not create local store") } }() remoteContainer = { do { let schema = Schema(versionedSchema: RemoteSchema.self) let config = ModelConfiguration("remote", schema: schema, isStoredInMemoryOnly: true, allowsSave: true, cloudKitDatabase: .none) return try ModelContainer(for: schema, configurations: config) } catch { fatalError("could not create remote store") } }() } var body: some View { HStack { VStack { Text("\(localCount)") Button("Save Local") { do { log.info("save local") localId += 1 let context = ModelContext(localContainer) let item = LocalSchema.Item(title: "local: \(localId)", created: .now, modified: .now) context.insert(item) try context.save() localCount = try context.fetchCount(FetchDescriptor<LocalSchema.Item>()) } catch { log.error("\(error.localizedDescription)") } } } VStack { Text("\(remoteCount)") Button("Save Remote") { do { log.info("save remote") remoteId += 1 let context = ModelContext(remoteContainer) let item = RemoteSchema.Item(title: "remote: \(remoteId)", created: .now, modified: .now, origin: "from space") context.insert(item) try context.save() remoteCount = try context.fetchCount(FetchDescriptor<RemoteSchema.Item>()) } catch { log.error("\(error.localizedDescription)") } } } } } }
Replies
Boosts
Views
Activity
Mar ’26
Reply to macOS 26: retain cycle detected when navigation link label contains a Swift Chart
I have created FB20099118 and the attached project still reproduces the issue.
Topic: UI Frameworks SubTopic: SwiftUI Tags:
Replies
Boosts
Views
Activity
Nov ’25
Reply to How to detect which entity was tapped?
Do the entities that you want to drag have colliders and InputTargetComponents? If so you can use the entity value on the tap and drag gesture directly. TargetedToAnyEntity requires an input target component to trigger. The below lets you tap on a box to change the material and drag a box to a different location. I believe both Tap and Drag gestures have a hitTest method that you can use as well. import SwiftUI import RealityKit struct ContentView: View { @State var root: Entity = Entity() @GestureState private var isDragging: Bool = false var body: some View { ZStack(alignment: .bottom) { RealityView { content in content.add(root) for idx in 0...3 { let ball = ModelEntity(mesh: .generateBox(size: 0.1), materials: [SimpleMaterial(color: .blue, isMetallic: false)]) ball.generateCollisionShapes(recursive: true) ball.components.set(InputTargetComponent()) ball.position.y = 0.3 * Float(idx) root.addChild(ball) } } Button("Reset") { for entity in root.children { guard entity.components.has(InputTargetComponent.self) else { continue } entity .components[ModelComponent.self]?.materials = [ SimpleMaterial(color: .blue, isMetallic: false) ] } } } .gesture(TapGesture().targetedToAnyEntity().onEnded{ tap in tap.entity .components[ModelComponent.self]?.materials = [ SimpleMaterial(color: .green, isMetallic: false) ] }) .gesture(DragGesture(coordinateSpace: .global) .targetedToAnyEntity().updating($isDragging) { value, state, _ in if let location3d = value.unproject(value.location, from: .global, to: .scene) { value.entity.setPosition(location3d, relativeTo: root) } }) } } #Preview { ContentView() }
Topic: Graphics & Games SubTopic: RealityKit Tags:
Replies
Boosts
Views
Activity
Aug ’25
Reply to Unexpected lines appear in PDFView on visionOS 26 beta
I have created FB19426676. It includes an example project that reproduces the issue on my device.
Topic: UI Frameworks SubTopic: SwiftUI Tags:
Replies
Boosts
Views
Activity
Aug ’25
Reply to ARKit Planes do not appear where expected on visionOS
You can use simple planes if you want but you have to account for the fact that the anchor is not necessarily the center of the plane. You will still get a "bounding box" style representation and there may be some over/under lap but it should be much closer to what you were expecting. Something like the following should work for you on both vertical and horizontal planes. The relevant line is the setTransformationMatrix entity.setTransformMatrix( anchor.originFromAnchorTransform * anchor.geometry.extent.anchorFromExtentTransform, relativeTo: nil) if generateSimplifiedPlanes { let mesh: MeshResource = try! await MeshResource.generatePlane( width: anchor.geometry.extent.width, height: anchor.geometry.extent.height) modelEntity.model?.mesh = mesh modelEntity.collision?.shapes = [try! await ShapeResource.generateStaticMesh(from: mesh)] entity.setTransformMatrix( anchor.originFromAnchorTransform * anchor.geometry.extent.anchorFromExtentTransform, relativeTo: nil) } else { let shape: ShapeResource = try! await ShapeResource.generateStaticMesh( positions: anchor.geometry.meshVertices.asSIMD3(ofType: Float.self), faceIndices: anchor.geometry.meshFaces.asUInt16Array()) modelEntity.collision?.shapes = [shape] modelEntity.model?.mesh = planeAnchorToMeshResource(anchor) entity.transform = Transform(matrix: anchor.originFromAnchorTransform) } Notes: It appears that the extent is always defined on a vertical plane so if you apply anchorFromExtentTransform you always want to use a vertical plane. This is rough code from a while ago and I haven't checked to see if there are newer/easier ways to do this.
Replies
Boosts
Views
Activity
Apr ’25