Date:

Share:

Using KeyPaths to Drive Programmatic Focus

Related Articles

God .focused(_:equals:) The change is new in iOS15 and macOS12. It requires us to go through a FocusState And allows for programmatic definition and response to focus changes.

Common examples of this in action tend to use custom enum to allow transition between the fields in the form however in most cases the fields of the form naturally belong to the fields in your models. Therefore it is possible to use KeyPath As the target value, and in fact, since the value only needs to match the Hashable we can even use AnyKeyPath As a type so that we can deal with targeting across multiple domains spanning more than one sample.

struct ContentView: View 
  @State
  var project = Project()

  @FocusState
  var focus: AnyKeyPath?

  var body: some View 
    Form 
      TextField("Name", text: $project.name)
      .focused($focus, equals: Project.name)

      TextEditor(text: $project.body)
      .focused($focus, equals: Project.body)
    
  

Adding a submit button to the form allows us to verify and if necessary target the user in a field that lacks value.

Button("Submit") 
  guard project.name != "" else 
    focus = Project.name
    return
  
  guard project.body != "" else 
    focus = Project.body
    return
  
  

In addition, we can add an onAppear(perform:) Operation to from so that we can also move the focus as soon as the form appears on the screen.

.onAppear 
  guard project.name != "" else 
    focus = Project.name
    return
  
  guard project.body != "" else 
    focus = Project.body
    return
  

Response to focus changes can be useful as well, in this example we can force the focus back to name Field if not defined by adding onChange(of:perform:) Sub-form.

.onChange(of: focus)  newValue in
  if project.name == "" 
    focus = Project.name
  

Source

LEAVE A REPLY

Please enter your comment!
Please enter your name here

Popular Articles