Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

@State not updating in SwiftUI 2

Tags:

swiftui

Anybody see problems with @State variables not updating in SwiftUI 2 in Xcode 12b? The problem code is in the contextMenu buttons.

The showSheet var is toggled to true but the sheetItem value is not changed. This same code worked in SwiftUI 1.

I have filed a Feedback, but was wondering if anyone else has seen this problem.

Full code:

struct ConnectionsView: View {

@EnvironmentObject var connectionViewModel : FileDataViewModel<Connection>

@State private var editMode = EditMode.inactive
@State private var importedConnections = false
@State private var showEditSheet = false
@State private var selectedIndex = 0
@State private var showSheet = false
@State private var sheetItem = SheetItem.openFile //TOD: Set back to .none when ButtonActions fixed
@State private var newConnection = Connection()

var body : some View {
    NavigationView {
        List {
            ForEach(connectionViewModel.items) { connection in
                NavigationLink (destination: SSHSessionView (connection: connection)) {
                    ConnectionView(connection: connection)
                        //pass tap through the view to allow the NavigationLink to work
                        .allowsHitTesting(self.editMode == .inactive ? false : true)
                        .onTapGesture {
                            if self.editMode.isEditing {
                                self.selectedIndex = self.connectionViewModel.items.firstIndex(where: {$0.id == connection.id})!
                                self.sheetItem = .editItem
                                self.showSheet.toggle()
                            }
                        }
                }
            }
            .onDelete(perform: deleteItem)
            .onMove(perform: moveItem)
        }
        .onAppear {
            UITableView.appearance().tableFooterView = UIView()
        }
        .navigationBarTitle("Connections", displayMode: .large)
        .navigationBarItems(
            leading:
                EditButton()
                    .hoverWithPaddingModifier(),
            trailing:
                Button(action: {
                }, label: {
                    Image(systemName: "plus")
                })
                .contextMenu {
                    Button("New Connections file...", action: {
                        sheetItem = .newFile
                        showSheet.toggle()
                    })
                    Button("Open Connections file...", action: {
                        sheetItem = .openFile
                        showSheet = true
                    })
                    if connectionViewModel.fileOpened {
                        Button("New Connection", action: {
                            sheetItem = .newItem
                            showSheet.toggle()
                        })
                    }
                }
        )
            
        .environment(\.editMode, $editMode)
        
        .sheet(isPresented: $showSheet, content: {
            
            if self.sheetItem == .editItem {
                AddEditConnectionView (connection: self.$connectionViewModel.items[self.selectedIndex], newConnection: false)
                    .environmentObject(self.connectionViewModel)
            }
            
            if self.sheetItem == .newFile {
                FilePickerView(callback : self.importedConnections == false ? self.pickedDocuments : self.newDocFromServerList, UTIs : connectionUTIs, newFileURL : FileDataViewModel<Connection>.getBlankFile (fileType : ViewTypes.connections)!)
            }
            
            if self.sheetItem == .openFile {
                FilePickerView(callback : self.pickedDocuments, UTIs : connectionUTIs, newFileURL: nil)
            }

            if self.sheetItem == .newItem {
                AddEditConnectionView (connection: self.$newConnection, newConnection: true)
                    .environmentObject(self.connectionViewModel)
            }
        })
    }
}
like image 212
Ferdinand Rios Avatar asked Jun 30 '20 21:06

Ferdinand Rios


1 Answers

It's late but it will help others who are facing the same issue. Use @Binding variable instead of @State.

struct CarListView: View {
    @State var isPresented = false
    @State var selectedCar: Car?

    var body: some View {
        Button(action: {
            self.selectedCar = cars[selectedIndex]
            self.isPresented.toggle()
        }) {
            Text("Test")
        }
        .sheet(isPresented: self.$isPresented) {
            WorkoutDetails(workout: selectedCar)
        }
    }
}

struct CarDetailsView: View {
    @Binding var selectedCar: Car?
    // Set a Binding instead of the @State variable
    // If you not pass @Binding then you will not get updated variable here

    var body: some View {
        VStack {
            // your code
        }
    }
}
like image 162
Ronak Kalavadia Avatar answered Nov 27 '22 02:11

Ronak Kalavadia