How to set addObserver in SwiftUI?
The accepted answer may work but is not really how you're supposed to do this. In SwiftUI you don't need to add an observer in that way.
You add a publisher and it still can listen to NSNotification events triggered from non-SwiftUI parts of the app and without needing combine.
Here as an example, a list will update when it appears and when it receives a notification, from a completed network request on another view / controller or something similar etc.
If you need to then trigger an @objc func for some reason, you will need to create a Coordinator
with UIViewControllerRepresentable
struct YourSwiftUIView: View { let pub = NotificationCenter.default .publisher(for: NSNotification.Name("YourNameHere")) var body: some View { List() { ForEach(userData.viewModels) { viewModel in SomeRow(viewModel: viewModel) } } .onAppear(perform: loadData) .onReceive(pub) { (output) in self.loadData() } } func loadData() { // do stuff }}
I have one approach for NotificationCenter
usage in SwiftUI
.
For more information Apple Documentation
Notification extension
extension NSNotification { static let ImageClick = Notification.Name.init("ImageClick")}
ContentView
struct ContentView: View { var body: some View { VStack { DetailView() } .onReceive(NotificationCenter.default.publisher(for: NSNotification.ImageClick)) { obj in // Change key as per your "userInfo" if let userInfo = obj.userInfo, let info = userInfo["info"] { print(info) } } }}
DetailView
struct DetailView: View { var body: some View { Image(systemName: "wifi") .frame(width: 30,height: 30, alignment: .center) .foregroundColor(.black) .onTapGesture { NotificationCenter.default.post(name: NSNotification.ImageClick, object: nil, userInfo: ["info": "Test"]) } }}
It is not SwiftUI-native approach, which is declarative & reactive. Instead you should use NSNotificationCenter.publisher(for:object:) from Combine.
See more details in Apple Documentation