I have a register user screen for an app that uses a
UITableView
to create a list of required fields. Each section has the thing (i.e. "Username", "Email", etc) in the header, a text field, and a footer to display messages pertaining to that field, such as "Username too short." I have found two different ways of updating this text on the fly. The first way is to create an action for whenever the user types into those text fields and in that I call the following code:
UIView.setAnimationsEnabled(false)
self.tableView.beginUpdates()
if let containerView = tableView.footerView(forSection: section) {
containerView.textLabel!.textColor = UIColor.red
containerView.textLabel!.text = "Username too short"
containerView.textLabel!.font = UIFont(name: containerView.textLabel!.font.fontName, size: 12)
containerView.sizeToFit()
}
self.tableView.endUpdates()
UIView.setAnimationsEnabled(true)
This works, updating the footer when I type into the text box (I update the text and message depending on what is needed). However, when I scroll down and for example the username section unloads, when I scroll back up the "Username too short" text is gone. When I again type into the text field it reappears. I have also had issues with this updating it when the section isn't rendered (as expected). Thus, I tried overriding the
tableView(_ tableView: UITableView, viewForFooterInSection section: Int) -> UIView?
method in the following way:
override func tableView(_ tableView: UITableView, viewForFooterInSection section: Int) -> UIView? {
let view = UIView(frame: CGRect(x: 8, y: 0, width: 100, height: 40))
let label = UILabel(frame: view.frame)
label.text = "Username too short"
label.sizeToFit()
view.addSubview(label)
view.frame = CGRect(x: 8, y: 0, width: 100, height: 20)
return view
}
Again updating the text appropriately and not calling the previous code. This meant that I had to call
tableView.reloadData()
every time the user typed in a character. This also worked, but it caused the app to stop letting the user type in to the text field. They would have to click on it again to start typing after every character. I have tried countless ways of merging the two methods, attempting to call the former code in the
tableView
, but I found that whenever I returned a custom view
tableView.footerView(forSection: <anything>)
would return
nil
and if I called the
tableView
method itself, I would have infinite recursion. I also tried many methods to try to get just the footer to reload (thus not losing the text view focus), but none of them seemed to work.
How can I get the footer to update, persist when I unload the section (and as an extension be able to update it while the section isn't loaded), and not lose focus on the text field?
I apologize in advance as I am a bit new to app development. For some context, I have a static table and I am referring to the headers and footers of each section, not the table footer.