做 App 时,设置页里加一个「大号字体 / 关怀模式」开关,听起来简单,真做起来往往是一地鸡毛:每个 UILabel 手写 if isLarge { font = 22 } else { 15 },UIButton 还要分 normal/selected,UserDefaults 要记得存,切换时还得挨个页面刷新……
最近我把这套能力整理成独立库 XPFontSizeManage,并发布了 1.0.0 稳定版,已推送到 CocoaPods 公有源 和 GitHub。本文介绍它的设计思路与用法,方便你在项目里直接接入。
一、它解决什么问题?
XPFontSizeManage 是一个轻量级 UIKit 库,核心能力是:
- 在 App 内维护 普通(normal)/ 大号(large) 两档 UI 模式;
- 用 声明式 的方式描述两套资源(字体、颜色、边距、圆角等);
- 切换模式后,已绑定的控件自动刷新,无需满屏
if/else; - 模式 持久化 到
UserDefaults,下次启动保持用户选择。
主场景是 适老化、无障碍、设置页「字体大小」。以字号为主,也支持颜色、边距、圆角等配套(关怀模式里字号变大后,按钮边距、对比度往往也要一起调)。
二、核心设计(三层架构)
XPFontSizeManager(全局档位 + 持久化 + 通知)
↓ fontSizeDidChangeNotification
MixedResource<T>(normal / other → unfold())
↓
UIKit Extension(UILabel / UIButton / UIView / CALayer …)
-
XPFontSizeManager:单一数据源,切换时发
fontSizeDidChangeNotification。 -
MixedResource<T>:泛型双态资源,
unfold()按当前档位返回normal或other。 -
UIKit 扩展:关联对象保存配置 + 监听通知,自动写回
font、textColor、cornerRadius等。
低侵入:不用子类化控件,现有页面加几行绑定即可。
三、安装
CocoaPods(推荐,1.0.0 已上 Trunk):
pod 'XPFontSizeManage', '~> 1.0.0'
pod install
源码:
- GitHub:https://github.com/jamalping/XPFontSizeManage
- Gitee 镜像:https://gitee.com/jamalping/XPFontSizeManage
要求:iOS 9.0+,Swift 5.0+。
四、快速上手
1. 切换全局模式
import XPFontSizeManage
// 设置页开关
XPFontSizeManager.switchFontSize()
// 或直接指定(会持久化并广播通知)
XPFontSizeManager.fontSize = .large
if XPFontSizeManager.isLargeFont {
// 当前为大号模式
}
业务层也可监听统一通知:
NotificationCenter.default.addObserver(
forName: XPFontSizeManager.fontSizeDidChangeNotification,
object: nil,
queue: .main
) { _ in
// 刷新自定义 UI
}
2. 文本控件绑定字体
let label = UILabel()
label.text = "标题"
// 直接属性
label.fontSize = MixFont(
normal: .systemFont(ofSize: 15),
other: .systemFont(ofSize: 22)
)
// xp 命名空间(等价)
label.xp.fontSize = MixFont(normal: .systemFont(ofSize: 15), other: .systemFont(ofSize: 22))
// 按字号差值快速构造
label.fontSize = XPFont(normal: .systemFont(ofSize: 15), 3) // 大号 = 18pt
UITextField、UITextView 用法相同。
3. UIButton:分状态字体 / 颜色 / 边距
button.xpControlNormalFont = MixFont(normal: .systemFont(ofSize: 15), other: .systemFont(ofSize: 22))
button.xpControlSelectedFont = MixFont(normal: .boldSystemFont(ofSize: 16), other: .boldSystemFont(ofSize: 24))
button.xpControlNormalTitleColor = MixColor(normal: .white, other: UIColor(white: 1.0, alpha: 0.92))
button.xpControlNormalInset = MixImageEdgeInset(
normal: .zero,
other: UIEdgeInsets(top: 0, left: 20, bottom: 0, right: 0)
)
4. 自定义逻辑 & Layer
// UIView:任意自定义刷新
view.fontSizeChangeCallBack = { size in
view.alpha = (size == .large) ? 1.0 : 0.7
}
// CALayer:圆角、边框随模式变化
view.layer.xpCornerRadius = MixedResource(normal: 8, other: 20)
view.layer.xpBorderWidth = MixedResource(normal: 2, other: 6)
5. 移除监听
动态场景可将 fontSize 置为 nil,或调用 removeAllFontSizeObservers(),避免多余监听。
五、和系统 Dynamic Type 的区别?
| 系统 Dynamic Type | XPFontSizeManage | |
|---|---|---|
| 触发 | 系统「辅助功能 → 更大字体」 | App 内独立开关(关怀模式) |
| 档位 | 多级连续缩放 | 固定两档,布局可控 |
| 范围 | 主要影响字体 | 字体 + 颜色 + 边距 + 圆角等 |
二者可并存:系统字号交给 UIFontMetrics,业务关怀模式交给本库。
六、Example 与质量
仓库自带 Example 演示:文本三种绑定方式、Button 分状态、Layer/回调、移除监听等;含单元测试与 GitHub Actions CI。
本地运行:
git clone https://github.com/jamalping/XPFontSizeManage.git
cd XPFontSizeManage/Example
pod install
open XPFontSizeManage.xcworkspace
七、版本与链接
- 当前稳定版:1.0.0(MIT 协议)
- 1.0 起 API 统一为
XP/xp前缀 - GitHub:https://github.com/jamalping/XPFontSizeManage
-
CocoaPods:
pod 'XPFontSizeManage', '~> 1.0.0'
欢迎 Star、Issue 和 PR。若你在做适老化或设置页字号方案,希望这个库能少写一些重复代码。
作者:jamalping · 开源地址见上文 GitHub