Access Environment values through PresentationDetents.Context

I want to create a custom presentation detent to set a custom height for a sheet presentation. For that, I added a struct conforming to CustomPresentationDetent which has an only method static function height(in: Self.Context) -> CGFloat?.

Implementation works fine, the view presented inside the sheet modifier has the height returned by the custom detent. The problem comes when I try to access the Context's environment values inside the protocol conformance method.

PresentationDetent.Context has a subscript that enables accessing any environment value subscript<T>(dynamicMember _: KeyPath<EnvironmentValues, T>) -> T but using it from the custom detents height method only returns the default value for each one.

I'm trying to set the environment values through environment<V>(WritableKeyPath<EnvironmentValues, V>, V) modifier but it does not seem to work. When accessed via @Environment property wrapper from the view it does get the updated value though.

Is there any other way to set an environment value or any special way to set it so that it is visible from a presentation detent?

Answered by DTS Engineer in 799165022

You should be able to lookup dynamic properties using the context, however context is not mutable so you won't be able to set or update environment using the context values.

You should be able to lookup dynamic properties using the context, however context is not mutable so you won't be able to set or update environment using the context values.

Yes I'm able to lookup those properties using the context but I'm not able to see the updated values. I'm not trying to update environment using context but rather looking at its values.

I want to achieve something like this example but the printed value is the properties default value.

struct CustomValueKey: EnvironmentKey {
    static var defaultValue: CGFloat = 4
}

extension EnvironmentValues {
    var customValue: CGFloat {
        get { self[CustomValueKey.self] }
        set { self[CustomValueKey.self] = newValue }
    }
}

struct CustomDetent: CustomPresentationDetent {
    static func height(in context: Context) -> CGFloat? {
        let customValue = context.customValue
        // prints property's default value
        print(customValue)
        return 300
    }
}

struct Sheet: View {
    var body: some View {
        Color.red
            .presentationDetents([.custom(CustomDetent.self)])
    }
}

struct ContentView: View {
    @State var showSheet = false
    var body: some View {
        Button("Show sheet") {
            showSheet.toggle()
        }
        .sheet(isPresented: $showSheet) {
            Sheet()
        }
        .environment(\.customValue, 24) // this value is not available in custom detent's context
    }
}
``

I have the same issue, looks like there is bug that the context is not updated.

Same issue here. Only default values are being read by a CustomPresentationDetent implementation.

Access Environment values through PresentationDetents.Context
 
 
Q