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

如何在React Native Expo项目中全局修改默认字体

全局修改Expo项目默认字体(无需逐个组件设置)

我想修改项目的默认字体,不想给每个组件单独添加font-family样式,但找不到全局修改的相关文档。我已经按要求加载了字体,也在theme文件夹的index.ts里配置了字体,代码如下:

app/_layout.ts

import FontAwesome from "@expo/vector-icons/FontAwesome";
// import { useFonts } from "expo-font";
import { Stack } from "expo-router";
import * as SplashScreen from "expo-splash-screen";
import { useEffect } from "react";
import { ThemeProvider } from "styled-components";
import { Urbanist_400Regular, useFonts } from "@expo-google-fonts/urbanist";
// import { Anton_400Regular, useFonts } from "@expo-google-fonts/anton";
import { theme } from "@/constants/theme";

export {
  // Catch any errors thrown by the Layout component.
  ErrorBoundary,
} from "expo-router";

// Prevent the splash screen from auto-hiding before asset loading is complete.
SplashScreen.preventAutoHideAsync();

export default function RootLayout() {
  const [loaded, error] = useFonts({
    Urbanist_400Regular,
  });

  // Expo Router uses Error Boundaries to catch errors in the navigation tree.
  useEffect(() => {
    if (error) throw error;
  }, [error]);

  useEffect(() => {
    if (loaded) {
      SplashScreen.hideAsync();
    }
  }, [loaded]);

  if (!loaded) {
    return null;
  }

  return <RootLayoutNav />;
}

function RootLayoutNav() {
  return (
    <ThemeProvider theme={theme}>
      <Stack>
        <Stack.Screen name="index" options={{ headerShown: false }} />
        <Stack.Screen name="(auth)" options={{ headerShown: false }} />
        {/* <Stack.Screen name="(tabs)" options={{ headerShown: false }} /> */}
      </Stack>
    </ThemeProvider>
  );
}

assets/fonts/index.ts

import { colors } from "./colors";
import { space, lineHeights } from "./spacing";
import { sizes } from "./sizes";
import { fonts, fontSizes, fontWeights } from "./fonts";
import { DefaultTheme } from "styled-components";

export const theme = {
  colors,
  space,
  lineHeights,
  sizes,
  fonts,
  fontSizes,
  fontWeights,
};

fonts.ts

export const fonts = {
  body: "Urbanist_400Regular",
  heading: "Urbanist_400Regular",
  monospace: "Urbanist_400Regular",
};

export const fontWeights = {
  regular: 400,
  medium: 500,
  bold: 700,
};

export const fontSizes = {
  caption: "12px",
  button: "14px",
  body: "16px",
  title: "20px",
  h5: "24px",
  h4: "34px",
  h3: "45px",
  h2: "56px",
  h1: "112px",
};

解决方法

你已经完成了字体加载和theme配置,差最后一步:通过styled-components的全局样式注入字体规则。

1. 创建全局样式文件

在项目中新建constants/GlobalStyle.ts,内容如下:

import { createGlobalStyle } from "styled-components";

const GlobalStyle = createGlobalStyle`
  /* 给所有元素设置默认字体 */
  * {
    font-family: ${props => props.theme.fonts.body}, sans-serif;
  }

  /* 确保原生组件继承字体 */
  input, textarea, button, select {
    font-family: inherit;
  }
`;

export default GlobalStyle;

2. 在根布局中引入全局样式

修改app/_layout.ts里的RootLayoutNav组件,在ThemeProvider内部添加GlobalStyle:

// 新增导入
import GlobalStyle from "@/constants/GlobalStyle";

function RootLayoutNav() {
  return (
    <ThemeProvider theme={theme}>
      <GlobalStyle /> {/* 添加这一行 */}
      <Stack>
        <Stack.Screen name="index" options={{ headerShown: false }} />
        <Stack.Screen name="(auth)" options={{ headerShown: false }} />
        {/* <Stack.Screen name="(tabs)" options={{ headerShown: false }} /> */}
      </Stack>
    </ThemeProvider>
  );
}

3. 可选:区分标题和正文字体

如果需要给标题单独设置字体,修改全局样式:

const GlobalStyle = createGlobalStyle`
  * {
    font-family: ${props => props.theme.fonts.body}, sans-serif;
  }

  h1, h2, h3, h4, h5, h6 {
    font-family: ${props => props.theme.fonts.heading}, sans-serif;
  }

  input, textarea, button, select {
    font-family: inherit;
  }
`;

重新运行项目后,所有组件会自动使用你配置的字体,无需逐个设置font-family。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.28 19:13:17