Hi. As you can see, components are overlapped in a UIStackView
and I am struggling with that.
Here are some code snippets
class BottomSheetController: UIViewController {
lazy var headerLabel: UILabel = {
let label = UILabel()
label.text = "Workout"
return label
}()
lazy var header: UIView = {
let uiView = UIView()
return uiView
}()
lazy var workoutInput: UITextField = {
let textField = UITextField()
textField.placeholder = "Find or add option"
textField.sizeToFit()
textField.clipsToBounds = true
textField.backgroundColor = UIColor(red: 65 / 255.0, green: 65 / 255.0, blue: 65 / 255.0, alpha: 0.4)
textField.layer.cornerRadius = 5
textField.setImage(image: UIImage(named: "search_black")!)
textField.setClearTextButton()
return textField
}()
lazy var tagsView: UIScrollView = {
let scrollView = UIScrollView()
scrollView.backgroundColor = .red
return scrollView
}()
lazy var containerStackView: UIStackView = {
let stackView = UIStackView(arrangedSubviews: [header, workoutInput, tagsView])
stackView.clipsToBounds = true
stackView.axis = .vertical
stackView.backgroundColor = .systemGray2
return stackView
}()
// ...
private func setConstraint() {
header.addSubview(headerLabel)
header.addSubview(doneButton)
containerStackView.snp.makeConstraints { make in
make.top.left.right.bottom.equalToSuperview().inset(20)
}
headerLabel.snp.makeConstraints { make in
make.top.centerX.equalToSuperview()
}
doneButton.snp.makeConstraints { make in
make.top.right.equalToSuperview()
}
workoutInput.snp.makeConstraints {make in
make.height.equalTo(40)
}
}
}
My problem might be, header
view doesn't have constant height value
But I don't want to set the magic number to header
view. But rather assign the value corresponding to child views (workoutInput
)
You need to add enough constraints to satisfy auto-layout requirements.
A UIView
has no intrinsic size... so your header
ends up with a height of Zero.
Make a couple changes to control the height of that view:
private func setConstraint() {
header.addSubview(headerLabel)
header.addSubview(doneButton)
containerStackView.snp.makeConstraints { make in
// constrain to safe area, not to superView
make.top.left.right.bottom.equalTo(view.safeAreaLayoutGuide).inset(20)
}
headerLabel.snp.makeConstraints { make in
make.top.centerX.equalToSuperview()
// constrain label bottom to superview
make.bottom.equalToSuperview()
}
doneButton.snp.makeConstraints { make in
make.top.right.equalToSuperview()
// constrain button bottom to superview
make.bottom.equalToSuperview()
}
workoutInput.snp.makeConstraints {make in
make.height.equalTo(40)
}
}
As a side note, you'll find it much easier to debug your layout if you give your UI elements contrasting background colors, such as:
header.backgroundColor = .systemTeal
headerLabel.backgroundColor = .yellow
doneButton.backgroundColor = .green
With those changes, this is what you should see: