You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

SwiftUI中如何同步两个Text对象的字体大小并实现最大适配?

解决方案

要实现两个Text使用相同的最大适配字号,且各自限制在屏幕半宽容器内单行完整显示,核心思路是先分别计算两个文本在半宽容器内的最大可容纳字号,再取两者的最小值作为统一字号。以下是具体实现:

完整代码

struct ScoreView: View {
    let scoreA: String = "5"
    let scoreB: String = "234"
    
    // 计算文本在指定宽度内单行显示的最大字号(二分法优化性能)
    private func maxFontSize(for text: String, in width: CGFloat) -> CGFloat {
        let testText = Text(text)
        var low: CGFloat = 1
        var high: CGFloat = 1000
        var bestSize: CGFloat = 1
        
        while low <= high {
            let mid = (low + high) / 2
            let textSize = testText.font(.system(size: mid)).sizeThatFit(CGSize(width: width, height: .infinity))
            
            if textSize.width <= width {
                bestSize = mid
                low = mid + 1
            } else {
                high = mid - 1
            }
        }
        
        return bestSize
    }
    
    var body: some View {
        GeometryReader { geo in
            let halfScreenWidth = geo.size.width / 2
            // 分别计算两个文本的最大适配字号
            let maxSizeForA = maxFontSize(for: scoreA, in: halfScreenWidth)
            let maxSizeForB = maxFontSize(for: scoreB, in: halfScreenWidth)
            // 取最小值作为统一字号
            let unifiedFontSize = min(maxSizeForA, maxSizeForB)
            
            HStack(spacing: 0) {
                Text(scoreA)
                    .font(.system(size: unifiedFontSize))
                    .lineLimit(1)
                    .frame(width: halfScreenWidth, maxHeight: .infinity)
                    .background(.red.opacity(0.3))
                
                Text(scoreB)
                    .font(.system(size: unifiedFontSize))
                    .lineLimit(1)
                    .frame(width: halfScreenWidth, maxHeight: .infinity)
                    .background(.blue.opacity(0.3))
            }
        }
    }
}

关键说明

  1. 字号计算逻辑:

    • 通过GeometryReader获取父容器的总宽度,平分后得到每个Text的可用宽度。
    • 用二分法实现高效的字号计算:从1到1000的字号范围中,快速找到文本刚好能在指定宽度内单行显示的最大字号,比逐次递减字号的方式性能更优。
  2. 统一字号应用:

    • 取两个文本各自最大适配字号的最小值,确保两个Text使用相同字号时,都能在各自的半宽容器内完整显示,不会出现截断。
  3. 容器限制:

    • 每个Text的frame固定为半屏幕宽度,确保严格限制在自身区域内,避免布局溢出。

原代码问题分析

原代码中两个Text各自独立使用minimumScaleFactor缩放,由于"5"的字符长度远短于"234",其最终缩放比例更小、字号更大,无法实现两者字号统一的要求。新方案通过预计算统一字号,从根源上解决了这个问题。

内容的提问来源于stack exchange,提问作者soleil

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.12 21:34:48