Подкласс UIButton с системным шрифтом, полужирным шрифтом и кернингом - PullRequest
0 голосов
/ 28 мая 2020

Для выполнения кернинга необходимо использовать текст с атрибутами. Но. С другой стороны, вы не можете получить системные шрифты в текстовом меню с атрибутами IB.

Как мне создать (в коде) UIButton с системой

  • font, weight bold
  • size 11
  • Атрибут kern установлен на -2

В идеале он собирал бы текст кнопки из обычного текста Title в IB. Но если текст должен быть установлен в коде, это нормально.

class NiftyButton: UIButton { 
    ????
}

Обычно я инициализирую UIButton вот так ... но я даже не знаю, лучшее ли это место для этого? (Вы не можете сделать это в layoutSubviews, так как это будет l oop, конечно.)

class InitializeyButton: UIButton {

    override init(frame: CGRect) {
        super.init(frame: frame)
        common()
    }

    required init?(coder aDecoder: NSCoder) {
        super.init(coder: aDecoder)
        common()
    }

    func common() {
        ...
    }
}

Как достичь в коде ...

  • системный шрифт, жирный шрифт
  • размер 11
  • атрибут kern установлен на -2

Ответы [ 2 ]

1 голос
/ 28 мая 2020

Вот класс, который вы можете использовать для получения желаемого результата:

class InitializeyButton: UIButton {

   @IBInspectable var spacing:CGFloat = 0 {
      didSet {
        updateTitleOfLabel()
      }
   }

   override func setTitle(_ title: String?, for state: UIControl.State) {

        let color = super.titleColor(for: state) ?? UIColor.black
        let attributedTitle = NSAttributedString(
            string: title ?? "",
            attributes: [NSAttributedString.Key.kern: spacing,
                         NSAttributedString.Key.foregroundColor: color,
                         NSAttributedString.Key.font: UIFont.systemFont(ofSize: self.titleLabel?.font.pointSize ?? 11, weight: .bold)   ])
        super.setAttributedTitle(attributedTitle, for: state)
   }

  private func updateTitleOfLabel() {
    let states:[UIControl.State] = [.normal, .highlighted, .selected, .disabled]
      for state in states {
        let currentText = super.title(for: state)
        self.setTitle(currentText, for: state)
      }
   }
}
0 голосов
/ 01 июня 2020

Скопируйте и вставьте UIButton для systemFont + kerning:

Я убрал отличную информацию Jawad:

Во-первых, во время запуска вы должны создать присвоенный заголовок:

import UIKit

class SmallChatButton: UIIButton { // (note the extra "I" !!)
    
    override func common() {
        super.common()
        backgroundColor = .your corporate color
        contentEdgeInsets = UIEdgeInsets(top: 7, left: 11, bottom: 7, right: 11)
        titles()
    }
    
    private func titles() {
        let states: [UIControl.State] = [.normal, .highlighted, .selected, .disabled]
        for state in states {
            let currentText = super.title(for: state)
            setTitle(currentText, for: state)
        }
    }
    

чтобы добиться этого ..

    override func setTitle(_ title: String?, for state: UIControl.State) {

        let _f = UIFont.systemFont(ofSize: 10, weight: .heavy)
        
        let attributedTitle = NSAttributedString(
            string: title ?? "Click",
            attributes: [
                NSAttributedString.Key.kern: -0.5,
                NSAttributedString.Key.foregroundColor: UIColor.white,
                NSAttributedString.Key.font: _f
        ])
        setAttributedTitle(attributedTitle, for: state)
    }
    
    override func layoutSubviews() { // example of rounded corners
        super.layoutSubviews()
        layer.cornerRadius = bounds.height / 2.0
        clipsToBounds = true
    }
}

Обратите внимание, что керн «-0,5» - это примерно то, что большинство типографов хотят для типичного «слегка плотного шрифта» .

Хорошо смотрится, скажем, заглавными буквами, полужирным шрифтом или мелким шрифтом. Система измерения Apple не похожа ни на что, используемое типографами, поэтому вам просто нужно будет изменять ее, пока типограф в вашем приложении не будет удовлетворен.

Что такое UIIButton (обратите внимание на дополнительную букву «I» !! )

В любом проекте вам неизбежно понадобится UIButton с инициализатором «I», поэтому у вас, вероятно, будет:

import UIKit

class UIIButton: UIButton {
    
    override init(frame: CGRect) {
        super.init(frame: frame)
        common()
    }
    
    required init?(coder aDecoder: NSCoder) {
        super.init(coder: aDecoder)
        common()
    }
    
    func common() {
        
    }

}

(Удивительно, что в iOS один должен сделать все вышеперечисленное, чтобы "кернинг системного шрифта"!)

...