SwiftUI์์์ Single Source of Truth(SSOT, ๋จ์ผ ์ง์ค ๊ณต๊ธ์)๋ ๋ฐ์ดํฐ์ ์ผ๊ด์ฑ๊ณผ ์ ํ์ฑ์ ์ ์งํ๊ธฐ ์ํ ์ค์ํ ๊ฐ๋ ์ด๋ค.
์ ๋ณด ์์คํ ์ ๋ํ SSOT(Single Source Of Truth) ์ํคํ ์ฒ ๋๋ SPOT(Single Point Of Truth) ์ํคํ ์ฒ๋ ๋ชจ๋ ๋ฐ์ดํฐ ์์๊ฐ ๋ง์คํฐ(๋๋ ํธ์ง)๋๋๋ก ์ ๋ณด ๋ฐ ๋ชจ๋ธ ๊ด๋ จ ๋ฐ์ดํฐ ์คํค๋ง๋ฅผ ๊ตฌ์ฑํ๋ ๊ดํ์ด๋ค. ํ ๊ณณ์์๋ง ์ ๊ท ํ์์ผ๋ก ๋ฐ์ดํฐ ์ ๊ทํ๋ฅผ ์ ๊ณตํ๋ค. ์ด ๋ฐ์ดํฐ ์์์ ๋ํ ๋ชจ๋ ๊ฐ๋ฅํ ์ฐ๊ฒฐ์ ์ฐธ์กฐ์ฉ์ด๋ค. ๋ฐ์ดํฐ์ ๋ค๋ฅธ ๋ชจ๋ ์์น๋ "source of truth" ์์น๋ฅผ ๋ค์ ์ฐธ์กฐํ๊ธฐ ๋๋ฌธ์ ๊ธฐ๋ณธ ์์น์ ๋ฐ์ดํฐ ์์์ ๋ํ ์ ๋ฐ์ดํธ๋ ์ ์ฒด ์์คํ ์ ์ ํ๋์ด ํจ์จ์ฑ/์์ฐ์ฑ ํฅ์, ์๋ชป๋ ๋ถ์ผ์น์ ์ฌ์ด ๋ฐฉ์ง ๊ฐ์ ์ฌ๋ฌ ์ด์ ์ ๋์์ ์ ๊ณตํ๋ค. SSOT ์ํคํ ์ฒ๊ฐ ์์ผ๋ฉด ๋ช ํ์ฑ, ์์ฐ์ฑ์ ์์์์ผ ์ ์ง๊ด๋ฆฌ๊ฐ ํ๋ค์ด์ง๋ค
SwiftUI ์ฑ์์ ์ฌ์ฉ์ ์ธํฐํ์ด์ค(UI)๋ ๋ฐ์ดํฐ ๋ชจ๋ธ์ ๋ฐ์ธ๋ฉ๋์ด ์๋ค. ์ฆ, SwiftUI๋ UI๊ฐ @State์ ๊ฐ์ ๋ฐ์ดํฐ ๋ชจ๋ธ์ ๋ฐ์ธ๋ฉ๋์ด ์์ด UI๋ ๋ฐ์ดํฐ ๋ชจ๋ธ์ ๋ณ๊ฒฝ์ ์๋์ผ๋ก ๋ฐ์ํ๊ณ ๋ณ๊ฒฝ๋๋ค. ํ์ง๋ง UI๋ฅผ ๋ณ๊ฒฝํ๋ ์ํ๊ฐ ์ฌ๋ฌ ๊ณณ์์ ๋ณต์ฌ๋๊ณ ๋ณ๊ฒฝ๋๊ณ ์ฌ์ฉ๋๋ฉด ์ฌ์ฉ์ ๊ฒฝํ(UX)์ ์ผ๊ด์ฑ๊ณผ ์ ํ์ฑ์ ์ ์งํ๋ ๊ฒ์ด ์ด๋ ค์์ง๋ค.
๋ฐ๋ผ์ SwiftUI์์๋ ์ฃผ๋ก @State, @Binding, @ObservedObject, @EnvironmentObject์ ๊ฐ์ ์์ฑ ๋ํผ๋ฅผ ์ฌ์ฉํ์ฌ ๋ฐ์ดํฐ ๋ชจ๋ธ์ ๊ด๋ฆฌํ๋ค.
- @State: ๊ฐ ์ ํ์ ์์ฑ์ ๋ํ ์ ์ฅ์๋ก ์ฌ์ฉ
- @Binding: ๋ ๊ฐ์ ๋ทฐ ๊ฐ์ ๋ฐ์ดํฐ๋ฅผ ์ ๋ฌํ๊ณ ๋๊ธฐํํ๋ ๋ฐ ์ฌ์ฉ
- @ObservedObject: ๊ด์ฐฐ ๊ฐ๋ฅํ ๊ฐ์ฒด๋ฅผ ์์ฑ
- @EnvironmentObject: ์ฑ์ ์ ์ญ ์ํ๋ฅผ ๋ํ๋ด๋ ๋ฐ ์ฌ์ฉ
์๋ ์์ ์ฝ๋๋ https://www.youtube.com/watch?v=taoKnvqFy7k ์ ์ฝ๋์
๋ด๊ฐ ObservedObject, EnvironmentObject๋ฅผ ์ถ๊ฐํ์ฌ ์ฐ์ตํ ์ฝ๋๋ค!
// ContentView.swift
import SwiftUI
// ์ฌ์ฉ์ ๋ฐ์ดํฐ๋ฅผ ๊ด๋ฆฌํ๋ UserData ํด๋์ค
class UserData: ObservableObject {
@Published var name: String = ""
}
struct ContentView: View {
@State private var isDestinationPresented = false //@State๋ฅผ ํตํด์ ํ๋์ single source of truth๊ฐ ์์ฑ
@EnvironmentObject var userData: UserData // ์ ์ญ์ ์ผ๋ก ๊ณต์ ๋๋ UserData ๊ฐ์ฒด์ ์ ๊ทผํ๊ธฐ ์ํ ํ๊ฒฝ ๊ฐ์ฒด
var body: some View {
VStack {
// ์ฌ์ฉ์ ์ด๋ฆ์ ์
๋ ฅ๋ฐ๋ ํ
์คํธ ํ๋
TextField("Enter your name", text: $userData.name)
.textFieldStyle(.roundedBorder)
.padding()
// ์
๋ ฅ๋ ์ฌ์ฉ์ ์ด๋ฆ์ ํ์ํ๋ ํ
์คํธ
Text("Hello, \(userData.name)!")
.font(.title)
Text("Click here!")
.onTapGesture {
self.isDestinationPresented.toggle()
}
.sheet(isPresented: $isDestinationPresented) {
DestinationView(isDestinationPresented: self.$isDestinationPresented)
}
}
}
}
struct DestinationView: View {
@EnvironmentObject var userData: UserData // ์ ์ญ์ ์ผ๋ก ๊ณต์ ๋๋ UserData ๊ฐ์ฒด์ ์ ๊ทผํ๊ธฐ ์ํ ํ๊ฒฝ ๊ฐ์ฒด
@Binding var isDestinationPresented: Bool
var body: some View {
VStack {
Text("Another View")
.font(.title)
// ์ ์ญ UserData ๊ฐ์ฒด์ ์ด๋ฆ์ ํ์ํ๋ ํ
์คํธ
Text("Hello, \(userData.name)!")
.font(.headline)
}
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
}
}
// SourceOfTruthApp.swift
import SwiftUI
@main
struct SourceOfTruthApp: App {
@StateObject var userData = UserData() // ์ฑ์ ์ ์ญ ์ํ๋ก ์ฌ์ฉ๋๋ UserData ๊ฐ์ฒด
var body: some Scene {
WindowGroup {
ContentView()
.environmentObject(userData) // ContentView์ ์ ์ญ UserData ๊ฐ์ฒด๋ฅผ ์ฃผ์
ํ์ฌ ๊ณต์
}
}
}
์์ ์ฝ๋๋ ContentView์ DestinationView ๋ ๊ฐ์ ๋ทฐ๊ฐ ์๋ค.
UserData ํด๋์ค๋ ์ฌ์ฉ์ ๋ฐ์ดํฐ๋ฅผ ๊ด๋ฆฌํ๊ธฐ ์ํ ํด๋์ค๋ก ObservableObject ํ๋กํ ์ฝ์ ์ฑํํ๊ณ , @Published ์์ฑ ๋ํผ๋ฅผ ์ฌ์ฉํ์ฌ name ์์ฑ์ ๊ฐ์ ๊ฐ๋ฅํ๊ฒ ๋ง๋ ๋ค.
ContentView๋ ์ฌ์ฉ์๋ก๋ถํฐ ์ด๋ฆ์ ์
๋ ฅ๋ฐ๋ ํ
์คํธ ํ๋์ ์
๋ ฅ๋ ์ด๋ฆ์ ํ์ํ๋ ํ
์คํธ๊ฐ ํฌํจ๋ ๋ทฐ๋ค. @EnvironmentObject ์์ฑ ๋ํผ๋ฅผ ์ฌ์ฉํ์ฌ ์ ์ญ์ ์ผ๋ก ๊ณต์ ๋๋ UserData ๊ฐ์ฒด์ ์ ๊ทผํ๋ฉฐ, ์ฌ์ฉ์๊ฐ ์ด๋ฆ์ ์
๋ ฅํ๋ฉด ํด๋น ๊ฐ์ฒด์ name ์์ฑ์ด ์ค์๊ฐ์ผ๋ก ์
๋ฐ์ดํธ๋๋ค. (์์ ์ฐธ๊ณ !)
DestinationView๋ ๋ค๋ฅธ ๋ทฐ๋ก ์ด๋ํ๋ ๋ฐ๋ชจ์ฉ ๋ทฐ๋ก, UserData ๊ฐ์ฒด์ name ์์ฑ์ ํ์ํ๋ค. @EnvironmentObject ์์ฑ ๋ํผ๋ฅผ ์ฌ์ฉํ์ฌ ์ ์ญ์ ์ผ๋ก ๊ณต์ ๋๋ UserData ๊ฐ์ฒด์ ์ ๊ทผํ๋ค.
SourceOfTruthApp์ ์ฑ์ ์ง์
์ ์ผ๋ก, @StateObject ์์ฑ ๋ํผ๋ฅผ ์ฌ์ฉํ์ฌ ์ ์ญ์ ์ผ๋ก ์ฌ์ฉ๋๋ UserData ๊ฐ์ฒด๋ฅผ ์์ฑํ๊ณ , ContentView์ environmentObject๋ฅผ ์ฌ์ฉํ์ฌ UserData ๊ฐ์ฒด๋ฅผ ์ฃผ์
ํ์ฌ ๋ทฐ ๊ณ์ธต ๊ตฌ์กฐ์์ ๊ณต์ ๋ ์ ์๋๋ก ํ๋ค.
๊ผญ ContentView ๋ฅผ ๊ฐ์ธ๋ struct ๋ด์์ StateObject๋ก ๊ฐ์ฒด๋ฅผ ์ ์ธํ๊ณ , .environmentObject(userData) ๋ฅผ ๋ถ์ฌ์ ์ ์ญ UserData ๊ฐ์ฒด๋ฅผ ์ฃผ์
ํ์ฌ ๊ณต์ ํ ์ ์๋๋ก ํด์ผํ๋ค. ์ด๋ ๊ฒ ํ๋ฉด ContentView์ DestinationView๊ฐ ๋์ผํ UserData ๊ฐ์ฒด๋ฅผ ๊ณต์ ํ๊ณ , name ์์ฑ์ ์ฌ๋ฐ๋ฅด๊ฒ ๊ฐ์ ธ์ฌ ์ ์๋ค.
'๐ฑ App > ๐ Swift' ์นดํ ๊ณ ๋ฆฌ์ ๋ค๋ฅธ ๊ธ
[Swift] ๋ฐ๋ณต๋ฌธ์์ id: \.id ์ ์๋ฏธ (0) | 2023.06.08 |
---|---|
[Swift] load(_:) method (fetching JSON data) ๋ฏ์ด๋ณด๊ธฐ (0) | 2023.06.07 |
[Swift] Swift ์์ Hashable, Codable์ ๋ญ๊น? Protocol ์์๋ณด๊ธฐ (0) | 2023.06.03 |
[SwiftUI Tutorials] SwiftUI Essentials - Creating and Combining Views (0) | 2023.03.26 |
iOS ์ฑ๊ฐ๋ฐ ์ฑ ์ถ์ฒ : Doit! ์ค์ํํธ๋ก ์์ดํฐ์ฑ ๋ง๋ค๊ธฐ (0) | 2023.02.03 |
๋๊ธ