豪翔天下

Change My World by Program

0%

Cordova 开发手册

基本命令

  • npm install -g cordova
  • 如果要运行在xcode需要用xcode打开项目名.xcworkspace文件
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
# 创建工程
cordova create 目录名 com.haofly.mobile 应用名

# 平台管理
cordova platform add ios
cordova platform add android
cordova platform list # 列出当前添加了的平台
cordova platform rm android

# 编译运行,如果更新了www目录,可以直接重新build即可
cordova build # 编译所有平台
cordova build android # 仅编译指定平台,这条命令相当于cordova prepare android && codova compile android
cordova emulate ios # 启动模拟器
cordova run browser # 在指定平台运行

# 插件管理
cordova plugin search facebook # 搜索插件
cordova plugin ls # 列出当前已安装的插件
cordova plugin rm cordova-plugin-facebook4 # 移除插件
cordova plugin add cordova-plugin-facebook4 # 添加插件
corodva plugin add https://github.com/myproject#branch_name # 从github安装指定分支的cordova插件

目录结构

  • 编译后*-Info.plistResources目录下

  • 如果要添加配置到*-Info.plist文件里可以在config.xml里面的platform ios添加,不过添加完成后需要重新cordova platform remove ios && cordova platform add ios,否则可能出现错误doc.find is not a function

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    <platform name="ios">
    <!--下面这个配置可以避免NSURLConnection finished with error - code -1004问题-->
    <edit-config file="*-Info.plist" mode="merge" target="NSAppTransportSecurity">
    <dict>
    <key>NSAllowsArbitraryLoadsInWebContent</key>
    <true/>
    <key>NSAllowsArbitraryLoads</key>
    <true/>
    </dict>
    </edit-config>
    </platform>

使用Vue作前端

VUE配置步骤

  1. 初始化一个vue工程,vue init webpack project-name

  2. vue/index.htmlhead中添加内容:

    1
    2
    3
    <meta http-equiv=”Content-Security-Policy” content="default-src ‘self’ data: gap: https://ssl.gstatic.com ‘unsafe-eval’; style-src ‘self’ ‘unsafe-inline’; media-src *; img-src ‘self’ data: content:; connect-src ‘self’ ws:;">

    <script type="text/javascript" src="cordova.js"></script>
  3. 修改build配置,在config/index.js中修改如下配置

    1
    2
    3
    4
    build: {
    index: path.resolve(__dirname, ‘../www/index.html’), // 指向cordova的www目录
    assetsRoot: path.resolve(__dirname, ‘../www’),
    }

依赖管理Pod

  • 转为iOS工程提供的第三方库的依赖管理工具
1
2
3
4
sudo sudo	# 安装pod管理工具

pod search xxx # 查找第三方库
cd platforms/ios && pod repo update && pod install # cordova项目安装第三方库依赖

常用插件推荐

  • cordova-plugin-console: 只有很老的版本才需要了,现在可以直接使用console.log进行日志的输出,需要注意的是,必须先引入cordova.js才行,否则依然无法看到日志输出

  • cordova-plugin-device: 获取平台设备信息

  • cordova-plugin-facebook-connect: Facebook登陆插件,安装完成后得去platforms/ios目录执行一下pod repo update && pod install安装facebook SDK,这样使用:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    window.facebookConnectPlugin.login(['public_profile'], userData => {
    const authData = {
    access_token: userData.authResponse.accessToken
    };

    const userId = userData.authResponse.userID;

    window.facebookConnectPlugin.api(`${userId}/?fields=first_name,last_name,email`, null, result => {
    authData.first_name = result.first_name;
    authData.last_name = result.last_name;
    authData.email = result.email;
    resolve(authData);
    },
    error => {
    reject('error getting facebook user info' + error);
    });
    },
    error => {
    reject('error authenticating with facebook' + error);
    });
  • cordova-plugin-googleplus: Google登陆插件,只不过需要获取很多的账号相关的信息,实际的登陆只需要这样做即可:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    window.plugins.googleplus.isAvailable(avail => {
    if (avail) {
    let params = Platform.isIos() ? {} : {
    scopes: 'profile email openid',
    webClientId: config.GOOGLE_PLUS_WEB_CLIENT_ID,
    offline: true
    };

    window.plugins.googleplus.login(params, authData => {
    resolve({
    first_name: authData.givenName,
    last_name: authData.familyName,
    email: authData.email,
    access_token: authData.accessToken,
    id_token: authData.idToken
    });
    },
    error => {
    reject('error authenticating with google' + error);
    });
    }
    else {
    reject('google auth not available');
    }
    });
  • cordova-plugin-sign-in-with-apple: Apple ID登陆插件,需要在apple开发者后台给指定Bundle ID添加Sign In with Apple权限,使用同样非常简单:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    window.cordova.plugins.SignInWithApple.signin(
    { requestedScopes: [0, 1] },
    result => {
    console.log(result);
    alert(JSON.stringify(result));
    },
    error => {
    console.error(error);
    console.log(JSON.stringify(error));
    }
    );

插件开发Tips

  • 我不开发插件,但是很多很小众的插件,经常需要我们修改一下,所以还是需要学习一点插件开发的知识

IOS开发常用流程

  • 方法定义: 需要在src/ios/*.h中这样定义:

    1
    2
    3
    4
    5
    6
    7
    8
    #import <Cordova/CDV.h>

    @interface CordovaAppleMusic : CDVPlugin

    - (void) requestToken:(CDVInvokedUrlCommand*)command;
    - (void) requestAuthorization:(CDVInvokedUrlCommand*)command;

    @end
  • 方法实现,需要在src/ios/*.m中实现

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
      // 此方法来自于CordovaAppleMusic Plugin,是使用OC写的
    - (void)requestToken:(CDVInvokedUrlCommand*)command
    {
    NSString* callbackId = [command callbackId];
    NSString* developerToken = [[command arguments] objectAtIndex:0]; // 如果方法有参数可以这样获取参数
    SKCloudServiceController *serviceController = [[SKCloudServiceController alloc] init];
    [serviceController requestUserTokenForDeveloperToken:developerToken completionHandler:^(NSString * _Nullable userToken, NSError * _Nullable error) {
    if (error != nil) {
    NSLog(@"userToken_Error :%@", error);
    // 返回正确响应
    CDVPluginResult* result = [CDVPluginResult resultWithStatus:CDVCommandStatus_ERROR messageAsString:error.description];
    [self.commandDelegate sendPluginResult:result callbackId:callbackId];
    }
    else{
    // 返回错误响应
    CDVPluginResult* result = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:userToken];
    [self.commandDelegate sendPluginResult:result callbackId:callbackId];
    }
    }];
    }
  • 最后在www/*.js中暴露方法给JS

    1
    2
    3
    4
    5
    6
    7
    8
    9
    var exec = require('cordova/exec');
    module.exports = {
    requestAuthorization: function (successCallback, errorCallback) { // 无参数的方法
    exec(successCallback, errorCallback, "AppleMusic", "requestAuthorization", []);
    },
    requestToken: function (developerToken, successCallback, errorCallback) { // 带参数的方法
    exec(successCallback, errorCallback, "AppleMusic", "requestToken", [developerToken]);
    },
    }

TroubleShooting

  • 应用启动一直白屏: 网上有很多解决方法,都试过,我最后的解决方法是把系统语言切换成英文解决了

  • pod: Command failed with exit code 31: 尝试执行一下pod repo update,如果是Apple Silicon,那么需要使用arch -x86_64 zsh

  • 删除node_module可以解决的一些问题:

    • Cannot find module ‘./elementtree’
  • Current working directory is not a Cordova-based project.: 可能是www目录不见了

坚持原创技术分享,谢谢支持

欢迎关注我的其它发布渠道