当前位置: > > > Cordova - 与iOS原生代码交互1(通过JS调用Swift方法)

Cordova - 与iOS原生代码交互1(通过JS调用Swift方法)

(本文代码已升级至Swift3)

在前面的文章中介绍的了如何使用Cordova进行跨平台应用的开发,使用Cordova的话基本上就不需要在写系统原生代码了,只要通过编写html页面和js方法即可。
但在有些特殊情况下,还是是需要html页面能和系统原生代码(ios native code)进行交互。下面介绍如何实现 JSSwift 代码间的相互通信。

假设我们已经建立了一个名叫 HelloWorld 的Cordova工程项目(不太清楚如何使用Cordova的可以参考我前面写的几篇文章:使用Cordova开发iOS应用实战1(配置、开发第一个应用)

1,样例说明
(1)虽然使用Cordova创建的工程是一个 OC 工程,但由于苹果可以很方便的支持混合编程,所以我们用 Swift 来实现与 JS 的交互也是可以的。
(2)这里我们使用Swift来做个口令验证的功能,由于只是演示,所以代码很简单。Swift这边接收传输过来的口令字符串,判断正确与否并反馈回页面。如果验证失败还会返回具体的失败原因信息。

2,样例效果图
            

            

3,实现步骤
(1)我们在 Plugins 文件夹中新建一个Swift文件(HanggeSwiftPlugin.swift)。创建的时候系统会提示是否同时创建桥接头文件,这里选择确定。

(2)在新生成的桥接头文件 HelloWorld-Bridging-Header.h 中把 Cordova/CDV.h import 进来
#import <Cordova/CDV.h>

(3)新建的 HanggeSwiftPlugin.swift 中添加如下代码 
import Foundation

@objc(HWPHanggeSwiftPlugin) class HanggeSwiftPlugin : CDVPlugin {
    
    //验证口令方法
    @objc(verifyPassword:)
    func verifyPassword(command:CDVInvokedUrlCommand)
    {
        //返回结果
        var pluginResult:CDVPluginResult?
        //获取参数
        let password = command.arguments[0] as? String
        
        //开始验证
        if password == nil || password == "" {
            pluginResult = CDVPluginResult(status: CDVCommandStatus_ERROR,
                                           messageAs: "口令不能为空")
        }else if password != "hangge" {
            pluginResult = CDVPluginResult(status: CDVCommandStatus_ERROR,
                                           messageAs: "口令不正确")
        }else{
            pluginResult = CDVPluginResult(status:CDVCommandStatus_OK)
        }
        
        //发送结果
        self.commandDelegate.send(pluginResult, callbackId: command.callbackId)
    }
}

(4)在 config.xml 中添加如下配置,将我们创建的功能类给配置上
<feature name="HanggeSwiftPlugin">
    <param name="ios-package" value="HWPHanggeSwiftPlugin" />
</feature>

(5)首页 index.html 代码如下,修改运行后即可看到效果。
<!DOCTYPE html>
<html>
    <head>
        <title>口令验证</title>
        <meta http-equiv="Content-type" content="text/html; charset=utf-8">
            <script type="text/javascript" charset="utf-8" src="cordova.js"></script>
            <script type="text/javascript" charset="utf-8">
                //开始验证
                function verify() {
                    //获取输入的口令
                    var password = document.getElementById("pwd").value;
                    //调用自定义的验证插件
                    Cordova.exec(successFunction, failFunction, "HanggeSwiftPlugin",
                                 "verifyPassword", [password]);
                }
            
                //验证成功
                function successFunction(){
                    alert("口令验证成功!");
                }
            
                //验证失败
                function failFunction(message){
                    alert("验证失败:"+message);
                }
            </script>
            <style>
                * {
                    font-size:1em;
                }
            </style>
    </head>
    <body style="padding-top:50px;">
        <input type="text" id="pwd" >
        <button onclick="verify();">验证</button>
    </body>
</html>
源码下载:hello.zip
评论7
  • 7楼
    2017-04-28 10:41
    nf

    OC应该继承什么类?ViewController?还是NSObject?

    站长回复

    没用OC实现过,暂时帮不了你了。

  • 6楼
    2017-04-18 14:08
    yan.armark

    - (void)verifyPassword:(CDVInvokedUrlCommand *)command {
    //返回结果
    CDVPluginResult *pluginResult = nil;

    //获取参数
    NSString *password = command.arguments[0];

    //开始验证
    if (password == nil || [password isEqualToString:@""]) {
    pluginResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_ERROR
    messageAsString:@"口令不能为空"];

    }else if (![password isEqualToString:@"hangge"]) {
    pluginResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_ERROR
    messageAsString:@"口令不正确"];
    }else{
    pluginResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK
    messageAsString:@"口令正确"];
    }

    //发送结果
    [self.commandDelegate sendPluginResult:pluginResult callbackId:command.callbackId];

    }

    站长回复

    谢谢你提供的OC版代码。

  • 5楼
    2017-03-01 10:05
    yq

    我的报错
    2017-03-01 09:50:01.176032 HybridStandard[4590:2035381] ERROR: Method 'verifyPassword:' not defined in Plugin 'HanggeSwiftPlugin'
    2017-03-01 09:50:01.176448 HybridStandard[4590:2035381] -[CDVCommandQueue executePending] [Line 142] FAILED pluginJSON = ["HanggeSwiftPlugin895686577","HanggeSwiftPlugin","verifyPassword",[""]]
    是什么原因????

    站长回复

    这篇文章是早些时候写的,我看了了后来版本升级了。现已更新代码,不会报错了。你可以再看下。

  • 4楼
    2016-11-16 16:35
    code_LI

    -(void)verifyPassword:(CDVInvokedUrlCommand *)command
    {
    CDVPluginResult * result = nil;
    NSString * password = command.arguments[0];
    if (password == nil || [password isEqualToString: @""]) {
    result = [CDVPluginResult resultWithStatus:CDVCommandStatus_ERROR messageAsString:@"口令不能为空"];
    }else if ([password isEqualToString:@"123"]){
    result = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK];
    }else{
    result = [CDVPluginResult resultWithStatus:CDVCommandStatus_ERROR messageAsString:@"口令不正确"];
    }
    [self.commandDelegate sendPluginResult:result callbackId:command.callbackId];
    }

    站长回复

    谢谢你提供的OC版代码。

  • 3楼
    2016-09-28 14:40
    Poul

    站长能出个OC版的吗?

    站长回复

    目前文章还是以Swift为主,OC版的暂时不会出。

  • 2楼
    2016-07-25 16:57
    mubin

    谢谢分享

    站长回复

    不客气。欢迎常来看看。

  • 1楼
    2016-05-26 08:50
    mapanguan

    cordova 更新为最新版本 6.1.1后项目中出现了 libCordova.a文件,然后通过创建Swift文件编译运行提示:Swift is not supported for static libraries.我现在楼主的您的示例工程里面并没有这个文件。请教楼主这是新版本后生成的吗?出现这种问题如何解决。百度没收到相关解答。Google翻不过去

    站长回复

    不太清楚你这是什么问题,我看了下我电脑上Cordova版本也是6.1.1