In Swift 3, I used the following to replace all fonts in BOLD to MEDIUM in AppDelegate:
UILabel.appearance().substituteFontNameBold = "HelveticaNeue-Medium"
And by adding this extension to UILabel :
extension UILabel {
var substituteFontNameBold : String {
get { return self.font.fontName }
set {
if self.font.fontName.contains("Bold") {
self.font = UIFont(name: newValue, size: self.font.pointSize)
}
}
}
}
With the upgrade to Swift 4, I get a "fatal error: unexpectedly found nil while unwrapping an Optional value" on
if self.font.fontName.contains("Bold") {
How can I continue to replace all fonts in BOLD to MEDIUM in labels with Swift 4?
Swift 4.0
This will help you set custom font for all of your UILabel, UIButton, etc. Simply create a extension and replace with this.
var appFontName = "Gudea" //Please put your REGULAR font name
var appFontBoldName = "Gudea" //Please put your BOLD font name
var appFontItalicName = "Gudea" //Please put your ITALIC font name
extension UIFont {
@objc class func mySystemFont(ofSize size: CGFloat) -> UIFont {
return UIFont(name: appFontName, size: size)!
}
@objc class func myBoldSystemFont(ofSize size: CGFloat) -> UIFont {
return UIFont(name: appFontBoldName, size: size)!
}
@objc class func myItalicSystemFont(ofSize size: CGFloat) -> UIFont {
return UIFont(name: appFontItalicName, size: size)!
}
@objc convenience init(myCoder aDecoder: NSCoder) {
if let fontDescriptor = aDecoder.decodeObject(forKey: "UIFontDescriptor") as? UIFontDescriptor {
if let fontAttribute = fontDescriptor.fontAttributes[UIFontDescriptor.AttributeName(rawValue: "NSCTFontUIUsageAttribute")] as? String {
var fontName = ""
switch fontAttribute {
case "CTFontRegularUsage":
fontName = appFontName
case "CTFontEmphasizedUsage", "CTFontBoldUsage":
fontName = appFontBoldName
case "CTFontObliqueUsage":
fontName = appFontItalicName
default:
fontName = appFontName
}
self.init(name: fontName, size: fontDescriptor.pointSize)!
}
else {
self.init(myCoder: aDecoder)
}
}
else {
self.init(myCoder: aDecoder)
}
}
class func overrideInitialize() {
if self == UIFont.self {
let systemFontMethod = class_getClassMethod(self, #selector(systemFont(ofSize:)))
let mySystemFontMethod = class_getClassMethod(self, #selector(mySystemFont(ofSize:)))
method_exchangeImplementations(systemFontMethod!, mySystemFontMethod!)
let boldSystemFontMethod = class_getClassMethod(self, #selector(boldSystemFont(ofSize:)))
let myBoldSystemFontMethod = class_getClassMethod(self, #selector(myBoldSystemFont(ofSize:)))
method_exchangeImplementations(boldSystemFontMethod!, myBoldSystemFontMethod!)
let italicSystemFontMethod = class_getClassMethod(self, #selector(italicSystemFont(ofSize:)))
let myItalicSystemFontMethod = class_getClassMethod(self, #selector(myItalicSystemFont(ofSize:)))
method_exchangeImplementations(italicSystemFontMethod!, myItalicSystemFontMethod!)
let initCoderMethod = class_getInstanceMethod(self, #selector(UIFontDescriptor.init(coder:))) // Trick to get over the lack of UIFont.init(coder:))
let myInitCoderMethod = class_getInstanceMethod(self, #selector(UIFont.init(myCoder:)))
method_exchangeImplementations(initCoderMethod!, myInitCoderMethod!)
}
}
}
Update: Swift3.2
replace this line:
if let fontAttribute = fontDescriptor.fontAttributes[UIFontDescriptor.AttributeName(rawValue: "NSCTFontUIUsageAttribute")] as? String {
with:
if let fontAttribute = fontDescriptor.fontAttributes["NSCTFontUIUsageAttribute"] as? String {
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With