ios - 如何使用 WatchConnectivity 在我的 iOS 和 Watch 应用程序之间共享信息?

标签 ios swift watchkit apple-watch watchconnectivity

[免责声明:此问题旨在成为一个wiki问题,以回答有关watchkit下的iOS和 watch 应用程序之间发送数据的常见问题。和 watch-os标签。]

我正在开发 Apple Watch 应用程序并希望在 iOS 之间发送数据应用程序及其 WatchKit extension .我看过WatchConnectivity框架,但并不真正了解其所有方法之间的区别。

如果我希望即使我的应用程序在后台也能发送数据,我应该使用哪个功能?

我应该使用哪个功能将 UI 更新发送到 Watch?

我应该使用哪个函数来发送大数据?

最佳答案

在撰写此答案时(watchOS3 是当前稳定版本,watchOS4 处于测试阶段), 的唯一选择直接 iOS 之间的通信应用程序及其 WatchKit extensionWatchConnectivity框架。 (我说直接,因为本问答不涉及使用 CloudKit 等云技术将文件从一台设备上传到互联网并在另一台设备上下载。)

首先,让我们讨论WCSession的哪个功能应该用于什么目的。对于代码示例,请向下滚动。

在深入了解细节之前,简要介绍每个功能以及何时使用它们:

  • updateApplicationContext : 同步应用程序之间的状态,发送要显示在UI上的数据(仅用于发送小块数据)
  • transferUserInfo :在后台发送数据字典
  • transferFile : 后台发送文件
  • sendMessage :至少在 watch 应用程序在前台运行之间发送即时消息

  • 详细说明

    updateApplicationContext(_:)如果您想同步您的应用程序(例如保持 UI 更新或发送状态信息,例如用户登录等),则应使用。您可以发送数据字典。对该函数的后续调用将替换先前发送的字典,因此对应应用程序仅接收使用 updateApplicationContext 发送的最后一项.系统会尝试在适当的时间调用此函数,以便在需要时接收数据,同时最大限度地减少功耗。因此,当两个应用程序都没有在前台运行时,可以调用该函数,但是 WCSession需要激活才能成功传输。频繁调用尝试使用 updateApplicationContext 传输大量数据可能会失败,所以对于这个用法调用 transferUserInfo反而。

    transferUserInfo(:)transferCurrentComplicationUserInfo( :)如果您想在后台发送需要由其他应用程序接收的数据,则应使用。对该方法的后续调用将被排队,并接收从一个应用程序发送到另一个应用程序的所有信息。 transferCurrentComplicationUserInfo可用于将并发症相关数据发送到 WatchKit extension使用高优先级消息并唤醒 WatchKit app如果需要的话。但是,请注意,此功能有每日限制,一旦超过,数据将使用 transferUserInfo 传输。功能。

    transferFile(_:metadata:)在实现和性质上类似于 transferUserInfo , 但它接受 fileURL 而不是字典作为其输入参数,因此它应该用于将设备本地的文件发送到其对应方。随后的调用排队。收到的文件必须保存到 session(_:didReceive:) 中的新位置方法,否则将被删除。

    sendMessage(:replyHandler:errorHandler:)sendMessageData( :replyHandler:errorHandler:)立即将数据发送到对应的应用程序。在调用此方法之前,必须可以访问对应的应用程序。 iOS 应用程序始终被认为是可访问的,并且从您的 Watch 应用程序调用此方法会根据需要在后台唤醒 iOS 应用程序。 Watch 应用程序仅在安装和运行时才被认为是可访问的。传输必须在前台启动。对该方法的后续调用将排队。

    欲了解更多信息,请参阅 App programming guide for watchOS - Sharing Data .

    现在一些代码示例:

    设置WatchConnectivityiOS应用程序的AppDelegate :
    import UIKit
    import WatchConnectivity
    
    @UIApplicationMain
    class AppDelegate: UIResponder, UIApplicationDelegate {
    
        var window: UIWindow?
    
        func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool {
            if WCSession.isSupported() {
                let session = WCSession.default()
                session.delegate = self
                session.activate()
            }
            return true
        }
    }
    
    extension AppDelegate: WCSessionDelegate {
    
        func session(_ session: WCSession, didReceiveMessage message: [String : Any]) {
            print("Message received: ",message)
        }
    
        //below 3 functions are needed to be able to connect to several Watches
        func session(_ session: WCSession, activationDidCompleteWith activationState: WCSessionActivationState, error: Error?) {}
    
        func sessionDidDeactivate(_ session: WCSession) {}
    
        func sessionDidBecomeInactive(_ session: WCSession) {}
    }
    

    让您的WatchKit类符合 WCSessionDelegate :
    extension InterfaceController: WCSessionDelegate {
        func session(_ session: WCSession, activationDidCompleteWith activationState: WCSessionActivationState, error: Error?) {}
    }
    

    使用即时通讯功能,sendMessage :

    WatchKit app当您想立即向 iOS 发送信息时使用此代码应用程序。
    if WCSession.isSupported() {
        print("WCSession supported")
        let session = WCSession.default()
        session.delegate = self
        session.activate()
        if session.isReachable {
            session.sendMessage(["Instant":"Message"], replyHandler: nil, errorHandler: { error in
                print("Error sending message",error)
            })
        }
    }
    

    关于ios - 如何使用 WatchConnectivity 在我的 iOS 和 Watch 应用程序之间共享信息?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45489037/

    相关文章:

    jQuery Mobile + Phonegap : Page Header and Contents go Blank after Transition Completes

    swift - 将多个参数添加到 UITableView 中的目标 #selector

    ios - Firebase 无法在 iOS 上运行

    swift - 如何在代码中添加新页面到基于页面的导航 Apple Watch

    swift - 在 iWatch 上通过 Kingfisher 从 URL 加载图像需要很长时间

    ios - 'RTCPeerConnection' 没有可见的@interface 声明选择器 'setLocalDescription:'

    android - 如何更新应用程序的内容而不将新版本发布到 Play 商店

    swift - 如何使用 slider 设置 WKInterfaceTimer 的时间值

    ios - 实现 `backgroundColor` 的 `UIView` 的动画 `drawRect`

    ios - Swift 集成的 XWebView 项目现在要创建 iPA 文件