/ BalanceKit / MealPresetView.swift
MealPresetView.swift
  1  //
  2  //  MealPresetView.swift
  3  //  BalanceKit
  4  //
  5  //  Created by Alexander Kunau on 12.07.25.
  6  //
  7  
  8  import SwiftUI
  9  
 10  struct MealPresetView: View {
 11      @Environment(\.dismiss) private var dismiss
 12      @ObservedObject var dataManager: FoodDataManager
 13      
 14      @State private var presetName = ""
 15      @State private var selectedMealType: MealType = .breakfast
 16      @State private var foodItems: [PresetFoodItem] = []
 17      
 18      @State private var showingAddFood = false
 19      @State private var newFoodName = ""
 20      @State private var newFoodCalories = ""
 21      @State private var newFoodProtein = ""
 22      @State private var newFoodCarbs = ""
 23      @State private var newFoodFat = ""
 24      
 25      var body: some View {
 26          NavigationStack {
 27              Form {
 28                  Section(header: Text("Vorlage Details")) {
 29                      TextField("Name der Vorlage", text: $presetName)
 30                      
 31                      Picker("Mahlzeit", selection: $selectedMealType) {
 32                          ForEach(MealType.allCases, id: \.self) { type in
 33                              Label(type.rawValue, systemImage: type.icon)
 34                          }
 35                      }
 36                  }
 37                  
 38                  Section(header: VStack(alignment: .leading, spacing: 4) {
 39                      HStack {
 40                          Text("Nahrungsmittel")
 41                          Spacer()
 42                          Text("\(totalCalories) kcal")
 43                              .fontWeight(.bold)
 44                              .foregroundColor(.green)
 45                      }
 46                      
 47                      HStack(spacing: 12) {
 48                          Label("\(String(format: "%.1f", totalProtein))g", systemImage: "p.circle")
 49                              .font(.caption)
 50                              .foregroundColor(.blue)
 51                          
 52                          Label("\(String(format: "%.1f", totalCarbs))g", systemImage: "c.circle")
 53                              .font(.caption)
 54                              .foregroundColor(.orange)
 55                          
 56                          Label("\(String(format: "%.1f", totalFat))g", systemImage: "f.circle")
 57                              .font(.caption)
 58                              .foregroundColor(.purple)
 59                      }
 60                  }) {
 61                      if foodItems.isEmpty {
 62                          Text("Keine Nahrungsmittel hinzugefügt")
 63                              .foregroundColor(.secondary)
 64                              .italic()
 65                      } else {
 66                          ForEach(foodItems) { item in
 67                              VStack(alignment: .leading, spacing: 4) {
 68                                  HStack {
 69                                      Text(item.name)
 70                                      Spacer()
 71                                      Text("\(item.calories) kcal")
 72                                          .foregroundColor(.secondary)
 73                                  }
 74                                  
 75                                  HStack(spacing: 12) {
 76                                      Text("P: \(String(format: "%.1f", item.protein))g")
 77                                          .font(.caption)
 78                                          .foregroundColor(.blue)
 79                                      
 80                                      Text("K: \(String(format: "%.1f", item.carbs))g")
 81                                          .font(.caption)
 82                                          .foregroundColor(.orange)
 83                                      
 84                                      Text("F: \(String(format: "%.1f", item.fat))g")
 85                                          .font(.caption)
 86                                          .foregroundColor(.purple)
 87                                  }
 88                              }
 89                          }
 90                          .onDelete { indexSet in
 91                              foodItems.remove(atOffsets: indexSet)
 92                          }
 93                      }
 94                      
 95                      Button("Nahrungsmittel hinzufügen") {
 96                          showingAddFood = true
 97                      }
 98                  }
 99                  
100                  Section {
101                      Button("Vorlage speichern") {
102                          savePreset()
103                      }
104                      .disabled(presetName.isEmpty || foodItems.isEmpty)
105                  }
106              }
107              .navigationTitle("Mahlzeiten-Vorlage")
108              .toolbar {
109                  ToolbarItem(placement: .cancellationAction) {
110                      Button("Abbrechen") {
111                          dismiss()
112                      }
113                  }
114              }
115              .sheet(isPresented: $showingAddFood) {
116                  NavigationStack {
117                      Form {
118                          Section(header: Text("Neues Nahrungsmittel")) {
119                              TextField("Name", text: $newFoodName)
120                              
121                              TextField("Kalorien", text: $newFoodCalories)
122                                  .keyboardType(.numberPad)
123                              
124                              TextField("Protein (g)", text: $newFoodProtein)
125                                  .keyboardType(.decimalPad)
126                              
127                              TextField("Kohlenhydrate (g)", text: $newFoodCarbs)
128                                  .keyboardType(.decimalPad)
129                              
130                              TextField("Fett (g)", text: $newFoodFat)
131                                  .keyboardType(.decimalPad)
132                          }
133                          
134                          Section {
135                              Button("Hinzufügen") {
136                                  addFoodToPreset()
137                              }
138                              .disabled(newFoodName.isEmpty || newFoodCalories.isEmpty)
139                          }
140                      }
141                      .navigationTitle("Nahrungsmittel hinzufügen")
142                      .toolbar {
143                          ToolbarItem(placement: .cancellationAction) {
144                              Button("Abbrechen") {
145                                  showingAddFood = false
146                              }
147                          }
148                      }
149                  }
150              }
151          }
152      }
153      
154      private var totalCalories: Int {
155          foodItems.reduce(0) { $0 + $1.calories }
156      }
157      
158      private var totalProtein: Double {
159          foodItems.reduce(0) { $0 + $1.protein }
160      }
161      
162      private var totalCarbs: Double {
163          foodItems.reduce(0) { $0 + $1.carbs }
164      }
165      
166      private var totalFat: Double {
167          foodItems.reduce(0) { $0 + $1.fat }
168      }
169      
170      private func addFoodToPreset() {
171          if let calories = Int(newFoodCalories), !newFoodName.isEmpty {
172              let protein = Double(newFoodProtein) ?? 0
173              let carbs = Double(newFoodCarbs) ?? 0
174              let fat = Double(newFoodFat) ?? 0
175              
176              let newItem = PresetFoodItem(
177                  name: newFoodName,
178                  calories: calories,
179                  protein: protein,
180                  carbs: carbs,
181                  fat: fat
182              )
183              foodItems.append(newItem)
184              newFoodName = ""
185              newFoodCalories = ""
186              newFoodProtein = ""
187              newFoodCarbs = ""
188              newFoodFat = ""
189              showingAddFood = false
190          }
191      }
192      
193      private func savePreset() {
194          if !presetName.isEmpty && !foodItems.isEmpty {
195              dataManager.createPreset(name: presetName, mealType: selectedMealType, foods: foodItems)
196              dismiss()
197          }
198      }
199  }
200  
201  #Preview {
202      MealPresetView(dataManager: FoodDataManager())
203  }