github: github.com/young-cowbo…git
一共有 4 個頁面 HabitListView, AddButtonView, HabitDetailView, AddItemViewgithub
項目涉及到三個數據結構: HabitItem(習慣項), HabitIconArray(習慣圖標), HabitColor(習慣主題)swift
HabitColor 主題色,保存了習慣的主題xcode
public let UserColorArray = [ Color(red:75 / 255, green:166 / 255, blue: 239 / 255), Color(red:161 / 255, green:206 / 255, blue: 97 / 255), Color(red:248 / 255, green:214 / 255, blue: 80 / 255), Color(red:243 / 255, green:176 / 255, blue: 74 / 255), Color(red:238 / 255, green:140 / 255, blue: 111 / 255), Color(red:237 / 255, green:113 / 255, blue: 165 / 255), Color(red:207 / 255, green:102 / 255, blue: 247 / 255), Color(red:77 / 255, green:110 / 255, blue: 247 / 255), Color(red:236 / 255, green:107 / 255, blue: 102 / 255) ] 複製代碼
HabitIconArray 習慣的圖標庫markdown
public let IconNameArray: [String] = [ "alarm", "book", "pencil", "desktopcomputer", "gamecontroller", "sportscourt", "lightbulb" ] 複製代碼
HabitItem 用來保存習慣的詳細信息,這裏實現 ObservableObject 協議,用來告訴 SwiftUI 這個對象須要監聽,用 Published property wrapper 包裝了 checkList 屬性,表示這個屬性是要監聽的,由於它可能須要傳遞給子 View數據結構
class HabitItem: Identifiable, ObservableObject { var name: String = "" var iconName: String = "clock" var theme: Color = UserColor.color1.value var uuid: Int = 0 @Published var checkList: [Bool] = [false, false, false, false, false, false, false] init () { } init(name: String, iconName: String, theme: Color) { self.name = name self.iconName = iconName self.theme = theme self.uuid = generatteID() } } 複製代碼
具體代碼參考倉庫代碼,這裏講解一個流程,新建一個「習慣」項,在 MainView 裏閉包
MainView
app
... @State var sheetVisible: Bool = false @State var sheetType: String = "add" ... ... AddButtonView() { self.sheetType = "add" self.sheetVisible = true } ... 複製代碼
AddButtonView 利用尾部閉包語法
內聯了一個閉包用來相應事件oop
AddButtonView
裏定義了 onPressed 屬性ui
struct AddButtonView: View { var onPressed: () -> Void var body: some View { Button(action: { self.onPressed() }) { HStack { Image(systemName: "plus.circle.fill") .resizable() .frame(width: 60, height: 60) .foregroundColor(Color.blue) } } } } 複製代碼
AddItemView
裏的新增按鈕點擊後相應事件,把選中的數據傳遞 onSumit 屬性回調裏
struct AddItemView: View { @State var newItemTitle = "" @State var selectIconIndex: Int = 0 @State var selectColorIndex: Int = 0 var onSumit: (HabitItem) -> Void var onDissmis: () -> Void var body: some View { VStack { ... ... VStack { Button(action: { if self.newItemTitle != "" { let iconName = IconNameArray[self.selectIconIndex]; let theme = UserColorArray[self.selectColorIndex]; self.onSumit(HabitItem(name: self.newItemTitle, iconName: iconName, theme: theme)) } }) { Text("新增").frame(minWidth: 0, maxWidth: .infinity) } ... } ... } ... } } } 複製代碼
在 MainView 裏,利用閉包處理回調事件新增選項
AddItemView(onSumit: { item in self.habitItemList.insert(item, at: 0) self.sheetVisible = false }, onDissmis: { self.sheetVisible = false }) 複製代碼
剩下的功能大同小異,能夠把代碼拉下來本地運行看看效果
謝謝