9

I am using Expo and the create-react-native app. I enjoy the live/hot reloading feature on my phone, but I'm wondering about custom fonts.

https://docs.expo.io/versions/v17.0.0/guides/using-custom-fonts.html#loading-the-font-in-your-app

The API for Expo only has directions to load them asynchronously. Do I have to do this on every component I want a custom font on? This seems like it would cause some unnecessary calls when I've already loaded it once.

Is there a way to set the font as global or pass it via props once loaded? It seems like they suggest this approach via their last line in that link:

Note: Typically you will want to load your apps primary fonts before the app is displayed to avoid text flashing in after the font loads. The recommended approach is to move the Font.loadAsync call to your top-level component.

...But they give no explanation on HOW to do that, if that's what they are implying.

So my questions are:

1) Does loading the custom font in multiple times (on each component), cause performance issues? (or maybe it's pulled from cache after the first?)

2) After loading it can you pass the font down via properties or set it as a global?

and finally

3) Is this an Expo only issue? Or a create-react-native app only issue? Or just a livereload/hotloading issue?

Also note, I'm working on Windows/Android

4

3 回答 3

9

1)你应该只加载一次字体。正如您所指出的,Expo 建议将 Font.loadAsync 方法放在顶级组件的 componentDidMount() 方法中。

您所指的性能问题可能是异步调用背后发生的魔力——但同样,这应该只发生一次。

2)从那时起,您可以在任何子组件中使用字体,使用<Text>. 正如他们的示例(我稍作修改)所示:

首先在顶层组件中加载字体。

export default class App extends React.Component {
  componentDidMount() {
    Font.loadAsync({
      'open-sans-bold': require('./assets/fonts/OpenSans-Bold.ttf'),
    });
  }

  render() {
    return (
       <HelloWorld />
    )
  }
}

然后在应用程序的任何组件中使用它。(在字体加载之前,您会看到系统字体 - iOS 上的 San Francisco,Android 上的 Roboto。这就是为什么 Expo 建议设置加载状态...以避免在系统字体和新加载的自定义字体之间出现尴尬的闪烁。 )

export default class HelloWorld extends React.Component {
  render() {
    <Text style={{ fontFamily: 'open-sans-bold', fontSize: 56 }}>
      Hello, world!
    </Text>
  }
}

3)这是一个与世博会相关的“问题”(或解决方案......取决于你如何看待它)。例如,在 iOS 上,添加自定义字体涉及几个步骤(将字体文件添加到本机项目,确保字体显示在 Bundle Resources 中,将字体添加到 Info.plist...)。不确定 Android 的流程是什么,但它是不同的,可能也很烦人。

Expo 使用他们的 Font 模块将其抽象化,它允许您做一件事 - 并跨平台获得相同的结果。这很酷,在我的书中。

于 2017-07-07T03:18:28.237 回答
1

要有效地使用字体(expo),您可以在最根组件中加载字体,并且在加载时您可以 在全局状态 [Redux] 中更新状态fontLoaded:true 。

我在媒体上对此进行了很好的解释,请参阅此

希望这可以帮助。

于 2018-03-23T15:13:21.327 回答
1

我知道线程很旧,但这也可能对其他人有帮助。直接使用Font.asyncLoad()会导致系统字体错误

fontFamily "roboto-medium" 不是系统字体,没有通过 Font.loadAsync 加载

export default class App extends React.Component {

    state = {
        assetsLoaded: false,
    };

    async componentDidMount() {
        await Font.loadAsync({
            'roboto-medium': require('./assets/fonts/Roboto-Medium.ttf')
        });

        this.setState({ assetsLoaded: true });
    }

    render() {

        const {assetsLoaded} = this.state;

        if( assetsLoaded ) {
            return (
                <View style={styles.container}>
                    <Text style={styles.heading}>Custom Roboto Font</Text>
                    <Text style={{fontSize: 40}}>Default Font</Text>
                </View>
            );
        }
        else {
            return (
                <View style={styles.container}>
                    <ActivityIndicator />
                    <StatusBar barStyle="default" />
                </View>
            );
        }
    }
}

如果您想了解更多详细信息,请点击链接。

https://webomnizz.com/add-custom-font-to-react-native-using-expo/

于 2019-10-07T09:05:44.650 回答