Core utilities for building navigators in React Native applications
—
Utilities for creating navigation structures from static configuration objects, enabling declarative navigation setup and automatic path configuration generation.
Create a React component that renders a navigator based on static configuration, enabling declarative navigation setup.
/**
* Create a navigation component from static configuration
* @param tree - Static navigation configuration object
* @param displayName - Component display name for React DevTools
* @returns React component that renders the configured navigation
*/
function createComponentForStaticNavigation<T extends StaticNavigation<any, any, any>>(
tree: T,
displayName?: string
): React.ComponentType<{}>;
interface StaticNavigation<
ScreenOptions extends {},
EventMap extends EventMapBase,
NavigatorID extends string | undefined
> {
/** Configuration for screens in this navigator */
screens: StaticConfigScreens<any, ScreenOptions, EventMap>;
/** Navigator configuration */
config?: StaticConfig<ScreenOptions, EventMap, NavigatorID>;
/** Groups configuration */
groups?: Record<string, StaticConfigGroup<any, ScreenOptions>>;
}
interface StaticConfig<
ScreenOptions extends {},
EventMap extends EventMapBase,
NavigatorID extends string | undefined
> {
/** Navigator ID for getParent references */
navigationId?: NavigatorID;
/** Initial route name */
initialRouteName?: string;
/** Default screen options */
screenOptions?: ScreenOptions;
/** Screen layout component */
screenLayout?: React.ComponentType<any>;
/** Event listeners */
screenListeners?: any;
}
type StaticConfigScreens<
ParamList extends ParamListBase,
ScreenOptions extends {},
EventMap extends EventMapBase
> = {
[K in keyof ParamList]: StaticScreenProps<ParamList, K, ScreenOptions, EventMap>;
};
interface StaticScreenProps<
ParamList extends ParamListBase,
RouteName extends keyof ParamList,
ScreenOptions extends {},
EventMap extends EventMapBase
> {
/** Screen component to render */
component?: React.ComponentType<any>;
/** Lazy-loaded screen component */
getComponent?: () => React.ComponentType<any>;
/** Screen options */
options?: ScreenOptions;
/** Initial parameters */
initialParams?: ParamList[RouteName];
/** Event listeners */
listeners?: any;
/** Screen ID function */
getId?: ({ params }: { params: ParamList[RouteName] }) => string | undefined;
/** Navigation key */
navigationKey?: string;
/** Screen layout */
layout?: React.ComponentType<any>;
/** Children for nested navigation */
children?: StaticNavigation<ScreenOptions, EventMap, any>;
}Usage Examples:
import { createComponentForStaticNavigation } from "@react-navigation/core";
// Define static navigation configuration
const staticConfig = {
screens: {
Home: {
component: HomeScreen,
options: { title: 'Welcome' }
},
Profile: {
component: ProfileScreen,
options: { title: 'Profile' },
initialParams: { tab: 'info' }
},
Settings: {
getComponent: () => import('./SettingsScreen'),
options: { title: 'Settings' }
}
},
config: {
initialRouteName: 'Home',
screenOptions: {
headerStyle: { backgroundColor: '#6200ee' },
headerTintColor: 'white'
}
}
};
// Create navigation component
const AppNavigator = createComponentForStaticNavigation(
staticConfig,
'AppNavigator'
);
// Use in app
function App() {
return (
<BaseNavigationContainer>
<AppNavigator />
</BaseNavigationContainer>
);
}
// Nested navigation example
const nestedConfig = {
screens: {
Main: {
children: {
screens: {
Home: { component: HomeScreen },
Feed: { component: FeedScreen }
},
config: { initialRouteName: 'Home' }
}
},
Profile: {
component: ProfileScreen
}
},
config: {
initialRouteName: 'Main'
}
};
const NestedNavigator = createComponentForStaticNavigation(
nestedConfig,
'NestedNavigator'
);
// Groups configuration
const groupedConfig = {
screens: {
Home: {
component: HomeScreen,
options: { title: 'Home' }
},
Profile: {
component: ProfileScreen,
options: { title: 'Profile' }
},
Settings: {
component: SettingsScreen,
options: { title: 'Settings' }
}
},
groups: {
user: {
screens: ['Profile', 'Settings'],
screenOptions: {
headerStyle: { backgroundColor: 'blue' }
}
}
},
config: {
initialRouteName: 'Home'
}
};
const GroupedNavigator = createComponentForStaticNavigation(
groupedConfig,
'GroupedNavigator'
);Generate path configuration from static navigation configuration for deep linking support.
/**
* Create path configuration from static navigation for deep linking
* @param tree - Static navigation configuration
* @param options - Additional configuration options
* @param auto - Whether to automatically generate paths
* @returns Path configuration object for linking
*/
function createPathConfigForStaticNavigation(
tree: StaticNavigation<any, any, any>,
options?: { initialRouteName?: string },
auto?: boolean
): PathConfigMap<any>;Usage Examples:
import {
createPathConfigForStaticNavigation,
createComponentForStaticNavigation
} from "@react-navigation/core";
// Static navigation with path hints
const navigationConfig = {
screens: {
Home: {
component: HomeScreen,
// Path configuration can be inferred from screen name
},
Profile: {
component: ProfileScreen,
// Will generate path: '/Profile'
},
UserDetails: {
component: UserDetailsScreen,
// Will generate path: '/UserDetails'
}
},
config: {
initialRouteName: 'Home'
}
};
// Create path configuration automatically
const pathConfig = createPathConfigForStaticNavigation(
navigationConfig,
{ initialRouteName: 'Home' },
true // Auto-generate paths
);
// Result path config:
// {
// Home: '',
// Profile: 'Profile',
// UserDetails: 'UserDetails'
// }
// Manual path configuration with parameters
const manualConfig = {
screens: {
Home: { component: HomeScreen },
Profile: {
component: ProfileScreen,
// Add path metadata for parameter extraction
linkingPath: '/user/:userId'
},
Settings: {
component: SettingsScreen,
linkingPath: '/settings/:section?'
}
}
};
const manualPathConfig = createPathConfigForStaticNavigation(manualConfig);
// Use with navigation container
function App() {
const Navigator = createComponentForStaticNavigation(navigationConfig);
return (
<BaseNavigationContainer
linking={{
prefixes: ['https://myapp.com/', 'myapp://'],
config: {
screens: pathConfig
}
}}
>
<Navigator />
</BaseNavigationContainer>
);
}
// Complex nested navigation with paths
const complexConfig = {
screens: {
Auth: {
children: {
screens: {
Login: { component: LoginScreen },
Register: { component: RegisterScreen }
}
}
},
Main: {
children: {
screens: {
Home: { component: HomeScreen },
Profile: { component: ProfileScreen }
}
}
}
}
};
const complexPathConfig = createPathConfigForStaticNavigation(
complexConfig,
undefined,
true
);
// Result:
// {
// Auth: {
// screens: {
// Login: 'Login',
// Register: 'Register'
// }
// },
// Main: {
// screens: {
// Home: 'Home',
// Profile: 'Profile'
// }
// }
// }Core types for static navigation configuration.
/**
* Group configuration for organizing screens
*/
interface StaticConfigGroup<
ParamList extends ParamListBase,
ScreenOptions extends {}
> {
/** Screen names that belong to this group */
screens?: (keyof ParamList)[];
/** Options applied to all screens in the group */
screenOptions?: ScreenOptions;
/** Layout component for screens in the group */
screenLayout?: React.ComponentType<any>;
/** Navigation key for the group */
navigationKey?: string;
}
/**
* Parameter list type for static navigation
*/
type StaticParamList<T extends StaticNavigation<any, any, any>> =
T extends StaticNavigation<any, any, any>
? T['screens'] extends StaticConfigScreens<infer P, any, any>
? P
: ParamListBase
: ParamListBase;
/**
* Screen props type for static navigation screens
*/
type StaticScreenProps<
Navigation extends StaticNavigation<any, any, any>,
RouteName extends keyof Navigation['screens']
> = {
navigation: NavigationProp<StaticParamList<Navigation>, RouteName>;
route: RouteProp<StaticParamList<Navigation>, RouteName>;
};Usage Examples:
// Type-safe static navigation configuration
interface AppParamList {
Home: undefined;
Profile: { userId: string };
Settings: { section?: string };
}
const typedConfig: StaticNavigation<
{ title?: string; headerShown?: boolean },
{},
undefined
> = {
screens: {
Home: {
component: HomeScreen,
options: { title: 'Welcome' }
},
Profile: {
component: ProfileScreen,
options: { title: 'Profile' },
initialParams: { userId: 'default' }
},
Settings: {
component: SettingsScreen,
options: { title: 'Settings' }
}
} satisfies StaticConfigScreens<AppParamList, any, any>,
config: {
initialRouteName: 'Home',
screenOptions: { headerShown: true }
}
};
// Type-safe screen components
function ProfileScreen({
navigation,
route
}: StaticScreenProps<typeof typedConfig, 'Profile'>) {
// route.params is typed as { userId: string }
const { userId } = route.params;
return (
<View>
<Text>User ID: {userId}</Text>
<Button
title="Go to Settings"
onPress={() => navigation.navigate('Settings', { section: 'account' })}
/>
</View>
);
}
// Groups with type safety
const groupedTypedConfig = {
...typedConfig,
groups: {
user: {
screens: ['Profile', 'Settings'] as const,
screenOptions: {
headerStyle: { backgroundColor: '#007AFF' }
}
}
}
};Using static navigation with the navigation container and linking configuration.
// Complete app setup with static navigation and deep linking
function createAppWithStaticNavigation() {
const navigationConfig = {
screens: {
Home: { component: HomeScreen },
Profile: { component: ProfileScreen },
Settings: { component: SettingsScreen }
},
config: {
initialRouteName: 'Home'
}
};
const Navigator = createComponentForStaticNavigation(
navigationConfig,
'AppNavigator'
);
const pathConfig = createPathConfigForStaticNavigation(
navigationConfig,
{ initialRouteName: 'Home' },
true
);
return function App() {
return (
<BaseNavigationContainer
linking={{
prefixes: ['myapp://'],
config: { screens: pathConfig }
}}
>
<Navigator />
</BaseNavigationContainer>
);
};
}
const App = createAppWithStaticNavigation();Install with Tessl CLI
npx tessl i tessl/npm-react-navigation--core