I need a way to understand why I cannot show alert messages in swiftui for this code, I'd like to show alert if something happens while loading web page (also monitoring cookies, but is another task) I even tried using a UIAlertController, but with no success. , I think my issue is about alert with is presenting one after the other, but I'm presenting only one. :
import SwiftUI
import WebKit
struct ContentView: View {
@State private var showWebView = false
@State private var showError = false
@State private var errorMessage = ""
var body: some View {
Button("open WebView") {
if !showError {
showWebView = true
}
}
.fullScreenCover(isPresented: $showWebView) {
if let url = URL(string: "https://www.google.com") {
WebView(url: url) { error in
self.errorMessage = error
self.showError = true
}
} else {
Text("not valid url")
}
}
.alert(isPresented: $showError) {
Alert(title: Text("Error"), message: Text(errorMessage), dismissButton: .default(Text("OK"), action: {}))
}
}
}
struct WebView: UIViewRepresentable {
let url: URL
var handleError: ((String) -> Void)?
func makeUIView(context: Context) -> WKWebView {
let webView = WKWebView()
webView.navigationDelegate = context.coordinator
return webView
}
func updateUIView(_ uiView: WKWebView, context: Context) {
let request = URLRequest(url: url)
uiView.load(request)
}
func makeCoordinator() -> Coordinator {
Coordinator(self)
}
//-------------------------------------------------------------------------------------
class Coordinator: NSObject, WKNavigationDelegate {
var parent: WebView
init(_ parent: WebView) {
self.parent = parent
}
func webView(_ webView: WKWebView, didFailProvisionalNavigation navigation: WKNavigation!, withError error: Error) {
// self.parent.handleError?(error.localizedDescription)
}
func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
self.parent.handleError?("Hello, fake error for testing")
}
}
//-------------------------------------------------------------------------------------
}
on console I get this messages
2024-02-21 15:48:06.529734+0100 testRedirectWebView[32686:38145275] [Sandbox] Could not enable Mach bootstrap, errno = 1. 2024-02-21 15:48:06.529863+0100 testRedirectWebView[32686:38145275] [Sandbox] Could not enable Mach bootstrap, errno = 1. 2024-02-21 15:48:07.385311+0100 testRedirectWebView[32686:38145275] [Security] This method should not be called on the main thread as it may lead to UI unresponsiveness.
2024-02-21 15:48:07.385440+0100 testRedirectWebView[32686:38145275] [Security] This method should not be called on the main thread as it may lead to UI unresponsiveness.
2024-02-21 15:48:08.063187+0100 testRedirectWebView[32686:38145275] [Presentation] Attempt to present <SwiftUI.PlatformAlertController: 0x103033a00> on <TtGC7SwiftUI19UIHostingControllerGVS_15ModifiedContentVS_7AnyViewVS_12RootModifier_: 0x10301e800> (from <TtGC7SwiftUI19UIHostingControllerGVS_15ModifiedContentVS_7AnyViewVS_12RootModifier_: 0x10301e800>) which is already presenting <TtGC7SwiftUI29PresentationHostingControllerVS_7AnyView: 0x103031e00>.
2024-02-21 15:48:08.225535+0100 testRedirectWebView[32686:38145275] [Security] This method should not be called on the main thread as it may lead to UI unresponsiveness.
2024-02-21 15:48:08.225651+0100 testRedirectWebView[32686:38145275] [Security] This method should not be called on the main thread as it may lead to UI unresponsiveness.
If you attach the alert to the WebView
instead of the Button
, the alert displays as expected with no console errors.
.fullScreenCover(isPresented: $showWebView) {
if let url = URL(string: "https://www.google.com") {
WebView(url: url) { error in
self.errorMessage = error
self.showError = true
}
.alert(isPresented: $showError) {
Alert(title: Text("Error"), message: Text(errorMessage), dismissButton: .default(Text("OK"), action: {}))
}
} else {
Text("not valid url")
}
}
I believe the error you saw came from the button trying to present the web page and the alert. This way, the button presents the web page, then the web page presents the alert.