3

我试图在 Apple Watch 复杂功能中显示用户的每日步数。我通过调用 HKHealthStore 的 requestAuthorizationToShareTypes 方法来设置我的课程,当首次将其添加到表盘时,复杂功能会正确显示步骤。但是,在进行健康包查询时,刷新永远不会成功。我怀疑这与 HealthKit 权限有关,因为 HKSampleQuery 的完成处理程序没有被调用。如果我只是注释掉 health kit 查询,那么我的代码会按预期刷新。有谁知道我可能会错过什么?或者如果复杂的后台刷新不允许访问 HealthKit?

这是有效的代码块:

/// Provide the entry that should currently be displayed.
/// If you pass back nil, we will conclude you have no content loaded and will stop talking to you until you next call -reloadTimelineForComplication:.
func getCurrentTimelineEntryForComplication(complication: CLKComplication, withHandler handler: (CLKComplicationTimelineEntry?) -> Void) {

        let calendar = NSCalendar.currentCalendar()
        let now = NSDate()
        var startDate: NSDate? = nil
        var interval: NSTimeInterval = 0
        let endDate = NSDate()

        calendar.rangeOfUnit(NSCalendarUnit.Day, startDate: &startDate, interval: &interval, forDate: now)

        // Show dummy step data...
        let timelineEntry = self.buildTimelineEntry(complication, stepCount: 10, currentDateInterval: NSDate())
        handler(timelineEntry)
}

这是不起作用的代码块。错误情况下的更新甚至不会被调用:

/// Provide the entry that should currently be displayed.
/// If you pass back nil, we will conclude you have no content loaded and will stop talking to you until you next call -reloadTimelineForComplication:.
func getCurrentTimelineEntryForComplication(complication: CLKComplication, withHandler handler: (CLKComplicationTimelineEntry?) -> Void) {

        let calendar = NSCalendar.currentCalendar()
        let now = NSDate()
        var startDate: NSDate? = nil
        var interval: NSTimeInterval = 0
        let endDate = NSDate()

        calendar.rangeOfUnit(NSCalendarUnit.Day, startDate: &startDate, interval: &interval, forDate: now)

        let predicate = HKQuery.predicateForSamplesWithStartDate(startDate, endDate: endDate, options: HKQueryOptions.StrictStartDate)
        let sortDescriptor = NSSortDescriptor(key:HKSampleSortIdentifierStartDate, ascending: true)
        let stepSampleType = HKQuantityType.quantityTypeForIdentifier(HKQuantityTypeIdentifierStepCount)!
        let sampleQuery = HKSampleQuery(sampleType: stepSampleType, predicate: predicate, limit: 0, sortDescriptors: [sortDescriptor]) { (sampleQuery, results, error ) -> Void in

            if error != nil {
                dispatch_async(dispatch_get_main_queue(), { () -> Void in
                    let timelineEntry = self.buildTimelineEntry(complication, stepCount: 10, currentDateInterval: NSDate())
                    handler(timelineEntry)
                })

                return
            }

            self.currentSteps = [HKQuantitySample]()

            if results != nil {
                self.currentSteps = results as! [HKQuantitySample]
            }

            let countUnit = HKUnit(fromString: "count")
            var stepCount = 0.0
            var currentDate = now
            for result in self.currentSteps {
                stepCount += result.quantity.doubleValueForUnit(countUnit)
                currentDate = result.endDate
            }

            dispatch_async(dispatch_get_main_queue(), { () -> Void in
                let timelineEntry = self.buildTimelineEntry(complication, stepCount: stepCount, currentDateInterval: currentDate)
                handler(timelineEntry)
            })
        }

        self.healthStore.executeQuery(sampleQuery)
}
4

1 回答 1

3

尝试在并发症控制器中异步获取(HealthKit)数据将是不可靠的。

此外,尝试在并发症控制器中获取或计算将不必要地耗尽分配给您的并发症的执行时间预算。

Apple 建议您在复杂数据源需要之前获取数据并缓存它。

数据源类的工作是尽快为 ClockKit 提供任何请求的数据。您的数据源方法的实现应该是最少的。不要使用您的数据源方法从网络中获取数据、计算值或执行任何可能延迟该数据交付的事情。如果您需要为您的复杂功能获取或计算数据,请在您的 iOS 应用程序或您的 WatchKit 扩展的其他部分中执行此操作,并将数据缓存在您的复杂数据源可以访问它的位置。您的数据源方法唯一应该做的就是获取缓存的数据并将其放入 ClockKit 所需的格式。

于 2016-01-02T18:27:31.807 回答