Apple health app gives the data by Date wise as shown in below image.
By using HealthKit
i am fetching the steps data from apple health
as
let p1 = HKQuery.predicateForSamples(withStart: fromDate, end: Date(), options: .strictStartDate)
let p2 = HKQuery.predicateForObjects(withMetadataKey: HKMetadataKeyWasUserEntered, operatorType: .notEqualTo, value: true)
let timeSortDesriptor = NSSortDescriptor(key: HKSampleSortIdentifierEndDate, ascending: false)//as in health kit entry
let quantityType = HKQuantityType.quantityType(forIdentifier: HKQuantityTypeIdentifier.stepCount)!
let predicate = HKQuery.predicateForSamples(withStart: fromDate, end: Date(), options: .strictStartDate)
let sourceQuery = HKSourceQuery(sampleType: quantityType, samplePredicate: predicate, completionHandler: { query,sources,error in
if sources?.count != 0 && sources != nil {
let lastIndex = sources!.count - 1
var sourcesArray = Array(sources!)
for i in 0..<sourcesArray.count {
let sourcePredicate = HKQuery.predicateForObjects(from: sourcesArray[i])
let predicate = NSCompoundPredicate(andPredicateWithSubpredicates: [p1, p2,sourcePredicate])
let query = HKSampleQuery(sampleType: quantityType, predicate: predicate, limit: HKObjectQueryNoLimit, sortDescriptors: [timeSortDesriptor], resultsHandler: { query, results, error in
guard let samples = results as? [HKQuantitySample] else {
return
}......
sourceQuery gives multiple object like Apple watch, My iPhone.
further i am using for loop with HKSampleQuery
which gives HKQuantitySample
object.
Problem is [HKQuantitySample]
gives Array of step data which is not sorted datewise.
I am looking for data which are club for the date like what apple health show in Health app.
Yes there is workaround like manually sort the data from [HKQuantitySample]
by date wise. but there may be workaround by using predicates
or something else. Please feel free to ask if you need any extra information.
EDIT: As suggested by @Allan I have added HKStatisticsCollectionQuery, YES it gives data datewise but the steps count receiving is not same as in Apple health App. is something Addition/modification required in below code ?
let last10Day = Calendar.current.date(byAdding: .day, value: -10, to: Date())!
var interval = DateComponents()
interval.day = 1
let quantityType1 = HKQuantityType.quantityType(forIdentifier: HKQuantityTypeIdentifier.stepCount)!
// Create the query
let query = HKStatisticsCollectionQuery(quantityType: quantityType1,
quantitySamplePredicate: nil,
options: .cumulativeSum,
anchorDate: last10Day,
intervalComponents: interval)
// Set the results handler
query.initialResultsHandler = {
query, results, error in
guard let statsCollection = results else {
// Perform proper error handling here
fatalError("*** An error occurred while calculating the statistics: \(String(describing: error?.localizedDescription)) ***")
}
let endDate = Date()
statsCollection.enumerateStatistics(from: last10Day, to: endDate, with: { (statistics, stop) in
if let quantity = statistics.sumQuantity() {
let date = statistics.startDate
let value = quantity.doubleValue(for: HKUnit.count())
print("--value-->",value, ",--For Date-->",date)
}
})
}
healthStore.execute(query)
Use HKStatisticsCollectionQuery
to fetch data from a certain period. Here is an example showing how to fetch steps for the last 30 days:
private let healthStore = HKHealthStore()
private let stepsQuantityType = HKQuantityType.quantityType(forIdentifier: .stepCount)!
func importStepsHistory() {
let now = Date()
let startDate = Calendar.current.date(byAdding: .day, value: -30, to: now)!
var interval = DateComponents()
interval.day = 1
var anchorComponents = Calendar.current.dateComponents([.day, .month, .year], from: now)
anchorComponents.hour = 0
let anchorDate = Calendar.current.date(from: anchorComponents)!
let query = HKStatisticsCollectionQuery(
quantityType: stepsQuantityType,
quantitySamplePredicate: nil,
options: [.cumulativeSum],
anchorDate: anchorDate,
intervalComponents: interval
)
query.initialResultsHandler = { _, results, error in
guard let results = results else {
log.error("Error returned form resultHandler = \(String(describing: error?.localizedDescription))")
return
}
results.enumerateStatistics(from: startDate, to: now) { statistics, _ in
if let sum = statistics.sumQuantity() {
let steps = sum.doubleValue(for: HKUnit.count())
print("Amount of steps: \(steps), date: \(statistics.startDate)")
}
}
}
healthStore.execute(query)
}
If you want totals for step count separated by day like in the Health app, you should use HKStatisticsCollectionQuery
, not HKSampleQuery
. The documentation provides example code for grouping results by week, but you can modify it group by day instead.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With