skip to Main Content

I have created a simple UIViewController which contains a UITableView. When adding a tableHeaderView which includes a UIButton it seems not to be possible to change the button label using appearance settings. Other buttons outside the tableHeaderView are updated correctly.

enter image description here
enter image description here

Here the button which was placed directly in the ViewControllers view is updated correctly while the appearance settings seem not to effect the button inside the tableHeaderView.

class ListViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {
    @IBOutlet weak var tableHeaderView: UIView!
    @IBOutlet weak var tableView: UITableView!
    
    override func viewDidLoad() {
        UILabel.appearance(whenContainedInInstancesOf: [TestButton.self]).font = UIFont.systemFont(ofSize: 30)
        UILabel.appearance(whenContainedInInstancesOf: [TestButton.self]).textColor = .red
        
        super.viewDidLoad()
        tableView.register(UITableViewCell.self, forCellReuseIdentifier: "cell")
        tableView.tableHeaderView = tableHeaderView
    }
    
    ...
}

class TestButton: UIButton {}

There are now other appearance settings in the project which might explain this. Moving the appearance settings to some other place, e.g. application:didFinishLaunchingWithOptions does not change the problem.

Is this a bug or am I missing something?

2

Answers


  1. I’m not sure this is what you are looking for or not.

    1. Select button style to default, then
    2. apply your theme or whatever property you want to change.

    and one more thing instead of using

    UILabel.appearance(whenContainedInInstancesOf: [TestButton.self]).font = UIFont.systemFont(ofSize: 30)
    

    Use the button to change property.

    TestButton.appearance().setTitleColor(.brown, for: .normal)
    
    Login or Signup to reply.
  2. That will likely not be a suitable approach.

    A UIButton does various things with its titleLabel – including changing the text color.

    Trying to use UILabel.appearance(...) will not override the normal behavior.

    You can see this by running your code as-is:

    • note that the view’s TestButton does get the appearance
    • rotate the device so auto-layout re-positions the button
    • the appearance is lost

    This is the same reason why we use:

    button.setTitleColor(.red, for: .normal)
    

    instead of:

    button.titleLabel?.textColor = .red
    

    You probably want to configure those properties in your custom TestButton class. Here’s the basics:

    class TestButton: UIButton {
        
        override init(frame: CGRect) {
            super.init(frame: frame)
            commonInit()
        }
        required init?(coder: NSCoder) {
            super.init(coder: coder)
            commonInit()
        }
        func commonInit() {
            setTitleColor(.red, for: .normal)
            setTitleColor(.lightGray, for: .highlighted)
            titleLabel?.font = UIFont.systemFont(ofSize: 30)
            backgroundColor = .systemBlue
            layer.cornerRadius = 6
        }
    }
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search