Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/ios/114.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Ios 当iPhone从配对的Apple Watch收到消息时,不会取消本地通知(有时)_Ios_Watchkit_Apple Watch_Appdelegate_Watchconnectivity - Fatal编程技术网

Ios 当iPhone从配对的Apple Watch收到消息时,不会取消本地通知(有时)

Ios 当iPhone从配对的Apple Watch收到消息时,不会取消本地通知(有时),ios,watchkit,apple-watch,appdelegate,watchconnectivity,Ios,Watchkit,Apple Watch,Appdelegate,Watchconnectivity,我有一个苹果手表应用程序,上面有一个按钮,可以用来记录事件。记录事件后,我想取消应用程序中所有挂起的本地通知。问题是,有时本地通知会被取消,而有时则不会 以下是Watch应用程序的代码。点击按钮时,我会向iPhone应用程序发送一条消息: func buttonTapped() { // check to make sure the session is reachable, so a message can be sent if session.reachable == tr

我有一个苹果手表应用程序,上面有一个按钮,可以用来记录事件。记录事件后,我想取消应用程序中所有挂起的本地通知。问题是,有时本地通知会被取消,而有时则不会

以下是Watch应用程序的代码。点击按钮时,我会向iPhone应用程序发送一条消息:

func buttonTapped() {

    // check to make sure the session is reachable, so a message can be sent
    if session.reachable == true {

        // a dict containing the date of the event to be sent to the iPhone
        let dict = ["date" : NSDate()]

        // send the dict and specify the replyHandler
        session.sendMessage(dict, replyHandler: { (reply) in

                if reply["success"] as? Bool == true {

                    print("notifications were cancelled")
                }

            }, errorHandler: { (error) in

                // some kind of error has occurred
            }
        )
    }
}
在iPhone上的AppDelegate中,我实现了WatchConnectivity委托方法来接收消息,这是清除通知的地方。然后,调用replyHandler向Watch应用程序指示消息已成功接收和处理:

func session(session: WCSession, didReceiveMessage message: [String : AnyObject], replyHandler: ([String : AnyObject]) -> Void) {

    if message["date"] != nil {

        dispatch_async(dispatch_get_main_queue()){

            let reply = ["success" : true]

            UIApplication.sharedApplication().cancelAllLocalNotifications()

            // send the reply to the Watch to confirm all this has happened
            replyHandler(reply)
        }
    }
}
即使我看到成功的回复返回到了Watch,本地通知有时也不会被取消。


这似乎是一个iOS或watchOS bug,而不是我可以解决的问题吗?也许在后台启动应用程序时,某些API不能保证可访问?(这似乎是使用WatchConnectivity发送消息时发生的情况)

当AppDelegate以这种方式接收消息时,应用程序将在后台启动(即使它没有显示在多任务屏幕上)。但由于我没有明确要求iOS提供后台时间,我在
didReceiveMessage
中的代码并不总是完全执行

解决办法是专门要求背景时间。下面是我如何更改didReceiveMessage以使其正常工作的:

// initialize a background task identifier
var backgroundTask: UIBackgroundTaskIdentifier = UIBackgroundTaskInvalid

func session(session: WCSession, didReceiveMessage message: [String : AnyObject], replyHandler: ([String : AnyObject]) -> Void) {

    if message["date"] != nil {

        dispatch_async(dispatch_get_main_queue()){

            // begin the background task
            self.backgroundTask = UIApplication.sharedApplication().beginBackgroundTaskWithName("CancelNotifications", expirationHandler: {

                // this expirationHandler will be called to end and invalidate the background task in case it doesn't have enough time to complete

                UIApplication.sharedApplication().endBackgroundTask(self.backgroundTask)
                self.backgroundTask = UIBackgroundTaskInvalid
            })

            let reply = ["success" : true]

            UIApplication.sharedApplication().cancelAllLocalNotifications()

            // send the reply to the Watch to confirm all this has happened
            replyHandler(reply)

            // let iOS know the background task is done
            UIApplication.sharedApplication().endBackgroundTask(self.backgroundTask)
            self.backgroundTask = UIBackgroundTaskInvalid
        }
    }
}
非常感谢大卫·沃尔什(一款很棒的苹果手表和iPhone应用程序),他向我展示了如何解决这个问题