1

I have a vertical UIStackView which has various of UITextFields (Now It is only 4) inside it. When I give spacing to UIStackView, I gave below error;

"<NSLayoutConstraint:0x1c4286720 H:|-(0)-[UIStackView:0x104d3e6f0](LTR)   (active, names: '|':Hello.OtpInputView:0x104d3c5b0 )>",
"<NSLayoutConstraint:0x1c4286770 UIStackView:0x104d3e6f0.right == Hello.OtpInputView:0x104d3c5b0.right   (active)>",
"<NSLayoutConstraint:0x1c4286860 '_UITemporaryLayoutWidth' Hello.OtpInputView:0x104d3c5b0.width == 0   (active)>",
"<NSLayoutConstraint:0x1c4286e50 'UISV-canvas-connection' UIStackView:0x104d3e6f0.leading == Hello.CustomOtpTextField:0x10588d600.leading   (active)>",
"<NSLayoutConstraint:0x1c4286ea0 'UISV-canvas-connection' H:[Hello.CustomOtpTextField:0x105082600]-(0)-|   (active, names: '|':UIStackView:0x104d3e6f0 )>",
"<NSLayoutConstraint:0x1c4286f40 'UISV-fill-equally' Hello.CustomOtpTextField:0x105024600.width == Hello.CustomOtpTextField:0x10588d600.width   (active)>",
"<NSLayoutConstraint:0x1c4287030 'UISV-fill-equally' Hello.CustomOtpTextField:0x105077a00.width == Hello.CustomOtpTextField:0x10588d600.width   (active)>",
"<NSLayoutConstraint:0x1c42871c0 'UISV-fill-equally' Hello.CustomOtpTextField:0x105082600.width == Hello.CustomOtpTextField:0x10588d600.width   (active)>",
"<NSLayoutConstraint:0x1c4286ef0 'UISV-spacing' H:[Hello.CustomOtpTextField:0x10588d600]-(10)-[Hello.CustomOtpTextField:0x105024600]   (active)>",
"<NSLayoutConstraint:0x1c4286fe0 'UISV-spacing' H:[Hello.CustomOtpTextField:0x105024600]-(10)-[Hello.CustomOtpTextField:0x105077a00]   (active)>",
"<NSLayoutConstraint:0x1c42870d0 'UISV-spacing' H:[Hello.CustomOtpTextField:0x105077a00]-(10)-[Hello.CustomOtpTextField:0x105082600]   (active)>"

)

Will attempt to recover by breaking constraint

How I declare StackView:

stackView.translatesAutoresizingMaskIntoConstraints = false
stackView.axis = .horizontal
stackView.distribution = .fillEqually
stackView.spacing = 10

//textFields is just an array of UITextFields
textFields.enumerated().forEach { (index,field) in
    field.textColor = UIColor.darkGray
    field.font = Font.sourceSansRegular?.withSize(46)
    field.keyboardType = .numberPad
    field.delegate = self
    field.translatesAutoresizingMaskIntoConstraints = false
    field.tag = index
    field.textAlignment = .center
    field.myDelegate = self
    field.sizeToFit()
    stackView.addArrangedSubview(field)
    field.widthAnchor.constraint(equalTo: stackView.widthAnchor, multiplier: (CGFloat(0 / textFields.count)),constant: CGFloat(10 * (textFields.count - 1))).isActive = true
}

self.addSubview(stackView)
stackView.anchor(self.topAnchor, left: self.leftAnchor, bottom: self.bottomAnchor, right: self.rightAnchor, topConstant: 0, leftConstant: 0, bottomConstant: 0, rightConstant: 0, widthConstant: 0, heightConstant: 0)

What I want Is that for example UIStackView has 110pt width and 10 space then UITextFields should has 20pt ((20 * 4) + (3 * 10) which is 110). Therefore, all UITextFields should has same width (Fill Equally)

How can I achieve this?

EDIT: I think I need to specify at least one width for one TextField so I added

 field.widthAnchor.constraint(equalTo: stackView.widthAnchor, multiplier: (CGFloat(0 / textFields.count)),constant: CGFloat(10 * (textFields.count - 1))).isActive = true

However this also give break error.

EDIT2: This stack view is in a custom UIView and I'm giving anchors inside

 override init(frame: CGRect) {
    super.init(frame: frame)
    //Where I gave all anchors
    setupUI()
}

Also How I initialize this custom UIView

    override func viewDidLoad() {
    super.viewDidLoad()

    // Do any additional setup after loading the view.
    self.view.backgroundColor = UIColor.white
    self.view.addSubview(otpField)
    otpField.anchor(self.view.topAnchor, left: self.view.leftAnchor, bottom: nil, right: self.view.rightAnchor, topConstant: 40, leftConstant: 40, bottomConstant: 0, rightConstant: 40, widthConstant: 0, heightConstant: 60)
}

What I want to achieve in a picture:

Image

Emre Önder
  • 2,408
  • 2
  • 23
  • 73

1 Answers1

0

You just need to add a single constraint for height if you already set the stackView.distribution = .fillEqually add a constraint to any of your textFiled like this

let height = NSLayoutConstraint(item: textField1, attribute: .height, relatedBy: .equal, toItem: nil, attribute: .height, multiplier: 1.0, constant: 40.0)
textField1.addConstraint = height

By doing this way All of your textfield will be of height 40 and the total size will depend on the number of item and spacing given for i.e. Height = 40 , Space = 10 Then Total height will be (Height * Number of textfields) + (Space * (number of textfield - 1))

NOTE : Concept is same for vertical and horizontal stackview you need to play with height and width.

tryKuldeepTanwar
  • 3,490
  • 2
  • 19
  • 49