React Native List View Does not Render - react-native

My code:
const tabscreen = (screen, path, label, src) => {
return {
screen, path,
navigationOptions: {
tabBarLabel: label,
tabBarIcon: ({
tintColor,
focused = true
}) => (<TabIcon src={src} active={focused}/>),
}
};
};
const MainTab = TabNavigator({
Home: tabscreen(HomeScreen, '/home', 'home', 'home'),
Chat: tabscreen(ChatScreen, '/chat', 'chat', 'chat'),
Find: tabscreen(FindScreen, '/find', 'find', 'find'),
Profile: tabscreen(ProfileScreen, '/profile', 'find', 'profile')
}, {
tabBarPosition: 'bottom',
swipeEnabled: false,
animationEnabled: false,
lazy: false,
//...other configs
tabBarOptions: {
// tint color is passed to text and icons (if enabled) on the tab bar
activeTintColor: '#1BBC9B',
inactiveTintColor: '#9B9B9B',
showIcon: true,
style: {
backgroundColor: '#F4F4F4',
borderTopWidth: 0,
height: 49
},
labelStyle: {
marginTop: 0,
marginLeft: 0,
marginRight: 0,
marginBottom: 1.5
}
}
});
const AppNavigator = StackNavigator({
Main: {
screen: MainTab ,
path: '/',
navigationOptions: {
header: null,
headerVisible: false,
gesturesEnabled: false,
}
},
}, {
initialRouteName: 'Main',
mode: 'card',
headerMode: 'screen',
navigationOptions: {
headerVisible: false,
gesturesEnabled: true,
headerStyle: styles.headerStyle,
headerTitleStyle: styles.headerTitleStyle,
headerTintColor: 'white',
headerBackTitle: null,
}
});
This demo uses redux to control state.
In the FindScreen, I use the List view to render a list. The problem is when I click the Find tab. The List view does not render. I have to first swipe the screen, then the List view show.
I used connect of redux-react to map the dispatch to FindScreen component. I request the data source of the List view in the componentDidMount lifecycle hook.
componentWillReceiveProps(nextProps) {
if( nextProps.doctorList !== this.props.doctorList){
debugger;
this.setState({
isRefreshing: false,
dataSource: this.state.dataSource.cloneWithRows(nextProps.doctorList),
})
}
}
As the code above, I set the debugger in the componentWillReceiveProps lifecycle hook. The breakpoint stops at the line of the debugger. Now, I know I request the data from the backend well.
Do you know the reason of the List view does not render?
What can I do to show the List view in the first render?
I know one way of solving this problem is change lazy: false, to lazy: true. Due to the lazy: false is written by my leader, so I had better not change it.

Add removeClippedSubviews={false} to your ListView.
You can refer to https://github.com/react-community/react-navigation/issues/1279 for the fix.
Please note that this is not an ideal fix because this is disabling a performance optimization.
You can read about the performance optimization here https://facebook.github.io/react-native/docs/listview.html#removeclippedsubviews

Related

React navigation v1 hide an item in tab bar

I am using React navigation v1, I have a bottom tab bar set up like this
const HomeTabs = TabNavigator(
{
Startside: {
screen: MessagesList,
navigationOptions: { tabBarTestIDProps: { accessibilityLabel: "Hjem" } },
},
NewMessage: {
screen: NewMessage,
navigationOptions: {
tabBarTestIDProps: { accessibilityLabel: "Skriv melding" },
},
},
ClassList: {
screen: ClassList,
navigationOptions: {
tabBarTestIDProps: { accessibilityLabel: "Klasseliste" },
},
},
Archive: {
screen: Archive,
navigationOptions: { tabBarTestIDProps: { accessibilityLabel: "Arkiv" } },
},
Settings: {
screen: Settings,
navigationOptions: {
tabBarTestIDProps: { accessibilityLabel: "Innstillinger" },
},
},
},
{
navigationOptions: ({ navigation }) => ({
headerStyle: {
elevation: 0,
shadowOpacity: 0,
},
}),
tabBarOptions: {
showLabel: false,
style: {
borderTopColor: "rgba(0, 0, 0, 0.1)",
},
},
tabBarComponent: TabBarBottom,
// tabBarComponent: (props) => <CustomTabsNavigator isAdmin={false} />,
tabBarPosition: "bottom",
animationEnabled: false,
swipeEnabled: false,
focused: true,
lazy: false,
initialRouteName: "Startside",
}
);
Then I am included in the stack navigator like this
const MainStack = StackNavigator(
{
ContactSelector: {
screen: ContactSelector,
}
},
{
focused: true,
lazy: true,
initialRouteName: "Login",
navigationOptions: {
headerStyle: {
elevation: 0,
shadowOpacity: 0,
},
},
cardStyle: {
shadowColor: "transparent",
},
}
);
What I want is to show a tab bar item only certain users. Is it possible? I have been searching and searching but can't find anything and it seems like impossible. Any pointers?
"react-native": "^0.59.10"
React Navigation 1.x
I strongly recommend you to upgrade react navigation version. I am not sure what you want is achievable but maybe you can try something like this:
//TabNavigator takes an object as parameter
//so basically you need to update that object based on some condition
//you want. For instance you display the Admin tab only if user is authenticated
const Tabs = {
Startside: {
screen: MessagesList,
navigationOptions: { tabBarTestIDProps: { accessibilityLabel: "Hjem" } },
},
NewMessage: {
screen: NewMessage,
navigationOptions: {
tabBarTestIDProps: { accessibilityLabel: "Skriv melding" },
},
},
ClassList: {
screen: ClassList,
navigationOptions: {
tabBarTestIDProps: { accessibilityLabel: "Klasseliste" },
},
},
Archive: {
screen: Archive,
navigationOptions: { tabBarTestIDProps: { accessibilityLabel: "Arkiv" } },
},
Settings: {
screen: Settings,
navigationOptions: {
tabBarTestIDProps: { accessibilityLabel: "Innstillinger" },
},
},
}
//if some condition is met add the Admin tab to the navigator
if(authenticated) {
tabs.Admin : {
screen: Admin
}
}
const HomeTabs = TabNavigator(tabs)

How to use "createStackNavigator" and "createMaterialTopTabNavigator" together?

On my react native app i was using "createStackNavigator" but when i combine "createMaterialTopTabNavigator" it gives Error. How can i use both navigation ? I tried aolot but did not able to resolve this issue. In my code i use createStackNavigator two times one for home and other for tabScreen both work fine when i use seperatly it work but cannot able to combine.
Main.js
const Home = createStackNavigator(
{
Profile: Profile,
Feed: Feed,
Chemein: Chemein,
Graph: Graph,
},
{
initialRouteName: 'Profile',
defaultNavigationOptions: {
headerStyle: {
backgroundColor: '#744DD2',
},
headerTintColor: '#fff',
headerTitleStyle: {
fontWeight: 'bold',
},
},
},
);
const TabScreen = createMaterialTopTabNavigator(
{
Clubs: { screen: Clubs },
Members: { screen: Members },
},
{
tabBarPosition: 'top',
swipeEnabled: true,
tabBarOptions: {
activeTintColor: '#ffff',
inactiveTintColor: '#ccc',
style: {
backgroundColor: '#744DD2',
},
},
}
);
const TopTab = createStackNavigator({
TabScreen: {
screen: TabScreen,
navigationOptions: {
headerStyle: {
backgroundColor: '#744DD2',
},
headerTintColor: '#FFFFFF',
title: 'Clubs',
},
},
});
const container = createAppContainer(Home);
// const container = createAppContainer(TabScreen );
export default container;
Ive done somthing like this :
const TabNavigator = createBottomTabNavigator(
{
Home: AppStack,
Notification: Notifications,
Account: SettingsScreen,
},
{
defaultNavigationOptions: ({navigation}) => ({
tabBarIcon: ({focused, tintColor}) =>
getTabBarIcon(navigation, focused, tintColor),
}),
tabBarOptions: {
activeTintColor: colors.tealC,
inactiveTintColor: 'gray',
},
},
);
And my appstack is my stack navigator with the code below :
const AppStack = createStackNavigator(
{
HomeScreen: {
screen: Home,
},
AirportMeeting: {
screen: AirportMeeting,
},
MeetingPoint: {
screen: MeetingPoint,
},
DriverDetails: {
screen: DriverDetails,
},
SightSeeing: {
screen: SightSeeing,
},
HotelDetails: {
screen: HotelDetails,
},
FlightDetails: {
screen: FlightDetails,
},
AddSight: {
screen: AddSight,
},
SightSeeingPurchase: {
screen: SightSeeingPurchase,
},
AddMeals: {
screen: AddMeals,
},
HomeCard: {
screen: HomeCard,
},
Trips: {
screen: Trips,
},
FAQ: {
screen: FAQ,
},
Support: {
screen: Support,
},
BeforeTravel: {
screen: BeforeTravel,
},
Weather: {
screen: Weather,
},
},
{
defaultNavigationOptions: {
headerShown: false,
},
initialRouteName: 'HomeCard',
transitionConfig: () => fromRight(),
},
);
So basically in my home route of tabnavigator ive used Appstack which is a stack navigator.
Just in case you are curious, ive alos made a switchnavigator where ive added tab navigator and other stack navigtors too, so everythings possible:
const navigation = createAppContainer(
createSwitchNavigator(
{
App: TabNavigator,
Auth: AuthStack,
SplashScreen: SplashScreen,
},
{
initialRouteName: 'SplashScreen',
},
),
);

How to update All Tab Navigation title dynamically?

I have 3 Tabs Tab1, Tab2 and Tab3. How can I Change this Tab title dynamically form any tab.
Below is My Code..
const TabNav = createBottomTabNavigator(
{
TabName1: {
header: null,
screen: StackNav1,
navigationOptions: ({ navigation }) => ({
title: 'Tab1',
header: null,
tabBarIcon: ({ tintColor }) => {
return;
}
})
},
TabName2: {
header: null,
screen: StackNav2,
navigationOptions: ({ navigation }) => ({
title: 'Tab2'
})
},
TabName3: {
screen: StackNav3,
navigationOptions: ({ navigation }) => ({
header: null,
title: 'Tab3'
})
}
},
{
initialRouteName: "TabName1",
tabBarPosition: "bottom",
headerMode: "none",
swipeEnabled: false,
animationEnabled: false,
lazy: true,
removeClippedSubviews: true,
order: ["TabName1", "TabName2", "TabName3"],
backBehavior: "initialRoute",
}
);
Please help me how can change Tab title dynamically.
Thanks,

Is there any way to scroll react navigation tabNavigator header?

Want to scroll tab navigator header options left and right. Only want to scroll the options not the component. Is there any way?
const MyNav = TabNavigator({
News: { screen: NewsScreen },
Videos: { screen: VideosScreen },
Bands: { screen: BandsScreen },
Jokes: { screen: JokesScreen },
}, {
tabBarPosition: 'top',
animationEnabled: true,
tabBarOptions: {
activeTintColor: '#e91e63',
},
});
add this to taBarOptions
scrollEnabled: true

TabNavigator: Style tab label based on target platform

I'm using react-native TabNavigator to navigate between tabs in my application.
const TabNav = TabNavigator({
Home: {
screen: HomeScene,
navigationOptions:{
tabBar: {
label: 'Home',
icon: ({ focused }) => {
let imgSource = focused
? require('../common/img/selected-home-75.png')
: require('../common/img/unselected-home-75.png');
return <Image
source={imgSource}
style={tabBarStyles.icon}
/>
}
}
}
},
...
}, {
swipeEnabled: false,
tabBarOptions: {
showIcon: true,
upperCaseLabel: false,
labelStyle: tabBarStyles.labelStyle,
style: tabBarStyles.style
}
});
Each tab contains an icon and a label. I would like to style the TabBar slightly differently depending on whether the application is running on iOS or Android.
The documentation for "tabNavigationConfig describes two sections of "tabBarOptions" for "TabBarBottom" and "TabBarTop" which makes me think it IS possible to provide a configuration for the top TabBar and another for the bottom TabBar.
Is it possible to provide "tabBarOptions" for iOS and different options for Android (ie top and bottom)?
It's possible to apply options based on the platform with usage of:
import {Platform} from 'react-native';
So you can assign a separate options for each platform based on the Platform.OS value :
const iosTabBarOptions = {
showIcon: false,
upperCaseLabel: false,
labelStyle: tabBarStyles.labelStyle,
style: tabBarStyles.style
};
const androidTabBarOptions = {
showIcon: true,
upperCaseLabel: true,
labelStyle: tabBarStyles.labelStyle,
style: tabBarStyles.style
};
tabBarOptions: Platform.OS === 'ios'
? iosTabBarOptions
: androidTabBarOptions