将用户导航到 listitem 上的新屏幕单击 React native
Posted
技术标签:
【中文标题】将用户导航到 listitem 上的新屏幕单击 React native【英文标题】:Navigate user to New Screen on listitem click React native 【发布时间】:2017-11-16 05:22:48 【问题描述】:我试图在用户单击列表项时将用户导航到下一个屏幕。我正在尝试在这方面使用 Navigator,我是新手,有 Redux 和 Flux 两种不同的架构,因为我的反应不是很好,所以我对那里的工作有点困惑。我们可以使用 Navigator 和 Action 来导航用户。这是我的课:-
我遇到的错误是:- 未定义不是函数(正在评估'_this4.goDetailPage(rowData)')
Today.js
import React, Component from 'react';
import
StyleSheet,
Text,
from 'react-native';
import FeedStack from './movielistdeatilrouter';
export default class TodayView extends Component
constructor(props , context)
super(props , context);
render()
return (
<FeedStack />
);
movielistdeutilrouter.js:-
import React from 'react';
import StackNavigator from 'react-navigation';
import MovieDeatilScreen from './MovieDeatilScreen';
import Movielisting from './movielisting';
export const FeedStack = StackNavigator(
Movielisting:
screen: Movielisting,
navigationOptions:
title: 'Movielisting',
,
,
MovieDeatilScreen:
screen: MovieDeatilScreen,
navigationOptions: ( navigation ) => (
title: 'MovieDeatilScreen',
),
,
);
movielistiing.js :-
import React, Component from 'react';
import StatusBar from 'react-native'
import StackNavigator from 'react-navigation';
import NavigationActions from 'react-navigation';
import Actions, ActionConst from 'react-native-router-flux';
import home from '../images/home.png';
import MovieDeatilScreen from './MovieDeatilScreen'
const width: viewportWidth, height: viewportHeight = Dimensions.get('window');
import
StyleSheet,
Text,
Image,
View,
AsyncStorage,
TouchableOpacity,
TouchableHighlight,
Dimensions,
ListView
from 'react-native';
const uri = 'http://csswrap.com/wp-content/uploads/2015/03/showmenu.png';
export default class Movielisting extends Component
constructor(props)
super(props);
var ds = new ListView.DataSource(rowHasChanged: (r1, r2) => r1 !== r2);
this.state =
moviesData: ds.cloneWithRows([]),
;
componentDidMount()
this.fetchMoviesData();
fetchMoviesData()
var url = 'http://api.themoviedb.org/3/movie/now_playing?api_key=17e62b78e65bd6b35f038505c1eec409';
fetch(url)
.then(response => response.json())
.then(jsonData =>
this.setState(
moviesData: this.state.moviesData.cloneWithRows(jsonData.results),
);
)
.catch( error => console.log('Error fetching: ' + error) );
render()
return (
<View style=styles.container>
<ListView
dataSource=this.state.moviesData
renderRow=this.renderRow
enableEmptySections=true
style=styles.ListViewcontainer
/>
</View>
);
renderRow(rowData)
return (
<View style=styles.thumb >
<TouchableOpacity onPress=() => this.goDeatilPage(rowData)>
<Image
source=uri:'https://image.tmdb.org/t/p/w500_and_h281_bestv2/'+rowData.poster_path
resizeMode="cover"
style=styles.img />
<Text style=styles.txt>rowData.title (Rating: Math.round( rowData.vote_average * 10 ) / 10)</Text>
</TouchableOpacity>
</View>
);
goDeatilPage = (rowData) =>
alert('hi');
AsyncStorage.setItem('moviesData', JSON.stringify(rowData));
this.props.navigation.navigate('MovieDeatilScreen');
;
const styles = StyleSheet.create(
container:
position:'relative',
flex: 1,
justifyContent: 'center',
alignItems: 'center',
backgroundColor: '#F5FCFF',
,
welcome:
fontSize: 20,
textAlign: 'center',
margin: 10,
,action:
flex: 0.4,
,thumb:
backgroundColor: '#ffffff',
marginBottom: 5,
elevation: 1
,
img:
height: 300
,
txt:
margin: 10,
fontSize: 16,
textAlign: 'left'
,ListViewcontainer:
marginTop:50,
bottom: 50,
);
Index.android.js :-
import React, Component from 'react';
import
AppRegistry,
StyleSheet,
Text,
StatusBar,
View
from 'react-native';
import App from './app';
import DrawerMenu from './Drawer/drawer-toolbar-android';
import BookmarkView from './Pages/bookmark';
import CalendarView from './Pages/calendar';
import ClientView from './Pages/client';
import InfoView from './Pages/info';
import SettingsView from './Pages/setting';
import DrawerNavigator, StackNavigator from 'react-navigation';
const stackNavigator = StackNavigator(
Info: screen: InfoView ,
Settings: screen: SettingsView ,
Bookmark: screen: BookmarkView ,
Calendar: screen: CalendarView,
Client: screen: ClientView,
,
headerMode: 'none'
);
const easyRNRoute = DrawerNavigator(
Home:
screen: App,
,
Stack:
screen: stackNavigator
,
contentComponent: DrawerMenu,
contentOptions:
activeTintColor: '#e91e63',
style:
flex: 1,
paddingTop: 15,
);
AppRegistry.registerComponent('flightbot', () => easyRNRoute);
App.js 类 :-
import React, Component from 'react';
import
AppRegistry,
StyleSheet,
Text,
StatusBar,
View
from 'react-native';
import Navigator, NativeModules from 'react-native';
import COLOR, ThemeProvider from 'react-native-material-ui';
import Toolbar, BottomNavigation, Icon from 'react-native-material-ui';
import Container from './Container';
import TabRouter from 'react-navigation';
import TodayView from './Contents/today';
import ProfileView from './Contents/profile';
import MapView from './Contents/map';
import ChatView from './Contents/chat';
const uiTheme =
palette:
primaryColor: COLOR.green500,
accentColor: COLOR.pink500,
,
toolbar:
container:
height: 70,
paddingTop: 20
const TabRoute = TabRouter(
Today: screen: TodayView ,
Profile: screen: ProfileView ,
Map: screen: MapView ,
Chat: screen: ChatView
,
initialRouteName: 'Today',
);
class TabContentNavigator extends Component
constructor(props, context)
super(props, context);
this.state =
active: props.value.active,
;
//this method will not get called first time
componentWillReceiveProps(newProps)
this.setState(
active: newProps.value.active,
);
render()
const Component = TabRoute.getComponentForRouteName(this.state.active);
return <Component/>;
export default class App extends Component
constructor(props, context)
super(props, context);
this.state =
active: 'Today',
;
static navigationOptions =
title: 'Menu',
;
navigate()
this.props.navigation.navigate('DrawerOpen'); // open drawer
render()
return (
<ThemeProvider uiTheme=uiTheme>
<Container>
<StatusBar backgroundColor="rgba(0, 0, 0, 0.2)" translucent />
<Toolbar
leftElement="menu"
centerElement=this.state.active
onLeftElementPress=() => this.navigate()
/>
<TabContentNavigator value=this.state key=this.state />
<BottomNavigation active=this.state.active
hidden=false
style= container: position: 'absolute', bottom: 0, left: 0, right: 0
>
<BottomNavigation.Action
key="Today"
icon="today"
label="Today"
onPress=() => this.setState( active: 'Today' )
/>
<BottomNavigation.Action
key="Profile"
icon="person"
label="Profile"
onPress=() =>
this.setState( active: 'Profile' );
/>
<BottomNavigation.Action
key="Map"
icon="map"
label="Map"
onPress=() => this.setState( active: 'Map' )
/>
<BottomNavigation.Action
key="Chat"
icon="chat"
label="Chat"
onPress=() => this.setState( active: 'Chat' )
/>
</BottomNavigation>
</Container>
</ThemeProvider>
);
我正在尽我最大的努力来解决这个问题,今天已经快 3 天了,我正在寻找解决方案,我该如何做到这一点,我只想在单击列表项时打开一个新屏幕。谁能告诉我该怎么做。如果有人让我知道导航到下一个屏幕的方式,我将非常感激。
我的错误截图:-
谢谢!!!
【问题讨论】:
【参考方案1】:使用“React Navigation”应该可以帮助您解决问题。
欲了解更多信息,您可以在这里找到:https://reactnavigation.org
干杯,
====== 更新 ======
我认为您设置 Today 组件的方式不正确,而且您的问题也不清楚,我花了一段时间才明白您想要做什么。
无论如何,Today 组件应该是一个 StackNavigator,如果你想从中打开一个详细屏幕,它将控制 2 个屏幕(ListScreen 和 DetailScreen):
const TodayView = StackNavigator(
List:
screen: ListScreen,
,
Detail:
screen: DetailScreen,
,
);
然后像这样设置你的屏幕:
class ListScreen extends Component
static navigationOptions =
title: 'List',
constructor(props , context)
super(props , context);
this.goToDetailScreen = this.goToDetailScreen.bind(this);
goToDetailScreen()
this.props.navigation.navigate('Detail');
render()
return (
<TouchableOpacity onPress=() => this.goToDetailScreen()>
<Text>GO TO DETAIL</Text>
</TouchableOpacity>
);
class DetailScreen extends Component
static navigationOptions =
title: 'Detail',
render()
return (
<TouchableOpacity onPress=() => this.props.navigation.goBack()>
<Text>BACK TO LIST SCREEN</Text>
</TouchableOpacity>
);
在他们的 Github 存储库中有一个名为“StacksInTabs”的示例,您可能想看看它:https://github.com/react-community/react-navigation/blob/master/examples/NavigationPlayground/js/StacksInTabs.js
干杯,
【讨论】:
你好@Goon,谢谢你的回复,是的,我之前看过这个,问题是上面的类在我的 TabRouter 下,当我尝试声明 const navigate = this.props.navigation; 它给了我错误,因为 Undefined is not an object(evalating this.props.navigation.navigate) ,让我发布我剩下的课程,我正在从一个链接学习并尝试理解流程.,请查看我更新的问题。让我在上面的课程中使用这种方法。谢谢 只需更新答案,让我知道它是否有效@sid :) 嘿@Goon,我有点困惑,问题出在 Today.js 类中,我无法使用 RenderRow 函数中的 onpress 事件调用导航器,我也像你一样更新了我的 App.js 文件上面提到,但仍然无法在单击 ListItem 时导航到详细信息屏幕。 是的,我已经研究了链接,并按照您提到的方式相应地更改了我的流程,但是我的函数没有被调用,我知道我可能会犯一些愚蠢的错误让我更新我的问题你。 嘿@GoonNguyen。感谢您的回复。您上次共享的 Git 存储库无法访问。你能更新那个链接吗?谢谢【参考方案2】:终于成功了,这就是我在更改代码后所做的事情。 :-
<View style=styles.container>
<ListView
dataSource=this.state.moviesData
renderRow=this.renderRow.bind(this)
enableEmptySections=true
style=styles.ListViewcontainer
/>
</View>
我刚刚在 renderRow 中添加了 .bind(this) 函数。
休息是一样的:-
renderRow(rowData)
return (
<View style=styles.thumb >
<TouchableOpacity onPress=()=>this.goDeatilPage(rowData)>
<Image
source=uri:'https://image.tmdb.org/t/p/w500_and_h281_bestv2/'+rowData.poster_path
resizeMode="cover"
style=styles.img />
<Text style=styles.txt>rowData.title (Rating: Math.round( rowData.vote_average * 10 ) / 10)</Text>
</TouchableOpacity>
</View>
);
goDeatilPage = (rowData) =>
alert('hi');
AsyncStorage.setItem('moviesData', JSON.stringify(rowData));
this.props.navigation.navigate('MovieDeatilScreen');
感谢@Goon 抽出宝贵时间,非常感谢您的努力。谢谢大哥。
【讨论】:
告诉你,伙计。我确实试图告诉您在第一时间检查绑定功能:D 很高兴能帮上忙!【参考方案3】:使用 React Navigation 导航屏幕,非常易于使用,
在 react native 中创建 3 个类定义的导航器类 2.第一屏 3.导航屏幕
1.Basic.js
import
StackNavigator,
from 'react-navigation';
const BasicApp = StackNavigator(
Main: screen: Movielistiing,
Detail: screen: Movielistdeatilrouter,
);
module.exports = BasicApp;
2.Movielistiing.js
class Movielistiing extends React.Component
static navigationOptions =
title: 'Welcome',
;
render()
const navigate = this.props.navigation;
return (
<Button
title="Go to movie detail"
onPress=() =>
navigate('Detail', name: 'Jane' )
/>
);
3.Movielistdeutilrouter.js
class Movielistdeatilrouter extends React.Component
static navigationOptions = (navigation) => (
title: navigation.state.params.name,
);
render()
const goBack = this.props.navigation;
return (
<Button
title="Go back"
onPress=() => goBack()
/>
);
【讨论】:
以上是关于将用户导航到 listitem 上的新屏幕单击 React native的主要内容,如果未能解决你的问题,请参考以下文章
如何将用户重定向到 div 上的新页面单击 JQuery [重复]
swiftUI:登录完成后导航到主屏幕。通过按钮单击导航视图