Post

Replies

Boosts

Views

Activity

Reply to How to toggle CoreData CloudKit sync during App runtime
I further investigated this issue. The problem seems to be in the following line. Here I inject the viewContext into my view hierarchy. ContentView()                 .environment(\.managedObjectContext, persistence.container.viewContext) First I deactivate the CloudKit Sync. The persistence container will be reinitialized. Therefore, I get a new instance of the viewContext. 021-12-04 22:08:19.063535+0100 TestApp[67682:1918331] [persistence] Deactivating Core Data CloudKit sync. 2021-12-04 22:08:19.063750+0100 TestApp[67682:1918331] [persistence] Persistence -> viewContext before deactivating cloudKit = <NSManagedObjectContext: 0x60000129d040> 2021-12-04 22:08:19.071889+0100 TestApp[67682:1918331] [persistence] Persistence set to local CoreData. 2021-12-04 22:08:19.102950+0100 TestApp[67682:1918331] [persistence] Persistence -> viewContext after deactivating cloudKit = <NSManagedObjectContext: 0x6000012f4ea0> Afterwards I add a new test entity to the viewContext. The viewContext stored in the appDelegate has been set correctly. The @Environment(\.managedObjectContext) private var viewContext ones it not updated automatically. Is there a way to force the update? 2021-12-04 22:08:47.352342+0100 TestApp[67682:1918331] [common] Adding test entitiy. 2021-12-04 22:08:47.352552+0100 TestApp[67682:1918331] [common] ShotResultList -> environment viewContext = <NSManagedObjectContext: 0x60000129d040> 2021-12-04 22:08:47.352699+0100 TestApp[67682:1918331] [common] ShotResultList -> appDelegate viewContext = <NSManagedObjectContext: 0x6000012f4ea0>
Dec ’21
Reply to How to toggle CoreData CloudKit sync during App runtime
I fixed the issue mentioned above by the following changes. The persistence instance can be reloaded in order switch between NSPersistentCloudKitContainerand NSPersistentContainer. After every reload I increase the attribute persistenceContainerReloaded by one. The line .id(persistence.persistenceContainerReloaded)triggers the reload of the full view hierarchy. Now every view uses the correct viewContext instance. @main struct TargetShooterApp: App {     @StateObject var persistence: Persistence = Persistence.shared     var body: some Scene {         WindowGroup {             ContentView()                 .environment(\.managedObjectContext, persistence.container.viewContext)                 .id(persistence.persistenceContainerReloaded)         }     } } Now I faced a new issue. I still see CoreData+CloudKit debug outputs in the terminal, although the storeDescription.cloudKitContainerOptionsis nil. The device is still able to sync local changes to other devices, but is not capable to receive changes made on other devices. After the restart of the app, everything works as expected. It seems, there is still a background process NSCloudKitMirroringDelegate running, uploading CoreData changes. Any ideas?
Dec ’21
Reply to Dynamically change sort order a SwiftUI Sectioned List
Hi, I checked out some WWDC 2021 videos and found some hints. The following code changes the sort order of the groups. That's works fine so far. But in addition to that I'd like to change the sort order of the timestamps as well. How can I do this? As soon as I add a second sort descriptor, the app crashes with the previous error. import SwiftUI import CoreData struct ContentView: View {     @Environment(\.managedObjectContext) private var viewContext     @State var counter: UInt32 = 0     @State var order: SortOrder = .reverse     @SectionedFetchRequest(         sectionIdentifier: \.group!,         sortDescriptors: [SortDescriptor(\Item.group, order: .reverse)],         predicate: nil,         animation: .linear     )     private var sectionedItems: SectionedFetchResults<String, Item>     var body: some View {         NavigationView {             List {                 ForEach(sectionedItems) { section in                     Section(header: Text("\(section.id)")) {                         ForEach(section, id: \Item.id) { item in                             NavigationLink {                                 VStack {                                     Text("Timestamp: \(item.timestamp!, formatter: itemFormatter)")                                     Text("UUID: \(item.uniqueId!)")                                     Text("\(item.group!)")                                 }                             } label: {                                 VStack {                                     Text(item.timestamp!, formatter: itemFormatter)                                 }                             }                         }                     }                 }             }             .navigationTitle("Sectioned List")             .toolbar {                 ToolbarItem(placement: .primaryAction) {                     Button(action: addItem) {                         Label("Add Item", systemImage: "plus")                     }                 }                 ToolbarItem(placement: .principal) {                     Button(action: toggleSortOrder) {                         Label("Sort Order", systemImage: "arrow.up.arrow.down")                     }                     .onChange(of: order) { _ in                         print("onChange order = \(order)")                         let sortDescriptors = [SortDescriptor(\Item.group, order: order)]                         let config = sectionedItems                         config.sortDescriptors = sortDescriptors                         config.sectionIdentifier = \Item.group!                     }                 }             }         }     }     private func addItem() { // ...     }     private func toggleSortOrder() {         order = (order == .reverse ? .forward : .reverse)         print("toggleSortOrder: order = \(order)")     } }
Jan ’22
Reply to Charts Framework: chartYScale(domain:) scales the y-axis correctly but BarMarks are drawn down to bottom part of the screen
I implemented an example project which shows the same issue. import SwiftUI import Charts struct Values: Identifiable { var name: String var value: Int var id = UUID() } /// Displays an exemplary bar chart. struct BarChartView: View { var chartData: [Values] = [.init(name: "A", value: 93), .init(name: "B", value: 92), .init(name: "C", value: 90), .init(name: "D", value: 91)] var minValueYAxis: Int = 89 var maxValueYAxis: Int = 93 var average: Double { get { var sum = 0 for data in chartData { sum += data.value } return Double(sum) / Double(chartData.count) } } var body: some View { GroupBox("Results") { Chart { ForEach(chartData) { values in BarMark(x: .value("name", values.name), y: .value("value", values.value)) .cornerRadius(5.0) .annotation(position: .overlay, alignment: .top, spacing: 10.0) { Text("\(values.value)") .foregroundColor(.white) .fontWeight(.bold) } RuleMark(y: .value("average", average)) .foregroundStyle(.red) .annotation(position: .overlay, alignment: .bottomTrailing, spacing: 0.0) { Text("ø = \(String(format: "%.2f", average))") .foregroundColor(.red) } } } .chartYScale(domain: minValueYAxis...maxValueYAxis) .frame(height: 220, alignment: .top) } .backgroundStyle(Color.white) .shadow(radius: 5.0, x: 2.0, y: 2.0) .padding() } } struct ContentView: View { var body: some View { ScrollView { VStack { Text("Chart 1") BarChartView() } } } } If I remove the line .chartYScale(domain: minValueYAxis...maxValueYAxis), everything looks ok, but it is hard to see the differences between the bars. And here's the resulting views on the iPhone 13 simulator.
Jun ’22
Reply to Is it possible to unload/change the PersistenceStore in a SwiftUI App during runtime
Not really. I found a way to unload and reload my persistence stores. But my App crashes because the old viewContext is still used in the view hierarchy. Therefore, I tried to completely unload my root view (ContentVIew) by switching to another view. But the ContentView() won't be released from memory, even if it is not shown. @StateObject private var appRootManager = AppRootManager() var body: some Scene { WindowGroup { Group { switch appRootManager.currentRoot { case .splash: SplashView() case .reloading: StatusView() case .ready: ContentView() } .environmentObject(appRootManager) } } }
Sep ’24
Reply to How to toggle CoreData CloudKit sync during App runtime
Not really. I found a way to unload and reload my persistence stores. But my App crashes because the old viewContext is still used in the view hierarchy. Therefore, I tried to completely unload my root view (ContentVIew) by switching to another view. But the ContentView() won't be released from memory, even if it is not shown. @StateObject private var appRootManager = AppRootManager() var body: some Scene { WindowGroup { Group { switch appRootManager.currentRoot { case .splash: SplashView() case .reloading: StatusView() case .ready: ContentView() } .environmentObject(appRootManager) } } }
Sep ’24