Monti

swift) webview-2 (자바스크립트 버튼 클릭 이벤트 핸들링) 본문

IOS/Swift

swift) webview-2 (자바스크립트 버튼 클릭 이벤트 핸들링)

montt 2022. 10. 8. 10:48

Swift에서 JavaScript Button 클릭 이벤트 핸들링 샘플

WebView 초기화

import WebKit
import UIKit

class ViewController: UIViewController {
    private var webView: WKWebView!

    override func viewWillAppear(_ animated: Bool) {
        super.viewWillAppear(animated)

        loadWebView()
    }
}

extension ViewController {
    func loadWebView() {
        guard let url = URL(string: "https://www.naver.com") else { 
            navigationController?.popViewController(animated: true)
            return
        }
        view = webView
        let urlRequest = URLRequest(url: url)
        webView.load(urlRequest)
    }    
}

브릿지 설정

HTML

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <script type=""text/javascript>
        function outLink(link) {
            webkit.messageHandlers.**outLink**.postMessage(link)
        }

        function button() {
            webkit.messageHandlers.**button**.postMessage(true)
        }
    </script>    
    <title>WebView</title>
</head>

<body>
    <header>
        <button type="button" onclick="button()"> button </button>
    </header>

    <section>
        <button type="button" onclick="outLink('https://www.naver.com/')"> 네이버 이동 </button>
    </section>

    <section>
        <button type="button" onclick="outLink('https://www.apple.com/')"> 애플 이동 </button>
    </section>

</body>
</html>

HTML 테스트

Swift 브릿지 등록

extension ViewController {
    func setupWebView() {
        let contentController = WKUserContentController()

        // Bridge 등록
        contentController.add(self, name: "button")
        contentController.add(self, name: "outLink")

        let configuration = WKWebViewConfiguration()
        configuration.userContentController = contentController

        webView = WKWebView(frame: .zero, configuration: configuration)
        }
}

Swift 브릿지 설정 (WKScriptMessageHandler Protocol 사용)

extension ViewController: WKScriptMessageHandler {
    func userContentController(_ userContentController: WKUserContentController, didReceive message: WKScriptMessage) {
        // 브릿지 키에 따른 Action 변경
                switch message.name {
        case "button":
            let alert = UIAlertController(title: "Swift 버튼 함수", message:"버튼 클릭", preferredStyle: .alert)
            let action = UIAlertAction(title: "확인", style: .default, handler: nil)
            alert.addAction(action)
            self.present(alert, animated: true, completion: nil)
            break
        case "outLink":
            guard let outLink = message.body as? String,
                  let url = URL(string: outLink) else { return }

            let alert = UIAlertController(title: "OutLink 버튼 클릭", message: "URL : \(outLink)", preferredStyle: .alert)
            let action = UIAlertAction(title: "링크 열기", style: .default) { _ in
                UIApplication.shared.open(url, options: [:], completionHandler: nil)
            }
            let cancelAction = UIAlertAction(title: "취소", style: .cancel, handler: nil)
            alert.addAction(action)
            alert.addAction(cancelAction)
            self.present(alert, animated: true, completion: nil)
        default:
            break
        }
    }
}

전체 코드

import UIKit
import WebKit

class ViewController: UIViewController{
    private var webView: WKWebView!

    override func viewDidLoad() {
        super.viewDidLoad()
        setupWebView()
    }

    override func viewWillAppear(_ animated: Bool) {
        super.viewWillAppear(animated)

        loadWebView()
    }
}

private extension ViewController {

    func setupWebView() {
        let contentController = WKUserContentController()

        // Bridge 등록
        contentController.add(self, name: "button")
        contentController.add(self, name: "outLink")

        let configuration = WKWebViewConfiguration()
        configuration.userContentController = contentController

        webView = WKWebView(frame: .zero, configuration: configuration)
        }

    func loadWebView() {
        guard let linkURL = URL(string: "url") else { navigationController?.popViewController(animated: true)
            return
        }
        view = webView
        let urlRequest = URLRequest(url: linkURL)
        webView.load(urlRequest)
    }
}

extension ViewController: WKScriptMessageHandler {
    func userContentController(_ userContentController: WKUserContentController, didReceive message: WKScriptMessage) {
        switch message.name {
        case "button":
            let alert = UIAlertController(title: "Swift 버튼 함수", message:"버튼 클릭", preferredStyle: .alert)
            let action = UIAlertAction(title: "확인", style: .default, handler: nil)
            alert.addAction(action)
            self.present(alert, animated: true, completion: nil)
            break
        case "outLink":
            guard let outLink = message.body as? String,
                  let url = URL(string: outLink) else { return }

            let alert = UIAlertController(title: "OutLink 버튼 클릭", message: "URL : \(outLink)", preferredStyle: .alert)
            let action = UIAlertAction(title: "링크 열기", style: .default) { _ in
                UIApplication.shared.open(url, options: [:], completionHandler: nil)
            }
            let cancelAction = UIAlertAction(title: "취소", style: .cancel, handler: nil)
            alert.addAction(action)
            alert.addAction(cancelAction)
            self.present(alert, animated: true, completion: nil)
        default:
            break
        }
    }
}

테스트 진행

WKWebView로 표현하는 index.html 화면

 

 

Comments