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

Android中Typeface.createFromFile加载网络字体失败求助

解决Typeface.createFromFile加载网络字体失败的问题

你遇到的核心问题很明确:Typeface.createFromFile()只能读取本地文件系统里的字体文件,根本无法直接识别网络URL,日志里反复出现的"Font not found"就是因为你传入了一个HTTP地址,而非本地文件路径。下面是具体的问题分析和可落地的解决方案:

问题根源拆解

你的代码里直接把从Intent拿到的网络字体地址传给了createFromFile(),但这个方法的设计逻辑是仅支持本地文件的绝对路径(比如/data/data/com.nani.font/files/custom_font.otf),完全不具备网络资源加载能力,自然会抛出找不到字体的异常。

解决方案:先下载字体到本地,再加载

你需要先把网络上的字体文件下载到应用的本地存储(推荐用应用私有目录,无需动态申请存储权限),再用本地路径创建Typeface。以下是完整的实现步骤和代码示例:

1. 先添加必要权限

在AndroidManifest.xml中添加网络权限:

<uses-permission android:name="android.permission.INTERNET" />

2. 实现字体下载工具方法

写一个方法把网络字体下载到应用私有文件目录:

private File downloadFontToLocal(String fontUrl) {
    try {
        URL url = new URL(fontUrl);
        HttpURLConnection connection = (HttpURLConnection) url.openConnection();
        connection.setDoInput(true);
        connection.connect();

        // 用应用私有目录存储字体,无需权限
        File fontFile = new File(getFilesDir(), "downloaded_font.otf");
        FileOutputStream outputStream = new FileOutputStream(fontFile);

        InputStream inputStream = connection.getInputStream();
        byte[] buffer = new byte[1024];
        int length;
        while ((length = inputStream.read(buffer)) != -1) {
            outputStream.write(buffer, 0, length);
        }

        // 关闭流和连接
        inputStream.close();
        outputStream.close();
        connection.disconnect();

        return fontFile;
    } catch (IOException e) {
        e.printStackTrace();
        return null;
    }
}

3. 在子线程中下载并加载字体

注意:网络请求不能在主线程执行,否则会触发ANR,这里用简单的线程实现:

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_final);

    TextView textView = findViewById(R.id.your_textview_id);
    String name = getIntent().getStringExtra("name");
    String fontUrl = getIntent().getStringExtra("font");

    // 先设置文本内容
    textView.setText(name);

    // 开启子线程下载字体
    new Thread(() -> {
        File fontFile = downloadFontToLocal(fontUrl);
        if (fontFile != null && fontFile.exists()) {
            // 加载本地字体后,切回主线程更新UI
            Typeface tf = Typeface.createFromFile(fontFile);
            runOnUiThread(() -> textView.setTypeface(tf));
        } else {
            // 下载失败提示
            runOnUiThread(() -> Toast.makeText(FinalActivity.this, "字体加载失败", Toast.LENGTH_SHORT).show());
        }
    }).start();
}

额外优化建议

  • 可以加入缓存逻辑,比如记录已下载字体的URL和本地路径,避免重复下载相同字体
  • 推荐用OkHttp这类成熟的网络库替代原生HttpURLConnection,简化网络请求代码
  • 可以增加字体文件合法性校验,比如检查文件大小、格式是否符合OTF标准

附:你的原始代码和报错日志

原始代码

textView.setText(getIntent().getStringExtra("name")); 
String path= getIntent().getStringExtra("font"); 
Typeface tf=Typeface.createFromFile(path); 
textView.setTypeface(tf);

Logcat报错日志

addFont failed to create font http://server/font/public/1526331572-font.otf
05-15 14:55:51.094 4245-4245/com.nani.font E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.nani.font, PID: 4245
java.lang.RuntimeException: Unable to start activity ComponentInfo{com.nani.font/com.nani.font.FinalActivity}: java.lang.RuntimeException: Font not found http://server/font/public/1526331572-font.otf
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2555)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2629)
at android.app.ActivityThread.access$800(ActivityThread.java:182)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1474)
at android.os.Handler.dispatchMessage(Handler.java:111)
at android.os.Looper.loop(Looper.java:194)
at android.app.ActivityThread.main(ActivityThread.java:5706)
at java.lang.reflect.Method.invoke(Native Method)
at java.lang.reflect.Method.invoke(Method.java:372)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1033)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:828)
Caused by: java.lang.RuntimeException: Font not found http://server/font/public/1526331572-font.otf
at android.graphics.Typeface.createFromFile(Typeface.java:250)
at com.nani.font.FinalActivity.onCreate(FinalActivity.java:29)
at android.app.Activity.performCreate(Activity.java:6092)
at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1112)
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2502)
... 11 more

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.27 09:56:56