UPGRADE YOUR SKILLS: Learn advanced Swift and SwiftUI on Hacking with Swift+! >>

Initialization Issue

Forums > SwiftUI

@ASH  

I have some lengthy code with explicit colors, that works . I have reduced the cogent parts to the simplification below . My View Model is passed to my view as an environment object.

struct ConteView: View {

@EnvironmentObject var game: colorGameVM ... // a bunch of @State vars ...

@State var angGrad: [Color] = [Color.red,Color.white,Color.blue]

var body: some View { // bunch of stuff }

}

I want to dynamically use colors from my View Model, so I changed it like this

struct ConteView: View {

@EnvironmentObject var game: colorGameVM ... // a bunch of @State vars ...

@State var angGrad: [Color] = [game.color1,game.color2,game.color3]

var body: some View { // bunch of stuff }

}

and got the "Cannot use instance member 'game' within property initializer; property initializers run before 'self' is available" error on the angGrad line.

I left the @State type def and moved angGrad code into an initializer but get an error "Variable 'self.manager' used before being initialized" in the init. I don't understand what this means. I cannot bring the game var into the init because as an Environment Object it's a get only property.

struct ConteView: View {

@EnvironmentObject var game: colorGameVM ... // a bunch of @State vars ...

@State var angGrad: [Color]

init() { self.angGrad = [game.color1,game.color2,game.color3] }

var body: some View { // bunch of stuff }

}

Any suggestions on how to achieve this? BTW, I know I can access the game.color directly in my View, the angGrad is a an array used for a background color gradient.

2      

The explanation why you can't use an EnvironmentObject in init is explained by roosterboy here.

Because when init is called on a View, that's no guarantee it will actually be displayed on screen. (e.g., the destination of a NavigationLink gets its init called when the NavigationLink is rendered, even if the user never follows the link) It's not until the body is rendered that it will be displayed and so that's when an environment needs to exist. If you used an environment object or value at init time, it could be different by the time the View is actually rendered.

Please, use code tags next time you describe your problem because it's easier to understand what's your code.

One solution could be that your ViewModel is passed in the init and it's not a StateObject but a ObserverdObject.

2      

@ASH  

Thank you @Hatsushira for that explanation. I will probably just rework the code to access the game.color values directly.

2      

Hacking with Swift is sponsored by Essential Developer

SPONSORED Join a FREE crash course for mid/senior iOS devs who want to achieve an expert level of technical and practical skills – it’s the fast track to being a complete senior developer! Hurry up because it'll be available only until April 28th.

Click to save your free spot now

Sponsor Hacking with Swift and reach the world's largest Swift community!

Archived topic

This topic has been closed due to inactivity, so you can't reply. Please create a new topic if you need to.

All interactions here are governed by our code of conduct.

 
Unknown user

You are not logged in

Log in or create account
 

Link copied to your pasteboard.