React Native + Expo导入自定义字体时出现组件类型无效错误
React Native Expo导入自定义字体时出现组件类型无效错误
错误信息
Warning: React.jsx: type is invalid -- expected a string (for built-in components) or a class/function (for composite components) but got: %s.%s%s, undefined, You likely forgot to export your component from the file it's defined in, or you might have mixed up default and named imports. Check the render method of `Layout`., in Layout in Unknown (created by Route()) in Route (created by Route()) in LocationProvider (created by Route()) in Route() (created by RootRoute) in RootRoute (created by ContextNavigator) ...
代码示例(_layout.js)
import { Stack, NavigationContainer } from 'expo-router'; import { useCallback } from 'react'; import { useFonts } from 'expo-font'; import * as SplashScreen from 'expo-splash-screen'; import { Provider } from '../hook/context/auth'; import { LoginPage } from './(auth)/login'; SplashScreen.preventAutoHideAsync(); export default function Layout(){ const [fontsLoaded] = useFonts({ 'DMBold': require('../assets/fonts/DMSans-Bold.ttf'), 'DMMedium': require('../assets/fonts/DMSans-Medium.ttf'), 'DMRegular': require('../assets/fonts/DMSans-Regular.ttf'), }) const onLayoutRootView = useCallback(async() => { if(fontsLoaded){ await SplashScreen.hideAsync() } }, [fontsLoaded]) if(!fontsLoaded){ return null; // 加载启动屏 } return ( <Provider> <NavigationContainer> <Stack.Navigator onLayout={onLayoutRootView}> <Stack.Screen name="Login" component={LoginPage} /> </Stack.Navigator> </NavigationContainer> </Provider> ) }
项目结构

问题排查与解决方案
1. 检查自定义组件的导入导出匹配
错误核心是获取到undefined类型的组件,大概率是LoginPage或Provider的导入导出方式不匹配:
- 针对LoginPage:
若./(auth)/login.js中是默认导出(export default LoginPage),则导入时需去掉花括号:
若使用命名导出,确保login.js中的导出语句为:import LoginPage from './(auth)/login';export function LoginPage() { /* 组件内容 */ } - 针对Provider:
同理,检查../hook/context/auth.js中的Provider导出方式,默认导出则用import Provider from '../hook/context/auth';,命名导出需保持花括号导入且导出语句正确。
2. 移除冗余的NavigationContainer
Expo Router的Stack组件已内置导航容器,无需额外嵌套NavigationContainer,否则会引发导航上下文冲突。修改后的返回结构:
return ( <Provider> <Stack.Navigator onLayout={onLayoutRootView}> <Stack.Screen name="Login" component={LoginPage} /> </Stack.Navigator> </Provider> )
3. 优化字体加载逻辑(可选)
可改用import方式导入字体,避免require可能的路径问题:
import DMBold from '../assets/fonts/DMSans-Bold.ttf'; import DMMedium from '../assets/fonts/DMSans-Medium.ttf'; import DMRegular from '../assets/fonts/DMSans-Regular.ttf'; const [fontsLoaded] = useFonts({ 'DMBold': DMBold, 'DMMedium': DMMedium, 'DMRegular': DMRegular, })
内容的提问来源于stack exchange,提问作者code writer 3000
相关产品推荐
相关产品推荐

