tags: iOS 8,Swift,App Groups
随着 iOS 8 的发布,苹果为广大开发者很多新的 API,其中最突出显著的就非 App Extension 莫属了。这为开发者们又带来了很多机会。
而我们在开发 App Extension 的时候,基本大多数人都会遇到这样一个问题。就是由于 App Store 的规则是 App Extension 不能独立的发布,而是要跟随一个宿主应用一起发布。
比如奇妙清单:
我们看到,通过 App 扩展,奇妙清单将主 App 的任务数据显示到了通知中心上面。而这个通知中心插件的数据是来自它的主应用的。
要达到这个效果,就需要这两个 App 之间的数据进行共享。注意,是两个独立的应用哦。App 扩展虽然是以插件形式附属在主 App 中的,但它也作为一个独立的 App。
在两个独立的应用间共享存储数据有什么方法呢?这就需要 App Groups 的概念。
从名字就可以看出来啦,App Groups 就是应用分组,将不同的应用分到一个 App Groups 中,即可在这些应用之间共享数据。
具体操作流程如下:
-
在项目的设置界面中找到应用的 Target,然后选择 Capabilities 选项卡,然后会列出很多选项,往下拉就会找到 App Groups 选项,我们打开它的开关。如下图:
(注意一点:打开 App Groups 需要关联你的苹果开发者账号。所以在这之前,你还需要拥有一个苹果开发者账号。) -
成功开启后,会出现 App Groups 设置界面。点击下方的加号按钮,来添加一个新的 App Groups。如下图:
App Groups 的命名规则和 Bundle Identifier 一样,都是使用反向 DNS 规则。比如group.app.test
添加完成后,新的 Group 就会显示在设置界面上,我们将它左边的复选框勾选上,就完成了。 -
到此为止,主 App 的设置步骤就完成了,下面我们还要对扩展 App 进行类似的操作。首先还是找到 App Groups 选项框,并打开开关。
(注意:这次我们的 Target 选择的是 extension) -
打开开关后,这次和刚才的操作步骤有所不同,因为我们之前已经创建过 App Groups 了,这次就不需要创建新的了,只需要点击 App Groups 设置界面中的刷新按钮,就可以看到我们之前创建过的 Group 了。
然后勾选上即可完成 App 扩展 的 Group 设置。
这些基本设置操作完成后,我们就可以在这两个 App 之间进行数据共享啦。大家可以想一想,我们用什么方法进行数据共享比较合适呢?
其实很简单啦,就是我们熟悉的 NSUserDefaults
了。相信每一位朋友对这个类都不陌生。没想到吧,它还有共享数据这个作用。如果仔细查看它的文档,你就会发现它还有这样一个初始化方法 initWithSuiteName:
而官方文档上对这个方法是这样解释的:
Returns an NSUserDefaults object initialized with the defaults for the specified app group.
看到了吧,里面提到了 App Group, 这个初始化方法就是为 App Group 量身打造的。如果有兴趣进一步研究,可以查看下 NSUserDefaults
的 官方文档。
下面我们就继续啦,App 数据共享即将大功告成。首先我们在主 App 中的 AppDelegate 中的 didFinishLaunchingWithOptions
方法中来写存入数据的代码:
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -\> Bool {var defaultForExtension:NSUserDefaults! = NSUserDefaults(suiteName: "group.app.test")if(defaultForExtension != nil){defaultForExtension.setObject("2014", forKey: "year")defaultForExtension.synchronize()}return true}
有没有注意到这里面 NSUserDefaults
的构造方法NSUserDefaults(suiteName: "group.app.test")
,我们将前面我们创建的 App Groups 的标识作为参数传给了它的构造方法。这样,这个 NSUserDefaults
就专为我们的这个 App Group 存储数据了。
接下来,再到 App 扩展 中,再用这个 NSUserDefaults
将我们设置的值读取出来:
var defaultForExtension:NSUserDefaults! = NSUserDefaults(suiteName: "group.app.test")
if(defaultForExtension != nil){var result:NSString = defaultForExtension.objectForKey("year") as NSStringprintln(result)
}
到这里,我们的 App 和 Extension 之间的数据共享就完成了, 是不是解决了一个大问题呢。反正我觉得是。
更多文章请访问我的个人博客 www.theswiftworld.com