TextView 字号设置

TextView

private void setTextSizeInternal(int unit, float size, boolean shouldRequestLayout) {
    mTextSizeUnit = unit;
    setRawTextSize(TypedValue.applyDimension(unit, size, getDisplayMetricsOrSystem()),
            shouldRequestLayout);
}

TypedValue

如果 unit 标志位是 COMPLEX_UNIT_SP,转化成 dp 值,递归调用自身,并把COMPLEX_UNIT_SP标志为改成COMPLEX_UNIT_DIP

public static float applyDimension(@ComplexDimensionUnit int unit, float value,
                                   DisplayMetrics metrics)
{
    switch (unit) {
        case COMPLEX_UNIT_PX:
            return value;
        case COMPLEX_UNIT_DIP:
            return value * metrics.density;
        case COMPLEX_UNIT_SP:
            if (metrics.fontScaleConverter != null) {
                return applyDimension(
                        COMPLEX_UNIT_DIP,
                        metrics.fontScaleConverter.convertSpToDp(value),
                        metrics);
            } else {
                return value * metrics.scaledDensity;
            }
        case COMPLEX_UNIT_PT:
            return value * metrics.xdpi * INCHES_PER_PT;
        case COMPLEX_UNIT_IN:
            return value * metrics.xdpi;
        case COMPLEX_UNIT_MM:
            return value * metrics.xdpi * INCHES_PER_MM;
    }
    return 0;
}

FontScaleConverter 初始化

ResourcesImpl

FontScaleConverterFactory 静态加载不同档位的缩放倍率, 收到 configuration 的时候会根据实际的 fontscale 插值计算一套合适的倍率

public void updateConfiguration(Configuration config, DisplayMetrics metrics,
                                CompatibilityInfo compat) {
    // ......

    if (mConfiguration.densityDpi != Configuration.DENSITY_DPI_UNDEFINED) {
        mMetrics.densityDpi = mConfiguration.densityDpi;
        mMetrics.density =
                mConfiguration.densityDpi * DisplayMetrics.DENSITY_DEFAULT_SCALE;
    }
    mMetrics.scaledDensity = mMetrics.density *
            (mConfiguration.fontScale != 0 ? mConfiguration.fontScale : 1.0f);
    mMetrics.fontScaleConverter =
            FontScaleConverterFactory.forScale(mConfiguration.fontScale);

    // ......
}

原始数据:

档位名称

200%

150%

100%

字号

sp->dp

100

100

100

100

30

38

30

30

24

36

28

24

20

34

26

20

18

30

24

18

14

26

22

14

12

24

18

12

10

20

15

10

8

16

12

8

计算方法:AOSPA/android_frameworks_base