-
Notifications
You must be signed in to change notification settings - Fork 3
SwiftUI์ Property Wrapper๋ค
Sue Cho edited this page Dec 20, 2020
·
4 revisions
- Swift 5.1 ๋ถํฐ ์๊ฐ ๋ Property Wrapper์ด์ง๋ง SwiftUI์์ ๋ณธ๊ฒฉ์ ์ผ๋ก ์ฌ์ฉ๋จ
- Property wrapper๋ฅผ ์ง์ ์์ฑํ๋ ๊ฒ๋ ๊ฐ๋ฅํ์ง๋ง SwiftUI์์๋ ๋ถํ์
- SwiftUI๋ ์ด 17๊ฐ์ Property Wrapper๋ค์ ์ ๊ณต
Property Wrapper | ๊ธฐ๋ฅ | ๋ฐ์ดํฐ์ ์์ ์ฃผ |
---|---|---|
@AppStorage | UserDefault๋ก๋ถํฐ ๊ฐ์ ์ฝ๊ณ ์. | X |
@State | ํ๋์ view(๊ตฌ์กฐ์ฒด) ๋ด์์ ์์ ๋จ์์ value type ๋ฐ์ดํฐ๋ฅผ ์์ . | O |
@Binding | ๋ค๋ฅธ view๊ฐ ์์ ํ๊ณ ์๋ value type์ ๊ฐ๋ฅดํค๋ฉฐ ํด๋น ๊ฐ์ด ๋ฐ๋๋ฉด ์ธ๋ถ์ ๊ฐ๋ ๋ฐ๋. | X |
@FocusedBinding | key window์ ์๋ ๊ฐ ๋ณํ๋ฅผ ๊ด์ฐฐ(ex. ํ์ฌ ์ ํ ๋ text field). | X |
@FocusedValue | FocusedBinding์ ๊ฐ๋จํ ํํ. | X |
@StateObject | ObservableObject protocol์ ๋ฐ๋ฅด๋ Reference type์ ์๋ก์ด ๊ฐ์ฒด๋ฅผ ์ ์ฅ. | O |
@ObservedObject | ObservableObject protocol์ ๋ฐ๋ฅด๋ Reference type์ ์ธ๋ถ ํด๋์ค์ ์๋ ๊ฐ์ฒด๋ฅผ ๊ฐ๋ฅดํด. | X |
@Environment | System์ผ๋ก๋ถํฐ ๋ฐ์ดํฐ(color scheme, accessibility option ๋ฑ)๋ฅผ ์ฝ์ ์ ์๊ฒ ํด์ค. ์ง์ ์ถ๊ฐ๋ ๊ฐ๋ฅ | X |
@EnvironmentObject | Environment์ ์ ์ฅํ shared object๋ฅผ ์ฝ์ด์ด. | X |
@Published | ObservableObject ๋ด์ property์ ๋ถ์ผ๋ฉฐ ํด๋น ๊ฐ์ด ๋ฐ๋๋ฉด ์ด property๋ฅผ ์ฐ๋ view๋ฅผ ์๋ก ๊ทธ๋ฆผ. | O |
@FetchRequest | CoreData์ ํน์ entity์ ๋ํ fetch request๋ฅผ ์์ | O |
@GestureState | ์ง๊ธ ์งํ๋๊ณ ์๋ gesture์ ๊ด๋ จ๋ ๊ฐ์ ์ ์ฅ(ex. ์ผ๋ง๋ swipe ํ๋๊ฐ) | O |
@Namespace | creates an animation namespace to allow matched geometry effects | O |
@UIApplicationDelegateAdaptor | class๋ฅผ iOS app์์ app delegate์ผ๋ก ์์ฑ ๋ฐ ๋ฑ๋ก | O |
@NSApplicationDelegateAdaptor | class๋ฅผ macOS app์์ app delegate์ผ๋ก ์์ฑ ๋ฐ ๋ฑ๋ก | O |
@ScaledMetric | reads the userโs Dynamic Type setting and scales numbers up or down based on an original value you provide | O |
@SceneStorage | ์ํ ๋ณต๊ตฌ๋ฅผ ์ํด ์ ์ ์์ ๋ฐ์ดํฐ๋ฅผ ์ ์ฅ&๋ณต๊ตฌ | O |
- ์ต์ SwiftUI๋ AppDelegate์ ์์ฑํด์ฃผ์ง ์์ง๋ง AppDelegate๋ค์ ๋ฉ์๋๋ค์ด ํ์ํ ๋๊ฐ ์์
- miniVIBE์์๋
didFinishLaunchingWithOptions
๋ฅผ ํตํด launch ๋ ์์ ์ ์ก์ ํ์๊ฐ ์์ด์ ์ฌ์ฉ - AppDelegate ํด๋์ค๋ฅผ ์์ฑํด์ฃผ๊ณ @main ์์์ ํด๋น property wrapper๋ฅผ ์จ์ ๊ด๋ฆฌ ๊ฐ๋ฅ
class AppDelegate: NSObject, UIApplicationDelegate {
func application(_ application: UIApplication,
didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]? = nil) -> Bool {
// action
return true
}
}
@main
struct OurApp: App {
@UIApplicationDelegateAdaptor(AppDelegate.self) var appDelegate
...
}
- ๊ตฌ์กฐ์ฒด๋ value type์ด๋ผ์ ๋ด๋ถ property๋ค์ ๊ฐ ๋ณ๊ฒฝ์ด (์์น์ ์ผ๋ก๋) ์๋จ
- @State๋ฅผ ์ฌ์ฉํ ๊ฒฝ์ฐ, ๊ทธ ๊ฐ์ ์ ์ฅํ๋ ๊ณณ์ด ๊ตฌ์กฐ์ฒด ๋ด๋ถ๊ฐ ์๋ SwiftUI๊ฐ ๊ด๋ฆฌํ๋ shared storage๋ก ๋ฐ๋. ๋ฐ๋ผ์ state ๊ฐ์ ๋ฐ๋ผ ์ธ์ ๋ ์ง SwiftUI๊ฐ ์ด ๊ตฌ์กฐ์ฒด๋ฅผ ์์ ๊ณ ์ฌ์์ฑ ๊ฐ๋ฅ. (๋น๋ฒํ ์ผ์ด๋จ)
- ๋ค๋ฅธ view ๋ค๊ณผ ๊ณต์ ํ์ง ์๋ ๊ฒ์ด ์์น. (Apple์ private์ผ๋ก ์์ฑํ ๊ฒ์ ๊ถ์ฅ)
- miniVIBE ์์๋ Player์์ ๋ฉ๋ด์ฐฝ์ด ์ด๋ ค์๋์ง ํ๋ณํ๊ณ ์กฐ์ ํ์ธํ๊ธฐ ์ํด ์ฌ์ฉ
struct PlayerView: View {
@State private var isMenuOpen: Bool = false
...
var body: some View {
ZStack {
// ๋ค์ํ component
}
.fullScreenCover(isMenuOpen: $isLyricsOpen) {
// ๋ณด์ฌ์ง content(ex. MenuView)
}
}
}
- ๊ฐ์ source๋ ์ธ๋ถ์ ์์ผ๋ฉฐ ๋ ๊ตฐ๋ฐ ๋ชจ๋์์ ๊ฐ์ ๊ณต์ ํด์ผํ ๋ ์ฌ์ฉ(@State์ ๊ฐ์ ๋๊ฒจ๋ฐ๋ ๋ฑ)
- miniVIBE์์๋ Player์์ ๊ฐ์ฌ์ฐฝ์ด ์ด๋ ค์๋์ง๋ฅผ ํ์ view์์ ๊ฐ์ ์กฐ์
struct PlayerThumbnail: View {
@Binding var isLyricsOpen: Bool
...
var body: some View {
...
Text("Open")
.onTapGesture {
isOpenLyrics = true
}
}
}
- ์ฌ์ ์ ์ ์๋ key ๊ฐ๋ค๋ก ์๋
- miniVIBE์์๋ modal ์ฐฝ์ ๋ซ๊ธฐ ์ํด ์ฌ์ ์ ์ ์๋ presentationMode ์ฌ์ฉ
struct PlayerMenu: View {
@Environment(\.presentationMode) var presentationMode
...
var body: some View {
Button {
presentationMode.wrappedValue.dismiss()
}, label: { Image(systemName: "xmark") }
}
}
- ์ฃผ๋ก SwiftUI app ์ ๋ฐ์์ ์ฐ์ผ ๊ณต์ ๋ฐ์ดํฐ๋ฅผ ์ํด ์ฐ์ด๋ property wrapper
- ObservableObject๋ฅผ ๋ฐ๋ผ์ผ ํจ
- EnvironmentObject๋ฅผ ๊ฐ์ง๋ view๊ฐ ์์ฑ์ ์ฑ ์์ ์ง์ง ์๊ณ SwiftUI์ Environment์ ์ํด ์ ๊ณต
- A, B, C, D view๊ฐ ๋ถ๋ชจ-์์ ๊ด๊ณ๋ฅผ ํ์ฑํ๊ณ ์๊ณ A์์ ์์ฑ๋ observableํ ๊ฐ์ฒด๋ฅผ D๊ฐ ํ์๋ก ํ ๋ ์ค๊ฐ B, C๊ฐ ๋๊ฒจ์ฃผ์ง ์์๋ ๋จ
- A๊ฐ ์์ฑํด์ environment์ ๋ฃ์ผ๋ฉด hierarchy์ ์๋ B, C, D ๋ชจ๋ ์ ๊ทผ ๊ฐ๋ฅ
- miniVIBE์์๋ ํ์ฌ ์ฌ์๊ณผ ๊ด๋ จ๋ class๋ ๋ชจ๋ ๋ทฐ์์ ์ ๊ทผ ๊ฐ๋ฅํด์ผ ํ๋ฏ๋ก App(์ต์๋จ)์์ ์์ฑ ํ environment์ ๋ฃ์
class NowPlaying: ObservableObject {
...
}
@main
struct MiniVibeApp: App {
let nowPlaying = NowPlaying()
...
var body: some Scene {
WindowGroup {
MainTab()
.environmentObject(nowPlaying)
}
}
}
- ํ์ฌ View ์ธ๋ถ์ data๋ฅผ ๊ด์ฐฐํ๊ณ ์ ํ ๋ ์ฌ์ฉ
- ์ค์๋ก ์ ์ฅํ๊ณ ์๋ object๋ฅผ ๋ฉ๋ชจ๋ฆฌ์์ ํด์ ์ํฌ ๊ฒฝ์ฐ๊ฐ ์๊น
- View ๋ด์์ reference type์ ์์ฑํ๊ณ ๋ฌด์กฐ๊ฑด ๋ฉ๋ชจ๋ฆฌ์ ์์ด์ผ ํ ๋ ์ฌ์ฉ
- ObservableObject ๋ด์ property ์์ ๋ถ์ด๋ฉด ํด๋น property์ ๊ฐ์ด ๋ฐ๋์์์ ์๋ฆฌ๊ณ ํด๋น ๊ฐ์ ์ฐ๋ view๋ ๋ฐ๋ ๊ฐ์ ๋ง๊ฒ ์ ๋ฐ์ดํธํ๊ฒ ํด์ค
- miniVIBE์์๋ View-ViewModel ๋ฐ์ธ๋ฉ์ @Published๋ก ํจ