React Native 一個小專案其中一些主要功能實現 (頂部導航欄(可滑動),網路解析,上拉重新整理,下拉載入)
阿新 • • 發佈:2018-12-10
//網路解析 import React, { Component } from "react"; import { View, Text, TouchableOpacity } from "react-native"; import RefreshListView, { RefreshState } from "react-native-refresh-list-view"; import { withNavigation } from "react-navigation"; import Item from "./Item"; import { getData } from "./Fetch"; class List extends Component { constructor(props) { super(props); this.state = { data: [], refreshState: RefreshState.Idle, page: 1, limit: 10, tab: props.tab }; } requestData = async () => { let request = await fetch("https://cnodejs.org/api/v1/topics", { method: "GET" }); let requestJson = await request.json(); return requestJson.data; }; requestFirstData = () => { try { this.setState( { refreshState: RefreshState.HeaderRefreshing, page: 1 }, async () => { let data = await this.requestData(); this.setState({ data: data, refreshState: RefreshState.Idle }); } ); } catch (error) { this.setState({ refreshState: RefreshState.Failure }); } }; requestNextData = () => { try { this.setState( { refreshState: RefreshState.FooterRefreshing, page: this.state.page + 1 }, async () => { let data = await this.requestData(); this.setState({ data: [...this.state.data, ...data], refreshState: this.state.data.length > 30 ? RefreshState.NoMoreData : RefreshState.Idle }); } ); } catch (error) { console.error(error); } }; componentDidMount() { this.requestFirstData(); } onHeader = () => { this.requestFirstData(); }; onFooter = () => { this.requestNextData(); }; renderItem = rowdata => { return ( <TouchableOpacity onPress={() => { this.props.navigate("Detail", { content: rowdata.item.content }); }} > <Item item={rowdata.item} /> </TouchableOpacity> ); }; render() { return ( <RefreshListView data={this.state.data} renderItem={this.renderItem} refreshState={this.state.refreshState} onHeaderRefresh={this.onHeader} onFooterRefresh={this.onFooter} keyExtractor={item => item.id} /> ); } } export default withNavigation(List); //Item 頁面佈局 import React, { Component } from "react"; import { View, Text, Image, StyleSheet } from "react-native"; export default class Item extends Component { render() { return ( <View style={styles.row}> <Image style={styles.img} source={{ uri: this.props.item.author.avatar_url }} /> <View> <Text>{this.props.item.title}</Text> <Text>{this.props.item.author.loginname}</Text> </View> </View> ); } } const styles = StyleSheet.create({ row: { flexDirection: "row", padding: 20 }, img: { width: 80, height: 80 } }); //請求方式 GET export const baseURL = "https://cnodejs.org/api/v1"; export const getURL = (url, obj) => { let objArray = []; Object.keys(obj).forEach(key => objArray.push(key + "=" + obj[key])); if (url.search(/\?/) === -1) { url += "?" + objArray.join("&"); } else { url += "&" + objArray.join("&"); } return url; }; export const getData = async (url, obj) => { url = obj ? getURL(url, obj) : url; let request = await fetch(baseURL + url, { method: "GET" }); let json = request.json(); return json; };