Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

iOS 16 keyboard safe area not updated on push

There's a strange keyboard issue on iOS 16, when pushing new screens. It seems the keyboard safe area is not updated when you come back from the pushed screen.

It's even reproducible with this chunk of code on an empty project:

struct ContentView: View {
    
    @State var text = ""
    
    var body: some View {
        NavigationView {
            VStack {
                Spacer()
                NavigationLink {
                    Text("test")
                } label: {
                    Text("Tap me")
                }
                TextField("", text: $text)
                    .textFieldStyle(.roundedBorder)
            }
            .padding()
        }
    }
}

Steps to reproduce:

  • Open the keyboard
  • Press the button "tap me" and navigate to the other screen
  • Quickly come back to the previous screen
  • The keyboard is dismissed, but there's a large gap that fits the keyboard size.

Anyone else had a similar issue?

like image 871
Martin Mitrevski Avatar asked Jan 30 '26 15:01

Martin Mitrevski


1 Answers

I found 2 ways to solve this problem and both will need to hide the keyboard before you go to the next screen

  1. Add hide keyboard to the button which activates navigation to another view
    @State var isActive: Bool = false
    
    var body: some View {
        NavigationView {
            ZStack {
                NavigationLink(isActive: $isActive, destination: { Text("Hello") }, label: EmptyView.init)
                
                VStack {
                    TextField("Text here", text: .constant(""))
                    Button("Press me") {
                        resignFirstResponder()
                        isActive.toggle()
                    }
                }
            }
        }
    }
  1. Add hide keyboard to onChange block
@State var isActive: Bool = false
    
    var body: some View {
        NavigationView {
            ZStack {
                NavigationLink(isActive: $isActive, destination: { Text("Hello") }, label: EmptyView.init)
                    .onChange(of: isActive) { newValue in
                        if newValue {
                            resignFirstResponder()
                        }
                    }
                
                VStack {
                    TextField("Text here", text: .constant(""))
                    Button("Press me") {
                        isActive.toggle()
                    }
                }
            }
        }
    }

Code for hide keyboard:

public func resignFirstResponder() {
    UIApplication.shared.sendAction(
        #selector(UIResponder.resignFirstResponder),
        to: nil,
        from: nil,
        for: nil
    )
}
like image 114
Mixorok Avatar answered Feb 01 '26 05:02

Mixorok



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!