I wanted to customize looks of a TextField in tvOS but I can't seem to figure out way to alter default look of textfield when it's focused.
struct ContentView: View {
@State var name: String = ""
@State var address: String = ""
var body: some View {
VStack {
TextField("Name", text: $name)
.textFieldStyle(OutlinedTextFieldStyle())
TextField("Address", text: $address)
}
.padding(200.0)
.background(.white)
.preferredColorScheme(.light)
}
}
struct OutlinedTextFieldStyle: TextFieldStyle {
@FocusState var isFocused: Bool
func _body(configuration: TextField<Self._Label>) -> some View {
configuration
.focused($isFocused)
.background(.clear)
.overlay {
RoundedRectangle(cornerRadius: 8, style: .continuous)
.stroke(.gray, lineWidth: isFocused ? 4 : 2)
}
}
}
This is the code I tried and here is the output:
As you can see when I focus on the textfield by default TextField expands and shadow appears. I want to remove this effect and add some more customization when TextField is focused. How can I achieve that?
This is related to the hoverEffect
which is not much customizable in tvOS.
But here is a close try:
func _body(configuration: TextField<Self._Label>) -> some View {
let shape = RoundedRectangle(cornerRadius: 8, style: .continuous)
configuration
.focused($isFocused)
.defaultHoverEffect(nil) // 👈 Suppress the lifting effect
.background(.clear)
.padding(.horizontal, isFocused ? 16 : 0) // 👈 Suppress the padding effect
.overlay {
shape.strokeBorder(.gray, lineWidth: isFocused ? 4 : 2)
}
.mask(shape) // 👈 Suppress the default shadow
}
Also, if you don't like the padding animation, you can:
TextField("", text: $name)
.textFieldStyle(OutlinedTextFieldStyle(placeholder: "Name", show: name.isEmpty))
.overlay(alignment: .leading) {
Text(placeholder)
.padding()
.foregroundStyle(.gray)
.opacity(show ? 1 : 0)
}
Note this is a work around and has side effects like loosing the title of the field in the edit screen and etc.