How to enable working FocusState with UIKit

160 views Asked by At

In out project we use SwiftUI as View layer working with UIKit for navigation. When view created with UIHostingController TextFields don't reacts to @FocusState property wrapper. If create similar example as on screenshot in full SwiftUI project @FocusState will work.

@FocusState var isFocused: Bool

@ViewBuilder
func phoneTextField() -> some View {
    TextField("",
              text: $viewModel.phoneTextfieldNumber,
              prompt: Text("Введите номер")
        .foregroundColor(Resources.Colors.textDark.swiftUIColor)
        .font(Fonts.Gilroy.semiBold.swiftUIFont(size: 16)))
    .textFieldStyle(PhoneNumberTextFieldStyleTest())
    .multilineTextAlignment(.leading)
    .frame(minWidth: 0, maxWidth: .infinity)
    .background(isFocused ? .clear : Resources.Colors.backgroundGrey100.swiftUIColor)
    .multilineTextAlignment(.leading)
    .cornerRadius(12)
    .overlay(content: {
        RoundedRectangle(cornerRadius: 12)
            .stroke(Resources.Colors.buttonRed100.swiftUIColor, lineWidth: isFocused ? 2 : 0)
    })
    .focused($isFocused)
    .animation(.default, value: isFocused)
    .onChange(of: isFocused, perform: { newValue in
        print("NEWFOCUS", newValue)
    })
}

I try to wrap TextField into Button and it's work to change appearance, but we can focus TextField programmatically with this method

struct FocusedTextField: View {

var placeholder: String
@Binding var text: String
@State private var isFocused: Bool = false

var body: some View {
    Button {
        isFocused = true
    } label: {
        TextField("",
                  text: $text,
                  prompt: Text(placeholder)
            .foregroundColor(Resources.Colors.textDark.swiftUIColor)
            .font(Fonts.Gilroy.semiBold.swiftUIFont(size: 16)))
        .textFieldStyle(PhoneNumberTextFieldStyle(isFocused: $isFocused))
        .multilineTextAlignment(.leading)
        .frame(minWidth: 0, maxWidth: .infinity)
    }
    .background(isFocused ? .clear : Resources.Colors.backgroundGrey100.swiftUIColor)
    .multilineTextAlignment(.leading)
    .cornerRadius(12)
    .overlay(content: {
        RoundedRectangle(cornerRadius: 12)
            .stroke(Resources.Colors.buttonRed100.swiftUIColor, lineWidth: isFocused ? 2 : 0)
    })
    .animation(.default, value: isFocused)
    .buttonStyle(NoneAnimateStyle())
}
}

UPD: Focus state brokes only when UIHostingController is part of UINavigationController

0

There are 0 answers