@capgo/inappbrowser 8.0.0 → 8.0.2
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/CapgoInappbrowser.podspec +2 -2
- package/LICENSE +373 -21
- package/Package.swift +28 -0
- package/README.md +600 -74
- package/android/build.gradle +17 -16
- package/android/src/main/AndroidManifest.xml +14 -2
- package/android/src/main/java/ee/forgr/capacitor_inappbrowser/InAppBrowserPlugin.java +952 -204
- package/android/src/main/java/ee/forgr/capacitor_inappbrowser/Options.java +478 -81
- package/android/src/main/java/ee/forgr/capacitor_inappbrowser/WebViewCallbacks.java +10 -4
- package/android/src/main/java/ee/forgr/capacitor_inappbrowser/WebViewDialog.java +3021 -226
- package/android/src/main/res/drawable/ic_refresh.xml +9 -0
- package/android/src/main/res/drawable/ic_share.xml +10 -0
- package/android/src/main/res/layout/activity_browser.xml +10 -0
- package/android/src/main/res/layout/content_browser.xml +3 -2
- package/android/src/main/res/layout/tool_bar.xml +44 -7
- package/android/src/main/res/values/strings.xml +4 -0
- package/android/src/main/res/values/themes.xml +27 -0
- package/android/src/main/res/xml/file_paths.xml +14 -0
- package/dist/docs.json +1289 -149
- package/dist/esm/definitions.d.ts +614 -25
- package/dist/esm/definitions.js +17 -1
- package/dist/esm/definitions.js.map +1 -1
- package/dist/esm/index.d.ts +2 -2
- package/dist/esm/index.js +4 -4
- package/dist/esm/index.js.map +1 -1
- package/dist/esm/web.d.ts +16 -3
- package/dist/esm/web.js +43 -7
- package/dist/esm/web.js.map +1 -1
- package/dist/plugin.cjs.js +60 -8
- package/dist/plugin.cjs.js.map +1 -1
- package/dist/plugin.js +60 -8
- package/dist/plugin.js.map +1 -1
- package/ios/{Plugin → Sources/InAppBrowserPlugin}/Enums.swift +5 -5
- package/ios/Sources/InAppBrowserPlugin/InAppBrowserPlugin.swift +954 -0
- package/ios/Sources/InAppBrowserPlugin/WKWebViewController.swift +2003 -0
- package/package.json +32 -30
- package/ios/Plugin/Assets.xcassets/Back.imageset/Back.png +0 -0
- package/ios/Plugin/Assets.xcassets/Back.imageset/Back@2x.png +0 -0
- package/ios/Plugin/Assets.xcassets/Back.imageset/Back@3x.png +0 -0
- package/ios/Plugin/Assets.xcassets/Back.imageset/Contents.json +0 -26
- package/ios/Plugin/Assets.xcassets/Contents.json +0 -6
- package/ios/Plugin/Assets.xcassets/Forward.imageset/Contents.json +0 -26
- package/ios/Plugin/Assets.xcassets/Forward.imageset/Forward.png +0 -0
- package/ios/Plugin/Assets.xcassets/Forward.imageset/Forward@2x.png +0 -0
- package/ios/Plugin/Assets.xcassets/Forward.imageset/Forward@3x.png +0 -0
- package/ios/Plugin/InAppBrowserPlugin.h +0 -10
- package/ios/Plugin/InAppBrowserPlugin.m +0 -17
- package/ios/Plugin/InAppBrowserPlugin.swift +0 -203
- package/ios/Plugin/Info.plist +0 -24
- package/ios/Plugin/WKWebViewController.swift +0 -784
|
@@ -1,784 +0,0 @@
|
|
|
1
|
-
//
|
|
2
|
-
// WKWebViewController.swift
|
|
3
|
-
// Sample
|
|
4
|
-
//
|
|
5
|
-
// Created by Meniny on 2018-01-20.
|
|
6
|
-
// Copyright © 2018年 Meniny. All rights reserved.
|
|
7
|
-
//
|
|
8
|
-
|
|
9
|
-
import UIKit
|
|
10
|
-
import WebKit
|
|
11
|
-
|
|
12
|
-
private let estimatedProgressKeyPath = "estimatedProgress"
|
|
13
|
-
private let titleKeyPath = "title"
|
|
14
|
-
private let cookieKey = "Cookie"
|
|
15
|
-
|
|
16
|
-
private struct UrlsHandledByApp {
|
|
17
|
-
static var hosts = ["itunes.apple.com"]
|
|
18
|
-
static var schemes = ["tel", "mailto", "sms"]
|
|
19
|
-
static var blank = true
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
@objc public protocol WKWebViewControllerDelegate {
|
|
23
|
-
@objc optional func webViewController(_ controller: WKWebViewController, canDismiss url: URL) -> Bool
|
|
24
|
-
|
|
25
|
-
@objc optional func webViewController(_ controller: WKWebViewController, didStart url: URL)
|
|
26
|
-
@objc optional func webViewController(_ controller: WKWebViewController, didFinish url: URL)
|
|
27
|
-
@objc optional func webViewController(_ controller: WKWebViewController, didFail url: URL, withError error: Error)
|
|
28
|
-
@objc optional func webViewController(_ controller: WKWebViewController, decidePolicy url: URL, navigationType: NavigationType) -> Bool
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
open class WKWebViewController: UIViewController {
|
|
32
|
-
|
|
33
|
-
public init() {
|
|
34
|
-
super.init(nibName: nil, bundle: nil)
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
public required init?(coder aDecoder: NSCoder) {
|
|
38
|
-
super.init(coder: aDecoder)
|
|
39
|
-
}
|
|
40
|
-
|
|
41
|
-
public init(source: WKWebSource?) {
|
|
42
|
-
super.init(nibName: nil, bundle: nil)
|
|
43
|
-
self.source = source
|
|
44
|
-
self.initWebview()
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
public init(url: URL) {
|
|
48
|
-
super.init(nibName: nil, bundle: nil)
|
|
49
|
-
self.source = .remote(url)
|
|
50
|
-
self.initWebview()
|
|
51
|
-
}
|
|
52
|
-
|
|
53
|
-
public init(url: URL, headers: [String: String]) {
|
|
54
|
-
super.init(nibName: nil, bundle: nil)
|
|
55
|
-
self.source = .remote(url)
|
|
56
|
-
self.setHeaders(headers: headers)
|
|
57
|
-
self.initWebview()
|
|
58
|
-
}
|
|
59
|
-
|
|
60
|
-
open var hasDynamicTitle = false
|
|
61
|
-
open var source: WKWebSource?
|
|
62
|
-
/// use `source` instead
|
|
63
|
-
open internal(set) var url: URL?
|
|
64
|
-
open var tintColor: UIColor?
|
|
65
|
-
open var allowsFileURL = true
|
|
66
|
-
open var delegate: WKWebViewControllerDelegate?
|
|
67
|
-
open var bypassedSSLHosts: [String]?
|
|
68
|
-
open var cookies: [HTTPCookie]?
|
|
69
|
-
open var headers: [String: String]?
|
|
70
|
-
open var capBrowserPlugin: InAppBrowserPlugin?
|
|
71
|
-
var shareDisclaimer: [String: Any]?
|
|
72
|
-
var shareSubject: String?
|
|
73
|
-
var didpageInit = false
|
|
74
|
-
var viewHeightLandscape: CGFloat?
|
|
75
|
-
var viewHeightPortrait: CGFloat?
|
|
76
|
-
var currentViewHeight: CGFloat?
|
|
77
|
-
|
|
78
|
-
func setHeaders(headers: [String: String]) {
|
|
79
|
-
self.headers = headers
|
|
80
|
-
let userAgent = self.headers?["User-Agent"]
|
|
81
|
-
self.headers?.removeValue(forKey: "User-Agent")
|
|
82
|
-
if userAgent != nil {
|
|
83
|
-
self.customUserAgent = userAgent
|
|
84
|
-
}
|
|
85
|
-
}
|
|
86
|
-
|
|
87
|
-
internal var customUserAgent: String? {
|
|
88
|
-
didSet {
|
|
89
|
-
guard let agent = userAgent else {
|
|
90
|
-
return
|
|
91
|
-
}
|
|
92
|
-
webView?.customUserAgent = agent
|
|
93
|
-
}
|
|
94
|
-
}
|
|
95
|
-
|
|
96
|
-
open var userAgent: String? {
|
|
97
|
-
didSet {
|
|
98
|
-
guard let originalUserAgent = originalUserAgent, let userAgent = userAgent else {
|
|
99
|
-
return
|
|
100
|
-
}
|
|
101
|
-
webView?.customUserAgent = [originalUserAgent, userAgent].joined(separator: " ")
|
|
102
|
-
}
|
|
103
|
-
}
|
|
104
|
-
|
|
105
|
-
open var pureUserAgent: String? {
|
|
106
|
-
didSet {
|
|
107
|
-
guard let agent = pureUserAgent else {
|
|
108
|
-
return
|
|
109
|
-
}
|
|
110
|
-
webView?.customUserAgent = agent
|
|
111
|
-
}
|
|
112
|
-
}
|
|
113
|
-
|
|
114
|
-
open var websiteTitleInNavigationBar = true
|
|
115
|
-
open var doneBarButtonItemPosition: NavigationBarPosition = .right
|
|
116
|
-
open var leftNavigaionBarItemTypes: [BarButtonItemType] = []
|
|
117
|
-
open var rightNavigaionBarItemTypes: [BarButtonItemType] = []
|
|
118
|
-
open var toolbarItemTypes: [BarButtonItemType] = [.back, .forward, .reload, .activity]
|
|
119
|
-
|
|
120
|
-
open var backBarButtonItemImage: UIImage?
|
|
121
|
-
open var forwardBarButtonItemImage: UIImage?
|
|
122
|
-
open var reloadBarButtonItemImage: UIImage?
|
|
123
|
-
open var stopBarButtonItemImage: UIImage?
|
|
124
|
-
open var activityBarButtonItemImage: UIImage?
|
|
125
|
-
|
|
126
|
-
fileprivate var webView: WKWebView?
|
|
127
|
-
fileprivate var progressView: UIProgressView?
|
|
128
|
-
|
|
129
|
-
fileprivate var previousNavigationBarState: (tintColor: UIColor, hidden: Bool) = (.black, false)
|
|
130
|
-
fileprivate var previousToolbarState: (tintColor: UIColor, hidden: Bool) = (.black, false)
|
|
131
|
-
|
|
132
|
-
fileprivate var originalUserAgent: String?
|
|
133
|
-
|
|
134
|
-
fileprivate lazy var backBarButtonItem: UIBarButtonItem = {
|
|
135
|
-
let bundle = Bundle(for: WKWebViewController.self)
|
|
136
|
-
return UIBarButtonItem(image: backBarButtonItemImage ?? UIImage(named: "Back", in: bundle, compatibleWith: nil), style: .plain, target: self, action: #selector(backDidClick(sender:)))
|
|
137
|
-
}()
|
|
138
|
-
|
|
139
|
-
fileprivate lazy var forwardBarButtonItem: UIBarButtonItem = {
|
|
140
|
-
let bundle = Bundle(for: WKWebViewController.self)
|
|
141
|
-
return UIBarButtonItem(image: forwardBarButtonItemImage ?? UIImage(named: "Forward", in: bundle, compatibleWith: nil), style: .plain, target: self, action: #selector(forwardDidClick(sender:)))
|
|
142
|
-
}()
|
|
143
|
-
|
|
144
|
-
fileprivate lazy var reloadBarButtonItem: UIBarButtonItem = {
|
|
145
|
-
if let image = reloadBarButtonItemImage {
|
|
146
|
-
return UIBarButtonItem(image: image, style: .plain, target: self, action: #selector(reloadDidClick(sender:)))
|
|
147
|
-
} else {
|
|
148
|
-
return UIBarButtonItem(barButtonSystemItem: .refresh, target: self, action: #selector(reloadDidClick(sender:)))
|
|
149
|
-
}
|
|
150
|
-
}()
|
|
151
|
-
|
|
152
|
-
fileprivate lazy var stopBarButtonItem: UIBarButtonItem = {
|
|
153
|
-
if let image = stopBarButtonItemImage {
|
|
154
|
-
return UIBarButtonItem(image: image, style: .plain, target: self, action: #selector(stopDidClick(sender:)))
|
|
155
|
-
} else {
|
|
156
|
-
return UIBarButtonItem(barButtonSystemItem: .stop, target: self, action: #selector(stopDidClick(sender:)))
|
|
157
|
-
}
|
|
158
|
-
}()
|
|
159
|
-
|
|
160
|
-
fileprivate lazy var activityBarButtonItem: UIBarButtonItem = {
|
|
161
|
-
if let image = activityBarButtonItemImage {
|
|
162
|
-
return UIBarButtonItem(image: image, style: .plain, target: self, action: #selector(activityDidClick(sender:)))
|
|
163
|
-
} else {
|
|
164
|
-
return UIBarButtonItem(barButtonSystemItem: .action, target: self, action: #selector(activityDidClick(sender:)))
|
|
165
|
-
}
|
|
166
|
-
}()
|
|
167
|
-
|
|
168
|
-
fileprivate lazy var doneBarButtonItem: UIBarButtonItem = {
|
|
169
|
-
return UIBarButtonItem(barButtonSystemItem: .done, target: self, action: #selector(doneDidClick(sender:)))
|
|
170
|
-
}()
|
|
171
|
-
|
|
172
|
-
fileprivate lazy var flexibleSpaceBarButtonItem: UIBarButtonItem = {
|
|
173
|
-
return UIBarButtonItem(barButtonSystemItem: .flexibleSpace, target: nil, action: nil)
|
|
174
|
-
}()
|
|
175
|
-
|
|
176
|
-
deinit {
|
|
177
|
-
webView?.removeObserver(self, forKeyPath: estimatedProgressKeyPath)
|
|
178
|
-
if websiteTitleInNavigationBar {
|
|
179
|
-
webView?.removeObserver(self, forKeyPath: titleKeyPath)
|
|
180
|
-
}
|
|
181
|
-
webView?.removeObserver(self, forKeyPath: #keyPath(WKWebView.url))
|
|
182
|
-
}
|
|
183
|
-
|
|
184
|
-
override open func viewDidLoad() {
|
|
185
|
-
super.viewDidLoad()
|
|
186
|
-
if self.webView == nil {
|
|
187
|
-
self.initWebview()
|
|
188
|
-
}
|
|
189
|
-
}
|
|
190
|
-
|
|
191
|
-
open func initWebview() {
|
|
192
|
-
|
|
193
|
-
self.view.backgroundColor = UIColor.white
|
|
194
|
-
|
|
195
|
-
self.extendedLayoutIncludesOpaqueBars = true
|
|
196
|
-
self.edgesForExtendedLayout = [.bottom]
|
|
197
|
-
|
|
198
|
-
let webConfiguration = WKWebViewConfiguration()
|
|
199
|
-
let webView = WKWebView(frame: .zero, configuration: webConfiguration)
|
|
200
|
-
|
|
201
|
-
webView.uiDelegate = self
|
|
202
|
-
webView.navigationDelegate = self
|
|
203
|
-
|
|
204
|
-
webView.allowsBackForwardNavigationGestures = true
|
|
205
|
-
webView.isMultipleTouchEnabled = true
|
|
206
|
-
|
|
207
|
-
webView.addObserver(self, forKeyPath: estimatedProgressKeyPath, options: .new, context: nil)
|
|
208
|
-
if websiteTitleInNavigationBar {
|
|
209
|
-
webView.addObserver(self, forKeyPath: titleKeyPath, options: .new, context: nil)
|
|
210
|
-
}
|
|
211
|
-
webView.addObserver(self, forKeyPath: #keyPath(WKWebView.url), options: .new, context: nil)
|
|
212
|
-
// NotificationCenter.default.addObserver(self, selector: #selector(restateViewHeight), name: UIDevice.orientationDidChangeNotification, object: nil)
|
|
213
|
-
|
|
214
|
-
self.view = webView
|
|
215
|
-
self.webView = webView
|
|
216
|
-
|
|
217
|
-
self.webView?.customUserAgent = self.customUserAgent ?? self.userAgent ?? self.originalUserAgent
|
|
218
|
-
|
|
219
|
-
self.navigationItem.title = self.navigationItem.title ?? self.source?.absoluteString
|
|
220
|
-
|
|
221
|
-
if let navigation = self.navigationController {
|
|
222
|
-
self.previousNavigationBarState = (navigation.navigationBar.tintColor, navigation.navigationBar.isHidden)
|
|
223
|
-
self.previousToolbarState = (navigation.toolbar.tintColor, navigation.toolbar.isHidden)
|
|
224
|
-
}
|
|
225
|
-
|
|
226
|
-
// self.restateViewHeight()
|
|
227
|
-
|
|
228
|
-
if let s = self.source {
|
|
229
|
-
self.load(source: s)
|
|
230
|
-
} else {
|
|
231
|
-
print("[\(type(of: self))][Error] Invalid url")
|
|
232
|
-
}
|
|
233
|
-
}
|
|
234
|
-
|
|
235
|
-
open func setupViewElements() {
|
|
236
|
-
self.setUpProgressView()
|
|
237
|
-
self.setUpConstraints()
|
|
238
|
-
self.addBarButtonItems()
|
|
239
|
-
}
|
|
240
|
-
|
|
241
|
-
@objc func restateViewHeight() {
|
|
242
|
-
var bottomPadding = CGFloat(0.0)
|
|
243
|
-
var topPadding = CGFloat(0.0)
|
|
244
|
-
if #available(iOS 11.0, *) {
|
|
245
|
-
let window = UIApplication.shared.keyWindow
|
|
246
|
-
bottomPadding = (window?.safeAreaInsets.bottom)!
|
|
247
|
-
topPadding = (window?.safeAreaInsets.top)!
|
|
248
|
-
}
|
|
249
|
-
if UIDevice.current.orientation.isPortrait {
|
|
250
|
-
self.navigationController?.toolbar.isHidden = false
|
|
251
|
-
if self.viewHeightPortrait == nil {
|
|
252
|
-
self.viewHeightPortrait = self.view.safeAreaLayoutGuide.layoutFrame.size.height
|
|
253
|
-
if toolbarItemTypes.count == 0 {
|
|
254
|
-
self.viewHeightPortrait! = self.viewHeightPortrait! + bottomPadding
|
|
255
|
-
}
|
|
256
|
-
if self.navigationController?.navigationBar.isHidden == true {
|
|
257
|
-
self.viewHeightPortrait = self.viewHeightPortrait! + topPadding
|
|
258
|
-
}
|
|
259
|
-
}
|
|
260
|
-
self.currentViewHeight = self.viewHeightPortrait
|
|
261
|
-
} else if UIDevice.current.orientation.isLandscape {
|
|
262
|
-
self.navigationController?.toolbar.isHidden = false
|
|
263
|
-
if self.viewHeightLandscape == nil {
|
|
264
|
-
self.viewHeightLandscape = self.view.safeAreaLayoutGuide.layoutFrame.size.height
|
|
265
|
-
if toolbarItemTypes.count == 0 {
|
|
266
|
-
self.viewHeightLandscape! = self.viewHeightLandscape! + bottomPadding
|
|
267
|
-
}
|
|
268
|
-
if self.navigationController?.navigationBar.isHidden == true {
|
|
269
|
-
self.viewHeightLandscape = self.viewHeightLandscape! + topPadding
|
|
270
|
-
}
|
|
271
|
-
}
|
|
272
|
-
self.currentViewHeight = self.viewHeightLandscape
|
|
273
|
-
}
|
|
274
|
-
}
|
|
275
|
-
|
|
276
|
-
override open func viewWillTransition(to size: CGSize, with coordinator: UIViewControllerTransitionCoordinator) {
|
|
277
|
-
// self.view.frame.size.height = self.currentViewHeight!
|
|
278
|
-
}
|
|
279
|
-
|
|
280
|
-
override open func viewWillLayoutSubviews() {
|
|
281
|
-
restateViewHeight()
|
|
282
|
-
if self.currentViewHeight != nil {
|
|
283
|
-
self.view.frame.size.height = self.currentViewHeight!
|
|
284
|
-
}
|
|
285
|
-
}
|
|
286
|
-
|
|
287
|
-
override open func viewWillAppear(_ animated: Bool) {
|
|
288
|
-
super.viewWillAppear(animated)
|
|
289
|
-
self.setupViewElements()
|
|
290
|
-
setUpState()
|
|
291
|
-
}
|
|
292
|
-
|
|
293
|
-
override open func viewWillDisappear(_ animated: Bool) {
|
|
294
|
-
super.viewWillDisappear(animated)
|
|
295
|
-
rollbackState()
|
|
296
|
-
}
|
|
297
|
-
|
|
298
|
-
override open func didReceiveMemoryWarning() {
|
|
299
|
-
super.didReceiveMemoryWarning()
|
|
300
|
-
// Dispose of any resources that can be recreated.
|
|
301
|
-
}
|
|
302
|
-
|
|
303
|
-
override open func observeValue(forKeyPath keyPath: String?, of object: Any?, change: [NSKeyValueChangeKey: Any]?, context: UnsafeMutableRawPointer?) {
|
|
304
|
-
switch keyPath {
|
|
305
|
-
case estimatedProgressKeyPath?:
|
|
306
|
-
guard let estimatedProgress = self.webView?.estimatedProgress else {
|
|
307
|
-
return
|
|
308
|
-
}
|
|
309
|
-
self.progressView?.alpha = 1
|
|
310
|
-
self.progressView?.setProgress(Float(estimatedProgress), animated: true)
|
|
311
|
-
|
|
312
|
-
if estimatedProgress >= 1.0 {
|
|
313
|
-
UIView.animate(withDuration: 0.3, delay: 0.3, options: .curveEaseOut, animations: {
|
|
314
|
-
self.progressView?.alpha = 0
|
|
315
|
-
}, completion: {
|
|
316
|
-
_ in
|
|
317
|
-
self.progressView?.setProgress(0, animated: false)
|
|
318
|
-
})
|
|
319
|
-
}
|
|
320
|
-
case titleKeyPath?:
|
|
321
|
-
if self.hasDynamicTitle {
|
|
322
|
-
self.navigationItem.title = webView?.url?.host
|
|
323
|
-
}
|
|
324
|
-
case "URL":
|
|
325
|
-
self.capBrowserPlugin?.notifyListeners("urlChangeEvent", data: ["url": webView?.url?.absoluteString ?? ""])
|
|
326
|
-
default:
|
|
327
|
-
super.observeValue(forKeyPath: keyPath, of: object, change: change, context: context)
|
|
328
|
-
}
|
|
329
|
-
}
|
|
330
|
-
}
|
|
331
|
-
|
|
332
|
-
// MARK: - Public Methods
|
|
333
|
-
public extension WKWebViewController {
|
|
334
|
-
|
|
335
|
-
func load(source s: WKWebSource) {
|
|
336
|
-
switch s {
|
|
337
|
-
case .remote(let url):
|
|
338
|
-
self.load(remote: url)
|
|
339
|
-
case .file(let url, access: let access):
|
|
340
|
-
self.load(file: url, access: access)
|
|
341
|
-
case .string(let str, base: let base):
|
|
342
|
-
self.load(string: str, base: base)
|
|
343
|
-
}
|
|
344
|
-
}
|
|
345
|
-
|
|
346
|
-
func load(remote: URL) {
|
|
347
|
-
webView?.load(createRequest(url: remote))
|
|
348
|
-
}
|
|
349
|
-
|
|
350
|
-
func load(file: URL, access: URL) {
|
|
351
|
-
webView?.loadFileURL(file, allowingReadAccessTo: access)
|
|
352
|
-
}
|
|
353
|
-
|
|
354
|
-
func load(string: String, base: URL? = nil) {
|
|
355
|
-
webView?.loadHTMLString(string, baseURL: base)
|
|
356
|
-
}
|
|
357
|
-
|
|
358
|
-
func goBackToFirstPage() {
|
|
359
|
-
if let firstPageItem = webView?.backForwardList.backList.first {
|
|
360
|
-
webView?.go(to: firstPageItem)
|
|
361
|
-
}
|
|
362
|
-
}
|
|
363
|
-
}
|
|
364
|
-
|
|
365
|
-
// MARK: - Fileprivate Methods
|
|
366
|
-
fileprivate extension WKWebViewController {
|
|
367
|
-
var availableCookies: [HTTPCookie]? {
|
|
368
|
-
return cookies?.filter {
|
|
369
|
-
cookie in
|
|
370
|
-
var result = true
|
|
371
|
-
let url = self.source?.remoteURL
|
|
372
|
-
if let host = url?.host, !cookie.domain.hasSuffix(host) {
|
|
373
|
-
result = false
|
|
374
|
-
}
|
|
375
|
-
if cookie.isSecure && url?.scheme != "https" {
|
|
376
|
-
result = false
|
|
377
|
-
}
|
|
378
|
-
|
|
379
|
-
return result
|
|
380
|
-
}
|
|
381
|
-
}
|
|
382
|
-
func createRequest(url: URL) -> URLRequest {
|
|
383
|
-
var request = URLRequest(url: url)
|
|
384
|
-
|
|
385
|
-
// Set up headers
|
|
386
|
-
if let headers = headers {
|
|
387
|
-
for (field, value) in headers {
|
|
388
|
-
request.addValue(value, forHTTPHeaderField: field)
|
|
389
|
-
}
|
|
390
|
-
}
|
|
391
|
-
|
|
392
|
-
// Set up Cookies
|
|
393
|
-
if let cookies = availableCookies, let value = HTTPCookie.requestHeaderFields(with: cookies)[cookieKey] {
|
|
394
|
-
request.addValue(value, forHTTPHeaderField: cookieKey)
|
|
395
|
-
}
|
|
396
|
-
|
|
397
|
-
return request
|
|
398
|
-
}
|
|
399
|
-
|
|
400
|
-
func setUpProgressView() {
|
|
401
|
-
let progressView = UIProgressView(progressViewStyle: .default)
|
|
402
|
-
progressView.trackTintColor = UIColor(white: 1, alpha: 0)
|
|
403
|
-
self.progressView = progressView
|
|
404
|
-
// updateProgressViewFrame()
|
|
405
|
-
}
|
|
406
|
-
|
|
407
|
-
func setUpConstraints() {
|
|
408
|
-
if !(self.navigationController?.navigationBar.isHidden)! {
|
|
409
|
-
self.progressView?.frame.origin.y = CGFloat((self.navigationController?.navigationBar.frame.height)!)
|
|
410
|
-
self.navigationController?.navigationBar.addSubview(self.progressView!)
|
|
411
|
-
webView?.addObserver(self, forKeyPath: #keyPath(WKWebView.estimatedProgress), options: .new, context: nil)
|
|
412
|
-
}
|
|
413
|
-
}
|
|
414
|
-
|
|
415
|
-
func addBarButtonItems() {
|
|
416
|
-
func barButtonItem(_ type: BarButtonItemType) -> UIBarButtonItem? {
|
|
417
|
-
switch type {
|
|
418
|
-
case .back:
|
|
419
|
-
return backBarButtonItem
|
|
420
|
-
case .forward:
|
|
421
|
-
return forwardBarButtonItem
|
|
422
|
-
case .reload:
|
|
423
|
-
return reloadBarButtonItem
|
|
424
|
-
case .stop:
|
|
425
|
-
return stopBarButtonItem
|
|
426
|
-
case .activity:
|
|
427
|
-
return activityBarButtonItem
|
|
428
|
-
case .done:
|
|
429
|
-
return doneBarButtonItem
|
|
430
|
-
case .flexibleSpace:
|
|
431
|
-
return flexibleSpaceBarButtonItem
|
|
432
|
-
case .custom(let icon, let title, let action):
|
|
433
|
-
let item: BlockBarButtonItem
|
|
434
|
-
if let icon = icon {
|
|
435
|
-
item = BlockBarButtonItem(image: icon, style: .plain, target: self, action: #selector(customDidClick(sender:)))
|
|
436
|
-
} else {
|
|
437
|
-
item = BlockBarButtonItem(title: title, style: .plain, target: self, action: #selector(customDidClick(sender:)))
|
|
438
|
-
}
|
|
439
|
-
item.block = action
|
|
440
|
-
return item
|
|
441
|
-
}
|
|
442
|
-
}
|
|
443
|
-
|
|
444
|
-
// if presentingViewController != nil {
|
|
445
|
-
switch doneBarButtonItemPosition {
|
|
446
|
-
case .left:
|
|
447
|
-
if !leftNavigaionBarItemTypes.contains(where: { type in
|
|
448
|
-
switch type {
|
|
449
|
-
case .done:
|
|
450
|
-
return true
|
|
451
|
-
default:
|
|
452
|
-
return false
|
|
453
|
-
}
|
|
454
|
-
}) {
|
|
455
|
-
leftNavigaionBarItemTypes.insert(.done, at: 0)
|
|
456
|
-
}
|
|
457
|
-
case .right:
|
|
458
|
-
if !rightNavigaionBarItemTypes.contains(where: { type in
|
|
459
|
-
switch type {
|
|
460
|
-
case .done:
|
|
461
|
-
return true
|
|
462
|
-
default:
|
|
463
|
-
return false
|
|
464
|
-
}
|
|
465
|
-
}) {
|
|
466
|
-
rightNavigaionBarItemTypes.insert(.done, at: 0)
|
|
467
|
-
}
|
|
468
|
-
case .none:
|
|
469
|
-
break
|
|
470
|
-
}
|
|
471
|
-
// }
|
|
472
|
-
|
|
473
|
-
navigationItem.leftBarButtonItems = leftNavigaionBarItemTypes.map {
|
|
474
|
-
barButtonItemType in
|
|
475
|
-
if let barButtonItem = barButtonItem(barButtonItemType) {
|
|
476
|
-
return barButtonItem
|
|
477
|
-
}
|
|
478
|
-
return UIBarButtonItem()
|
|
479
|
-
}
|
|
480
|
-
|
|
481
|
-
navigationItem.rightBarButtonItems = rightNavigaionBarItemTypes.map {
|
|
482
|
-
barButtonItemType in
|
|
483
|
-
if let barButtonItem = barButtonItem(barButtonItemType) {
|
|
484
|
-
return barButtonItem
|
|
485
|
-
}
|
|
486
|
-
return UIBarButtonItem()
|
|
487
|
-
}
|
|
488
|
-
|
|
489
|
-
if toolbarItemTypes.count > 0 {
|
|
490
|
-
for index in 0..<toolbarItemTypes.count - 1 {
|
|
491
|
-
toolbarItemTypes.insert(.flexibleSpace, at: 2 * index + 1)
|
|
492
|
-
}
|
|
493
|
-
}
|
|
494
|
-
|
|
495
|
-
setToolbarItems(toolbarItemTypes.map {
|
|
496
|
-
barButtonItemType -> UIBarButtonItem in
|
|
497
|
-
if let barButtonItem = barButtonItem(barButtonItemType) {
|
|
498
|
-
return barButtonItem
|
|
499
|
-
}
|
|
500
|
-
return UIBarButtonItem()
|
|
501
|
-
}, animated: true)
|
|
502
|
-
}
|
|
503
|
-
|
|
504
|
-
func updateBarButtonItems() {
|
|
505
|
-
backBarButtonItem.isEnabled = webView?.canGoBack ?? false
|
|
506
|
-
forwardBarButtonItem.isEnabled = webView?.canGoForward ?? false
|
|
507
|
-
|
|
508
|
-
let updateReloadBarButtonItem: (UIBarButtonItem, Bool) -> UIBarButtonItem = {
|
|
509
|
-
[unowned self] barButtonItem, isLoading in
|
|
510
|
-
switch barButtonItem {
|
|
511
|
-
case self.reloadBarButtonItem:
|
|
512
|
-
fallthrough
|
|
513
|
-
case self.stopBarButtonItem:
|
|
514
|
-
return isLoading ? self.stopBarButtonItem : self.reloadBarButtonItem
|
|
515
|
-
default:
|
|
516
|
-
break
|
|
517
|
-
}
|
|
518
|
-
return barButtonItem
|
|
519
|
-
}
|
|
520
|
-
|
|
521
|
-
let isLoading = webView?.isLoading ?? false
|
|
522
|
-
toolbarItems = toolbarItems?.map {
|
|
523
|
-
barButtonItem -> UIBarButtonItem in
|
|
524
|
-
return updateReloadBarButtonItem(barButtonItem, isLoading)
|
|
525
|
-
}
|
|
526
|
-
|
|
527
|
-
navigationItem.leftBarButtonItems = navigationItem.leftBarButtonItems?.map {
|
|
528
|
-
barButtonItem -> UIBarButtonItem in
|
|
529
|
-
return updateReloadBarButtonItem(barButtonItem, isLoading)
|
|
530
|
-
}
|
|
531
|
-
|
|
532
|
-
navigationItem.rightBarButtonItems = navigationItem.rightBarButtonItems?.map {
|
|
533
|
-
barButtonItem -> UIBarButtonItem in
|
|
534
|
-
return updateReloadBarButtonItem(barButtonItem, isLoading)
|
|
535
|
-
}
|
|
536
|
-
}
|
|
537
|
-
|
|
538
|
-
func setUpState() {
|
|
539
|
-
navigationController?.setNavigationBarHidden(false, animated: true)
|
|
540
|
-
navigationController?.setToolbarHidden(toolbarItemTypes.count == 0, animated: true)
|
|
541
|
-
|
|
542
|
-
if let tintColor = tintColor {
|
|
543
|
-
progressView?.progressTintColor = tintColor
|
|
544
|
-
navigationController?.navigationBar.tintColor = tintColor
|
|
545
|
-
navigationController?.toolbar.tintColor = tintColor
|
|
546
|
-
}
|
|
547
|
-
}
|
|
548
|
-
|
|
549
|
-
func rollbackState() {
|
|
550
|
-
progressView?.progress = 0
|
|
551
|
-
|
|
552
|
-
navigationController?.navigationBar.tintColor = previousNavigationBarState.tintColor
|
|
553
|
-
navigationController?.toolbar.tintColor = previousToolbarState.tintColor
|
|
554
|
-
|
|
555
|
-
navigationController?.setToolbarHidden(previousToolbarState.hidden, animated: true)
|
|
556
|
-
navigationController?.setNavigationBarHidden(previousNavigationBarState.hidden, animated: true)
|
|
557
|
-
}
|
|
558
|
-
|
|
559
|
-
func checkRequestCookies(_ request: URLRequest, cookies: [HTTPCookie]) -> Bool {
|
|
560
|
-
if cookies.count <= 0 {
|
|
561
|
-
return true
|
|
562
|
-
}
|
|
563
|
-
guard let headerFields = request.allHTTPHeaderFields, let cookieString = headerFields[cookieKey] else {
|
|
564
|
-
return false
|
|
565
|
-
}
|
|
566
|
-
|
|
567
|
-
let requestCookies = cookieString.components(separatedBy: ";").map {
|
|
568
|
-
$0.trimmingCharacters(in: .whitespacesAndNewlines).split(separator: "=", maxSplits: 1).map(String.init)
|
|
569
|
-
}
|
|
570
|
-
|
|
571
|
-
var valid = false
|
|
572
|
-
for cookie in cookies {
|
|
573
|
-
valid = requestCookies.filter {
|
|
574
|
-
$0[0] == cookie.name && $0[1] == cookie.value
|
|
575
|
-
}.count > 0
|
|
576
|
-
if !valid {
|
|
577
|
-
break
|
|
578
|
-
}
|
|
579
|
-
}
|
|
580
|
-
return valid
|
|
581
|
-
}
|
|
582
|
-
|
|
583
|
-
func openURLWithApp(_ url: URL) -> Bool {
|
|
584
|
-
let application = UIApplication.shared
|
|
585
|
-
if application.canOpenURL(url) {
|
|
586
|
-
application.open(url, options: [:], completionHandler: nil)
|
|
587
|
-
return true
|
|
588
|
-
}
|
|
589
|
-
|
|
590
|
-
return false
|
|
591
|
-
}
|
|
592
|
-
|
|
593
|
-
func handleURLWithApp(_ url: URL, targetFrame: WKFrameInfo?) -> Bool {
|
|
594
|
-
let hosts = UrlsHandledByApp.hosts
|
|
595
|
-
let schemes = UrlsHandledByApp.schemes
|
|
596
|
-
let blank = UrlsHandledByApp.blank
|
|
597
|
-
|
|
598
|
-
var tryToOpenURLWithApp = false
|
|
599
|
-
if let host = url.host, hosts.contains(host) {
|
|
600
|
-
tryToOpenURLWithApp = true
|
|
601
|
-
}
|
|
602
|
-
if let scheme = url.scheme, schemes.contains(scheme) {
|
|
603
|
-
tryToOpenURLWithApp = true
|
|
604
|
-
}
|
|
605
|
-
if blank && targetFrame == nil {
|
|
606
|
-
tryToOpenURLWithApp = true
|
|
607
|
-
}
|
|
608
|
-
|
|
609
|
-
return tryToOpenURLWithApp ? openURLWithApp(url) : false
|
|
610
|
-
}
|
|
611
|
-
|
|
612
|
-
@objc func backDidClick(sender: AnyObject) {
|
|
613
|
-
webView?.goBack()
|
|
614
|
-
}
|
|
615
|
-
|
|
616
|
-
@objc func forwardDidClick(sender: AnyObject) {
|
|
617
|
-
webView?.goForward()
|
|
618
|
-
}
|
|
619
|
-
|
|
620
|
-
@objc func reloadDidClick(sender: AnyObject) {
|
|
621
|
-
webView?.stopLoading()
|
|
622
|
-
if webView?.url != nil {
|
|
623
|
-
webView?.reload()
|
|
624
|
-
} else if let s = self.source {
|
|
625
|
-
self.load(source: s)
|
|
626
|
-
}
|
|
627
|
-
}
|
|
628
|
-
|
|
629
|
-
@objc func stopDidClick(sender: AnyObject) {
|
|
630
|
-
webView?.stopLoading()
|
|
631
|
-
}
|
|
632
|
-
|
|
633
|
-
@objc func activityDidClick(sender: AnyObject) {
|
|
634
|
-
guard let s = self.source else {
|
|
635
|
-
return
|
|
636
|
-
}
|
|
637
|
-
|
|
638
|
-
let items: [Any]
|
|
639
|
-
switch s {
|
|
640
|
-
case .remote(let u):
|
|
641
|
-
items = [u]
|
|
642
|
-
case .file(let u, access: _):
|
|
643
|
-
items = [u]
|
|
644
|
-
case .string(let str, base: _):
|
|
645
|
-
items = [str]
|
|
646
|
-
}
|
|
647
|
-
showDisclaimer(items: items, sender: sender)
|
|
648
|
-
}
|
|
649
|
-
|
|
650
|
-
func showDisclaimer(items: [Any], sender: AnyObject) {
|
|
651
|
-
let showDisclaimer: Bool = self.shareDisclaimer != nil
|
|
652
|
-
if showDisclaimer {
|
|
653
|
-
let alert = UIAlertController(
|
|
654
|
-
title: self.shareDisclaimer?["title"] as? String ?? "Title",
|
|
655
|
-
message: self.shareDisclaimer?["message"] as? String ?? "Message",
|
|
656
|
-
preferredStyle: UIAlertController.Style.alert)
|
|
657
|
-
alert.addAction(UIAlertAction(title: self.shareDisclaimer?["confirmBtn"] as? String ?? "Confirm", style: UIAlertAction.Style.default, handler: { _ in
|
|
658
|
-
self.shareDisclaimer = nil
|
|
659
|
-
self.capBrowserPlugin?.notifyListeners("confirmBtnClicked", data: nil)
|
|
660
|
-
let activityViewController = UIActivityViewController(activityItems: items, applicationActivities: nil)
|
|
661
|
-
activityViewController.setValue(self.shareSubject ?? self.title, forKey: "subject")
|
|
662
|
-
activityViewController.popoverPresentationController?.barButtonItem = (sender as! UIBarButtonItem)
|
|
663
|
-
self.present(activityViewController, animated: true, completion: nil)
|
|
664
|
-
}))
|
|
665
|
-
alert.addAction(UIAlertAction(title: self.shareDisclaimer?["cancelBtn"] as? String ?? "Cancel", style: UIAlertAction.Style.default, handler: nil))
|
|
666
|
-
self.present(alert, animated: true, completion: nil)
|
|
667
|
-
} else {
|
|
668
|
-
let activityViewController = UIActivityViewController(activityItems: items, applicationActivities: nil)
|
|
669
|
-
activityViewController.setValue(self.shareSubject ?? self.title, forKey: "subject")
|
|
670
|
-
activityViewController.popoverPresentationController?.barButtonItem = (sender as! UIBarButtonItem)
|
|
671
|
-
self.present(activityViewController, animated: true, completion: nil)
|
|
672
|
-
}
|
|
673
|
-
}
|
|
674
|
-
|
|
675
|
-
@objc func doneDidClick(sender: AnyObject) {
|
|
676
|
-
var canDismiss = true
|
|
677
|
-
if let url = self.source?.url {
|
|
678
|
-
canDismiss = delegate?.webViewController?(self, canDismiss: url) ?? true
|
|
679
|
-
}
|
|
680
|
-
if canDismiss {
|
|
681
|
-
// UIDevice.current.setValue(Int(UIInterfaceOrientation.portrait.rawValue), forKey: "orientation")
|
|
682
|
-
self.capBrowserPlugin?.notifyListeners("closeEvent", data: ["url": webView?.url?.absoluteString ?? ""])
|
|
683
|
-
dismiss(animated: true, completion: nil)
|
|
684
|
-
}
|
|
685
|
-
}
|
|
686
|
-
|
|
687
|
-
@objc func customDidClick(sender: BlockBarButtonItem) {
|
|
688
|
-
sender.block?(self)
|
|
689
|
-
}
|
|
690
|
-
|
|
691
|
-
func canRotate() {}
|
|
692
|
-
}
|
|
693
|
-
|
|
694
|
-
// MARK: - WKUIDelegate
|
|
695
|
-
extension WKWebViewController: WKUIDelegate {
|
|
696
|
-
|
|
697
|
-
}
|
|
698
|
-
|
|
699
|
-
// MARK: - WKNavigationDelegate
|
|
700
|
-
extension WKWebViewController: WKNavigationDelegate {
|
|
701
|
-
public func webView(_ webView: WKWebView, didStartProvisionalNavigation navigation: WKNavigation!) {
|
|
702
|
-
updateBarButtonItems()
|
|
703
|
-
self.progressView?.progress = 0
|
|
704
|
-
if let u = webView.url {
|
|
705
|
-
self.url = u
|
|
706
|
-
delegate?.webViewController?(self, didStart: u)
|
|
707
|
-
}
|
|
708
|
-
}
|
|
709
|
-
public func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
|
|
710
|
-
if !didpageInit && self.capBrowserPlugin?.isPresentAfterPageLoad == true {
|
|
711
|
-
self.capBrowserPlugin?.presentView()
|
|
712
|
-
}
|
|
713
|
-
didpageInit = true
|
|
714
|
-
updateBarButtonItems()
|
|
715
|
-
self.progressView?.progress = 0
|
|
716
|
-
if let url = webView.url {
|
|
717
|
-
self.url = url
|
|
718
|
-
delegate?.webViewController?(self, didFinish: url)
|
|
719
|
-
}
|
|
720
|
-
}
|
|
721
|
-
|
|
722
|
-
public func webView(_ webView: WKWebView, didFailProvisionalNavigation navigation: WKNavigation!, withError error: Error) {
|
|
723
|
-
updateBarButtonItems()
|
|
724
|
-
self.progressView?.progress = 0
|
|
725
|
-
if let url = webView.url {
|
|
726
|
-
self.url = url
|
|
727
|
-
delegate?.webViewController?(self, didFail: url, withError: error)
|
|
728
|
-
}
|
|
729
|
-
}
|
|
730
|
-
|
|
731
|
-
public func webView(_ webView: WKWebView, didFail navigation: WKNavigation!, withError error: Error) {
|
|
732
|
-
updateBarButtonItems()
|
|
733
|
-
self.progressView?.progress = 0
|
|
734
|
-
if let url = webView.url {
|
|
735
|
-
self.url = url
|
|
736
|
-
delegate?.webViewController?(self, didFail: url, withError: error)
|
|
737
|
-
}
|
|
738
|
-
}
|
|
739
|
-
|
|
740
|
-
public func webView(_ webView: WKWebView, didReceive challenge: URLAuthenticationChallenge, completionHandler: @escaping (URLSession.AuthChallengeDisposition, URLCredential?) -> Void) {
|
|
741
|
-
if let bypassedSSLHosts = bypassedSSLHosts, bypassedSSLHosts.contains(challenge.protectionSpace.host) {
|
|
742
|
-
let credential = URLCredential(trust: challenge.protectionSpace.serverTrust!)
|
|
743
|
-
completionHandler(.useCredential, credential)
|
|
744
|
-
} else {
|
|
745
|
-
completionHandler(.performDefaultHandling, nil)
|
|
746
|
-
}
|
|
747
|
-
}
|
|
748
|
-
|
|
749
|
-
public func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void) {
|
|
750
|
-
var actionPolicy: WKNavigationActionPolicy = .allow
|
|
751
|
-
defer {
|
|
752
|
-
decisionHandler(actionPolicy)
|
|
753
|
-
}
|
|
754
|
-
guard let u = navigationAction.request.url else {
|
|
755
|
-
print("Cannot handle empty URLs")
|
|
756
|
-
return
|
|
757
|
-
}
|
|
758
|
-
|
|
759
|
-
if !self.allowsFileURL && u.isFileURL {
|
|
760
|
-
print("Cannot handle file URLs")
|
|
761
|
-
return
|
|
762
|
-
}
|
|
763
|
-
|
|
764
|
-
if handleURLWithApp(u, targetFrame: navigationAction.targetFrame) {
|
|
765
|
-
actionPolicy = .cancel
|
|
766
|
-
return
|
|
767
|
-
}
|
|
768
|
-
|
|
769
|
-
if u.host == self.source?.url?.host, let cookies = availableCookies, !checkRequestCookies(navigationAction.request, cookies: cookies) {
|
|
770
|
-
self.load(remote: u)
|
|
771
|
-
actionPolicy = .cancel
|
|
772
|
-
return
|
|
773
|
-
}
|
|
774
|
-
|
|
775
|
-
if let navigationType = NavigationType(rawValue: navigationAction.navigationType.rawValue), let result = delegate?.webViewController?(self, decidePolicy: u, navigationType: navigationType) {
|
|
776
|
-
actionPolicy = result ? .allow : .cancel
|
|
777
|
-
}
|
|
778
|
-
}
|
|
779
|
-
}
|
|
780
|
-
|
|
781
|
-
class BlockBarButtonItem: UIBarButtonItem {
|
|
782
|
-
|
|
783
|
-
var block: ((WKWebViewController) -> Void)?
|
|
784
|
-
}
|