Explorar el Código

use target picker from Override

Robert hace 1 año
padre
commit
78e21f542e

+ 93 - 55
FreeAPS/Sources/Modules/OverrideConfig/View/AddTempTargetForm.swift

@@ -2,18 +2,6 @@ import Foundation
 import SwiftUI
 import SwiftUI
 
 
 struct AddTempTargetForm: View {
 struct AddTempTargetForm: View {
-    // settings for picker steps
-    let smallMgdL = 1.0
-    let bigMgdL = 5.0
-    let smallMmolL = 0.1 / 0.0555
-    let bigMmolL = 0.5 / 0.0555
-    init(state: OverrideConfig.StateModel) {
-        _state = StateObject(wrappedValue: state)
-        _targetStep = State(initialValue: state.units == .mgdL ? bigMgdL : bigMmolL)
-    }
-
-    @State var toggleBigStepOn = true
-
     @StateObject var state: OverrideConfig.StateModel
     @StateObject var state: OverrideConfig.StateModel
     @Environment(\.presentationMode) var presentationMode
     @Environment(\.presentationMode) var presentationMode
     @Environment(\.colorScheme) var colorScheme
     @Environment(\.colorScheme) var colorScheme
@@ -21,7 +9,7 @@ struct AddTempTargetForm: View {
     @State private var displayPickerDuration: Bool = false
     @State private var displayPickerDuration: Bool = false
     @State private var durationHours = 0
     @State private var durationHours = 0
     @State private var durationMinutes = 0
     @State private var durationMinutes = 0
-    @State private var targetStep: Double
+    @State private var targetStep: Decimal = 5
     @State private var displayPickerTarget: Bool = false
     @State private var displayPickerTarget: Bool = false
     @State private var showAlert = false
     @State private var showAlert = false
     @State private var showPresetAlert = false
     @State private var showPresetAlert = false
@@ -105,6 +93,7 @@ struct AddTempTargetForm: View {
                     sheetTitle: "Help"
                     sheetTitle: "Help"
                 )
                 )
             }
             }
+            .onAppear { targetStep = state.units == .mgdL ? 5 : 9 }
         }
         }
     }
     }
 
 
@@ -170,58 +159,36 @@ struct AddTempTargetForm: View {
                 }
                 }
                 if displayPickerTarget {
                 if displayPickerTarget {
                     HStack {
                     HStack {
+                        // Radio buttons and text on the left side
                         VStack(alignment: .leading) {
                         VStack(alignment: .leading) {
-                            // Toggle for step iteration
-                            VStack {
-                                Text(formattedGlucose(glucose: Decimal(state.units == .mgdL ? smallMgdL : smallMmolL)))
-                                    .tag(Int(state.units == .mgdL ? smallMgdL : smallMmolL))
-                                    .foregroundColor(toggleBigStepOn ? .secondary : .tabBar)
-                                ZStack {
-                                    Group {
-                                        Capsule()
-                                            .frame(width: 26, height: 44)
-                                            .foregroundColor(Color.loopGray)
-                                        ZStack {
-                                            Circle()
-                                                .frame(width: 24, height: 24)
-                                            Image(systemName: toggleBigStepOn ? "forward.circle.fill" : "play.circle.fill")
-                                                .font(.system(size: 24))
-                                                .foregroundStyle(Color.white, Color.tabBar)
-                                        }
-//                                        .shadow(color: .black.opacity(0.14), radius: 4, x: 0, y: 2)
-                                        .offset(y: toggleBigStepOn ? 10 : -10)
-                                        .padding(12)
-                                    }
-                                }
-                                .onTapGesture {
-                                    // Toggling between small and big step
-                                    toggleBigStepOn.toggle()
-                                    targetStep = toggleBigStepOn ? (state.units == .mgdL ? bigMgdL : bigMmolL) :
-                                        (state.units == .mgdL ? smallMgdL : smallMmolL)
+                            // Radio buttons for step iteration
+                            let stepChoices: [Decimal] = state.units == .mgdL ? [1, 5] : [1, 9]
+                            ForEach(stepChoices, id: \.self) { step in
+                                RadioButton(
+                                    isSelected: targetStep == step,
+                                    label: "\(state.units == .mgdL ? step : step.asMmolL) \(state.units.rawValue)"
+                                ) {
+                                    targetStep = step
+                                    state.tempTargetTarget = roundTargetToStep(state.tempTargetTarget, targetStep)
                                 }
                                 }
-                                Text(formattedGlucose(glucose: Decimal(state.units == .mgdL ? bigMgdL : bigMmolL)))
-                                    .tag(Int(state.units == .mgdL ? bigMgdL : bigMmolL))
-                                    .foregroundColor(toggleBigStepOn ? .tabBar : .secondary)
+                                .padding(.top, 10)
                             }
                             }
-                            .padding(.top, 10)
                         }
                         }
                         .frame(maxWidth: .infinity)
                         .frame(maxWidth: .infinity)
 
 
                         Spacer()
                         Spacer()
 
 
                         // Picker on the right side
                         // Picker on the right side
-                        Picker(
-                            selection: Binding(
-                                get: { Int(truncating: state.tempTargetTarget as NSNumber) },
-                                set: { state.tempTargetTarget = Decimal($0) }
-                            ), label: Text("")
-                        ) {
+                        Picker(selection: Binding(
+                            get: { roundTargetToStep(state.tempTargetTarget, targetStep) },
+                            set: { state.tempTargetTarget = $0 }
+                        ), label: Text("")) {
                             ForEach(
                             ForEach(
-                                Array(stride(from: 80, through: 270, by: targetStep)),
+                                generateTargetPickerValues(),
                                 id: \.self
                                 id: \.self
-                            ) { glucoseTarget in
-                                Text(formattedGlucose(glucose: Decimal(glucoseTarget)))
-                                    .tag(Int(glucoseTarget))
+                            ) { glucose in
+                                Text(formattedGlucose(glucose: glucose))
+                                    .tag(glucose)
                             }
                             }
                         }
                         }
                         .pickerStyle(WheelPickerStyle())
                         .pickerStyle(WheelPickerStyle())
@@ -230,7 +197,6 @@ struct AddTempTargetForm: View {
                             state.percentage = Double(state.computeAdjustedPercentage() * 100)
                             state.percentage = Double(state.computeAdjustedPercentage() * 100)
                         }
                         }
                     }
                     }
-                    .frame(maxWidth: .infinity)
                 }
                 }
             }
             }
             if isSliderEnabled && state.tempTargetTarget != 0 {
             if isSliderEnabled && state.tempTargetTarget != 0 {
@@ -447,6 +413,60 @@ struct AddTempTargetForm: View {
         }
         }
         return "\(formattedValue) \(state.units.rawValue)"
         return "\(formattedValue) \(state.units.rawValue)"
     }
     }
+
+    private func roundTargetToStep(_ target: Decimal, _ step: Decimal) -> Decimal {
+        // Convert target and step to NSDecimalNumber
+        guard let targetValue = NSDecimalNumber(decimal: target).doubleValue as Double?,
+              let stepValue = NSDecimalNumber(decimal: step).doubleValue as Double?
+        else {
+            print("Failed to unwrap target or step as NSDecimalNumber")
+            return target
+        }
+
+        // Perform the remainder check using truncatingRemainder
+        let remainder = Decimal(targetValue.truncatingRemainder(dividingBy: stepValue))
+
+        if remainder != 0 {
+            // Calculate how much to adjust (up or down) based on the remainder
+            let adjustment = step - remainder
+            return target + adjustment
+        }
+
+        // Return the original target if no adjustment is needed
+        return target
+    }
+
+    func generateTargetPickerValues() -> [Decimal] {
+        var values: [Decimal] = []
+        var currentValue: Double = 72
+        let step = Double(targetStep)
+
+        // Adjust currentValue to be divisible by targetStep
+        let remainder = currentValue.truncatingRemainder(dividingBy: step)
+        if remainder != 0 {
+            // Move currentValue up to the next value divisible by targetStep
+            currentValue += (step - remainder)
+        }
+
+        // Now generate the picker values starting from currentValue
+        while currentValue <= 270 {
+            values.append(Decimal(currentValue))
+            currentValue += step
+        }
+
+        // Glucose values are stored as mg/dl values, so Integers.
+        // Filter out duplicate values when rounded to 1 decimal place.
+        if state.units == .mmolL {
+            // Use a Set to track unique values rounded to 1 decimal
+            var uniqueRoundedValues = Set<String>()
+            values = values.filter { value in
+                let roundedValue = String(format: "%.1f", NSDecimalNumber(decimal: value.asMmolL).doubleValue)
+                return uniqueRoundedValues.insert(roundedValue).inserted
+            }
+        }
+
+        return values
+    }
 }
 }
 
 
 func formatHrMin(_ durationInMinutes: Int) -> String {
 func formatHrMin(_ durationInMinutes: Int) -> String {
@@ -462,3 +482,21 @@ func formatHrMin(_ durationInMinutes: Int) -> String {
         return "\(hours) hr \(minutes) min"
         return "\(hours) hr \(minutes) min"
     }
     }
 }
 }
+
+struct RadioButton: View {
+    var isSelected: Bool
+    var label: String
+    var action: () -> Void
+
+    var body: some View {
+        Button(action: {
+            action()
+        }) {
+            HStack {
+                Image(systemName: isSelected ? "largecircle.fill.circle" : "circle")
+                Text(label) // Add label inside the button to make it tappable
+            }
+        }
+        .buttonStyle(PlainButtonStyle())
+    }
+}