I'm running into an issue trying to create a link to fileImporter as part of a list of options.
I have an enum of options that will be presented in a sidebar-style list menu:
And I am iterating over the enum as follows:
However, presenting fileImporter as its own view causes the interface to crash. It has to be attached to something as a view modifier. The workaround suggested on SO is to attach it to Color.clear:
But the result of is this that, after fileImporter has been dismissed, there's an empty sheet still displayed which has to be dismissed separately, and I can't find a way around that.
I have an enum of options that will be presented in a sidebar-style list menu:
Code Block enum MenuOption: Identifiable, CaseIterable { var id: Int { self.hashValue } case import case optionB case optionC case optionD case optionE @ViewBuilder var destination: some View { switch self { case .import: ImportView(isPresented: .constant(true), progress: ImportProgress()) case .optionB: OptionBView() // etc } }
And I am iterating over the enum as follows:
Code Block struct SidebarMenuView: View { @State private var selection : MenuOption? = nil var body: some View { List(selection: $selection) { ForEach(MenuOption.allCases) { option in Button(action: { self.selection = option} ) { option.label } .sheet(item: $selection) { sheet in sheet.destination } } } } }
However, presenting fileImporter as its own view causes the interface to crash. It has to be attached to something as a view modifier. The workaround suggested on SO is to attach it to Color.clear:
Code Block struct ImportView: View { @Binding var isPresented: Bool @ObservedObject var progress: ImportProgress var body: some View { Color.clear .fileImporter( isPresented: $isPresented, allowedContentTypes: [ ... ], allowsMultipleSelection: true) { result in if let urls = try? result.get() { do { // stuff } } } }
But the result of is this that, after fileImporter has been dismissed, there's an empty sheet still displayed which has to be dismissed separately, and I can't find a way around that.
I have run this code and it works as expected. Tapping import shows the file importer and the other rows shows a sheet.
You can refine the code and tailor it towards your app.
You can refine the code and tailor it towards your app.
Code Block Swift enum MenuOption: String, CaseIterable, Identifiable { case `import` case optionB case optionC case optionD case optionE var id: Int { hashValue } @ViewBuilder var destination: some View { switch self { case .optionB: OptionBView() ... default: EmptyView() } } }
Code Block Swift struct SidebarMenuView: View { @State private var selection: MenuOption? @State private var showingImport = false var body: some View { List { ForEach(MenuOption.allCases) { option in Button(option.rawValue) { switch option { case .import: showingImport = true default: selection = option } } .sheet(item: $selection) { option in option.destination } .fileImporter(isPresented: $showingImport, allowedContentTypes: [...], allowsMultipleSelection: true) { result in if let urls = try? result.get() { print("Got urls") } } } } } }