WKWebView - buttons not visible in full screen mode - ios

I have a ViewController with WebKit and two buttons above it. I want WebKit to be fullscreen and buttons to be above it.
This is code of my ViewController:
#IBOutlet weak var webview: WKWebView!
override func viewDidLoad() {
super.viewDidLoad()
// here I am loading URLRequest
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
}
override func loadView() {
webview = WKWebView()
webview.navigationDelegate = self
view = webview
}
func webView(_ webView: WKWebView, didStartProvisionalNavigation navigation: WKNavigation!) {
showLoading()
}
func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
hideLoading()
}
This is what my storyboard looks like:
Methods showLoading() and hideLoading() are handling loading popup.
With this code buttons are not visible. When I remove function loadView() buttons are visible but methods showLoading() and hideLoading() are never called.
How can I achieve mentioned behavior: fullscreen webview with buttons and functional methods (showLoading() and hideLoading())

what happens in your current code is you arbitrarily replace the current view with your webview instance and that directly removes the current view's subviews (=your buttons) as well.
you can either
a)
insert the webview directly:
override func loadView() {
webview = WKWebView()
webview.navigationDelegate = self
view.insertSubview(webview, at: 0)
webview.frame = view.bounds
}
or
b)
add the WKWebView to your view in the Interface Builder under your buttons then connect the outlet and the delegate(s) from IB and you can remove your loadView() implementation entirely.

Related

How to make an activity indecator with a WKwebView in Swift

I am trying to make an iOS app with Swift and I have sorted out the webView which works perfectly, however now i'd like to implement an activity indicator. It displays properly and is animated, however when the page is loaded, the activity indicator does not disappear.
This is my code:
import UIKit
import WebKit
class FirstViewController: UIViewController {
#IBOutlet var webview: WKWebView!
// #IBOutlet var bg: UIView!
// #IBOutlet var logo: UIImageView!
#IBOutlet var ActInd: UIActivityIndicatorView!
// #IBOutlet var LoadingLabel: UILabel!
override func viewDidLoad() {
super.viewDidLoad()
let url = URL(string: "https://www.google.com")
let request = URLRequest(url: url!)
webview.load(request)
// Do any additional setup after loading the view, typically from a nib.
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func webViewDidStartLoad(_ : WKWebView) {
ActInd.startAnimating()
//LoadingLabel.isHidden = true
//logo.isHidden = true
//bg.isHidden = true
}
func webViewDidFinishLoad(_ : WKWebView){
ActInd.stopAnimating()
// LoadingLabel.isHidden = true
//logo.isHidden = true
//bg.isHidden=true
}
}
I'd appreciate it enormously if someone could help me get the activity indicator to disappear.
Thank you in advance
Try setting
ActInd.hidesWhenStopped = true // In viewDidLoad
Conform to WKNavigationDelegate, and you can track webView processes..
The methods of the WKNavigationDelegate protocol help you implement custom behaviors that are triggered during a web view's process of accepting, loading, and completing a navigation request.
There are two methods that you can use :
func webView(WKWebView, didStartProvisionalNavigation: WKNavigation!)
Called when web content begins to load in a web view.
Here you can show the activity indicator
func webView(WKWebView, didFinish: WKNavigation!)
Called when the navigation is complete.
For more info check WKNavigationDelegate documentation
So here are the steps :
1- Conform to WKNavigationDelegate.
2- Assign your view controller to be your web view’s navigationDelegate.
3- Implement didStartProvisionalNavigation and didFinish methods
Example :
class ViewController: UIViewController, WKNavigationDelegate {
#IBOutlet var webview: WKWebView!
override func viewDidLoad() {
super.viewDidLoad()
webview.navigationDelegate = self
/*
....
*/
}
func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
// hide/stop indicator
}
func webView(_ webView: WKWebView, didStartProvisionalNavigation navigation: WKNavigation!) {
//show your activity
}
}
On view did load just start your indicator and on webViewDidFinishLoad just hide that loader.
The methods won't ever be called.
Because, you haven't set your ViewController as NavigationDelegate. It needs to conform to the WKNavigationDelegate. You can then set the delegate in the viewDidLoad() function:
webview.navigationDelegate = self
The 2 methods you're calling also don't seem to exist. These are the equivalent delegate methods: webView(:didCommit:) and webView(:didFinish:)
You can set "Hides when stopped" and "Animated" in the storyboard or do it programatically as it is explained in this answer.
You should also take a look at the API Design guidelines explaining how code should be written. Especially you should:
Follow case conventions. Names of types and protocols are UpperCamelCase. Everything else is lowerCamelCase.

iOS Swift WKWebKit with MBCircularProgressBarView

before posting this I was looking on the internet how to implement from cocoa pods MBCircularProgressBarView in iOS Swift WKWebKit to track progress of loading website.
I have tried with combination of some other progress bar codes but it didn't work.
I have tried to implement self.progressView.value = 0 in viewDidLoad
and
UIView.animate(withDuration: 1.0){
self.progressView.value = 100
}
in
didFinish navigation
which shows circular bar and animate but doesn't show proper loading progress.
Any idea how to make this work.
Make a class class WebpageViewController: UIViewController, UIWebViewDelegate containing:
#IBOutlet weak var activitySpinner: UIActivityIndicatorView!
#IBOutlet weak var activityLabel: UILabel!
override func viewDidAppear(_ animated: Bool)
{
activitySpinner.tintColor = R.color.YumaRed
activitySpinner.hidesWhenStopped = true
activityLabel.text = "Loading..."
webView.loadRequest(URLRequest(url: URL(string: "http://...")!))
}
func webViewDidStartLoad(_ webView: UIWebView)
{
activitySpinner.startAnimating()
}
func webViewDidFinishLoad(_ webView: UIWebView)
{
activitySpinner.stopAnimating()
activityLabel.isHidden = true
}
func webView(_ webView: UIWebView, didFailLoadWithError error: Error)
{
activitySpinner.stopAnimating()
}
override func viewDidLoad()
{
super.viewDidLoad()
webView.delegate = self
}

Disabling zooming on webview

I've searched around, but I couldn't find how to disable zooming in iOS.
I have this in my viewDidLoad() but it doesn't do anything.
webView.scrollView.isMultipleTouchEnabled = false;
Any ideas?
You can remove the pinchGestureRecognizer from scrollView in delegate method didFinish navigation by conforming your ViewController to WKNavigationDelegate as below,
class ViewController: UIViewController, WKNavigationDelegate {
var webView: WKWebView!
override func viewDidLoad() {
super.viewDidLoad()
// TODO: Initialize webView before setting the delegate
webView.navigationDelegate = self
}
func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
if let pinchGesture = webView.scrollView.pinchGestureRecognizer {
webView.scrollView.removeGestureRecognizer(pinchGesture)
}
}
}

UIActivityIndicatorView nil?

I have hooked up an activityIndicator in the storyboard and created a webView programmatically. However when I load the VC, the program crashes complaining that the activityIndicator is nil. Why is this? I confirmed that the outlet is connected properly.
import UIKit
import WebKit
class ViewController: UIViewController, WKUIDelegate, WKNavigationDelegate {
var webView: WKWebView!
#IBOutlet weak var activityIndicator: UIActivityIndicatorView!
override func loadView() {
let webConfiguration = WKWebViewConfiguration()
webView = WKWebView(frame: .zero, configuration: webConfiguration)
webView.uiDelegate = self
webView.navigationDelegate = self
view = webView
}
override func viewDidLoad() {
super.viewDidLoad()
let myURL = URL(string: "https://www.google.com/")
let myRequest = URLRequest(url: myURL!)
webView.load(myRequest)
}
override func didReceiveMemoryWarning() {
super.didReceiveMemoryWarning()
// Dispose of any resources that can be recreated.
}
func webView(_ webView: WKWebView, didStartProvisionalNavigation navigation: WKNavigation!) {
activityIndicator.startAnimating()
print("loadingwebpage")
}
func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
print("didfinishloadingwebpage")
activityIndicator.stopAnimating()
}
}
You have this line :
view = webView
this mean you assign created webView to viewController's view. thats why your indicator destroy and cause crash.
add webView to viewcontroller's subview and crash will gone. change:
webView.frame = self.view.bounds
self.view.addSubview(webView)

Why webViewDidStartLoad is not calling?

Using swift with Xcode8
Below is my view controller.swift
import UIKit
import WebKit
class ViewController: UIViewController, WKNavigationDelegate {
var XWebview: WKWebView!
var activity = UIActivityIndicatorView(activityIndicatorStyle: .whiteLarge)
override func loadView() {
super.loadView()
self.XWebview = WKWebView()
self.XWebview.navigationDelegate = self
self.view = self.XWebview
}
override func viewDidLoad() {
XWebview.navigationDelegate = self
activity.center = self.view.center
activity.color = UIColor.gray
XWebview.addSubview(activity)
super.viewDidLoad()
let XURL = NSURL(string: "http://www.yahoo.com")
let XURLRequest = NSURLRequest(url: XURL! as URL)
XWebview.load(XURLRequest as URLRequest)
}
override var prefersStatusBarHidden: Bool {
return true
}
func webView(_ webView: WKWebView, didStartProvisionalNavigation navigation: WKNavigation!) {
activity.startAnimating()
}
func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
activity.stopAnimating()
}
}
I did not see any indicator when load web view?
Did I do something wrong?
You are using WKWebView and implemented the UIWebView delegate. It will not trigger. You have to implement WKWebView protocol methods.
Implement the following WKNavigationDelegate protocol method to identify start loading the view. This will be triggered when a main frame navigation starts.
func webView(_ webView: WKWebView, didStartProvisionalNavigation navigation: WKNavigation!)
Make sure your activity indicator color with not same asWKWebView background color. Make it grey
Use main queue to show/hide activity indicator.
DispatchQueue.main.async {
activity.startAnimating()
}
DispatchQueue.main.async {
activity.stopAnimating()
}
Use grey color for activity indicator if your web view is white color.
var activity = UIActivityIndicatorView(activityIndicatorStyle: .gray)

Resources