How to access nested screen using expo linking - react-native

Here you can see in the last I tried to pass the URL of PaymenntMethod screen which is already defined in the stacks, I have the structure like this I am using the tabs in my react native application Home > More (Tab) > MyWallet (Screen) > PaymentMethod (Screen)
export const WalletStackScreen = () => {
return (
<EnterprisePromotionStack.Navigator screenOptions={stackOptions}>
<EnterprisePromotionStack.Screen name='MyWallet' component={MyWallet} />
<EnterprisePromotionStack.Screen name='PaymentMethod' component={PaymentMethod} />
</EnterprisePromotionStack.Navigator>
)
}
Above I mentioned the stacks, and the linking config are as follows
export const LinkingConfig = {
prefixes: [Linking.createURL('/')],
config: {
screens: {
Home: {
path: 'home',
screens: {
'PROMOTIONS': {
path:'Promotions',
screens: {
PromotionDetails:':id'
}
},
'MENU': {
path: 'More/MyWallet',
// screens: 'PaymentMethod'
screens: {
PaymentMethod: ''
}
},
}
},
Login: 'login'
}
}
}
I want the exact structure and the path which will be redirected to PaymentMehod Screen

Related

React Navigation dynamic screens and deep linking

I want to create dynamically tab screens with react navigation, but I don't know how to figure it out with the deep linking.
I would like to have my tabs screens accessible with deeplinking like : /tabs/:tabId but I don't know how to deal with the linking config.
If there is someone who can help me, I have created this snack :
https://snack.expo.dev/#natinho68/getting-started-%7C-react-navigation
First you need to set it up via documentation
This is minimal example. Root stack is a stack navigator which has 3 screens: Splash, Login and App. And App is another stack navigator(nested) with 2 screens: Dashboard and Login.
const deepLinkDevPrefix = "https://custom.server.org"
const deepLinkLocalProtocol = "customprotocol://"
const deepLinkConfig = {
screens: {
Splash: "Splash",
Login: "Login",
App: {
path: "App",
screens: {
Dashboard: "Dashboard",
Profile: "Profile,
},
},
}
}
Inside of getInitialURL you can handle url that opened the app.
const App = () => {
const getInitialURL = async () => {
// Check if app was opened from a deep link
const url = await Linking.getInitialURL();
console.log('This is url')
console.log(url)
if (url !== null) {
return url;
}
return undefined
}
const linking = {
prefixes: [deepLinkDevPrefix, deepLinkLocalProtocol],
deepLinkConfig,
getInitialURL
};
return (
<NavigationContainer linking={linking}>
<RootStack />
</NavigationContainer>
);
}
Here you can find out how to navigate without navigation prop.

Set navigator parameters from child navigator?

I have a Stack navigator (RecipesTab) nested in a Tab navigator (NavBar) and I'm trying to hide the Tab Bar on RecipeSite. My current solution is to pass showTabBar up the tree but I'm having trouble setting the navigation parameters for NavBar from RecipesTab. Wondering if it's possible to somehow call this.props.navigation.setParams({...}) from the RecipesTab navigator or pass parameters to NavBar from RecipesTab in another way.
//class RecipeList...
//class IngredientsTab...
class RecipeSite extends Component {
render() {
this.props.navigation.setParams({showTabBar: false});
return;
}
}
const RecipesTab = createStackNavigator(
{
Main: {
screen: RecipeList,
},
Site: {
screen: RecipeSite,
}
},
{
initialRouteName: 'Main',
}
);
export default NavBar = createBottomTabNavigator(
{
Recipe: {
screen: RecipesTab,
navigationOptions: ({ navigation }) => ({
tabBarVisible: navigation.getParam('showTabBar', true)
}),
},
Ingredient: {
screen: IngredientsTab,
}
},
);`
Basically I'm just trying to send data from RecipesTab to NavBar.

How to organize navigation structure in React Native?

I'm using react-navigation library. Currently the navigation is organized in this way:
App.js:
const Layout = createRootNavigator(signedIn);
return (
<AppFontLoader>
<Layout />
</AppFontLoader>
);
AppNavigator:
export const createRootNavigator = (signedIn = false) => {
return createSwitchNavigator(
{
SignedIn: {
screen: SignedIn
},
SignedOut: {
screen: SignedOut
}
},
{
initialRouteName: signedIn ? "SignedIn" : "SignedOut"
}
);
};
AppNavigator:
export const SignedIn = createMaterialBottomTabNavigator(
{
MeetingsScreen: {
...
}
MeetingsScreen:
const MeetingNavigator = createStackNavigator({
MeetingsListScreen: {
screen: MeetingsListScreen,
navigationOptions: {
}
},
AddMeetingForm: {
screen: AddMeetingFormScreen
},
MeetingScreen: {
screen: MeetingScreen
}
}, {initialRouteName: "MeetingsListScreen"});
The error is shown with the current structure:
You should only render one navigator explicitly in your app, and other navigators should by rendered by including them in that navigator.
Apparently, I shouldn't nest one navigator into another, but I'm struggling to come up with the right navigation structure.
How to organize the navigation so that I can have more layers of navigation to move between screens?
I've encountered the same issue, so what I ended up doing was just making one navigation. Rootstack. All routes are there. My app.js has only root stack and navigations.

Remove navigation header on screen for react native app

I want to remove header from my screen where I use bottom tab navigator.
Here is code example:
export class Home extends Component {
render() {
return <ProductList />;
}
}
export class Settings extends Component {
render() {
return <Chat />;
}
}
const Main = createBottomTabNavigator({
Home: {
screen: Home,
navigationOptions: {
header: null,
},
},
Settings: {
screen: Settings,
},
});
navigationOptions for header seams to be ignored
navigationOptions: {
header: null,
},
But when I use navigation option on single page without createBottomTabNavigator it works.
Any ideas?
You can use this instead of above
export class Home extends Component {
static navigationOptions = {
header: {
visible: false,
}
}
render() {
return <ProductList />;
}
}
export class Settings extends Component {
render() {
return <Chat />;
}
}
const Main = createBottomTabNavigator({
Home: {
screen: Home
},
Settings: {
screen: Settings,
},
},
{
headerMode: 'screen'
});
Hope this will help you

Set initialRouteName dynamically in React Navigation TabNavigator

I want to set initialRouteName of my TabNavigator dynamically in splash screen. In splash, i decide initialRouteName based on an api result but i don't know how to pass this route name to my router file.
Router.tsx:
public static Routes = StackNavigator({
Splash: { screen: Splash },
Verification: { screen: Verification },
Login: { screen: Login },
Main: {
screen: TabNavigator({
Calendar: { screen: Calendar },
PendingReserves: { screen: PendingReserves },
Profile: { screen: Profile },
},
{initialRouteName: 'Calendar'}) // I want to set it from splash
}
}, {initialRouteName: 'Splash'} );
splash.tsx:
constructor(props: SplashScreenProps, context: any) {
super(props, context);
this.state = {
Error: false
}
this.check()
}
check = async () => {
let pending = await dataService.getPendingReserves(data);
if (pending.Success) {
if (pending.result.length > 0) {
// go to pendingReserve Tab
} else {
// go to Calendar Tab
}
} else {
this.setState({ Error: true })
}
}
I tried to route statically to PendingReserves and in it's constructor, check the api and change tab if necessary but i couldn't change tab programmatically with this code:
pendingReserves.tsx:
fetchData = async () => {
let res = await Utilities.getPendingReserves()
if (res && res.length > 0) {
...
} else {
const resetAction = NavigationActions.reset({
index: 0,
actions: [NavigationActions.navigate({ routeName: 'Calendar' })]
})
this.props.navigation.dispatch(resetAction)
// this.props.navigation.navigate({ routeName: 'Calendar' })
// both reset and simple navigate are not works correctly...
}
}
So any solution for dynamically set initialRouteName OR change tab programmatically will help me. Thanks
I'm using:
"react-native": "0.49.3",
"react-navigation": "^1.0.0-beta.13"
Finally... I didn't find a way to change tab programmatically in react navigation version 1, so i update to version 2 and this.props.navigation.navigate('Calendar') works correctly.