HealthKit框架的简要与基本使用(OC版)
HealthKit为苹果为采集各种健康数据源提供的接口,可以用来采集和整合各种健康数据的来源,如运动手环,AppleWatch,以及iPhone设备提供的健康数据。
个人也是刚接触该框架,主要应用到HealthKit提供的数据查询接口,故此篇文章主要说明一下查询iPhone设备提供的健康数据以及用户插入数据的方法。
————————————主要类与用法————————————
HKHealthStore —— 关键类(使用HealthKit框架必须创建该类)
HKHealthStore *myStore = [[HKHealthStore alloc] init];
// 查询是否设备是否支持HealthKit框架(官方暂不提供是否授权的接口)
[HKHealthStore isHealthDataAvailable];
// 查询是否支持写入授权(允许返回YES)
switch ([_healthStore authorizationStatusForType:[HKObjectType quantityTypeForIdentifier:HKQuantityTypeIdentifierStepCount]])
{
case 0:
NSLog(@"用户尚未作出选择,关于是否该应用程序可以保存指定类型的对象");
break;
case 1:
_isAuthorization = NO;
NSLog(@"此应用程序不允许保存指定类型的对象");
break;
case 2:
NSLog(@"此应用程序被授权保存指定类型的对象");
break;
default:
break;
}
HKQuantityType —— 样本类型
HKQuantityType *footType = [HKQuantityType quantityTypeForIdentifier:HKQuantityTypeIdentifierStepCount];
NSPredicate —— 过滤器(设定开始时间和结束时间,过滤数据源)
NSPredicate *predicate = [HKQuery predicateForSamplesWithStartDate:startDate endDate:endDate options:HKQueryOptionNone];
HKUnit —— 单位类(设定样本查询的单位)
HKUnit *myUnit = [HKUnit unitFromLengthFormatterUnit:NSLengthFormatterUnitKilometer]; // 设定查询单位为公里
————————————主要查询方法类和用法————————————
HealthKit提供几种健康数据查询方法的类:
HKHealthStore —— 直接查询的类
HKSampleQuery —— 样本查询的类:查询某个样本(运动,能量...)的数据
HKObserverQuery —— 观察者查询的类:数据改变时发送通知(可以后台)
HKAnchoredObjectQuery —— 锚定对象查询的类:数据插入后返回新插入的数据
HKStatisticsQuery —— 统计查询的类:返回样本的总和/最大值/最小值...
HKStatisticsCollectionQuery —— 统计集合查询的类:返回时间段内样本的数据
HKCorrelation —— 相关性查询的类:查询样本相关(使用少)
HKSourceQuery —— 来源查询的类:查询数据来源
(本文只提供统计查询和统计集合查询,其他用法会陆续更新)
HKStatisticsQuery —— 统计查询(以下代码统计今天凌晨到现在为止走的所有步数)
// 步数
HKQuantityType *footType = [HKQuantityType quantityTypeForIdentifier:HKQuantityTypeIdentifierStepCount];
// 公里
HKQuantityType *type = [HKQuantityType quantityTypeForIdentifier:HKQuantityTypeIdentifierDistanceWalkingRunning];
// 初始日期:初次安装记录的日期
NSDate *beginDate = [[NSUserDefaults standardUserDefaults] objectForKey:@"firstDate"];
NSLog(@"初次安装记录的日期:%@", beginDate);
// 结束日期:当前时间
NSDate *endDate = [[LLDateTools sharedTools] locationTime:[NSDate date]];
NSLog(@"结束时间:%@", endDate);
// **************每日步数**************
// 开始时间:今日零点
NSDate *startDate = [[LLDateTools sharedTools] zeroToday:[NSDate date]];
NSLog(@"今日步数开始时间:%@", startDate);
NSPredicate *predicate = [HKQuery predicateForSamplesWithStartDate:startDate endDate:endDate options:HKQueryOptionNone];
HKStatisticsQuery *query = [[HKStatisticsQuery alloc]initWithQuantityType:footType quantitySamplePredicate:predicate options:HKStatisticsOptionCumulativeSum completionHandler:^(HKStatisticsQuery * _Nonnull query, HKStatistics * _Nullable result, NSError * _Nullable error) {
if (result) {
// 行走的步数
_steps = [result.sumQuantity doubleValueForUnit:[HKUnit countUnit]]; }
}];
[self.healthStore executeQuery:query]; // ***注意:一定要加上这句话***
HKStatisticsCollectionQuery —— 统计集合查询(以下代码统计七天前每天的步数)
// **************周记步数**************
NSDateComponents *interval = [[NSDateComponents alloc] init];
interval.day = 1; // 间隔天数
// 样本统计查询
HKStatisticsCollectionQuery *queue = [[HKStatisticsCollectionQuery alloc] initWithQuantityType:footType
quantitySamplePredicate:nil
options:HKStatisticsOptionCumulativeSum
anchorDate:endDate intervalComponents:interval];
queue.initialResultsHandler = ^(HKStatisticsCollectionQuery *query, HKStatisticsCollection *results, NSError *error){
if (error) {
NSLog(@"error");
}
WS(weakSelf);
// 日历初始化(只能用currentCalendar初始化)
NSCalendar *calendar = [NSCalendar currentCalendar];
// 返回开始时间,距离现在的时间间隔,正为后一天,负为前一天,-7为一周前
NSDate *start = [[LLDateTools sharedTools] zeroToday:[calendar dateByAddingUnit:NSCalendarUnitDay value:-6 toDate:endDate options:0]];
// 开始循环,循环七次,每次取一天的步数
[_aWeekSteps removeAllObjects];
[results enumerateStatisticsFromDate:start toDate:endDate withBlock:^(HKStatistics * _Nonnull result, BOOL * _Nonnull stop) {
HKQuantity *quantity = result.sumQuantity; // quantity为一个数组记录当天各个时间段的步数,取和为一天总步数
if (quantity) {
// 一天之内走的步数,18000封顶
double value1 = [quantity doubleValueForUnit:[HKUnit countUnit]] >= 18000 ? 18000 : [quantity doubleValueForUnit:[HKUnit countUnit]];
NSNumber *step = [NSNumber numberWithDouble:value1];
[weakSelf.aWeekSteps addObject:step];
}
}];
};
[self.healthStore executeQuery:queue];