1

I have a @EnvironmentObject.

@main
struct Image_WidgetApp: App {
    @State var imageNumString = ""
    @State var showDetailView = false  
    @EnvironmentObject var userData: UserData
    var body: some Scene {        
        WindowGroup {
            if(!showDetailView){
                ContentView()
                    .onOpenURL { url in
                        imageNumString = url.absoluteString
                        showDetailView = true
                    }
                    .environmentObject(UserData())   // First instance of the environmentObject
            }
            else{
                ImageDetailView( mySubstring: $imageNumString, doneFunction: {
                    self.showDetailView = false
                })                                    
                .environmentObject(UserData())   // Second instance of the environmentObject
            }
        }
    }
}

If user open the app via the app icon, I set ContentView() active.

If user open the app via the widget, I set ImageDetailView() active by setting the showDetailView = true in onOpenURL.

Everything is okay until now.

The problem is possibly I have 2 different instance of the same environmentObject. See https://github.com/peterfriese/Swift-EnvironmentObject-Demo

Because when I change anything in any view, the other view doesn't aware of it.

To get rid of the problem, I have tried to use NavigationLink, since this approach aims to push the ImageDetailView() as a child view but no chance. Widget click doesn't push the ImageDetailView() to the navigation stack.

@main
struct Image_WidgetApp: App {
    @State var imageNumString = ""
    @State var showDetailView = false  
    @EnvironmentObject var userData: UserData
    var body: some Scene {        
        WindowGroup {
                ContentView()
                    .onOpenURL { url in
                        imageNumString = url.absoluteString
                        showDetailView = true
                        if imageNumString.count > 0{

                            imageNumString = url.absoluteString
            
                            NavigationLink(destination: ImageDetailView(mySubstring: $imageNumString), isActive: $showDetailView) {
                                EmptyView()
                            } .hidden()
                        }
                        .environmentObject(UserData())  
            }
        }
    }     
}

How can I use the @EnvironmentObject as a single instance?

1 Answer 1

3

How can I use the @EnvironmentObject as a single instance?

You can create one global UserData instance and inject where necessary:

@main
struct Image_WidgetApp: App { 
    @StateObject var userData = UserData()

    var body: some Scene {        
        WindowGroup {
                FirstView()
                    .environmentObject(userData)
                SecondView()
                    .environmentObject(userData)
            }
        }
    }     
}

Regarding launching a different view from an App/Widget see:

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.