目录
1、配置工程
注意:Team这个地方必须是企业的或者是公司的,不能是Personal Team。如下图
2、设置Capabilities
设置完了之后,左侧会出现 XZHealthDemo.entitlements。如下图:
3、设置 Info.plist
注意:描述语句只能写 "some string value stating the reason",其他的都会崩溃。
Privacy - Health Share Usage Description // 读取权限
some string value stating the reason
Privacy - Health Update Usage Description // 写入权限
some string value stating the reason
或者
<key>NSHealthShareUsageDescription</key>
<string>some string value stating the reason</string>
<key>NSHealthUpdateUsageDescription</key>
<string>some string value stating the reason</string>
4、错误解决
出现错误:
*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'NSHealthUpdateUsageDescription must be set in the app's Info.plist in order to request write authorization for the following types: HKQuantityTypeIdentifierStepCount'
解决 同 3 设置Info.plist
5、代码编写
1>判断设备是否支持 HealthKit 框架
func isHealthDataAvailable() -> Bool
2>判断是否支持健康记录,iOS 12.0 以上系统
func supportsHealthRecords() -> Bool
3>某一种健康类型的支持状态
func authorizationStatus(for type: HKObjectType) -> HKAuthorizationStatus
HKAuthorizationStatus 有3种结果:
notDetermined // 不确定
sharingDenied // 不允许
sharingAuthorized // 允许
4>请求读写权限:在用户读取和写入数据之前,需要请求是否有权限。
要自定义显示在授权表上的消息,请在您的应用程序中设置以下键 Info.plist 中:
设置NSHealthShareUsageDescription键,自定义用于读取数据的消息。
设置NSHealthUpdateUsageDescription键,自定义用于编写数据的消息。
func requestAuthorization(toShare typesToShare: Set<HKSampleType>?, read typesToRead: Set<HKObjectType>?, completion: @escaping (Bool, Error?) -> Void)
5>是否有读写的权限,iOS 12.0 系统以上
func getRequestStatusForAuthorization(toShare typesToShare: Set<HKSampleType>, read typesToRead: Set<HKObjectType>, completion: @escaping (HKAuthorizationRequestStatus, Error?) -> Void)
6>保存某个数据
func save(_ object: HKObject, withCompletion completion: @escaping (Bool, Error?) -> Void)
7>保存多个数据
func save(_ objects: [HKObject], withCompletion completion: @escaping (Bool, Error?) -> Void)
8>执行查询方法
func execute(_ query: HKQuery)
9>停止查询
func stop(_ query: HKQuery)
导入HealthKit框架
import HealthKit
授权读写步数
/// 授权 步数 读写
func authorizeStepCount(completed: @escaping ((_ isSuccess: Bool)->Void)) {
if HKHealthStore.isHealthDataAvailable() {
let writeTypes = stepCountToWrite()
let readTypes = stepCountToRead()
healthStore.requestAuthorization(toShare: writeTypes, read: readTypes) { (success, error) in
completed(success)
print("----步数读写:", success)
}
}
}
/// 步数 读 权限
func stepCountToRead() -> Set<HKQuantityType>? {
let stepType = HKQuantityType.quantityType(forIdentifier: .stepCount)
return Set(arrayLiteral: stepType!)
}
/// 步数 写 权限
func stepCountToWrite() -> Set<HKQuantityType>? {
let stepType = HKQuantityType.quantityType(forIdentifier: .stepCount)
return Set(arrayLiteral: stepType!)
}
授权 读写 健康数据
func authorizeHealthKit(completed: @escaping ((_ isSuccess: Bool)->Void)) {
let version = UIDevice.current.systemVersion.floatValue()
if version >= 8.0 {
if !HKHealthStore.isHealthDataAvailable() {
// let error = NSError(domain: "com.xz.healthkit", code: 2, userInfo: [NSLocalizedDescriptionKey:"HealthKit is not available in th is Device"])
completed(false)
}else { // 可用
// 需要读写的数据类型
let writeDataTypes = dateTypeToWrite()
let readDataTypes = dateTypeToRead()
// 注册需要读写的数据类型,也可以在'健康'中重新修改
healthStore.requestAuthorization(toShare: writeDataTypes, read: readDataTypes, completion: { (isSuccess, error) in
print("错误:", error)
print("权限结果:", isSuccess)
completed(isSuccess)
})
}
}else {
print("iOS 系统低于8.0")
completed(false)
}
}
// 读取 Health 数据
func dateTypeToRead() -> Set<HKQuantityType>? {
// 身高
let heightType = HKObjectType.quantityType(forIdentifier: .height)
// 体重
let weightType = HKObjectType.quantityType(forIdentifier: .bodyMass)
// 体温
let temperatureType = HKObjectType.quantityType(forIdentifier: .bodyTemperature)
// 生日
let birthdayType = HKObjectType.characteristicType(forIdentifier: .dateOfBirth)
// 性别
let sexType = HKObjectType.characteristicType(forIdentifier: .biologicalSex)
// 步数
let stepCountType = HKQuantityType.quantityType(forIdentifier: .stepCount)
// 距离
let distanceType = HKObjectType.quantityType(forIdentifier: .distanceWalkingRunning)
// 活动能量
let activeEnergyType = HKObjectType.quantityType(forIdentifier: .activeEnergyBurned)
return Set(arrayLiteral: heightType, temperatureType, birthdayType, sexType, weightType, stepCountType, distanceType, activeEnergyType) as? Set<HKQuantityType>
}
// 写 Health 数据
func dateTypeToWrite() -> Set<HKQuantityType>? {
// 身高
let heightType = HKObjectType.quantityType(forIdentifier: .height)
// 体重
let weightType = HKObjectType.quantityType(forIdentifier: .bodyMass)
// 体温
let temperatureType = HKObjectType.quantityType(forIdentifier: .bodyTemperature)
// 活动能量
let activeEnergyType = HKObjectType.quantityType(forIdentifier: .activeEnergyBurned)
return Set(arrayLiteral: heightType, temperatureType, weightType, activeEnergyType) as? Set<HKQuantityType>
}
修改数据
func recordStepData(step: Int, completed: @escaping ((_ success: Bool)->Void)) {
let stepType = HKQuantityType.quantityType(forIdentifier: .stepCount)
if HKHealthStore.isHealthDataAvailable() {
let stepQuantity = HKQuantity(unit: HKUnit.count(), doubleValue: Double(step))
let stepSample = HKQuantitySample(type: stepType!, quantity: stepQuantity, start: Date(), end: Date())
healthStore.save(stepSample) { (isSuccess, error) in
print("修改结果:", isSuccess)
completed(isSuccess)
}
}else {
print("写入不允许")
}
}
获取步数数据
/// 获取步数
func getStepCount(completion: @escaping ((_ value: Int)->Void)) {
// 步数
let stepType = HKObjectType.quantityType(forIdentifier: .stepCount)
let timeSortDescriptor = NSSortDescriptor(key: HKSampleSortIdentifierEndDate, ascending: false)
let query = HKSampleQuery(sampleType: stepType!, predicate: predicateForSampelsToday(), limit: HKObjectQueryNoLimit, sortDescriptors: [timeSortDescriptor]) { (query, results, error) in
if error != nil {
completion(0)
}else {
var totalStep = 0
if let results = results {
for quantitySample in results {
let quantitySam = quantitySample as! HKQuantitySample
let quantity = quantitySam.quantity
let heightUnit = HKUnit.count()
let usersHeight = quantity.doubleValue(for: heightUnit)
totalStep += Int(usersHeight)
}
print("当天行走步数 =", totalStep)
completion(totalStep)
}
}
}
// 执行查询
healthStore.execute(query)
}