0

I'm trying to generate some mock data for my preview in Xcode with a method written directly in ContentView_Previews but I have no success and I don't understand why.

struct ContentView_Previews: PreviewProvider {
    static let healthManager = generateMockData()
    
    static var previews: some View {
        MainView().environmentObject(healthManager)
    }
    
    static func generateMockData() -> HealthManager {
        let defaultHealthManager = HealthManager()
        defaultHealthManager.gavePermissions = true
        
        for i in 1...10 {
            let defaultWorkout = HKWorkout(activityType: .traditionalStrengthTraining,
                                           start: .now - Double(i * 50),
                                           end: .now,
                                           duration: Double(i * 100),
                                           totalEnergyBurned: HKQuantity(unit: .largeCalorie(), doubleValue: Double(i * 100)),
                                           totalDistance: nil,
                                           device: nil,
                                           metadata: nil)
            
            defaultHealthManager.previousWorkouts.append(defaultWorkout)
        }
        
        
        return defaultHealthManager
    }
}

Basically it shows up defaultHealthManager object has no values set besides the default ones. If I call ContentView_Previews. generateMockData() for my property in the actual view at runtime, it works fine.

trusk
  • 1,634
  • 2
  • 18
  • 32

1 Answers1

1

On occasion, I seem to need to create what I call an intermediary view to get things to work. Does something like this work?

struct MainViewIntermediary: View {
    @State var healthManager: HealthManager

    init() {
        let defaultHealthManager = HealthManager()
        defaultHealthManager.gavePermissions = true
        
        for i in 1...10 {
            let defaultWorkout = HKWorkout(activityType: .traditionalStrengthTraining,
                                           start: .now - Double(i * 50),
                                           end: .now,
                                           duration: Double(i * 100),
                                           totalEnergyBurned: HKQuantity(unit: .largeCalorie(), doubleValue: Double(i * 100)),
                                           totalDistance: nil,
                                           device: nil,
                                           metadata: nil)
            
            defaultHealthManager.previousWorkouts.append(defaultWorkout)
            _healthManager = State(initialValue: defaultHealthManager)
        }
    }

   var body: some View {
        MainView().environmentObject(healthManager)
    }
}

Then your preview provider becomes:

struct ContentView_Previews: PreviewProvider {
    
    static var previews: some View {
        MainViewIntermediary()
    }
}
Yrb
  • 8,103
  • 2
  • 14
  • 44
  • It's a workaround, yes. At this point I got it running by calling `.generate` directly from the view, but I would like to see if I can get it to work as I initially tried. – trusk Feb 08 '22 at 16:50
  • It is a work around, but you wrap is in an `#if DEBUG` and it never makes it to code. Previews is about testing your view, not about having production code. – Yrb Feb 08 '22 at 17:48