(一) :知识点准备:
(1) reduce函数:性能比for和while好
(1)
array.reduce(callbackfn,[initialValue])
(2)
function callbackfn(preValue,curValue,index,array){}
( preValue:上一次调用回调返回的值,或者是提供的初始值(initialValue))
( curValue:数组中当前被处理的数组项 )
( index:当前数组项在数组中的索引值 )
没有初始值,数组中第一项为preValue,第二项为curValue,所以index从1开始。
有初始值,初始值为preValue,数组第一项为curValue,所以index从0开始。
( array:调用reduce() 方法的数组 )
--------------------------------------------------------------
例子一:(无初始值)
var arr = [0,1,2,3,4];
arr.reduce(function (preValue,curValue,index,array) { return preValue + curValue; });
// 10
--------------------------------------------------------------
例子二:(有初始值)
var arr = [0,1,2,3,4];
arr.reduce(function (preValue,curValue,index,array) { return preValue + curValue; }, 5);
//15
http://www.w3cplus.com/javascript/array-part-8.html
(2) Math.round() ,Math.floor() ,Math.ceil的区别
Math.round() 四舍五入
Math.ceil() 向上取整
Math.floor() 向下取整
(3) Math.random()
返回介于 0 ~ 1 之间的一个随机数。
( random:是随机数的意思 )
--------------------------------
Math.round(Math.random() * 100000)/100,
(4) toFixed()
toFixed() 方法可把 Number 四舍五入为指定小数位数的数字。
--------------------------------
如: toFixed(1) 四舍五入为一位小数位
(5) slice()函数
- slice() 方法可从已有的数组中返回选定的元素。
arrayObject.slice(start,end)
-----------
start : 必需。规定从何处开始选取。
如果是负数,那么它规定从数组尾部开始算起的位置。也就是说,-1 指最后一个元素,-2 指倒数第二个元素,以此类推。
-----------
end:可选。规定从何处结束选取。
-----------
例子:
dataSource = { this.ds.cloneWithRows(this.Cart.item.slice(0) ) }
//从第0项开始选取
(二) :mobx状态管理:
(1) 安装
- (1) 安装mobx
npm install mobx --save
- (2) 安装mobx-react
npm install mobx-react --save
- (3) 为了使用ES7的语法,我们还需要安装三个babel插件
npm install
babel-plugin-transform-decorators-legacy
babel-plugin-syntax-decorators
babel-preset-react-native-stage-0 --save-dev
- (4) 现在你的工程目录下应该有.babelrc文件(如果没有可自行创建),修改文件的内容为:
{
"presets": ["react-native"],
"plugins": [
"syntax-decorators", //这个也需要的
"transform-decorators-legacy"
]
}
(2) mobx相关知识点
(1) mobx
- observable 被观察者
- computed 计算属性,注意这里是属性
- action 函数
(2) mobx-react/native
- observer 观察者
(3) useStrict(true);严格模式
(详细) http://www.jianshu.com/p/505d9d9fe36a
http://www.jianshu.com/p/3c818b107858
购物车详细代码:
完整代码:
/**
* Created by WOOW.WU on 2017/7/16.
*/
/**
* Sample React Native App
* https://github.com/facebook/react-native
* @flow
*/
import React, { PropTypes, Component } from 'react';
import {
AppRegistry,
StyleSheet,
Text,
View,
ListView,
Image,
TouchableOpacity,
Dimensions,
Modal,
} from 'react-native';
import { observable, computed, action, useStrict } from 'mobx';
import { observer } from 'mobx-react/native';
useStrict(true);
// import Icon from 'react-native-vector-icons/Ionicons';
// import Icon2 from 'react-native-vector-icons/MaterialCommunityIcons';
const { width, height } = Dimensions.get('window');
class CartItem {
name = '';
price = 0;
detail = '';
img = '';
@observable
isSelect = false;
@observable
count = 0;
constructor(name,price,detail,img){ //初始化数据
this.name = name;
this.price = price;
this.detail = detail;
this.img = img;
}
@action
inc = () => {
++this.count; //增加和选中状态同步
this.isSelect = true;
}
@action
dec = () => {
if( this.count > 0) {
--this.count;
this.isSelect = true;
}else{
this.isSelect = false;
this.count = 0;
}
}
@action
selected = () => { //切换选中的状态,选中+1,未选中count为0
this.isSelect = !this.isSelect;
if(this.isSelect){
++this.count
}else{
this.count = 0;
}
}
}
class Cart {
//被观察者
@observable
item = [];
//注意这里new CartItem实例化,传参
constructor() {
this.item.push( new CartItem("八宝丹","500.00","0.3*1粒/盒",'https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1502445576159&di=7be6d7fb59760357f08c2e3e7e1ac963&imgtype=0&src=http%3A%2F%2Fwww.jzj.cn%2Fjup%2Fpro%2Fat%2FJ201634_1185080623.jpg') )
this.item.push( new CartItem("福禄胶囊",'20.00',"0.3*1粒/盒",'https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1502635549043&di=0348d8b05b0b7096fe4bacf4843100a8&imgtype=jpg&src=http%3A%2F%2Fimg1.imgtn.bdimg.com%2Fit%2Fu%3D3067211693%2C4169374304%26fm%3D214%26gp%3D0.jpg') )
this.item.push( new CartItem("杜仲双降袋泡剂",'30.00',"0.8*1粒/盒",'https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1502445882398&di=0cfca8dc0e0f682a1ebab87db21ae271&imgtype=0&src=http%3A%2F%2Fp4.maiyaole.com%2Fimg%2F201607%2F28%2F330_20160728161743758.jpg') )
this.item.push( new CartItem("豨莶通栓丸",'80.00',"0.2*1粒/盒",'https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1502446144560&di=e9320f632932641b65dea83b5fb97471&imgtype=0&src=http%3A%2F%2Fwww.315jiage.cn%2Fupload%2F2016-05%2F16050514411057.jpg') )
this.item.push( new CartItem("天芪降糖胶囊",'60.00',"2.8*10粒/盒",'https://timgsa.baidu.com/timg?image&quality=80&size=b9999_10000&sec=1502446107003&di=7ae286f58b410ce05160f427031ed4cd&imgtype=0&src=http%3A%2F%2Fimg01.img.ehaoyao.com%2Fdata%2Fgoodscenter%2Fimges%2Fmanager%2FCBG216001G_54281%2F20160912170326_69_gw_047.jpg') )
}
//总数量
@computed
get count() {
return this.item.reduce( (a,b) => a + b.count, 0)
}
//总价
@computed
get price() {
return this.item.reduce( (a,b) => a + (b.price * b.count),0 )
}
}
@observer //观察者,观察被观察这observable的状态变化
class Item extends Component {
static propTypes = {
data: PropTypes.instanceOf(CartItem),
};
render() {
const { data } = this.props;//接受父组件的传值
return(
<TouchableOpacity onPress = { data.selected } activeOpacity={1}>
<View style={ data.isSelect
?
{backgroundColor:'#ccf3ff',flexDirection:'row',paddingLeft:14,paddingRight:14,paddingTop:20,paddingBottom:20,borderBottomWidth:1,borderBottomColor:'rgba(0,0,0,0.1)'}
:
{flexDirection:'row',paddingLeft:14,paddingRight:14,paddingTop:20,paddingBottom:20,borderBottomWidth:1,borderBottomColor:'rgba(0,0,0,0.1)'}
}>
<View style={{ padding: 2,justifyContent:'center',alignItems:'center',marginRight: 20}}>
{
data.isSelect ?
<Image source={ require('../radio1.png') } style={{width:28,height:28}} ></Image>
:
<Image source={ require('../radio2.png') } style={{width:28,height:28}} ></Image>
}
</View>
{/*每个item中的药品图片*/}
<View style={{ width:150,height:150,borderRadius:20,borderWidth:1,borderColor:'rgba(0,0,0,0.3)',justifyContent:'center',alignItems:'center'}}>
<Image source={{ uri: data.img }} style={{ width:130,height:120}}></Image>
</View>
<View style={{ flexDirection:'column',justifyContent:'space-around',marginLeft:20,alignItems:'flex-start'}}>
<View>
<Text style={{fontSize:20}}> { data.name } </Text>
</View>
<View style={{ marginLeft: 2 }}>
<Text>{ data.detail }</Text>
</View>
<View style={{ flexDirection:'row'}}>
<TouchableOpacity onPress={ data.inc} activeOpacity={1}>
<View style={{ borderWidth:1,
borderColor:'rgba(0,0,0,0.4)' ,
width:40,
height:40,
borderTopLeftRadius:8,
borderBottomLeftRadius:8,
justifyContent:'center',
alignItems:'center'
}}>
<Text style={{ fontSize:18 }}>+</Text>
</View>
</TouchableOpacity>
<View style={{ backgroundColor:'rgba(0,0,0,0.1)',
width:60,
height:40,
justifyContent:'center',
alignItems:'center',
}} >
<Text style={{fontSize: 20}}>{ data.count }</Text>
</View>
<TouchableOpacity onPress={ data.dec } activeOpacity={1}>
<View style={{
borderWidth:1,
borderColor:'rgba(0,0,0,0.4)',
width:40,
height:40,
borderTopRightRadius:8,
borderBottomRightRadius:8,
justifyContent:'center',
alignItems:'center'
}}>
<Text style={{ fontSize:18 }} >-</Text>
</View>
</TouchableOpacity>
</View>
</View>
<View style={{ paddingTop:6,flex:1,justifyContent:'flex-end',flexDirection:'row',paddingRight:20}}>
<Text style={{ fontSize: 26 ,color:'red'}}> ¥{ data.price } </Text>
</View>
</View>
</TouchableOpacity>
)
}
}
@observer
class Info extends Component{
render() {
const { cart } = this.props;
return(
<View style={{ flexDirection:'row',width:width,height:100,justifyContent:'space-between',backgroundColor:'#454c54'}}>
<View style={{justifyContent:'center',paddingLeft:20,alignItems:'center'}}>
<View style={{ flexDirection:'row',justifyContent:'flex-start',alignItems:'center'}}>
<Text style={{ fontSize:20,color:'white'}} >
总金额:
</Text>
<Text style={{ fontSize:30,color:'#ff7454'}}>
¥{ cart.price }
</Text>
</View>
<View>
<Text style={{color:'white'}}>
总数量:{ cart.count }
</Text>
</View>
</View>
<View style={{ height:100,
width:200,
backgroundColor:'#ff7454',
justifyContent:'center',
alignItems:'center',
}}>
<Text style={{ color:'white', fontSize: 20}}>
拟购申请
</Text>
</View>
</View>
)
}
}
export default class ww extends Component {
constructor(props){
super(props)
this.state = {
show2: false,
modalVisible: true
}
}
Cart = new Cart();
ds = new ListView.DataSource({
rowHasChanged: (v1,v2) => v1 !== v2
})
_renderRow(data) {
return (
<Item data={ data } />
) //父子通信,父组件将data属性传给子组件Item
}
_raido() {
const { cart } = props.
return (
this.setState({
show2 : !this.state.show2
})
)
}
_showHide( backFromInfo ) {
this.setSate({
modalVisible:backFromInfo
})
}
render() {
return (
<View style={styles.container}>
{/*拟购车*/}
<View style={{ width:width, height:64,justifyContent:'center',alignItems:'center'}}>
<Text style={{fontSize:18}}>拟购车</Text>
</View>
{/*全选*/}
<TouchableOpacity
activeOpacity={ 1 }
onPress={ this._raido.bind(this) }
>
<View style={{ paddingLeft:14,backgroundColor:'#f7f7f7',width:width ,height:50,justifyContent:'flex-start',flexDirection:'row',alignItems:'center'}}>
<TouchableOpacity onPress={ Cart.selected }>
<View style={{ padding: 2}}>
{
this.state.show2 ?
<Image source={ require('../radio1.png') } style={{width:28,height:28}} ></Image>
:
<Image source={ require('../radio2.png') } style={{width:28,height:28}} ></Image>
}
</View>
</TouchableOpacity>
<Text style={{ fontSize: 18,marginLeft:10}}>
全选
</Text>
</View>
</TouchableOpacity>
{/*listView列表*/}
<ListView
dataSource = { this.ds.cloneWithRows(this.Cart.item.slice(0)) }
renderRow = { this._renderRow }
></ListView>
{/*底部的购物车总价,总数量*/}
<Info cart={ this.Cart } ></Info>
</View>
);
}
}
const styles = StyleSheet.create({
container: {
flex: 1,
backgroundColor: 'white',
}
});
AppRegistry.registerComponent('ww', () => ww);
http://www.jianshu.com/p/02449397762d
http://www.jianshu.com/p/c581c48a601f
http://www.jianshu.com/p/3b37a58619b6