Capacitor iOS 插件指南
构建适用于 iOS 的 Capacitor 插件需要编写 Swift(或 Objective-C)代码来与 Apple 的 iOS SDK 进行交互。
Capacitor 采用标准的 iOS 开发工具来构建 iOS 插件。我们相信直接使用 Swift(或 Objective-C)可以更轻松地利用 Stack Overflow 上的现有解决方案、与现有的原生开发者共享成果,并能在平台功能发布后立即使用。
入门
首先,按照插件指南的入门部分所述生成一个插件。
然后,在 Xcode 中打开 your-plugin/ios/Plugin.xcworkspace。
使用 Swift 构建插件
一个适用于 iOS 的 Capacitor 插件是一个简单的 Swift 类,它继承自 CAPPlugin,并包含一些可以从 JavaScript 调用的导出方法。
插件生成后,你可以通过打开 Plugin.swift 开始编辑。
简单示例
在生成的示例中,有一个简单的 echo 插件,其中包含一个 echo 函数,该函数简单地返回传递给它的值。
这个示例展示了 Capacitor 插件的几个核心组件:从 Plugin Call 接收数据,以及将数据返回给调用者。
Plugin.swift
import Capacitor
@objc(MyPlugin)
public class MyPlugin: CAPPlugin {
@objc override public func load() {
// 当插件首次在 bridge 中构建时调用
}
@objc func echo(_ call: CAPPluginCall) {
let value = call.getString("value") ?? ""
call.resolve([
"value": value
])
}
}
访问调用数据
每个插件方法都会收到一个 CAPPluginCall 实例,其中包含客户端调用插件方法的所有信息。
客户端可以发送任何可 JSON 序列化的数据,例如数字、文本、布尔值、对象和数组。这些数据可以通过调用实例的 options 字段访问,或使用 getString、getObject 等便捷方法访问。
例如,以下是如何获取传递给方法的数据:
@objc func storeContact(_ call: CAPPluginCall) {
let name = call.getString("yourName") ?? "default name"
let address = call.getObject("address") ?? [:]
let isAwesome = call.getBool("isAwesome") ?? false
guard let id = call.options["id"] as? String else {
call.reject("Must provide an id")
return
}
// ...
call.resolve()
}
注意 CAPPluginCall 实例上各种数据访问方式,包括如何使用 guard 来要求某些选项必须存在。
返回数据
插件调用可以成功或失败。对于使用 Promise(最常见)的调用,成功对应调用 Promise 的 resolve,失败对应调用 reject。对于使用回调的调用, 成功会调用成功回调,失败则调用错误回调。
CAPPluginCall 的 resolve 方法接受一个字典,支持 JSON 可序列化的数据类型。以下是将数据返回给客户端的示例:
call.resolve([
"added": true,
"info": [
"id": id
]
])
要使调用失败或拒绝,调用 call.reject,传入错误字符串和(可选的)Error 实例及额外数据:
call.reject(error.localizedDescription, error, [
"item1": true
])
添加初始化逻辑
插件可以重写 load 方法,在插件首次初始化时运行一些代码:
@objc(MyPlugin)
public class MyPlugin: CAPPlugin {
@objc override public func load() {
// 当插件首次在 bridge 中构建时调用
}
}
呈现原生界面
要在 Capacitor 界面上呈现原生界面,我们需要访问 Capacitor 的 View Controller。要访问 Capacitor 的 View Controller,我们需要使用 CAPPlugin 类上可用的 CAPBridge 对象。
我们可以使用 UIViewController 在其上呈现原生 View Controller,如下所示:
DispatchQueue.main.async {
self.bridge.viewController.present(ourCustomViewController, animated: true, completion: nil)
}