Reputation: 174
Problem
I'm trying to fully understand building a Swift app entirely programmatically but I'm getting hung up on layout anchors. I have a tableview and if a row is selected it will push a new viewcontroller into the view.
override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
let currentCell = tableView.cellForRow(at: indexPath)! as! CoinCell
if let coin = currentCell.coin {
let newViewController = CoinViewController(coin)
self.navigationController?.pushViewController(newViewController, animated: true)
}
tableView.deselectRow(at: indexPath, animated: true)
}
Below is my code for the viewcontroller that is being pushed. I'm able to see that the nameLabel has text while debugging but I can't seem to have the labels actually show in the view.
var coin: Coin? {
didSet {
nameLabel.text = coin?.name
}
}
init(_ coin: Coin) {
super.init(nibName: nil, bundle: nil)
self.coin = coin
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
override func viewDidLoad() {
super.viewDidLoad()
view.backgroundColor = UIColor.white
view.addSubview(nameLabel)
view.addSubview(testLabel)
setupView()
}
let nameLabel: UILabel = {
let label = UILabel()
label.translatesAutoresizingMaskIntoConstraints = false
return label
}()
let testLabel: UILabel = {
let label = UILabel()
label.translatesAutoresizingMaskIntoConstraints = false
label.text = "TEST"
return label
}()
func setupView() {
nameLabel.leftAnchor.constraint(equalTo: view.leftAnchor).isActive = true
nameLabel.topAnchor.constraint(equalTo: view.topAnchor).isActive = true
nameLabel.widthAnchor.constraint(equalToConstant: 50).isActive = true
nameLabel.heightAnchor.constraint(equalToConstant: 50).isActive = true
}
I'm still a beginner with this so I'm not sure of the best way to actually debug an issue like this. Thanks for the help.
Upvotes: 0
Views: 4767
Reputation: 10199
You try to set the text nameLabel
in the property observer:
var coin: Coin? {
didSet {
nameLabel.text = coin?.name
}
}
But didSet
will not be called from the initializer, therfore the label will remain empty.
In iOS (Cocoa Touch), you should fill your views after/within viewDidLoad
(or viewDidAppear
) or - in your case - in setupView
:
func setupView() {
nameLabel.text = coin?.name
// ...
}
Upvotes: 1
Reputation: 3030
Since you are precisely making sure that your controller receive data (or non optional data) via the initializer
, you should replace the property observer
(didSet) to just a simple property.
let coin: Coin
init(_ coin: Coin) {
self.coin = coin
super.init(nibName: nil, bundle: nil)
}
// now in viewDidLoad() you can set the text of your label i.e namelabel.text = self.coin.something
Upvotes: 1