Issue #37
I like to write UI in code, and with Auto Layout, it is an easy task. However that leaves ViewController with a lots of code. One way we can do is to separate V from C in MVC, by using a dedicated view
We can do that with generic, that initialises a view and replace the view, let’s call it root
import UIKit
class BaseController<T: UIView>: UIViewController {
  let root = T()
  override func loadView() {
    view = root
  }
}
Now we can have a UIView subclass, like LoginView
final class LoginView: UIView {
 lazy var textField: UITextField = UITextField().then {
    $0.textAlignment = .center
    $0.borderStyle = .roundedRect
    $0.keyboardType = .phonePad
  }
  lazy var button: UIButton = UIButton().then {
    $0.setTitleColor(.black, for: .normal)
    $0.backgroundColor = .lightGray
  }
  override init(frame: CGRect) {
    super.init(frame: frame)
    addSubviews(
      textField,
      button
    )
    Constraint.on(
      textField.centerXAnchor.constraint(equalTo: textField.superview!.centerXAnchor),
      textField.centerYAnchor.constraint(equalTo: textField.superview!.centerYAnchor),
      textField.widthAnchor.constraint(equalTo: textField.superview!.widthAnchor, constant: -20),
      button.topAnchor.constraint(equalTo: textField.bottomAnchor, constant: 20),
      button.centerXAnchor.constraint(equalTo: button.superview!.centerXAnchor),
      button.widthAnchor.constraint(equalTo: textField.widthAnchor, multiplier: 0.8),
      button.heightAnchor.constraint(equalToConstant: 44)
    )
  }
  required init?(coder aDecoder: NSCoder) {
    fatalError()
  }
}
And then the LoginController
final class LoginController: BaseController<LoginView> {
  override func viewDidLoad() {
    super.viewDidLoad()
    view.backgroundColor = .white
    let gr = UITapGestureRecognizer(target: self, action: #selector(viewTapped))
    root.addGestureRecognizer(gr)
    root.button.setTitle("Login", for: .normal)
    root.button.addTarget(self, action: #selector(loginButtonTouched), for: .touchUpInside)
    root.button.isEnabled = false
    root.button.showsTouchWhenHighlighted = true
    root.textField.placeholder = "Phone number"
    root.textField.delegate = self
    root.textField.text = dependencyContainer.phoneService.prefix
    root.textField.addTarget(self, action: #selector(textFieldDidChange), for: .editingChanged)
  }
}
And this is how we declare the LoginController
let loginController = LoginController()
navigationController.viewControllers = [loginController]
Start the conversation