NSAttributedString动态文本适配:修改系统字号后UILabel不更新问题求解
解决NSAttributedString下UILabel字号不随系统无障碍设置更新的问题
当你用NSAttributedString给UILabel设置attributedText时,adjustsFontForContentSizeCategory = true不会自动生效——这个属性仅对普通的text属性有效。要让富文本字号跟随系统无障碍设置变化,需要手动监听字号更新通知,重新生成富文本。
具体实现步骤:
- 添加
UIContentSizeCategory.didChangeNotification通知监听,捕捉系统字号变化事件 - 在通知回调中,重新生成包含自适应字体的
NSAttributedString并赋值给UILabel - 在合适的时机移除监听,避免内存泄漏
代码示例(ViewController中实现):
class YourViewController: UIViewController { @IBOutlet weak var customLabel: UILabel! override func viewDidLoad() { super.viewDidLoad() // 初始化时设置富文本 updateAttributedText() // 注册字号变化通知 NotificationCenter.default.addObserver(self, selector: #selector(contentSizeCategoryChanged), name: UIContentSizeCategory.didChangeNotification, object: nil) } deinit { // 移除通知监听 NotificationCenter.default.removeObserver(self, name: UIContentSizeCategory.didChangeNotification, object: nil) } @objc private func contentSizeCategoryChanged() { // 字号变化时重新生成富文本 updateAttributedText() } private func updateAttributedText() { // 生成适配当前字号类别的字体 let scaledFont = UIFontMetrics(forTextStyle: .caption2).scaledFont(for: UIFont.systemFont(ofSize: 11)) // 构建富文本属性 let attributes: [NSAttributedString.Key: Any] = [ .font: scaledFont, .foregroundColor: UIColor.black ] // 赋值给Label customLabel.attributedText = NSAttributedString(string: "你的富文本内容", attributes: attributes) } }
更优雅的封装:自定义UILabel
如果多个页面需要这个功能,可以封装成自定义Label,内部处理监听逻辑:
class AutoScalingAttributedLabel: UILabel { // 定义闭包,用于外部提供富文本生成逻辑 var attributedTextBuilder: (() -> NSAttributedString?)? { didSet { refreshAttributedText() } } override init(frame: CGRect) { super.init(frame: frame) setupNotification() } required init?(coder: NSCoder) { super.init(coder: coder) setupNotification() } private func setupNotification() { NotificationCenter.default.addObserver(self, selector: #selector(onContentSizeChanged), name: UIContentSizeCategory.didChangeNotification, object: nil) } @objc private func onContentSizeChanged() { refreshAttributedText() } private func refreshAttributedText() { attributedText = attributedTextBuilder?() } deinit { NotificationCenter.default.removeObserver(self) } } // 使用示例 let label = AutoScalingAttributedLabel() label.attributedTextBuilder = { let scaledFont = UIFontMetrics(forTextStyle: .caption2).scaledFont(for: UIFont.systemFont(ofSize: 11)) return NSAttributedString(string: "自适应富文本内容", attributes: [.font: scaledFont]) }
内容的提问来源于stack exchange,提问作者PGDev
相关产品推荐
相关产品推荐

