Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

addArrangedSubview vs addSubview

I'm newbie and I've wrote a customView inherited from StackView and I created a button programmatically with few attributes and when I add it to my custom view, I have two problems:

  1. If I use addArrangedSubview(myBtn), my view ignores attributes that I added and fills the whole width. But if I use addSubView(myBtn), It's ok(a blue square in 44x44)
  2. If I use addArrangedSubview(myBtn), addTarget() not works and myBtn is not clickable, but when I use addSubView(myBtn), It works perfectly.

Here is my custom view class:

import UIKit

class RatingControl: UIStackView {

//MARK: Initialization
override init(frame: CGRect) {
    super.init(frame: frame)
    setupButtons()
}

required init(coder: NSCoder) {
    super.init(coder:coder)
    setupButtons()
}

//MARK: Private Methods
private func setupButtons() {

    // Create the button
    let button = UIButton()
    button.backgroundColor = UIColor.blue

    // Add constraints
    button.translatesAutoresizingMaskIntoConstraints = false
    button.heightAnchor.constraint(equalToConstant: 44.0).isActive = true
    button.widthAnchor.constraint(equalToConstant: 44.0).isActive = true

    // Setup the button action
    button.addTarget(self, action: #selector(ratingButtonTapped(_:)), for: .touchUpInside)

    // Add the button to the stack
    addArrangedSubview(button)

}
//MARK: Button Action
@objc func ratingButtonTapped(_ sender: Any) {
    print("Button pressed 👍")
}

}

Here is the preview:

enter image description here enter image description here

What's difference between addSubView() and addArrangedSubview()? why these problems happens?

like image 596
Mahdi Moqadasi Avatar asked Mar 18 '19 12:03

Mahdi Moqadasi


1 Answers

I'm assuming you want to add several buttons horizontally (such as with a typical "stars" rating control).

A UIStackView, as might be guessed from its .addArrangedSubview() method, arranges its subviews, based on its .axis, .alignment, .distribution and .spacing properties, as well as its frame.

So, do some reading about UIStackView and how it can be used. Most likely, you are currently constraining your custom view with:

  • top
  • leading
  • trailing (or width)

So adding your button as an arrangedSubView results in it stretching to the width of the stack view, because that's the default.

Adding it as a subview simply overlays the button on the stack view, instead of allowing the stack view to arrange it, and your stack view likely then has a height of zero -- so the button cannot be tapped.

Try setting only top and leading constraints when you add your custom stack view. That should give you a 44 x 44 button that can be tapped.

As you add more buttons using .addArrangedSubview(), those buttons will be arranged horizontally, which is probably what you want.

like image 82
DonMag Avatar answered Oct 26 '22 23:10

DonMag