资源缓存


本节涵盖与在应用中加载资源相关的所有内容,从与应用二进制文件打包到缓存、预加载和发布。

🌐 This section covers all things related to loading assets in your apps, from bundling with an app binary, to caching, pre-loading and publishing.

打包资源

🌐 Bundling assets

将资源打包到你的二进制文件中将提供最佳的用户体验,因为你的资源可以立即使用。这样,你的应用无需向 CDN 发起网络请求来获取已发布的资源,而是从本地磁盘获取,从而实现更快、更高效的加载体验。打包资源还可以实现离线功能。

🌐 Bundling assets into your binary will provide the best user experience as your assets will be available immediately. Instead of having to make a network request to the CDN to fetch your published assets, your app will fetch them from the local disk resulting in a faster, more efficient loading experience. Bundling assets also allows offline functionality.

要将资源打包到二进制文件中,请在 app.json 中使用 assetBundlePatterns 键来提供项目目录中的路径列表:

🌐 To bundle assets in your binary, use the assetBundlePatterns key in app.json to provide a list of paths in your project directory:

"assetBundlePatterns": [ "assets/images/*" ],

下次你运行 eas build 时,路径与所给模式匹配的图片将被打包到你的本地二进制文件中。

🌐 Images with paths matching the given patterns will be bundled into your native binaries next time you run eas build.

注意:如果你的应用包含异常数量的资源或大小异常大的资源,资源打包可能不是最佳解决方案,因为这会导致你的应用体积膨胀。在这种情况下,请有选择地打包那些必需的资源,其余资源则存储在 CDN 上。

预加载和缓存资源

🌐 Pre-loading and caching assets

资源的缓存方式取决于它们的存储位置和使用方式。本节提供了最佳实践,以确保只有在需要时才下载资源。为了在缓存资源时保持加载屏幕可见,建议在所有内容准备就绪之前渲染一个 启动屏幕

🌐 Assets are cached differently depending on where they are stored and how they are used. This section offers best practices to ensure you only download assets when needed. To keep the loading screen visible while caching assets, it's a good idea to render a SplashScreen until everything is ready.

要下载并缓存保存到本地文件系统的图片,请使用 Asset.fromModule(image).downloadAsync()。对于带有远程 URL 的图片,请使用 Image.prefetch(image)

🌐 To download and cache the images saved to the local filesystem, use Asset.fromModule(image).downloadAsync(). For images with remote URLs, use Image.prefetch(image).

字体使用 Font.loadAsync(font) 预加载。此方法中的 font 参数是一个对象,例如:{OpenSans: require('./assets/fonts/OpenSans.ttf')}@expo/vector-icons 为此对象提供了一个方便的快捷方式,如以下例子中的 FontAwesome.font

🌐 Fonts are pre-loaded using Font.loadAsync(font). The font argument in this method is an object such as: {OpenSans: require('./assets/fonts/OpenSans.ttf')}. @expo/vector-icons provides a helpful shortcut for this object as FontAwesome.font in the following example:

Pre-loading and Caching Assets
import React, { useState, useEffect } from 'react'; import { View, Text, Image, StyleSheet } from 'react-native'; import * as SplashScreen from 'expo-splash-screen'; import * as Font from 'expo-font'; import { Asset } from 'expo-asset'; import FontAwesome from '@expo/vector-icons/FontAwesome'; function cacheImages(images) { return images.map(image => { if (typeof image === 'string') { return Image.prefetch(image); } else { return Asset.fromModule(image).downloadAsync(); } }); } function cacheFonts(fonts) { return fonts.map(font => Font.loadAsync(font)); } export default function App() { const [appIsReady, setAppIsReady] = useState(false); // Load any resources or data that you need before rendering the app useEffect(() => { async function loadResourcesAndDataAsync() { try { SplashScreen.preventAutoHideAsync(); const imageAssets = cacheImages([ 'https://www.google.com/images/branding/googlelogo/2x/googlelogo_color_272x92dp.png', require('./assets/images/circle.jpg'), ]); const fontAssets = cacheFonts([FontAwesome.font]); await Promise.all([...imageAssets, ...fontAssets]); } catch (e) { // You might want to provide this error information to an error reporting service console.warn(e); } finally { setAppIsReady(true); SplashScreen.hideAsync(); } } loadResourcesAndDataAsync(); }, []); if (!appIsReady) { return null; } return ( <View style={styles.container}> <Text>Hello world, this is my app.</Text> </View> ); } const styles = StyleSheet.create({ container: { flex: 1, backgroundColor: '#fff', alignItems: 'center', justifyContent: 'center', }, });

如需使用本地图片资源,你可以在项目中继续正常引用图片来源,例如:

🌐 To use the local image asset, you can continue referencing the source of the image normally in your project, for example:

<Image source={require('path/to/image.png')} />

请参阅 Expo 的标签模板项目 中的完整工作示例。你也可以运行 npx create-expo-app --template tabs 来使用相同的模板设置本地项目。

🌐 See the complete working example in Expo's tabs template project. You can also run npx create-expo-app --template tabs to set up a local project with the same template.