@capacitor-plus/ios 8.0.0-beta.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/Capacitor/Capacitor/AppUUID.swift +51 -0
- package/Capacitor/Capacitor/Array+Capacitor.swift +31 -0
- package/Capacitor/Capacitor/CAPApplicationDelegateProxy.swift +32 -0
- package/Capacitor/Capacitor/CAPBridge.swift +25 -0
- package/Capacitor/Capacitor/CAPBridgeDelegate.swift +6 -0
- package/Capacitor/Capacitor/CAPBridgeProtocol.swift +148 -0
- package/Capacitor/Capacitor/CAPBridgeViewController+CDVScreenOrientationDelegate.h +6 -0
- package/Capacitor/Capacitor/CAPBridgeViewController+CDVScreenOrientationDelegate.m +5 -0
- package/Capacitor/Capacitor/CAPBridgeViewController.swift +384 -0
- package/Capacitor/Capacitor/CAPBridgedJSTypes.h +18 -0
- package/Capacitor/Capacitor/CAPBridgedJSTypes.m +43 -0
- package/Capacitor/Capacitor/CAPBridgedPlugin+getMethod.swift +13 -0
- package/Capacitor/Capacitor/CAPBridgedPlugin.h +41 -0
- package/Capacitor/Capacitor/CAPFile.swift +14 -0
- package/Capacitor/Capacitor/CAPInstanceConfiguration.h +38 -0
- package/Capacitor/Capacitor/CAPInstanceConfiguration.m +93 -0
- package/Capacitor/Capacitor/CAPInstanceConfiguration.swift +78 -0
- package/Capacitor/Capacitor/CAPInstanceDescriptor.h +167 -0
- package/Capacitor/Capacitor/CAPInstanceDescriptor.m +56 -0
- package/Capacitor/Capacitor/CAPInstanceDescriptor.swift +198 -0
- package/Capacitor/Capacitor/CAPInstancePlugin.swift +10 -0
- package/Capacitor/Capacitor/CAPLog.swift +11 -0
- package/Capacitor/Capacitor/CAPNotifications.swift +69 -0
- package/Capacitor/Capacitor/CAPPlugin+LoadInstance.swift +20 -0
- package/Capacitor/Capacitor/CAPPlugin.h +60 -0
- package/Capacitor/Capacitor/CAPPlugin.m +180 -0
- package/Capacitor/Capacitor/CAPPluginCall.h +25 -0
- package/Capacitor/Capacitor/CAPPluginCall.m +36 -0
- package/Capacitor/Capacitor/CAPPluginCall.swift +97 -0
- package/Capacitor/Capacitor/CAPPluginMethod.h +36 -0
- package/Capacitor/Capacitor/CAPPluginMethod.m +44 -0
- package/Capacitor/Capacitor/CAPPluginMethod.swift +17 -0
- package/Capacitor/Capacitor/Capacitor.h +15 -0
- package/Capacitor/Capacitor/Capacitor.modulemap +8 -0
- package/Capacitor/Capacitor/CapacitorBridge.swift +768 -0
- package/Capacitor/Capacitor/CapacitorExtension.swift +24 -0
- package/Capacitor/Capacitor/Codable/JSValueDecoder.swift +479 -0
- package/Capacitor/Capacitor/Codable/JSValueEncoder.swift +671 -0
- package/Capacitor/Capacitor/Data+Capacitor.swift +22 -0
- package/Capacitor/Capacitor/DocLinks.swift +8 -0
- package/Capacitor/Capacitor/Info.plist +24 -0
- package/Capacitor/Capacitor/JS.swift +122 -0
- package/Capacitor/Capacitor/JSExport.swift +218 -0
- package/Capacitor/Capacitor/JSTypes.swift +254 -0
- package/Capacitor/Capacitor/KeyPath.swift +60 -0
- package/Capacitor/Capacitor/KeyValueStore.swift +303 -0
- package/Capacitor/Capacitor/NotificationHandlerProtocol.swift +6 -0
- package/Capacitor/Capacitor/NotificationRouter.swift +60 -0
- package/Capacitor/Capacitor/PluginCallResult.swift +106 -0
- package/Capacitor/Capacitor/PluginConfig.swift +56 -0
- package/Capacitor/Capacitor/Plugins/CapacitorCookieManager.swift +141 -0
- package/Capacitor/Capacitor/Plugins/CapacitorCookies.swift +57 -0
- package/Capacitor/Capacitor/Plugins/CapacitorHttp.swift +57 -0
- package/Capacitor/Capacitor/Plugins/CapacitorUrlRequest.swift +225 -0
- package/Capacitor/Capacitor/Plugins/Console.swift +16 -0
- package/Capacitor/Capacitor/Plugins/HttpRequestHandler.swift +236 -0
- package/Capacitor/Capacitor/Plugins/SystemBars.swift +133 -0
- package/Capacitor/Capacitor/Plugins/WebView.swift +44 -0
- package/Capacitor/Capacitor/PrivacyInfo.xcprivacy +14 -0
- package/Capacitor/Capacitor/Router.swift +29 -0
- package/Capacitor/Capacitor/TmpViewController.swift +8 -0
- package/Capacitor/Capacitor/UIColor.swift +55 -0
- package/Capacitor/Capacitor/UIStatusBarManager+CAPHandleTapAction.m +37 -0
- package/Capacitor/Capacitor/WKWebView+Capacitor.m +15 -0
- package/Capacitor/Capacitor/WKWebView+Capacitor.swift +80 -0
- package/Capacitor/Capacitor/WebViewAssetHandler.swift +550 -0
- package/Capacitor/Capacitor/WebViewDelegationHandler.swift +361 -0
- package/Capacitor/Capacitor/assets/native-bridge.js +1029 -0
- package/Capacitor.podspec +23 -0
- package/CapacitorCordova/CapacitorCordova/CapacitorCordova.h +25 -0
- package/CapacitorCordova/CapacitorCordova/CapacitorCordova.modulemap +6 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/AppDelegate.h +8 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/AppDelegate.m +5 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDV.h +28 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVAvailability.h +109 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVAvailabilityDeprecated.h +21 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVCommandDelegate.h +49 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVCommandDelegateImpl.h +39 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVCommandDelegateImpl.m +149 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVConfigParser.h +31 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVConfigParser.m +81 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVInvokedUrlCommand.h +52 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVInvokedUrlCommand.m +116 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVPlugin+Resources.h +39 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVPlugin+Resources.m +38 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVPlugin.h +76 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVPlugin.m +136 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVPluginManager.h +25 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVPluginManager.m +77 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVPluginResult.h +82 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVPluginResult.m +216 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVScreenOrientationDelegate.h +33 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVURLProtocol.h +27 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVURLProtocol.m +74 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVViewController.h +30 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVViewController.m +37 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVWebViewProcessPoolFactory.h +34 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/CDVWebViewProcessPoolFactory.m +55 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/NSDictionary+CordovaPreferences.h +35 -0
- package/CapacitorCordova/CapacitorCordova/Classes/Public/NSDictionary+CordovaPreferences.m +63 -0
- package/CapacitorCordova/CapacitorCordova/Info.plist +26 -0
- package/CapacitorCordova/CapacitorCordova/PrivacyInfo.xcprivacy +14 -0
- package/CapacitorCordova.podspec +26 -0
- package/LICENSE +21 -0
- package/package.json +33 -0
- package/scripts/pods_helpers.rb +12 -0
|
@@ -0,0 +1,361 @@
|
|
|
1
|
+
import Foundation
|
|
2
|
+
import WebKit
|
|
3
|
+
|
|
4
|
+
// adopting a public protocol in an internal class is by design
|
|
5
|
+
// swiftlint:disable lower_acl_than_parent
|
|
6
|
+
@objc(CAPWebViewDelegationHandler)
|
|
7
|
+
open class WebViewDelegationHandler: NSObject, WKNavigationDelegate, WKUIDelegate, WKScriptMessageHandler, UIScrollViewDelegate {
|
|
8
|
+
public internal(set) weak var bridge: CapacitorBridge?
|
|
9
|
+
open fileprivate(set) var contentController = WKUserContentController()
|
|
10
|
+
enum WebViewLoadingState {
|
|
11
|
+
case unloaded
|
|
12
|
+
case initialLoad(isOpaque: Bool)
|
|
13
|
+
case subsequentLoad
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
fileprivate(set) var webViewLoadingState = WebViewLoadingState.unloaded
|
|
17
|
+
|
|
18
|
+
private let handlerName = "bridge"
|
|
19
|
+
|
|
20
|
+
override public init() {
|
|
21
|
+
super.init()
|
|
22
|
+
contentController.add(self, name: handlerName)
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
open func cleanUp() {
|
|
26
|
+
contentController.removeScriptMessageHandler(forName: handlerName)
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
open func willLoadWebview(_ webView: WKWebView?) {
|
|
30
|
+
// Set the webview to be not opaque on the inital load. This prevents
|
|
31
|
+
// the webview from showing a white background, which is its default
|
|
32
|
+
// loading display, as that can appear as a screen flash. The opacity
|
|
33
|
+
// might have been set by something else, like a plugin, so we want
|
|
34
|
+
// to save the current value so it can be reset on success or failure.
|
|
35
|
+
if let webView = webView, case .unloaded = webViewLoadingState {
|
|
36
|
+
webViewLoadingState = .initialLoad(isOpaque: webView.isOpaque)
|
|
37
|
+
webView.isOpaque = false
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
// MARK: - WKNavigationDelegate
|
|
42
|
+
|
|
43
|
+
// The force unwrap is part of the protocol declaration, so we should keep it.
|
|
44
|
+
// swiftlint:disable:next implicitly_unwrapped_optional
|
|
45
|
+
open func webView(_ webView: WKWebView, didStartProvisionalNavigation navigation: WKNavigation!) {
|
|
46
|
+
// Reset the bridge on each navigation
|
|
47
|
+
bridge?.reset()
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
open func webView(
|
|
51
|
+
_ webView: WKWebView,
|
|
52
|
+
requestMediaCapturePermissionFor origin: WKSecurityOrigin,
|
|
53
|
+
initiatedByFrame frame: WKFrameInfo,
|
|
54
|
+
type: WKMediaCaptureType,
|
|
55
|
+
decisionHandler: @escaping (WKPermissionDecision) -> Void
|
|
56
|
+
) {
|
|
57
|
+
decisionHandler(.grant)
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
open func webView(_ webView: WKWebView,
|
|
61
|
+
requestDeviceOrientationAndMotionPermissionFor origin: WKSecurityOrigin,
|
|
62
|
+
initiatedByFrame frame: WKFrameInfo,
|
|
63
|
+
decisionHandler: @escaping (WKPermissionDecision) -> Void) {
|
|
64
|
+
decisionHandler(.grant)
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
open func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void) {
|
|
68
|
+
// post a notification for any listeners
|
|
69
|
+
NotificationCenter.default.post(name: .capacitorDecidePolicyForNavigationAction, object: navigationAction)
|
|
70
|
+
|
|
71
|
+
// sanity check, these shouldn't ever be nil in practice
|
|
72
|
+
guard let bridge = bridge, let navURL = navigationAction.request.url else {
|
|
73
|
+
decisionHandler(.allow)
|
|
74
|
+
return
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
// first, give plugins the chance to handle the decision
|
|
78
|
+
for pluginObject in bridge.plugins {
|
|
79
|
+
let plugin = pluginObject.value
|
|
80
|
+
let selector = NSSelectorFromString("shouldOverrideLoad:")
|
|
81
|
+
if plugin.responds(to: selector) {
|
|
82
|
+
let shouldOverrideLoad = plugin.shouldOverrideLoad(navigationAction)
|
|
83
|
+
if shouldOverrideLoad != nil {
|
|
84
|
+
if shouldOverrideLoad == true {
|
|
85
|
+
decisionHandler(.cancel)
|
|
86
|
+
return
|
|
87
|
+
} else if shouldOverrideLoad == false {
|
|
88
|
+
decisionHandler(.allow)
|
|
89
|
+
return
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
// next, check if this is covered by the allowedNavigation configuration
|
|
96
|
+
if let host = navURL.host, bridge.config.shouldAllowNavigation(to: host) {
|
|
97
|
+
decisionHandler(.allow)
|
|
98
|
+
return
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
// otherwise, is this a new window or a main frame navigation but to an outside source
|
|
102
|
+
let toplevelNavigation = (navigationAction.targetFrame == nil || navigationAction.targetFrame?.isMainFrame == true)
|
|
103
|
+
|
|
104
|
+
// Check if the url being navigated to is configured as an application url (whether local or remote)
|
|
105
|
+
let isApplicationNavigation = navURL.absoluteString.starts(with: bridge.config.serverURL.absoluteString) ||
|
|
106
|
+
navURL.absoluteString.starts(with: bridge.config.localURL.absoluteString)
|
|
107
|
+
|
|
108
|
+
if !isApplicationNavigation, toplevelNavigation {
|
|
109
|
+
// disallow and let the system handle it
|
|
110
|
+
if UIApplication.shared.applicationState == .active {
|
|
111
|
+
UIApplication.shared.open(navURL, options: [:], completionHandler: nil)
|
|
112
|
+
}
|
|
113
|
+
decisionHandler(.cancel)
|
|
114
|
+
return
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
// fallthrough to allowing it
|
|
118
|
+
decisionHandler(.allow)
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
// The force unwrap is part of the protocol declaration, so we should keep it.
|
|
122
|
+
// swiftlint:disable:next implicitly_unwrapped_optional
|
|
123
|
+
open func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
|
|
124
|
+
if case .initialLoad(let isOpaque) = webViewLoadingState {
|
|
125
|
+
webView.isOpaque = isOpaque
|
|
126
|
+
webViewLoadingState = .subsequentLoad
|
|
127
|
+
}
|
|
128
|
+
CAPLog.print("⚡️ WebView loaded")
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
// The force unwrap is part of the protocol declaration, so we should keep it.
|
|
132
|
+
// swiftlint:disable:next implicitly_unwrapped_optional
|
|
133
|
+
open func webView(_ webView: WKWebView, didFail navigation: WKNavigation!, withError error: Error) {
|
|
134
|
+
if case .initialLoad(let isOpaque) = webViewLoadingState {
|
|
135
|
+
webView.isOpaque = isOpaque
|
|
136
|
+
webViewLoadingState = .subsequentLoad
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
if let errorURL = bridge?.config.errorPathURL {
|
|
140
|
+
webView.load(URLRequest(url: errorURL))
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
CAPLog.print("⚡️ WebView failed to load")
|
|
144
|
+
CAPLog.print("⚡️ Error: " + error.localizedDescription)
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
// The force unwrap is part of the protocol declaration, so we should keep it.
|
|
148
|
+
// swiftlint:disable:next implicitly_unwrapped_optional
|
|
149
|
+
open func webView(_ webView: WKWebView, didFailProvisionalNavigation navigation: WKNavigation!, withError error: Error) {
|
|
150
|
+
if let errorURL = bridge?.config.errorPathURL {
|
|
151
|
+
webView.load(URLRequest(url: errorURL))
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
CAPLog.print("⚡️ WebView failed provisional navigation")
|
|
155
|
+
CAPLog.print("⚡️ Error: " + error.localizedDescription)
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
open func webViewWebContentProcessDidTerminate(_ webView: WKWebView) {
|
|
159
|
+
CAPLog.print("⚡️ WebView process terminated")
|
|
160
|
+
bridge?.reset()
|
|
161
|
+
webView.reload()
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
open func webView(_ webView: WKWebView, didReceive challenge: URLAuthenticationChallenge, completionHandler: @escaping @MainActor (URLSession.AuthChallengeDisposition, URLCredential?) -> Void) {
|
|
165
|
+
guard let bridge = bridge else {
|
|
166
|
+
completionHandler(.rejectProtectionSpace, nil)
|
|
167
|
+
return
|
|
168
|
+
}
|
|
169
|
+
|
|
170
|
+
for pluginObject in bridge.plugins {
|
|
171
|
+
let plugin = pluginObject.value
|
|
172
|
+
let selector = NSSelectorFromString("handleWKWebViewURLAuthenticationChallenge:completionHandler:")
|
|
173
|
+
if plugin.responds(to: selector) {
|
|
174
|
+
if plugin.handleWKWebViewURLAuthenticationChallenge(challenge, completionHandler: completionHandler) {
|
|
175
|
+
return
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
completionHandler(.rejectProtectionSpace, nil)
|
|
181
|
+
return
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
// MARK: - WKScriptMessageHandler
|
|
185
|
+
|
|
186
|
+
open func userContentController(_ userContentController: WKUserContentController, didReceive message: WKScriptMessage) {
|
|
187
|
+
guard let bridge = bridge else {
|
|
188
|
+
return
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
let body = message.body
|
|
192
|
+
if let dict = body as? [String: Any] {
|
|
193
|
+
let type = dict["type"] as? String ?? ""
|
|
194
|
+
|
|
195
|
+
if type == "js.error" {
|
|
196
|
+
if let error = dict["error"] as? [String: Any] {
|
|
197
|
+
logJSError(error)
|
|
198
|
+
}
|
|
199
|
+
} else if type == "message" {
|
|
200
|
+
let pluginId = dict["pluginId"] as? String ?? ""
|
|
201
|
+
let method = dict["methodName"] as? String ?? ""
|
|
202
|
+
let callbackId = dict["callbackId"] as? String ?? ""
|
|
203
|
+
|
|
204
|
+
let options = dict["options"] as? [String: Any] ?? [:]
|
|
205
|
+
|
|
206
|
+
if pluginId != "Console" {
|
|
207
|
+
CAPLog.print("⚡️ To Native -> ", pluginId, method, callbackId)
|
|
208
|
+
}
|
|
209
|
+
|
|
210
|
+
bridge.handleJSCall(call: JSCall(options: options, pluginId: pluginId, method: method, callbackId: callbackId))
|
|
211
|
+
} else if type == "cordova" {
|
|
212
|
+
let pluginId = dict["service"] as? String ?? ""
|
|
213
|
+
let method = dict["action"] as? String ?? ""
|
|
214
|
+
let callbackId = dict["callbackId"] as? String ?? ""
|
|
215
|
+
|
|
216
|
+
let args = dict["actionArgs"] as? Array ?? []
|
|
217
|
+
let options = ["options": args]
|
|
218
|
+
|
|
219
|
+
CAPLog.print("To Native Cordova -> ", pluginId, method, callbackId, options)
|
|
220
|
+
|
|
221
|
+
bridge.handleCordovaJSCall(call: JSCall(options: options, pluginId: pluginId, method: method, callbackId: callbackId))
|
|
222
|
+
}
|
|
223
|
+
}
|
|
224
|
+
}
|
|
225
|
+
|
|
226
|
+
// MARK: - WKUIDelegate
|
|
227
|
+
|
|
228
|
+
open func webView(_ webView: WKWebView, runJavaScriptAlertPanelWithMessage message: String, initiatedByFrame frame: WKFrameInfo, completionHandler: @escaping () -> Void) {
|
|
229
|
+
guard var viewController = bridge?.viewController else {
|
|
230
|
+
completionHandler()
|
|
231
|
+
return
|
|
232
|
+
}
|
|
233
|
+
|
|
234
|
+
if let presentedVC = viewController.presentedViewController, !presentedVC.isBeingDismissed {
|
|
235
|
+
viewController = presentedVC
|
|
236
|
+
}
|
|
237
|
+
|
|
238
|
+
let alertController = UIAlertController(title: nil, message: message, preferredStyle: .alert)
|
|
239
|
+
|
|
240
|
+
alertController.addAction(UIAlertAction(title: "Ok", style: .default, handler: { (_) in
|
|
241
|
+
completionHandler()
|
|
242
|
+
}))
|
|
243
|
+
|
|
244
|
+
viewController.present(alertController, animated: true, completion: nil)
|
|
245
|
+
}
|
|
246
|
+
|
|
247
|
+
open func webView(_ webView: WKWebView, runJavaScriptConfirmPanelWithMessage message: String, initiatedByFrame frame: WKFrameInfo, completionHandler: @escaping (Bool) -> Void) {
|
|
248
|
+
guard let viewController = bridge?.viewController else {
|
|
249
|
+
return
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
let alertController = UIAlertController(title: nil, message: message, preferredStyle: .alert)
|
|
253
|
+
|
|
254
|
+
alertController.addAction(UIAlertAction(title: "Cancel", style: .default, handler: { (_) in
|
|
255
|
+
completionHandler(false)
|
|
256
|
+
}))
|
|
257
|
+
|
|
258
|
+
alertController.addAction(UIAlertAction(title: "Ok", style: .default, handler: { (_) in
|
|
259
|
+
completionHandler(true)
|
|
260
|
+
}))
|
|
261
|
+
|
|
262
|
+
viewController.present(alertController, animated: true, completion: nil)
|
|
263
|
+
}
|
|
264
|
+
|
|
265
|
+
open func webView(_ webView: WKWebView, runJavaScriptTextInputPanelWithPrompt prompt: String, defaultText: String?, initiatedByFrame frame: WKFrameInfo, completionHandler: @escaping (String?) -> Void) {
|
|
266
|
+
|
|
267
|
+
// Check if this is synchronous cookie or http call
|
|
268
|
+
do {
|
|
269
|
+
if let dataFromString = prompt.data(using: .utf8, allowLossyConversion: false) {
|
|
270
|
+
if let payload = try JSONSerialization.jsonObject(with: dataFromString, options: .fragmentsAllowed) as? [String: AnyObject] {
|
|
271
|
+
let type = payload["type"] as? String
|
|
272
|
+
|
|
273
|
+
if type == "CapacitorCookies.get" {
|
|
274
|
+
completionHandler(CapacitorCookieManager(bridge!.config).getCookies())
|
|
275
|
+
// Don't present prompt
|
|
276
|
+
return
|
|
277
|
+
} else if type == "CapacitorCookies.set" {
|
|
278
|
+
// swiftlint:disable force_cast
|
|
279
|
+
let action = payload["action"] as! String
|
|
280
|
+
let domain = payload["domain"] as! String
|
|
281
|
+
CapacitorCookieManager(bridge!.config).setCookie(domain, action)
|
|
282
|
+
completionHandler("")
|
|
283
|
+
// swiftlint:enable force_cast
|
|
284
|
+
// Don't present prompt
|
|
285
|
+
return
|
|
286
|
+
} else if type == "CapacitorCookies.isEnabled" {
|
|
287
|
+
let pluginConfig = bridge!.config.getPluginConfig("CapacitorCookies")
|
|
288
|
+
completionHandler(String(pluginConfig.getBoolean("enabled", false)))
|
|
289
|
+
// Don't present prompt
|
|
290
|
+
return
|
|
291
|
+
} else if type == "CapacitorHttp" {
|
|
292
|
+
let pluginConfig = bridge!.config.getPluginConfig("CapacitorHttp")
|
|
293
|
+
completionHandler(String(pluginConfig.getBoolean("enabled", false)))
|
|
294
|
+
// Don't present prompt
|
|
295
|
+
return
|
|
296
|
+
}
|
|
297
|
+
}
|
|
298
|
+
}
|
|
299
|
+
} catch {
|
|
300
|
+
// Continue with regular prompt
|
|
301
|
+
}
|
|
302
|
+
|
|
303
|
+
guard let viewController = bridge?.viewController else {
|
|
304
|
+
return
|
|
305
|
+
}
|
|
306
|
+
|
|
307
|
+
let alertController = UIAlertController(title: nil, message: prompt, preferredStyle: .alert)
|
|
308
|
+
|
|
309
|
+
alertController.addTextField { (textField) in
|
|
310
|
+
textField.text = defaultText
|
|
311
|
+
}
|
|
312
|
+
|
|
313
|
+
alertController.addAction(UIAlertAction(title: "Cancel", style: .default, handler: { (_) in
|
|
314
|
+
completionHandler(nil)
|
|
315
|
+
}))
|
|
316
|
+
|
|
317
|
+
alertController.addAction(UIAlertAction(title: "Ok", style: .default, handler: { (_) in
|
|
318
|
+
if let text = alertController.textFields?.first?.text {
|
|
319
|
+
completionHandler(text)
|
|
320
|
+
} else {
|
|
321
|
+
completionHandler(defaultText)
|
|
322
|
+
}
|
|
323
|
+
}))
|
|
324
|
+
|
|
325
|
+
viewController.present(alertController, animated: true, completion: nil)
|
|
326
|
+
}
|
|
327
|
+
|
|
328
|
+
open func webView(_ webView: WKWebView, createWebViewWith configuration: WKWebViewConfiguration, for navigationAction: WKNavigationAction, windowFeatures: WKWindowFeatures) -> WKWebView? {
|
|
329
|
+
if let url = navigationAction.request.url {
|
|
330
|
+
UIApplication.shared.open(url, options: [:], completionHandler: nil)
|
|
331
|
+
}
|
|
332
|
+
return nil
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
// MARK: - UIScrollViewDelegate
|
|
336
|
+
|
|
337
|
+
// disable zooming in WKWebView ScrollView
|
|
338
|
+
open func scrollViewWillBeginZooming(_ scrollView: UIScrollView, with view: UIView?) {
|
|
339
|
+
scrollView.pinchGestureRecognizer?.isEnabled = false
|
|
340
|
+
}
|
|
341
|
+
|
|
342
|
+
// MARK: - Private
|
|
343
|
+
|
|
344
|
+
private func logJSError(_ error: [String: Any]) {
|
|
345
|
+
let message = error["message"] ?? "No message"
|
|
346
|
+
let url = error["url"] as? String ?? ""
|
|
347
|
+
let line = error["line"] ?? ""
|
|
348
|
+
let col = error["col"] ?? ""
|
|
349
|
+
var filename = ""
|
|
350
|
+
if let filenameIndex = url.range(of: "/", options: .backwards)?.lowerBound {
|
|
351
|
+
let index = url.index(after: filenameIndex)
|
|
352
|
+
filename = String(url[index...])
|
|
353
|
+
}
|
|
354
|
+
|
|
355
|
+
CAPLog.print("\n⚡️ ------ STARTUP JS ERROR ------\n")
|
|
356
|
+
CAPLog.print("⚡️ \(message)")
|
|
357
|
+
CAPLog.print("⚡️ URL: \(url)")
|
|
358
|
+
CAPLog.print("⚡️ \(filename):\(line):\(col)")
|
|
359
|
+
CAPLog.print("\n⚡️ See above for help with debugging blank-screen issues")
|
|
360
|
+
}
|
|
361
|
+
}
|