cordova插件实现拨打电话,支持两种形式:

1,直接拨号;

2,跳转到拨号界面,但不拨号,自动填充号码;


最近项目上有个需求,点击客服电话拨打电话,在github上找了一下,用下面这个插件实现了效果:


插件地址:

https://github.com/Rohfosho/CordovaCallNumberPlugin


1,安装插件

sudo cordova plugin add https://github.com/Rohfosho/CordovaCallNumberPlugin.git


2,js中使用

$$(document).on('click','#tel_number_content',function () {
		    //弹出拨号确认框(Framework7框架)
                    myApp.confirm("确认拨打电话?",function(){
				  //调用插件
                                  window.plugins.CallNumber.callNumber(function onSuccess(result){
                                                                       console.log("Success:call number"+result);
                                                                       },
                                                                      function onError(result) {
                                                                       console.log("Error:call number"+result);
                                                                       },
                                                                      "18589082142",true);
                                  },function(){
                                    console.log("cancle call number");
                                  });
    });



后来领导又提出不能直接拨号,要求点击客服电话后跳转到拨号界面,自动填充电话号码但不拨号。我在github上翻了个遍,网上的插件都是只支持直接拨号的,没办法,只有自己动手改造插件以满足需求了。好在搞过两年安卓,就先从安卓开始。

我先去看了下这个插件作者是怎么写的,安卓交互是在CFCallNumber.java文件,实现拨号的是下面这个方法:

private void callPhone(JSONArray args) throws JSONException {
    String number = args.getString(0);
    number = number.replaceAll("#", "%23");

    if (!number.startsWith("tel:")) {
      number = String.format("tel:%s", number);
    }
    try {
      Intent intent = new Intent(isTelephonyEnabled() ? Intent.ACTION_CALL : Intent.ACTION_VIEW);
      intent.setData(Uri.parse(number));

      boolean bypassAppChooser = Boolean.parseBoolean(args.getString(1));
      if (bypassAppChooser) {
        intent.setPackage(getDialerPackage(intent));
      }

      cordova.getActivity().startActivity(intent);
      callbackContext.success();
    } catch (Exception e) {
      callbackContext.error("CouldNotCallPhoneNumber");
    }
  }


恍然大悟,作者这样写的那肯定就是直接拨号啊,立刻顺手就改了,改后如下:

private void callPhone(JSONArray args) throws JSONException {
    String number = args.getString(0);
    number = number.replaceAll("#", "%23");

    if (!number.startsWith("tel:")) {
      number = String.format("tel:%s", number);
    }
    try {
/*      //自动拨号
Intent intent = new Intent(isTelephonyEnabled() ? Intent.ACTION_CALL : Intent.ACTION_VIEW);
      intent.setData(Uri.parse(number));
      boolean bypassAppChooser = Boolean.parseBoolean(args.getString(1));
      if (bypassAppChooser) {
        intent.setPackage(getDialerPackage(intent));
      }
*/
//跳转到拨号界面,填充号码,不自动拨号
      Intent intent = new Intent(isTelephonyEnabled() ? Intent.ACTION_DIAL : Intent.ACTION_VIEW);
      intent.setData(Uri.parse(number));
      intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

      cordova.getActivity().startActivity(intent);
      callbackContext.success();
    } catch (Exception e) {
      callbackContext.error("CouldNotCallPhoneNumber");
    }
  }


我在修改CFCallNumber.java文件时碰到了权限问题,这个文件被锁定了,所以先修改文件权限,执行如下命令:

sudo chmod -R 777 (文件路径)



修改文件权限后再按照上面所说的修改插件代码,运行,ok。以前没写过插件,都是网上搜的现成的也没去研究具体怎么实现的,这次顺便研究了下,才发现插件的实现方式还是很好理解的,只要写过安卓就能写了。不能畏惧。

安卓下是ok了,开始改造ios的。同样先去看下插件作者是怎么写的,ios实现拨号是在CFCallNumber.m文件,实现方式如下:

[self.commandDelegate runInBackground:^{

        CDVPluginResult* pluginResult = nil;
        NSString* number = [command.arguments objectAtIndex:0];
        number = [number stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];

        if( ! [number hasPrefix:@"tel:"]){
            number =  [NSString stringWithFormat:@"tel:%@", number];
        }

        if(![[UIApplication sharedApplication] canOpenURL:[NSURL URLWithString:number]]) {
            pluginResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_ERROR messageAsString:@"NoFeatureCallSupported"];
        }
        else if(![[UIApplication sharedApplication] openURL:[NSURL URLWithString:number]]) {
            // missing phone number
            pluginResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_ERROR messageAsString:@"CouldNotCallPhoneNumber"];
        } else {
            pluginResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK];
        }

        // return result
        [self.commandDelegate sendPluginResult:pluginResult callbackId:command.callbackId];

    }];


虽然能看懂,但也确实不知道怎么改,尝试了网上的各种方法都只能实现直接拨号,翻遍了论坛、博客,最后得出结论:ios没有提供跳转到拨号界面的API!只能直接拨号!可参看以下帖子:

http://www.cocoachina.com/bbs/read.php?tid-1693841-page-1.html

没办法,只能作区分了。最后是在js中先判断设备类型,如果是android设备就直接跳转到拨号界面,是ios设备就在底部弹出拨号确认框(模仿的支付宝,支付宝、美团UI也都是这样做的),代码如下:

$$(document).on('click','#tel_number_content',function () {
                    var device = Framework7.prototype.device;
                    if (device.iphone) {
                    console.log('this is iPhone');
                    var button_number = [
                                   {
                                   text: '18589082142',
                                   onClick: function () {
                                   window.plugins.CallNumber.callNumber(
                                                                        function onSuccess(result){
                                                                        console.log("Success:call number"+result);
                                                                        },
                                                                        function onError(result) {
                                                                        console.log("Error:call number"+result);
                                                                        },
                                                                        "18589082142",true);
                                   }
                                   }
                                   ];
                    var button_cancle = [
                                         {
                                         text: '取消',
                                         color: 'red',
                                         onClick: function () {
                                         console.log('ios cancle call 18589082142');
                                         }
                                         }
                    ];
                    var groups = [button_number, button_cancle];
                    myApp.actions(groups);
                    }else{
                    console.log('this is android');
                    window.plugins.CallNumber.callNumber(
                                                         function onSuccess(result){
                                                         console.log("Success:call number"+result);
                                                         },
                                                         function onError(result) {
                                                         console.log("Error:call number"+result);
                                                         },
                                                         "18589082142",true);
                    }
                    });



IOS效果如下:

自动拨号程序JAVA 自动拨号插件_自动拨号程序JAVA