Home > OS >  SwiftUI NavigationView detail view binding to sheet modal not working
SwiftUI NavigationView detail view binding to sheet modal not working

Time:05-09

I have a List where the navigationLink destination is a view with a binding property for a user struct. works fine, if in the detail view I create another navigationLink to an edit view with a binding property for the user struct, that will update all the views as expected when the user is modified.

My problem is when I don't use the navigationLink from the detail view and use a sheet modal instead. When I update in the sheet, the master a detail views update, but not the sheet, is there something I'm missing?

NavigationView using NavigationLinks works:

MasterView (List of Users)
    | (NavigationLink)
DetailView(user: $user) this binding works
    | (NavigationLink)
EditView(user: $user) this binding works

NavigationView using NavigationLink to detail, and sheet to edit:

MasterView (List of Users)
    | (NavigationLink)
DetailView(user: $user) this binding works
    | (sheet)
EditView(user: $user) this binding doesn't work

My implementation of opening sheets is as follows:

struct UserDetailView: View {

    @Binding var user: User
    @State private var sheetItem: SheetItem?

    var body: some View {
        VStack {
            // content
        }
        .toolbar {
            ToolbarItem(placement: .navigationBarTrailing) {
                Button(action: {
                    sheetItem = SheetItem(view: AnyView(EditUserView(user: $user)))
                }) {
                    Text("Edit")
                }
            }
        }
        .sheet(item: $sheetItem) { view in
            showSheet(sheet: view)
        }
    }
}

struct SheetItem: Identifiable {
    var id = UUID()
    var view: AnyView
}

func showSheet(sheet: SheetItem) -> some View {
    return sheet.view
}

CodePudding user response:

By following @jnpdx suggestion, I was able to solve it with using a different approach to rendering sheets

struct UserDetailView: View {

    @Binding var user: User
    @State private var sheetEnum: SheetEnum<SheetType>?
    enum SheetType {
        case EditUser
    }

    var body: some View {
        VStack {
            // content
        }
        .toolbar {
            ToolbarItem(placement: .navigationBarTrailing) {
                Button(action: {
                    sheetEnum = SheetEnum(type: .EditUser)
                }) {
                    Text("Edit")
                }
            }
        }
        .sheet(item: $sheetEnum) { sheet in
            if sheet.type == .EditUser {
                EditUserView(user: $user)
            {
        }
    }
}

struct SheetEnum<T>: Identifiable {
    var id = UUID()
    var type: T
}
  • Related