用swift5开发一个混合编程的app

 

 

最近在家里研究了一下用swift5开发一个混合编程的app

app主要界面和功能是用h5来实现,用到native编码的就是二维码扫描

碰到了了一些问题做一下记录:

1、如何定义自己的ViewController并且能绑定xib视图文件

     1) 新建文件选择 Cocoa Touch Class,下一步时勾选also create XIB file

图1

     2)选中xib文件如图可以看到是否已关联,也可以通过这个单独创建并关联

    图2

2、两个ViewController导航切换:

    1)这个app需要两个ViewController,一个为MainViewController和ScaningViewController。先要配一个rootViewController

    前面版本是在AppDelegate.swift文件里配,但swift5在SceneDelegate.swift里配置,


func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) {
        window?.rootViewController = UINavigationController(rootViewController: MainViewController())
        guard let _ = (scene as? UIWindowScene) else { return }
    }

图3

  2)两个页面切换代码

从MainViewController跳转到ScaningViewController

let vc=ScaningViewController()
navigationController?.pushViewController(vc, animated: true)

     从ScaningViewController返回到 MainViewController

navigationController?.popViewController(animated: true)

3)数据从ScaningViewController返回到 MainViewController中

 MainViewControllerx定义回调方法

  //扫描返回
  func someFunctionThatTakesAClosure(string:String) -> Void {    
      print("string :"+string)
      self.navigationController?.setNavigationBarHidden(true, animated: false)
      self.theWebView!.evaluateJavaScript("iosCallback(true,'(string)')",
         completionHandler: nil)
   }

     跳转设置

    //打开扫描二维码页面
    func qrcode(){
        print("qrcode")
        let vc = ScaningViewController()
        vc.initWithClosure(closure: someFunctionThatTakesAClosure)
        navigationController?.pushViewController(vc, animated: true)
    }

ScaningViewController中定义闭包

   //声明一个闭包
   var myClosure:sendValueClosure?
       //下面这个方法需要传入上个界面的someFunctionThatTakesAClosure函数指针
   func initWithClosure(closure:sendValueClosure?){
       //将函数指针赋值给myClosure闭包,该闭包中涵盖了
       //someFunctionThatTakesAClosure函数中的局部变量等的引用
     myClosure = closure
   }

   在二维码收到字符串的地方,把字符串返回给MainViewController

if (myClosure != nil){
    //闭包隐式调用someFunctionThatTakesAClosure函数:回调。
      myClosure!("\(k)")
 }              
 navigationController?.popViewController(animated: true)

3、js调用webview

   MainViewController中

import UIKit
import WebKit

class MainViewController: UIViewController ,WKScriptMessageHandler{
    
    //定义webview
    var theWebView:WKWebView?
    //定义本地网页路径
    let path = Bundle.main.path(forResource: "index", ofType: ".html",
               inDirectory: "public")
    
    //app页面装载
    override func viewDidLoad() {
        super.viewDidLoad()
        //隐藏首页的导航栏 true 有动画
        self.navigationController?.setNavigationBarHidden(true, animated: false)
        //加载页面
        initWebView()
    }
    override func viewWillAppear(_ animated: Bool) {
            super.viewWillAppear(animated)
                // 隐藏首页的导航栏 true 有动画
                self.navigationController?.setNavigationBarHidden(true, animated: true)
    }
    override func viewWillDisappear(_ animated: Bool) {
            super.viewWillDisappear(animated)
            // 跳转页面的导航 不隐藏 false
            self.navigationController?.setNavigationBarHidden(false, animated: true)
    }
   
    //webview初始设置
    func initWebView(){
        let url = URL(fileURLWithPath:path!)
        let request = URLRequest(url:url)
        //创建供js调用的接口
        let theConfiguration = WKWebViewConfiguration()
        theConfiguration.userContentController.add(self, name: "jsbridge")//网页端用这个
        //将浏览器视图全屏(在内容区域全屏,不占用顶端时间条)
        let frame = CGRect(x:0, y:20, width:UIScreen.main.bounds.width,
                    height:UIScreen.main.bounds.height-20)
        theWebView = WKWebView(frame:frame, configuration: theConfiguration)
        //禁用页面在最顶端时下拉拖动效果
        theWebView!.scrollView.bounces = false
        //加载页面
        theWebView!.load(request)
        self.view.addSubview(theWebView!)
    }
    
    //js与swift交互
    func userContentController(_ userContentController: WKUserContentController,
       didReceive message: WKScriptMessage) {
       let sentData = message.body as! Dictionary<String,String>
       print("hello")
       if(sentData["method"] == "qrcode"){
           qrcode()
       }
    }
    //打开扫描二维码页面
    func qrcode(){
        print("qrcode")
        let vc = ScaningViewController()
        vc.initWithClosure(closure: someFunctionThatTakesAClosure)
        navigationController?.pushViewController(vc, animated: true)
    }
    //扫描返回
    func someFunctionThatTakesAClosure(string:String) -> Void {       
        print("string :"+string)
            self.navigationController?.setNavigationBarHidden(true, animated: false)
         self.theWebView!.evaluateJavaScript("iosCallback(true,'\(string)')",completionHandler: nil)
    }

}

  html测试代码

<!DOCTYPE HTML>
<html>
<body>
<script>
    function callback(success,code){
        document.getElementById("qr").innerHTML=code;
    }
    function scanQrcode(){
        if(window.webkit && window.webkit.messageHandlers && window.webkit.messageHandlers.jsbridge){
            var message = {"method":"qrcode"};
            window.iosCallback=callback;
            window.webkit.messageHandlers.jsbridge.postMessage(message);
        }
        
    }
</script>
    <button style="width:100px;height:50px;margin-left:100px;margin-top:200px;font-size:30px;" onclick="scanQrcode()">scan</button>
    <div id="qr" style="width:250px;height:250px;margin-left:100px;margin-top:250px;font-size:30px;">
    
    </div>
</body>
</html>

plist中加权限配置

图4

 

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值