客户端开发算是告一段落,做个总结,总结经验,以便更好的开发商家端
导航
导航结构纠结来纠结去的,最终采用的是 react-navigation 确实很强大,强大到令你窒息,支持iOS的stack,还有tabbar,结构,各种跳转,重置,router and so on。具体自己查,这里不展开了
- 创建
首先介绍下项目结构,先看图
![](https://img.haomeiwen.com/i1775672/b7c4552868d42556.jpg)
大致来说 Tab结构有四个组件
- Tab
- 订水
- 水站
- 购物车
- 我
看代码
const Tab =TabNavigator(
{
Home:{
screen:Home
},
WaterStationList:{
screen:WaterStationList
},
ShoppingCart:{
screen:ShoppingCart
},
Me:{
screen:Me
});
这是底层最基本的组件。这里使用了TabNavigator组件,
- App初始化
目前的初始化流程如下
1 应用启动 -- 申请定位 -- 获取用户当前位置信息 -- 后台请求当前位置附近的水站列表 -- 当前位置变化 -- 重新获取附近的水站列表
全局结构
然后呢?其他界面咋办?那就要用到 react-navigation家族的另外一个组件了,StackNavigator比如首页,点击商品,或者水票。这里简写一下,看代码,秒懂。
const App = StackNavigator(
{
Root: {screen: Tab},
ProductDetail:{screen: ProductDetail}
TicketList:{screen: TicketList}
.....
},
Mobx vs Redux
这次采用了mobx的状态容器管理,对于两者 的对比,这里不展开介绍,只点拨下实现原理。
- Redux
应用中所有的 state 都以一个对象树的形式储存在一个单一的 store 中,纯函数式实现。 - Mobx
Mobx 使用了 Object.defineProperty 拦截 getter 和 setter,这个就是核心。最新实现机制【es6之后】可能会转向为proxy (代理模式),
数据
与后台交互
先吐槽一下,我希望的后台返回的数据结构,这个结构不能变,我前端能很方便的从底层全局处理一些展示,
response:{
retCode:200/xxx
status:'success/fail'
message:'xxxxxx',
data:{
xxxxx
oooo
}
}
,然鹅现在返回的狗屎数据我也就将就将了。
- 支付
前端没啥逻辑流程上
1 商品确认
2 生成订单
3 后台生成tn
4 客户端向第三方【微信 支付包】请求并传递tn等参数
5 从第三方返回应用后,向后台请求支付结果查询
6 展示支付结果
- 异常处理
按理说 应该在请求底层拦截status后全局处理,现在没处理。
React
- 类
- 静态
- 函数式
- lamda表达式
购物车
![](https://img.haomeiwen.com/i1775672/c1d55775606555bc.jpeg)
目前的购物车主要逻辑由后台完成,前端主要展示数据以及简单的加减商品操作,基于店铺维度的支付,建立如下模型
import {observer} from 'mobx-react/native'
import {observable, action, computed, observe} from 'mobx'
class ProductItem{
@observable _selectCount = 0;
constructor(item){
this._selectCount = item.selectCount ;
}
@action increase(){
this._selectCount++ ;
}
@action decrease(){
this._selectCount-- ;
}
@computed get selectCount(){
return this._selectCount ;
}
}
class Shop{
@observable _productItemList = [] ;
constructor(shop){
this._productItemList = shop.list.map(item=>{
return new ProductItem(item);
})
}
@computed get productItemList(){
return this._productItemList ;
}
}
class ShoppingCartStore{
@observable _shoplist = [] ;
constructor(){
this.refreshShoppingCart();
}
@action
refreshShoppingCart(){
let result = shoplist ; //模拟网络请求
this._shoplist = result.map(shop=>{
return new Shop(shop);
})
}
@computed get shopList(){
return this._shoplist ;
}
}
- 本地
- 同步
用户角色
- 游客 tourist
- 登录用户 user
本地把购物车模块逻辑放到后台处理,就引申出来一个问题,未登录用户的操作数据该如何保存,现在的处理逻辑是:
用户启动App,即给登陆一个游客身份,这样一来,用户的操作就可以保存了,例如加入购物车,当真正手机号登录的时候,数据迁移到正式用户中,保证体验的一致。
性能优化
- 性能优化点很多,简单的罗列几个
1:代码规范方面 调试的console要能很方便的去除,最简单的
global.LOG = (...args) => {
console.log('**********************');
console.log(...args);
console.log('**********************');
return args[args.length - 1];
};
等正式发布的时候
global.LOG = (...args) => {};
2:项目中能用色值就不用图片,减少安装包的大小。
3:慎用setState,因其容易导致重新渲染
4:方法的bind一律置于constructor
5:只传递component需要的props
6:尽量使用const element,
7: 组件尽量细化,尽量实现局部渲染
8:list优化。。。。待完善
网友评论