07-18-2023, 09:34 PM
I have a `UIViewController` called `LoginViewController`. I want to build the view of that `LoginViewController` **fully programmatically** in a custom `UIView` class called `LoginView` instead of building all the elements within my `LoginViewController`. This way I'm preventing "View" code in a Controller class (MVC).
In the code below I'm setting the view of my `LoginViewController` to my `LoginView` which for simplicity only contains 2 `UILabels`
class LoginViewController: UIViewController {
override func loadView() {
super.loadView()
self.view = LoginView(frame: CGRect.zero)
}
The LoginView class initialises both labels and should set some constraints.
class LoginView: UIView {
var usernameLabel: UILabel!
var passwordLabel: UILabel!
override init (frame : CGRect) {
super.init(frame : frame)
setupLabels()
}
convenience init () {
self.init(frame:CGRect.zero)
}
required init?(coder aDecoder: NSCoder) {
super.init(coder: aDecoder)
}
private func setupLabels(){
//Init labels and set a simple text
self.usernameLabel = UILabel()
self.usernameLabel.text = "Username"
self.passwordLabel = UILabel()
self.passwordLabel.text = "Password"
//Set constraints which aren't possible since there is no contentView, perhaps using the frame?
}
}
This doesn't work since the view's bounds are 0. However I couldn't find any resource that gives insight in whether this is possible, so I tried my approach which didn't work.
How you set the view of a UIViewController to a custom UIView which is made programmatically? Or is the above snippet recommended?
> **This is the working solution based on Jadar's answer:**
>
> class LoginViewController: UIViewController {
>
> override func loadView() {
> view = LoginView()
> }
>
> override func viewDidLoad() {
> super.viewDidLoad()
> // Do any additional setup after loading the view.
>
> }
> }
>
> class LoginView: UIView {
>
> var usernameLabel: UILabel!
> var passwordLabel: UILabel!
>
> override init(frame: CGRect) {
> super.init(frame: frame)
>
> self.usernameLabel = UILabel()
> self.usernameLabel.text = "Username"
> self.passwordLabel = UILabel()
> self.passwordLabel.text = "Password"
>
> addSubview(usernameLabel)
> addSubview(passwordLabel)
>
> if let superview = usernameLabel.superview{
> //Setting AutoLayout using SnapKit framework
> usernameLabel.snp.makeConstraints { (make) in
> make.center.equalTo(superview)
> }
> }
> }
Result:
[![Result][1]][1]
[1]:
In the code below I'm setting the view of my `LoginViewController` to my `LoginView` which for simplicity only contains 2 `UILabels`
class LoginViewController: UIViewController {
override func loadView() {
super.loadView()
self.view = LoginView(frame: CGRect.zero)
}
The LoginView class initialises both labels and should set some constraints.
class LoginView: UIView {
var usernameLabel: UILabel!
var passwordLabel: UILabel!
override init (frame : CGRect) {
super.init(frame : frame)
setupLabels()
}
convenience init () {
self.init(frame:CGRect.zero)
}
required init?(coder aDecoder: NSCoder) {
super.init(coder: aDecoder)
}
private func setupLabels(){
//Init labels and set a simple text
self.usernameLabel = UILabel()
self.usernameLabel.text = "Username"
self.passwordLabel = UILabel()
self.passwordLabel.text = "Password"
//Set constraints which aren't possible since there is no contentView, perhaps using the frame?
}
}
This doesn't work since the view's bounds are 0. However I couldn't find any resource that gives insight in whether this is possible, so I tried my approach which didn't work.
How you set the view of a UIViewController to a custom UIView which is made programmatically? Or is the above snippet recommended?
> **This is the working solution based on Jadar's answer:**
>
> class LoginViewController: UIViewController {
>
> override func loadView() {
> view = LoginView()
> }
>
> override func viewDidLoad() {
> super.viewDidLoad()
> // Do any additional setup after loading the view.
>
> }
> }
>
> class LoginView: UIView {
>
> var usernameLabel: UILabel!
> var passwordLabel: UILabel!
>
> override init(frame: CGRect) {
> super.init(frame: frame)
>
> self.usernameLabel = UILabel()
> self.usernameLabel.text = "Username"
> self.passwordLabel = UILabel()
> self.passwordLabel.text = "Password"
>
> addSubview(usernameLabel)
> addSubview(passwordLabel)
>
> if let superview = usernameLabel.superview{
> //Setting AutoLayout using SnapKit framework
> usernameLabel.snp.makeConstraints { (make) in
> make.center.equalTo(superview)
> }
> }
> }
Result:
[![Result][1]][1]
[1]: