Expo Web: @expo/vector-icons icons not loading after npx expo export -p web (Failed to decode downloaded font)
18:06 04 Sep 2025

I'm building a React Native app using Expo and deploying it as a static web app with expo-router. Everything works fine on iOS and Android, but when I build for web using:

npx expo export -p web

My app builds successfully and deploys to Firebase Hosting, but on the browser console I get:

Failed to decode downloaded font: https://shopping-list-08090208.web.app/assets/node_modules/@expo/vector-icons/MaterialIcons.ttf?platform=web&hash=...
OTS parsing error: invalid sfntVersion: 1008813135

And all my MaterialIcons, Entypo, and other icons fail to render. What I’ve Tried:

1. Tried manually loading icon fonts

I used Font.loadAsync in app/_layout.tsx:

await Font.loadAsync({
  'Material Icons': require('../assets/fonts/MaterialIcons.ttf'),
  'Material Design Icons': require('../assets/fonts/MaterialCommunityIcons.ttf'),
  Entypo: require('../assets/fonts/Entypo.ttf'),
});

Still fails on web, and throws "Failed to decode downloaded font" in the console.

2. Tried overriding loadFont() manually

(MaterialIcons as any).loadFont = async () => {};

Did not fix the problem.

3. Verified app.config.js

assetBundlePatterns: ['**/*']

Fonts are correctly included in the exported /dist/assets folder.

Environment

  • Expo SDK: 51
  • expo-router: latest
  • @expo/vector-icons: bundled with Expo
  • Deployment: Firebase Hosting (expo export:web)
  • Platform: Web only (iOS/Android fine)

Expected Behavior

Icons from @expo/vector-icons (MaterialIcons, Entypo, etc.) should display correctly after expo export:web and deployment.

Actual Behavior

Fonts fail to load and icons do not render.
Console shows Failed to decode downloaded font and OTS parsing error.

Happens only on web after export.

Assumptions

  • Maybe Expo isn’t preloading the vector icon fonts on web?
  • Firebase Hosting isn’t serving .ttf fonts with the correct Content-Type?
  • I need to call .loadFont() for each icon set before rendering?

Question

How do I properly preload @expo/vector-icons fonts for web builds with expo-router? Do I need to change anything in app.config.js or firebase.json?

app.config.js:

    import 'dotenv/config';
    process.env.EXPO_ROUTER_APP_ROOT = 'app';
    
    export default {
      expo: {
        name: 'Shopping List',
        slug: 'shopping-list',
        version: '1.0.0',
        orientation: 'portrait',
        icon: './app/assets/images/icon.png',
        scheme: 'shoppinglist',
        userInterfaceStyle: 'automatic',
        platforms: ['ios', 'android', 'web'],
        android: {
          package: '...',
          googleServicesFile: './google-services.json',
          intentFilters: [
            {
              action: 'VIEW',
              data: [
                { scheme: 'shoppinglist' },
                {
                  scheme: 'https',
                  host: '...',
                },
              ],
              category: ['BROWSABLE', 'DEFAULT'],
            },
          ],
        },
        web: {
          bundler: 'metro',
          output: 'static',
          favicon: './app/assets/images/icon.png',
        },
        assetBundlePatterns: ['**/*'],
        extra: {
          eas: {
            projectId: '...',
          },
        },
        plugins: [
          'expo-router',
          ['expo-build-properties', { ios: { useFrameworks: 'static' } }],
          '@react-native-firebase/app',
          '@react-native-firebase/auth',
        ],
        experiments: {
          typedRoutes: true,
        },
      },
    };
    
    ```
    firebase.json:```{
      "hosting": {
        "public": "dist",
        "ignore": ["firebase.json", "**/.*", "**/node_modules/**"],
        "rewrites": [{ "source": "**", "destination": "/index.html" }],
        "headers": [
          {
            "source": "**/*.ttf",
            "headers": [{ "key": "Content-Type", "value": "font/ttf" }]
          }
        ]
      }
    }

This is how I load the icons:

    import { MaterialIcons } from '@expo/vector-icons';   
    

Is there a correct way to make Expo load these fonts during static export so icons render correctly?

Icons render fine in dev but not after expo export -p web.

android firebase react-native fonts expo