React-navigation-redux-helpers error : This navigator has both navigation and container props, so it is unclear if it should own its own state - react-native

I am trying to integrate redux with react-navigation using react-navigation-redux-helpers in react-native with expo. However, though I followed the documentations I get the following error.
This navigator has both navigation and container props, so it is unclear if it should own its own state. Remove props: "nav" if the navigator should get its state from the navigation prop. If the navigator should maintain its own state, do not pass a navigation prop.
Following is my code related to the redux and react-navigation implementation.
AppNavigator.js
import React from 'react';
import {createSwitchNavigator, createStackNavigator} from 'react-navigation';
import {connect} from 'react-redux';
import {reduxifyNavigator,createReactNavigationReduxMiddleware} from "react-navigation-redux-helpers";
import MainTabNavigator from './MainTabNavigator';
export const AuthStack = createStackNavigator(
{
Main: MainTabNavigator,
},
{
headerMode: 'none'
}
);
export const AppNavigator = createSwitchNavigator(
{
Auth: AuthStack,
},
{
headerMode: 'none',
initialRouteName: 'Auth',
}
);
export const NavMiddleware = createReactNavigationReduxMiddleware(
"root",
state => state.nav,
);
const addListener = reduxifyNavigator(AppNavigator, 'root');
const mapStateToProps = state => ({
nav: state.nav,
});
export const AppWithNavigationState = connect(mapStateToProps)(addListener);
App.js
import React from 'react';
import {Platform, StatusBar, StyleSheet, View} from 'react-native';
import {AppLoading, Asset, Font, Icon} from 'expo';
import {AppWithNavigationState} from './navigation/AppNavigator';
import {applyMiddleware, createStore} from "redux";
import AppReducer from './reducers/AppReducer'
import {Provider} from "react-redux";
import {NavMiddleware} from './navigation/AppNavigator'
const store = createStore(AppReducer,applyMiddleware(NavMiddleware));
export default class App extends React.Component {
state = {
isLoadingComplete: false,
};
render() {
if (!this.state.isLoadingComplete && !this.props.skipLoadingScreen) {
return (
<AppLoading
startAsync={this._loadResourcesAsync}
onError={this._handleLoadingError}
onFinish={this._handleFinishLoading}
/>
);
} else {
return (
<View style={styles.container}>
{Platform.OS === 'ios' && <StatusBar barStyle="default" />}
<Provider store={store}>
<AppWithNavigationState/>
</Provider>
</View>
);
}
}
_loadResourcesAsync = async () => {
return Promise.all([
Asset.loadAsync([
require('./assets/images/robot-dev.png'),
require('./assets/images/robot-prod.png'),
]),
Font.loadAsync({
// This is the font that we are using for our tab bar
...Icon.Ionicons.font,
// We include SpaceMono because we use it in HomeScreen.js. Feel free
// to remove this if you are not using it in your app
'space-mono': require('./assets/fonts/SpaceMono-Regular.ttf'),
}),
]);
};
_handleLoadingError = error => {
// In this case, you might want to report the error to your error
// reporting service, for example Sentry
console.warn(error);
};
_handleFinishLoading = () => {
this.setState({ isLoadingComplete: true });
};
}
const styles = StyleSheet.create({
container: {
flex: 1,
backgroundColor: '#fff',
},
});
navReducer.js
import {AppNavigator} from '../navigation/AppNavigator';
const router = AppNavigator.router;
const mainNavAction = router.getActionForPathAndParams('Auth');
const initialNavState = router.getStateForAction(mainNavAction);
const NavigationReducer = (state = initialNavState, action) => {
console.log('routes', router);
return router.getStateForAction(action, state) || state;
};
export default NavigationReducer;
AppReducer.js
"use strict";
import {VendorReducer} from './vendorReducer';
import {combineReducers} from "redux";
import NavigationReducer from "./navReducer";
const AppReducer = combineReducers({
nav:NavigationReducer,
vendor: VendorReducer,
});
export default AppReducer;
Following is my package.json.
{
"name": "my-new-project",
"main": "node_modules/expo/AppEntry.js",
"private": true,
"scripts": {
"start": "expo start",
"android": "expo start --android",
"ios": "expo start --ios",
"eject": "expo eject",
"test": "node ./node_modules/jest/bin/jest.js --watchAll"
},
"jest": {
"preset": "jest-expo"
},
"dependencies": {
"#expo/samples": "2.1.1",
"expo": "^30.0.1",
"react": "16.3.1",
"react-native": "https://github.com/expo/react-native/archive/sdk-30.0.0.tar.gz",
"react-navigation": "2.16.0",
"react-navigation-redux-helpers": "2.0.6",
"react-redux": "5.0.7",
"redux": "4.0.0",
"redux-logger": "3.0.6",
"redux-thunk": "2.3.0"
},
"devDependencies": {
"jest-expo": "30.0.0",
"redux-devtools": "3.4.1"
}
}
I hope someone could help me to get through this. Thanks in-advance.

This was also my mistake! solved it by:
const mapStateToProps = state => ({
state: state.nav,
});
pay attention to state: state.nav.
If you need, i can post my whole redux integration with the navigation that work for me.

Related

Why is my navigation ref not ready in React Navigation 6 with Redux?

In React Navigation 6, my research shows that to navigate without a prop I should make a reference and use createNavigationContainerRef. I'm able to pass down the screen name to my dispatch but for some reason when I evaluate the condition with isReady I'm always told it isn't. The code:
App.js:
import React from 'react'
import { NavigationContainer } from '#react-navigation/native'
import 'react-native-gesture-handler'
// Provider
import { Provider as AuthProvider } from './src/context/AuthContext'
// Navigation
import { navigationRef } from './src/navigation/NavRef'
// Screens
import ResolveAuthScreen from './src/screens/ResolveAuthScreen'
const App = () => {
return (
<AuthProvider>
<NavigationContainer ref={navigationRef}>
<ResolveAuthScreen />
</NavigationContainer>
</AuthProvider>
)
}
export default App
ResolveAuthScreen.js:
import React, { useEffect, useContext } from 'react'
// Context
import { Context as AuthContext } from '../context/AuthContext'
const ResolveAuthScreen = () => {
const { tryLocalSignIn } = useContext(AuthContext)
useEffect(() => {
tryLocalSignIn()
}, [])
return null
}
export default ResolveAuthScreen
AuthContext.js (stripped down):
import AsyncStorage from '#react-native-async-storage/async-storage'
// Context
import createContext from './createContext'
// Nav
import * as NavRef from '../navigation/NavRef'
const authReducer = (state, action) => {
switch (action.type) {
case 'signin':
return { errorMessage: '', token: action.payload }
case 'clear_error':
return { ...state, errorMessage: '' }
default:
return state
}
}
const tryLocalSignIn = dispatch => async () => {
const token = await AsyncStorage.getItem('token')
console.log({ token }) // renders token
if (token) {
dispatch({ type: 'signin', payload: token })
NavRef.navigate('TrackListScreen')
} else {
NavRef.navigate('SignUp')
}
}
export const { Provider, Context } = createContext(
authReducer,
{ tryLocalSignIn },
{ token: null, errorMessage: '' },
)
NavRef.js:
import { createNavigationContainerRef } from '#react-navigation/native'
export const navigationRef = createNavigationContainerRef()
export function navigate(name, params) {
console.log({ name, params })
if (navigationRef.isReady()) {
console.log('ready')
console.log({ name, params })
navigationRef.navigate('TrackDetailScreen', { name, params })
} else {
console.log('not ready')
}
}
When I log the token from dispatch I get back the token. When I log the screen I get back TrackListScreen from navigate but whenever it's fired it always returns the console log of not ready.
Docs:
Navigating without the navigation prop
Navigating to a screen in a nested navigator
"dependencies": {
"#react-native-async-storage/async-storage": "~1.15.0",
"#react-navigation/bottom-tabs": "^6.0.9",
"#react-navigation/native": "^6.0.6",
"#react-navigation/native-stack": "^6.2.5",
"axios": "^0.24.0",
"expo": "~43.0.0",
"expo-status-bar": "~1.1.0",
"react": "17.0.1",
"react-dom": "17.0.1",
"react-native": "0.64.2",
"react-native-elements": "^3.4.2",
"react-native-gesture-handler": "~1.10.2",
"react-native-reanimated": "~2.2.0",
"react-native-safe-area-context": "3.3.2",
"react-native-screens": "~3.8.0",
"react-native-web": "0.17.1"
},
Why is my navigate not working after my dispatch or why does the isReady false?
I'm having the same issue. When trying to access the exported navigationRef.isReady() from a redux-saga file, it always returns false. I'm not sure this is a safe approach, nor have I properly tested this, but the following workaround seems to work for me:
App.js
import {setNavigationRef, navigationIsReady} from './NavigationService';
const navigationRef = useNavigationContainerRef();
return (
<NavigationContainer
ref={navigationRef}
onReady={() => {
setNavigationRef(navigationRef);
}}>
...
</NavigationContainer>
);
NavigationService.js
export let navigationRefCopy = undefined;
export function setNavigationRef(navigationRef) {
navigationRefCopy = navigationRef;
}
export function navigationIsReady() {
return navigationRefCopy?.isReady(); // returns true when called in a redux saga file.
}

Assert fail - React native

i'm really new to react native and i encountered this error:
Components\MovieFocusCard.tsx: Assert fail
Failed building JavaScript bundle.
when trying to run the app.
i already tried removing & reinstalling node_modules but it didn't help.
i have no clue why this error is showing up and what the error message itself means. So any help is welcome!
Thanks in advance!
this is the error that shows up on the phone:
package.json:
{
"main": "node_modules/expo/AppEntry.js",
"scripts": {
"start": "expo start",
"android": "expo start --android",
"ios": "expo start --ios",
"web": "expo start --web",
"eject": "expo eject"
},
"dependencies": {
"#expo/vector-icons": "^10.0.0",
"babel-preset-react-native": "^4.0.0",
"expo": "^35.0.0",
"react": "16.8.3",
"react-dom": "16.8.3",
"react-native": "https://github.com/expo/react-native/archive/sdk-35.0.0.tar.gz",
"react-native-gesture-handler": "~1.3.0",
"react-native-reanimated": "~1.2.0",
"react-native-screens": "~1.0.0-alpha.23",
"react-native-paper": "^3.3.0",
"react-native-web": "^0.11.7",
"react-navigation": "^4.0.10",
"react-navigation-material-bottom-tabs": "^2.1.5",
"react-navigation-stack": "^1.10.3"
},
"devDependencies": {
"#types/react": "^16.9.14",
"#types/react-native": "^0.57.65",
"#types/react-navigation": "^3.4.0",
"babel-preset-expo": "^7.1.0",
"typescript": "^3.6.3"
},
"private": true
}
Below the code from the MovieFocusCard component:
import MovieDetails from "../Types/MovieDetails";
import { NavigationInjectedProps, withNavigation } from "react-navigation";
import React, { Component } from "react";
import { View, Text, Button, Image } from "react-native";
type MovieFocusCardProps = {};
type MovieFocusCardState = {
movieDetails: MovieDetails;
loaded: boolean;
};
class MovieFocusCard extends Component<
MovieFocusCardProps & NavigationInjectedProps,
MovieFocusCardState
> {
constructor(props: MovieFocusCardProps & NavigationInjectedProps) {
super(props);
this.state = {
movieDetails: null,
loaded: false
};
}
componentDidMount() {
this.GetMovieDetails(this.props.navigation.getParam("movieId", 0));
}
GetMovieDetails(id: number) {
let url: string = "https://api.themoviedb.org/3/movie/";
let apiKey: string = "?api_key=396734bc8915c8d1569cb4ff49b59c56";
fetch(url + id + apiKey)
.then(result => result.json())
.then(data =>
this.setState({
movieDetails: data,
loaded: true
})
)
.catch(console.log);
}
render() {
let posterUrl: string =
"https://image.tmdb.org/t/p/w200" + this.state.movieDetails.poster_path;
let rdate = new Date(
this.state.movieDetails.release_date
).toLocaleDateString();
let element;
this.state.loaded
? (element = (
<View>
<Text>{this.state.movieDetails.title}</Text>
<Image source={{ uri: posterUrl }} />
<Text>Release date: {rdate}</Text>
<Text>Summary: {this.state.movieDetails.overview}</Text>
<Text>Duration: {this.state.movieDetails.runtime} min</Text>
<Button
title="back"
onPress={() => {
this.props.navigation.goBack();
}}
>
Back
</Button>
</View>
))
: (element = <Text>Loading</Text>);
return { element };
}
}
export default withNavigation(MovieFocusCard);
//export default MovieFocusCard;
app.tsx code:
import React from "react";
import { createAppContainer } from "react-navigation";
import { createStackNavigator } from "react-navigation-stack";
import { createMaterialBottomTabNavigator } from "react-navigation-material-bottom-tabs";
import { Ionicons } from "#expo/vector-icons";
import MovieFocusCard from "./Components/MovieFocusCard";
import MovieHome from "./Components/MovieHome";
import HomeScreen from "./Components/HomeScreen";
const MovieHomeStack = createStackNavigator({
Movies: { screen: MovieHome },
MovieFocusCard: { screen: MovieFocusCard, params: { movieId: Number } }
});
const SerieHomeStack = createStackNavigator({});
const HomeStack = createStackNavigator({});
const MenuBarBottom = createAppContainer(
createMaterialBottomTabNavigator(
{
Movies: {
screen: MovieHomeStack,
navigationOptions: {
tabBarIcon: ({ tintColor }) => (
<Ionicons name="md-videocam" size={26} color={tintColor} />
)
}
},
Series: {
screen: SerieHomeStack,
navigationOptions: {
tabBarIcon: ({ tintColor }) => (
<Ionicons name="md-tv" size={26} color={tintColor} />
)
}
},
Home: {
screen: HomeStack,
navigationOptions: {
tabBarIcon: ({ tintColor }) => (
<Ionicons name="md-heart" size={26} color={tintColor} />
)
}
}
},
{
initialRouteName: "Home",
activeColor: "#000000",
inactiveColor: "#9e9e9e",
barStyle: { backgroundColor: "#ffffff" },
shifting: false //only shows label when clicked
}
)
);
export default MenuBarBottom;

Invariant Violation: Element type is invalid: expected a string using connect of react-redux

Supposedly, I've got a small problem, but can't tackle it.
I've got a small React-Native app, one screen only.
Redux is used as a store. It's being built via Expo. While using connect of react-redux, I've got the following error:
Invariant Violation: Invariant Violation: Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: object.
Check the render method of Home.
The app works if the component rendered by Home component isn't wrapped by connect().
Attach some code below.
App.js
import React from "react";
import { createStackNavigator, createAppContainer } from 'react-navigation';
import Home from './src/pages/Home';
import { Provider } from 'react-redux';
import configureStore from './src/stores/store';
const { store } = configureStore();
function App() {
return (
<Provider store={store}>
<AppContainer />
</Provider>
)
}
const MainNavigator = createStackNavigator({
Home: { screen: Home }
},
{
headerMode: 'none',
navigationOptions: {
headerVisible: false,
}
}
);
const AppContainer = createAppContainer(MainNavigator);
export default App;
Home.js
import React from "react";
import { StyleSheet, View, Text, Dimensions } from "react-native";
import SwitchEventTypes from "../components/SwitchEventTypes";
class Home extends React.Component {
constructor() {
super();
}
render() {
return (
<View>
<SwitchEventTypes />
</View>
)
}
}
SwitchEventTypes.js
import React, { Component } from "react";
import { connect } from 'react-redux';
import { StyleSheet, View, Text, Dimensions, TouchableOpacity } from "react-native";
import { updateEventType } from '../actions/actions';
const mapDispatchToProps = (dispatch) => {
return {
updateEventType: (newEventType) => {
dispatch(updateEventType(newEventType));
}
};
};
const mapStateToProps = (state) => {
return {
eventType: state.filter.eventType,
};
};
class SwitchEventTypes extends React.Component {
constructor() {
super();
this.state = {
isSwitchEventTypeOn: true
}
this.handleEventTypeChange = this.handleEventTypeChange.bind(this);
}
handleEventTypeChange(newEventType) {
this.props.updateEventType(newEventType);
}
render() {
return (
<View style={styles.switchTypesContainer}>
{this.props.eventType === 'active' ? <Text>123</Text> :
<Text>456</Text>
}
</View>
)
}
}
export default connect(mapStateToProps, mapDispatchToProps)(SwitchEventTypes);
store.js
import { createStore, applyMiddleware, compose } from 'redux';
import thunk from 'redux-thunk';
import rootReducer from '../reducers';
const middleware = [thunk];
const composeEnhancers = window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ || compose;
const composedEnhancers = composeEnhancers(
applyMiddleware(...middleware),
)
export default () => {
const store = createStore(rootReducer, composedEnhancers);
return { store };
};
package.json
"dependencies": {
"expo": "^32.0.6",
"expo-react-native-shadow": "^1.0.3",
"expo-svg-uri": "^1.0.1",
"prop-types": "^15.7.2",
"react": "16.8.6",
"react-native": "https://github.com/expo/react-native/archive/sdk-32.0.1.tar.gz",
"react-native-calendars": "^1.32.0",
"react-native-svg": "^9.4.0",
"react-navigation": "^3.9.1",
"react-redux": "^7.0.1",
"redux": "^4.0.1",
"redux-thunk": "^2.3.0",
"react-native-switch": "^1.5.0"
},
"devDependencies": {
"babel-preset-expo": "^5.0.0",
"redux-devtools-extension": "^2.13.8",
"schedule": "^0.4.0"
},
What may be the matter? Please, help. Thanks.
Your mapDispatchToProps is returning an object. You also don't need the extra returns as fat arrow functions already have an implicit return. Will make your code a little more readable.
const mapDispatchToProps = dispatch => ({
updateEventType: (newEventType) => dispatch(updateEventType(newEventType));
});
const mapStateToProps = state => {
eventType: state.filter.eventType, // might be worth your time to investigate selectors down the road
};

connect doesn't refresh when state change on react-native with redux

It's been 5 hours that I'm on the problem but decidedly it does not want to work...
I would like to dispatch the event when onScroll is detected on my home component and receive the status "true" or "false" in my TopNavigation component
For now my reducer works well (with a console.log(nextState) before the render) but I have the impression that the connection does not work with connect(mapStatetoProps)(TopNavigation) because my component does not re-render
Thank you for your answers
//TopNavigation
import React from 'react'
import { connect } from 'react-redux'
class TopNavigation extends React.Component {
constructor(props) {
super(props)
}
componentDidMount() {
console.log(this.props.scrollData)
}
}
// Render things...
const mapStatetoProps = (state) => {
return {
scrollData: state.scrollData
}
}
export default connect(mapStatetoProps)(TopNavigation)
// Home
import React from 'react'
import { StyleSheet, View, FlatList } from 'react-native'
import gStyles from '../../../Styles/global'
import { connect } from 'react-redux'
// Partials
import ItemBox from '../../Partials/ItemBox'
import TopNavigation from '../../Partials/TopNavigation'
// Data
import recetteData from '../../../api/recetteData'
class Home extends React.Component {
constructor(props) {
super(props)
}
render() {
return (
<View style={styles.mainContainer}>
<FlatList
data={recetteData}
keyExtractor={(item) => item.id.toString()}
onPress={() => this._toggleSet()}
renderItem={({ item }) => <ItemBox item={item} />}
onScroll={(event) => this.props.dispatch({ type: "POSITION", value: event.nativeEvent.contentOffset.y })}
style={styles.flatListContainer} />
<TopNavigation />
</View>
)
}
}
export default connect(mapStateToProps)(Home)
//ScrollData Reducer
const initialState = {
scrollData: {
scrolled: false
}
}
function scrollData(state = initialState, action) {
let nextState
switch (action.type) {
case 'POSITION':
if (action.value > 0) {
nextState = {
...state,
scrollData: {
...state.scrollData,
scrolled: true,
},
}
}
else {
nextState = {
...state,
scrollData: {
...state.scrollData,
scrolled: false
},
}
}
return nextState.scrollData.scrolled
default:
return state
}
}
export default scrollData
//ConfigureStore
import { createStore } from 'redux';
import buttonPreference from './Reducers/buttonPreference'
import scrollData from './Reducers/scrollData'
export default createStore(/*buttonPreference,*/scrollData)
On console (console.log of componentDidMount of TopNavigation):
Object {
"scrolled": false,
}
But no change when i'm scrolling
Here is my package.json
{
"main": "node_modules/expo/AppEntry.js",
"scripts": {
"start": "expo start",
"android": "expo start --android",
"ios": "expo start --ios",
"eject": "expo eject"
},
"dependencies": {
"expo": "^32.0.6",
"react": "^16.8.3",
"react-native": "https://github.com/expo/react-native/archive/sdk-32.0.1.tar.gz",
"react-native-elevated-view": "0.0.6",
"react-native-gesture-handler": "^1.1.0",
"react-native-paper": "^2.12.0",
"react-native-responsive-dimensions": "^2.0.1",
"react-navigation": "^2.0.1",
"react-navigation-material-bottom-tabs": "^0.4.0",
"react-redux": "^6.0.1",
"redux": "^4.0.1"
},
"devDependencies": {
"babel-preset-expo": "^5.0.0",
"react-test-renderer": "^16.6.0-alpha.8af6728",
"schedule": "^0.4.0"
},
"private": true
}
Update
Putting on TopNavigation:
//TopNavigation
constructor(props) {
super(props)
this.state = {
scrolledState: false
}
}
componentDidUpdate(prevProps) { // Instead of componentDidMount
if (this.props.scrollData.scrolled !== prevProps.scrollData.scrolled) {
console.log(this.props.scrollData);
this.setState({ scrolledState: this.props.scrollData });
}
}
But it still doesn't work, no event or state change...
Update 2
The store seems to be work oroperly, the problem more precisely is that it does not update in real time the component.
If I populate the store, I quite and return to the page using navigation, the data is well changed.
The real question is, why the component does not update in real time with the new store data passed by the reducer...
Update 3
Expo in production mode solved problem...
You have done everything right for the most part. The problem is with your TopNavigation file. Two important things to keep in mind here:
componentDidMount() is called only once, when your component is rendered for the first time. So even if your connect works correctly, you will not get more than one call to this function. To check if your props are updated correctly, you can have a console.log() inside componentDidUpdate() as follows:
componentDidUpdate(prevProps) {
if (this.props.scrollData.scrolled !== prevProps.scrollData.scrolled) {
console.log(this.props.scrollData);
}
}
Also keep in mind that this will not cause a re-render of your component. A component re-renders only when the state of the component changes. You can use this change in your props to trigger a state change, which will call the render function again, to trigger a re-render of your component, as follows:
state = {scrolledState: false};
...
...
componentDidUpdate(prevProps) {
if (this.props.scrollData.scrolled !== prevProps.scrollData.scrolled) {
// console.log(this.props.scrollData);
this.setState({scrolledState: this.props.scrollData});
}
}
Hope this helps!
That sounds like a bug with environnement. I launched Expo in production mode and it solved problem.
On folder .expo
//setting.json
{
"hostType": "lan",
"lanType": "ip",
"dev": false, // false for production env
"minify": false,
"urlRandomness": "53-g5j"
}
I hope it can help but it would be desirable to be able to continue working on dev mode...
I report a bug on expo github
The previous answer was right. But to make the code works try the below approach.
class Home extends React.Component {
constructor(props) {
super(props);
this.state = {
scrolling: false;
}
}
makeScroll = (event) => {
this.props.dispatch({ type: "POSITION", value: event.nativeEvent.contentOffset.y
});
setTimeout(() => this.setState({scrolling: true}), 150);
}
render() {
return (
<View style={styles.mainContainer}>
<FlatList
data={recetteData}
keyExtractor={(item) => item.id.toString()}
onPress={() => this._toggleSet()}
renderItem={({ item }) => <ItemBox item={item} />}
onScroll={(event) => this.makeScroll(event)}
style={styles.flatListContainer} />
<TopNavigation />
</View>
)
}
}
export default connect(mapStateToProps)(Home)
Instead of directly dispatch at onScroll event. Pass it into a function and do change the local state inside that after dispatch.

ReactNavigation Error - Cannot read property 'bind' of undefined

"react-native": "^0.57.0",
"react-navigation": "^3.0.0",
"react-navigation-redux-helpers": "^2.0.7",
"react-redux": "^5.0.6",
"redux": "^4.0.0",
"redux-thunk": "^2.3.0",
"reduxsauce": "0.7.0",
"react-native-gesture-handler": "^1.0.9",
Updating react-navigation to 3.0.0 in my React-Native app. I have followed the official docs here React Navigation and installed all the dependencies.
However cannot resolve this issue.
AppNavigation.js
const PrimaryNav = createStackNavigator({
HomeScreen: {
screen: MainTabNav,
}, {
mode: 'modal',
headerMode: 'none',
initialRouteName: 'HomeScreen',
navigationOptions: {
headerStyle: styles.header,
},
});
export default createAppContainer(PrimaryNav);
ReduxNavigation.js
import AppNavigation from './AppNavigation';
import { reduxifyNavigator, createReactNavigationReduxMiddleware } from
'react-navigation-redux-helpers';
createReactNavigationReduxMiddleware(
'root',
state => state.nav,
);
const ReduxAppNavigator = reduxifyNavigator(AppNavigation, 'root');
render() {
const { dispatch, nav } = this.props;
<ReduxAppNavigator state={nav} dispatch={dispatch} />
}
const mapStateToProps = state => ({ nav: state.nav });
export default connect(mapStateToProps)(ReduxNavigation);
navigation.js
import { Keyboard } from 'react-native';
import AppNavigation from '../navigation/AppNavigation';
export default (state, action) => {
Keyboard.dismiss();
const newState = AppNavigation.router.getStateForAction(action, state);
return newState || state;
};
CreateStore.js
import { createStore, applyMiddleware, compose } from 'redux';
import reduxThunkMiddleware from 'redux-thunk';
import { createReactNavigationReduxMiddleware } from 'react-navigation-redux-
helpers';
import screenTrackingMiddleware from './screenTrackingMiddleware';
export default (rootReducer) => {
const middleware = [];
const enhancers = [];
const navigationMiddleware = createReactNavigationReduxMiddleware(
'root',
state => state.nav,
);
middleware.push(screenTrackingMiddleware);
middleware.push(navigationMiddleware);
middleware.push(reduxThunkMiddleware);
enhancers.push(applyMiddleware(...middleware));
const store = createStore(rootReducer, compose(...enhancers));
return {
store,
};
};
RootContainer.js
import ReduxNavigation from 'navigation/ReduxNavigation';
export default class RootContainer extends Component {
render() {
return (
<View style={styles.applicationView}>
<StatusBar barStyle="light-content" />
<ReduxNavigation />
</View>
);
}
}
This happens because you didn't link react-native-gesture-handler
Just type react-native link in your project dir.
And run again react-native run-android
Solved the issue by adding this plugin to .babelrc file.
[
"#babel/plugin-transform-flow-strip-types",
]