Paint API之——Typeface(字型)

Paint API 之—— Typeface (字型)

在 Android 的绘图系统中,Paint 类的 Typeface 用于定义文本的字体样式,控制文字的外观,如字体家族、粗细、斜体等。Typeface 是一个独立的类,与 Paint 结合使用,通过 Paint.setTypeface(Typeface typeface) 方法设置文本的字体效果。它是自定义文本渲染的核心工具,广泛应用于 UI 设计、动态文本效果和品牌化界面。

Typeface 的作用与应用场景

  • 作用Typeface 定义了文本的字体样式,包括内置字体、自定义字体或系统字体,影响文本的视觉表现(如字形、粗细、斜体)。它与 Paint 的其他属性(如 textSizecolor)结合,控制文本的完整渲染效果。
  • 应用场景
  • 使用系统字体(如 Roboto、Sans Serif)进行标准 UI 渲染。
  • 加载自定义字体文件(如 .ttf 或 .otf)实现品牌化设计。
  • 为特定文本(如标题、按钮)设置粗体或斜体效果。
  • 动态切换字体以实现动画或主题变化。
  • 设置方法:通过 Paint.setTypeface(Typeface typeface) 设置字体,传入 null 恢复默认字体。

Typeface 的主要功能与创建方式

Typeface 提供了多种方式来创建和使用字体,涵盖系统字体和自定义字体。以下是主要方法:

1. 使用系统内置字体

Android 提供了一些默认字体家族,通过 Typeface 的静态方法直接获取:

  • 方法
  • Typeface.DEFAULT:默认字体(通常为 Sans Serif 或 Roboto)。
  • Typeface.DEFAULT_BOLD:默认粗体。
  • Typeface.SANS_SERIF:无衬线字体。
  • Typeface.SERIF:衬线字体。
  • Typeface.MONOSPACE:等宽字体(适合代码显示)。
  • 代码示例
  paint.setTypeface(Typeface.DEFAULT_BOLD); // 设置粗体
  canvas.drawText("Bold Text", 50, 50, paint);
2. 创建自定义字体样式

通过 Typeface.create(String familyName, int style)Typeface.create(Typeface family, int style) 创建指定字体家族或样式的字体。

  • style 参数Typeface 常量):
  • Typeface.NORMAL:正常(0)。
  • Typeface.BOLD:粗体(1)。
  • Typeface.ITALIC:斜体(2)。
  • Typeface.BOLD_ITALIC:粗斜体(3)。
  • 代码示例
  Typeface typeface = Typeface.create("serif", Typeface.BOLD_ITALIC); // 衬线粗斜体
  paint.setTypeface(typeface);
  canvas.drawText("Bold Italic Serif", 50, 100, paint);
3. 加载自定义字体文件

从资源文件(如 assets 或 res/font)或文件路径加载自定义字体(如 .ttf 或 .otf)。

  • 方法
  • Typeface.createFromAsset(AssetManager mgr, String path):从 assets 目录加载字体。
  • Typeface.createFromFile(String path)Typeface.createFromFile(File file):从文件路径加载字体。
  • ResourcesCompat.getFont(Context context, int resourceId)(API 26+):从 res/font 加载字体。
  • 代码示例(从 assets 加载):
  Typeface customFont = Typeface.createFromAsset(getContext().getAssets(), "fonts/custom_font.ttf");
  paint.setTypeface(customFont);
  canvas.drawText("Custom Font", 50, 150, paint);
4. 获取默认字体

Typeface.getSystemDefault()(API 29+)获取系统当前默认字体,适配系统主题变化。

  • 代码示例
  paint.setTypeface(Typeface.getSystemDefault());
  canvas.drawText("System Default", 50, 200, paint);

代码示例

以下是一个自定义 View 示例,展示不同 Typeface 的使用,包括系统字体和自定义字体。复制到 Android 项目中运行,可在画布上看到效果(需在 assets/fonts 目录下放置一个 .ttf 文件,例如 custom_font.ttf)。

import android.content.Context;
import android.graphics.*;
import android.util.AttributeSet;
import android.view.View;

public class TypefaceView extends View {
    private Paint paint;

    public TypefaceView(Context context, AttributeSet attrs) {
        super(context, attrs);
        paint = new Paint(Paint.ANTI_ALIAS_FLAG);
        paint.setTextSize(40f);
        paint.setColor(Color.BLACK);
    }

    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);

        // 1. 默认字体
        paint.setTypeface(Typeface.DEFAULT);
        canvas.drawText("Default Font", 50, 50, paint);

        // 2. 粗体无衬线字体
        paint.setTypeface(Typeface.create(Typeface.SANS_SERIF, Typeface.BOLD));
        canvas.drawText("Bold Sans Serif", 50, 100, paint);

        // 3. 斜体衬线字体
        paint.setTypeface(Typeface.create(Typeface.SERIF, Typeface.ITALIC));
        canvas.drawText("Italic Serif", 50, 150, paint);

        // 4. 自定义字体(需在 assets/fonts 下放置 custom_font.ttf)
        Typeface customFont = Typeface.createFromAsset(getContext().getAssets(), "fonts/custom_font.ttf");
        paint.setTypeface(customFont);
        canvas.drawText("Custom Font", 50, 200, paint);

        // 5. 带阴影的粗斜体等宽字体
        paint.setTypeface(Typeface.create(Typeface.MONOSPACE, Typeface.BOLD_ITALIC));
        paint.setShadowLayer(5f, 2f, 2f, Color.argb(128, 0, 0, 0)); // 添加阴影
        setLayerType(LAYER_TYPE_SOFTWARE, null); // 禁用硬件加速以支持阴影
        canvas.drawText("Bold Italic Monospace", 50, 250, paint);
    }
}
  • 运行效果:从上到下依次显示默认字体、粗体无衬线字体、斜体衬线字体、自定义字体、带阴影的粗斜体等宽字体。
  • 注意:确保 assets/fonts 目录下有 custom_font.ttf,否则第 4 项会失败。

注意事项

  • 性能:加载自定义字体(尤其大字体文件)可能增加内存开销,建议缓存 Typeface 对象,避免重复加载。
  • 兼容性Typeface 自 API 1 起支持,ResourcesCompat.getFont 需要 API 26+。自定义字体需确保文件格式正确(.ttf 或 .otf)。
  • 与 Paint 的其他属性结合
  • 结合 Paint.setTextSize 调整字体大小。
  • 结合 Paint.setShader 实现渐变文字。
  • 结合 Paint.setShadowLayer 添加阴影效果(如上例)。
  • 字体回退:如果指定的字体不可用,系统会回退到默认字体,建议提供备用字体。
  • 调试:Android SDK 的 ApiDemos 包含字体相关示例,可参考学习。

扩展:Jetpack Compose 中的等效实现

在 Jetpack Compose 中,字体相关功能通过 FontFamilyTextStyle 实现:

  • 系统字体:使用 FontFamily.DefaultFontFamily.SansSerifFontFamily.SerifFontFamily.Monospace
  • 自定义字体:通过 FontfontResource 从 res/font 或 assets 加载。
  • 阴影:使用 TextStyle.shadow 添加阴影效果。

示例(Compose 中的字体和阴影):

import androidx.compose.foundation.Canvas
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.TextStyle
import androidx.compose.ui.text.font.FontFamily
import androidx.compose.ui.text.font.FontWeight
import androidx.compose.ui.unit.sp
import androidx.compose.ui.unit.dp
import androidx.compose.ui.graphics.Shadow

@Composable
fun TypefaceExample() {
    Text(
        text = "Custom Font with Shadow",
        style = TextStyle(
            fontSize = 24.sp,
            fontFamily = FontFamily.Serif, // 系统衬线字体
            fontWeight = FontWeight.Bold,
            color = Color.Black,
            shadow = Shadow(
                color = Color.Gray,
                offset = Offset(2f, 2f),
                blurRadius = 5f
            )
        )
    )
}
  • 自定义字体加载(需在 res/font 放置字体文件):
val customFont = FontFamily(Font(R.font.custom_font))
Text(
    text = "Custom Font",
    style = TextStyle(fontSize = 24.sp, fontFamily = customFont)
)

总结

Typeface 是 Android 绘图中控制文本字体的核心工具,支持系统字体、自定义字体和样式调整,适合创建丰富的文本效果。结合 Paint 的其他属性(如 ShaderShadowLayer),可以实现渐变文字、阴影文字等高级效果。在 Jetpack Compose 中,FontFamilyTextStyle 提供了类似功能,更加现代化。如果需要更详细的某字体加载方式(如从网络动态加载字体)、动画效果,或 Compose 中的高级文本渲染,请告诉我!

类似文章

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注