Watch App 结构

2016/04/18 伟强 调研

Watch App结构及技术调研。

  • Watch App,运行在Apple Watch上,只包含与UI相关的storyboards和资源文件
  • WatchKit Extension,运行在iPhone或Apple Watch(WatchOS 2)上,包含应用的管理和响应用户交互的代码。
      Watch App只能随iOS App一起发布,应用安装后会同步至配对的Watch上,用户可以在“我的手表”中设置是否同步Watch应用。
      第三方Watch App必须依赖于iPhone5以上的设备运行。

  官方结构图如下:(含WatchOS 2)
  

Watch App界面:

  • App主界面
  • Glance界面
  • Notification自定义界面

主界面包含完整的用户界面,用户通过点击应用Icon启动应用,查看处理数据。
Glance界面是只读的,不能包含可交互的控件,点击界面后跳转到应用主界面。此界面只有一屏,所以要显示重要、及时的信息。
Notification界面可以自定义本地或远程通知的显示样式,可添加一些图片、文字等内容。

更多watchOS内容参考https://developer.apple.com/watchos/pre-release/

创建一个Watch App工程

  创建Watch App并添加Notification和Glance。
  
  

关于BundleID

  xcode会以iOS应用的BundleID加后缀的方式自动为WatchKit Extension和Watch App生成BundleID。

|应用|BundleID| |—|—| |iOS App|com.td.demo| |WatchKit Extension|com.td.demo.watchkitextension| |WatchKit App|com.td.demo.watchkitapp|  

Watch App代码交互详解

Watch App

  • 点击Watch app icon
    未初始化:init -> awakeWithContext -> willActivate
    已初始化:willActivate

  • 锁屏/Back键:DidDeactivate

参考代码:

// InterfaceController.m
@implementation InterfaceController

- (instancetype)init {
    self = [super init];
    if (self) {
    // 可在此处进行一些初始化操作
    }
    return self;
}

- (void)awakeWithContext:(id)context {
    [super awakeWithContext:context];
    // 可在此处配置界面对象
}

- (void)willActivate {
    // WatchApp视图即将可见
    [super willActivate];
}

- (void)didDeactivate {
    // WatchApp视图已不可见
    [super didDeactivate];
}

@end

Glance

  Glance对于Watch App并不是必须的,并且最多只能有一个。
  界面分为上下两个区域,上区有12种样式可选,下区有24种样式可选。在Group中可以添加无交互的控件,但尽量不要使用地图和表格控件。

  • 切换至Watch App的Glance
    未初始化:init -> awakeWithContext -> willActivate
    已初始化:willActivate
  • 锁屏/Back键/切换到其他Glance/进入Watch app:DidDeactivate
  • 点击Glance进入Watch App(代码交互参考Watch app)

参考代码:

// GlanceController.m
@implementation GlanceController

- (instancetype)init {
    self = [super init];
    if (self) {
    // 可在此处进行一些初始化操作
    }
    return self;
}

- (void)awakeWithContext:(id)context {
    [super awakeWithContext:context];
    // 可在此处配置界面对象
}

- (void)willActivate {
    // Glance视图即将可见
    [super willActivate];
}

- (void)didDeactivate {
    // Glance视图已不可见
    [super didDeactivate];
}

@end

Notification

  Notification界面分为Short-Look和Long-Look两种,而Long-Look又分为Static和Dynamic两种。

Short-Look

  只有一屏不可滚动、不可交互,UI由系统提供不能改变。Short-Look和iOS通知的条幅一样都是系统控制的,应用中无法得到通知显示等事件。
  本地通知或远程通知的Title不为空显示Title和“应用名”,否则只显示应用名。
    

Short-Look to Long-Look

  系统设置:在iPhone的“Apple Watch–我的手表–通知”中的“隐藏通知内容”:
  关:Watch上显示Short-Look约一秒时间会自动跳转到Long-Look界面。
  开:点击Short-Look界面跳转到Long-Look界面。按Back键Short-Look界面消失,可在“通知列表”中找到该通知。
  
  在Short-Look界面锁屏30秒内点亮屏幕依然是Short-Look界面,否则界面消失,可在“通知列表”中找到该通知,该状态由系统控制,开发者无法参与。

Long-Look

  一个Watch App可以创建多个Long-Look,每个Long-Look的Category需要设置为不同的名字。

Long-Look可以分为:

  • 显示系统默认样式的Long-Look界面
  • Default Long-Look
  • 具有特定category属性Long-Look界面

通知到达后会根据category属性来显示相应的Long-Look界面

Dynamic & Static

  如果Long-Look有Dynamic则通常情况下会显示Dynamic,除非Dynamic不可用或你明确告知系统显示Static。Dynamic需要绑定WKUserNotificationInterfaceController的子类,如未绑定则该Dynamic永远不会被显示。
    

Long-Look显示会触发以下方法进行布局:

  • 本地通知
    didReceiveLocalNotification:withCompletion:
  • 远程通知
    didReceiveRemoteNotification:withCompletion:

界面布局完成后通过completionHandler方法参数控制Dynamic或Static

  • WKUserNotificationInterfaceTypeCustom <-> Dynamic
  • WKUserNotificationInterfaceTypeDefault <-> Static

参考代码:

// NotificationController.m
@implementation NotificationController

- (instancetype)init {
    self = [super init];
    if (self){
        // 可在此处进行一些初始化操作
    }
    return self;
}

- (void)willActivate {
    // 通知视图即将可见
    [super willActivate];
}

- (void)didDeactivate {
    // 通知视图已不可见
    [super didDeactivate];
}

- (void)didReceiveLocalNotification:(UILocalNotification *)localNotification withCompletion:(void (^)(WKUserNotificationInterfaceType))completionHandler {
    // 根据本地通知实例,在此处对Long-Look Dynamic界面布局
    completionHandler(WKUserNotificationInterfaceTypeCustom);
}

- (void)didReceiveRemoteNotification:(NSDictionary *)remoteNotification withCompletion:(void (^)(WKUserNotificationInterfaceType))completionHandler {
    // 根据远程通知内容,在此处对Long-Look Dynamic界面布局
    completionHandler(WKUserNotificationInterfaceTypeCustom);
}

@end
Long-Look显示后

  Watch App入口类未实例化时,会调用入口类的init和awakeWithContext:方法。

Long-Look界面以下动作都会调用DidDeactivate:

  • 锁屏:30秒内点亮屏幕,依然是Long-Look界面;否则界面消失,可在“通知列表”中找到该通知;
  • Back键:可在“通知列表”中找到该通知;
  • “关闭”:从“通知列表”中清除该通知。
通知列表

  点击通知会显示Long-Look界面,但只能显示Static界面不能再显示Dynamic界面。
  

自定义按钮(最多4个)

  前台操作按钮:点击后WatchKit Extension启动并调用Watch app入口类的本地通知或远程通知方法。

// InterfaceController.m
@implementation InterfaceController

- (void)handleActionWithIdentifier:(NSString *)identifier forRemoteNotification:(NSDictionary *)remoteNotification {
    // 可根据Action的id和远程通知的内容进行处理
}

- (void)handleActionWithIdentifier:(NSString *)identifier forLocalNotification:(UILocalNotification *)localNotification {
    // 可根据Action的id和本地通知的实例进行处理
}

@end

  后台操作按钮:点击后WatchKit Extension不响应,直接调用相应iOS应用的方法,在后台进行处理。

// AppDelegate.m
@implementation AppDelegate

- (void)application:(UIApplication *)application handleActionWithIdentifier:(NSString *)identifier forLocalNotification:(UILocalNotification *)notification completionHandler:(void(^)())completionHandler {
    // 可根据Action的id和本地通知的实例进行处理
    completionHandler();
}

- (void)application:(UIApplication *)application handleActionWithIdentifier:(NSString *)identifier forRemoteNotification:(NSDictionary *)userInfo completionHandler:(void(^)())completionHandler {
    // 可根据Action的id和远程通知的内容进行处理
    completionHandler();
}

@end

Search

    欢迎下载我们的APP

    Table of Contents