Created
April 12, 2024 17:58
-
-
Save chockenberry/c5d75a1db4f31441990a3f1bd995c7b5 to your computer and use it in GitHub Desktop.
Optional Bindable
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// | |
// ContentView.swift | |
// BindableOptional | |
// | |
// Created by Craig Hockenberry on 4/12/24. | |
// | |
import SwiftUI | |
@Observable | |
class Whatever { | |
var number: Int = 0 | |
} | |
struct OtherView: View { | |
@Binding var whatever: Whatever | |
// This allows the view to work with @Bindable, but breaks the traditional $ binding | |
//@Bindable var whatever: Whatever | |
var body: some View { | |
Button("Do Whatever") { | |
whatever.number += 1 | |
} | |
.buttonStyle(.borderedProminent) | |
} | |
} | |
struct ContentView: View { | |
@State private var optionalWhatever: Whatever? | |
@State private var whatever = Whatever() | |
var body: some View { | |
#if DEBUG | |
let _ = Self._printChanges() | |
#endif | |
VStack { | |
if let whateverInstance = optionalWhatever { | |
Text("Optional Whatever = \(whateverInstance.number)") | |
@Bindable var whateverBinding = whateverInstance | |
// Cannot convert value of type 'Bindable<Whatever>' to expected argument type 'Binding<Whatever>' | |
//OtherView(whatever: $whateverBinding) | |
} | |
else { | |
Text("No Optional Whatever") | |
Button("Make Optional Whatever") { | |
optionalWhatever = Whatever() | |
optionalWhatever!.number = 999 | |
} | |
.buttonStyle(.borderedProminent) | |
} | |
} | |
.padding() | |
VStack { | |
Text("Whatever = \(whatever.number)") | |
OtherView(whatever: $whatever) | |
} | |
.padding() | |
} | |
} | |
#Preview { | |
ContentView() | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
The problem here is that you need to use properties of the Observable, not the Observable itself:
The view can then be used in both contexts:
and:
It's a subtle distinction, but the dynamic member lookup for both Bindable and Binding makes it work.