ISFEditorStateModel.swift 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596
  1. import SwiftUI
  2. extension ISFEditor {
  3. final class StateModel: BaseStateModel<Provider> {
  4. @Injected() var settingsManager: SettingsManager!
  5. @Published var items: [Item] = []
  6. private(set) var autosensISF: Decimal?
  7. private(set) var autosensRatio: Decimal = 0
  8. @Published var autotune: Autotune?
  9. let timeValues = stride(from: 0.0, to: 1.days.timeInterval, by: 30.minutes.timeInterval).map { $0 }
  10. var rateValues: [Decimal] {
  11. switch units {
  12. case .mgdL:
  13. return stride(from: 9, to: 540.01, by: 1.0).map { Decimal($0) }
  14. case .mmolL:
  15. return stride(from: 0.1, to: 30.01, by: 0.1).map { Decimal($0) }
  16. }
  17. }
  18. var canAdd: Bool {
  19. guard let lastItem = items.last else { return true }
  20. return lastItem.timeIndex < timeValues.count - 1
  21. }
  22. private(set) var units: GlucoseUnits = .mmolL
  23. override func subscribe() {
  24. let profile = provider.profile
  25. units = profile.units
  26. items = profile.sensitivities.map { value in
  27. let timeIndex = timeValues.firstIndex(of: Double(value.offset * 60)) ?? 0
  28. let rateIndex = rateValues.firstIndex(of: value.sensitivity) ?? 0
  29. return Item(rateIndex: rateIndex, timeIndex: timeIndex)
  30. }
  31. autotune = provider.autotune
  32. if let newISF = provider.autosense.newisf {
  33. switch units {
  34. case .mgdL:
  35. autosensISF = newISF
  36. case .mmolL:
  37. autosensISF = newISF * GlucoseUnits.exchangeRate
  38. }
  39. }
  40. autosensRatio = provider.autosense.ratio
  41. }
  42. func add() {
  43. var time = 0
  44. var rate = 0
  45. if let last = items.last {
  46. time = last.timeIndex + 1
  47. rate = last.rateIndex
  48. }
  49. let newItem = Item(rateIndex: rate, timeIndex: time)
  50. items.append(newItem)
  51. }
  52. func save() {
  53. let sensitivities = items.map { item -> InsulinSensitivityEntry in
  54. let fotmatter = DateFormatter()
  55. fotmatter.timeZone = TimeZone(secondsFromGMT: 0)
  56. fotmatter.dateFormat = "HH:mm:ss"
  57. let date = Date(timeIntervalSince1970: self.timeValues[item.timeIndex])
  58. let minutes = Int(date.timeIntervalSince1970 / 60)
  59. let rate = self.rateValues[item.rateIndex]
  60. return InsulinSensitivityEntry(sensitivity: rate, offset: minutes, start: fotmatter.string(from: date))
  61. }
  62. let profile = InsulinSensitivities(
  63. units: units,
  64. userPrefferedUnits: settingsManager.settings.units,
  65. sensitivities: sensitivities
  66. )
  67. provider.saveProfile(profile)
  68. }
  69. func validate() {
  70. DispatchQueue.main.async {
  71. let uniq = Array(Set(self.items))
  72. let sorted = uniq.sorted { $0.timeIndex < $1.timeIndex }
  73. sorted.first?.timeIndex = 0
  74. self.items = sorted
  75. if self.items.isEmpty {
  76. self.units = self.settingsManager.settings.units
  77. }
  78. }
  79. }
  80. }
  81. }