今天来写一个组件,相信很多人都会用到的——ViewStack。

ViewStack组件无疑是UI中很重要的一个组件,可惜react-native并没有内嵌进去,需要开发者自己去实现。

实现原理很简单,就是根据索引来显示一个子视图,用一个render即可完成:

 render(){
return(
<View>
{this.props.children[this.props.index]}
</View>
);
}

这样,一个最简单的ViewStack就完成了,那怎么使用呢:

 <ViewStack index={this.state.tabIndex}>
<PageSNS/>
<PageGroup/>
<PageLibrary/>
<PageChat/>
<PageProfile/>
</ViewStack>

通过修改state的tabIndex来切换子视图即可。

是不是挺简单呢!但是,你用着用着就会发现,这有点问题,当你来回切换视图的时候,会发现,子视图的状态每次都重置了,比如在PageSNS视图上,你滚动列表到了下面,然后切换到了其他子视图,再切换回来,会发现列表又从回到顶部了。

那么问题来了,有些开发者就想要这样的体验,那没事。而有些需求确是必须要保留状态,那怎么整呢?

为什么子视图会被重置呢?那就要涉及到react的渲染机制了,它会再render的时候遍历一次所有子节点,把要卸载的都卸载掉,要装载的给装载上去,那就一目了然了。我们的简单版ViewStack仅仅是每次渲染一个子视图,而其他的时候会被卸载掉,当要重新渲染那个视图的时候,那个视图其实已经不在了,在只是新new出来(或者从对象池里拿出来并初始化后)的那个视图了,所以这就是问题的所在了。

那么怎么保留子视图的状态呢?(这个状态并不是react的state机制,而说得是整个视图的逻辑状态,好吧,我也扯不清楚了)

我做了一些测试,发现只要组件被卸载了,那么这个组件就不可能恢复了,或者说恢复代价有点高。当然,方法是有的,而且很简单,只是这种方法比较鲁莽,听我道来。

在使用Navigator组件的时候,会发现,他的子视图怎么能保留状态呢,这个很神奇,难道他把什么引用存起来了?然后我深入Navigator的源码看了下去,发现他坑爹把全部子视图都render了,把要显示的视图给显示,而不需要显示的则移到了屏幕外面,就这么简单啦,我也懵了,原来就是这种方法,相信你也会说一句靠之类的感叹词吧,但是它的确就是这么做的,所以我说这种方法有些鲁莽。

然后我就写下了2.0版的ViewStack:

 /**
* Created by rockyl on 15/11/08.
*/
var React = require('react-native');
var {
StyleSheet,
Component,
View,
} = React;
var Dimensions = require('Dimensions');
var SCREEN_WIDTH = Dimensions.get('window').width;
var SCREEN_HEIGHT = Dimensions.get('window').height; class ViewStack extends Component {
constructor(props) {
super(props);
} static get defaultProps(){
return {
index: 0,
}
}; render(){
this.views = this.props.children.map((page, i)=>{
var style = this.props.index == i ? [styles.viewBase] : [styles.viewBase, styles.viewDisabled];
return (
<View
key={'view_' + i}
style={style}>
{page}
</View>
);
});
return (
<View style={[styles.container, this.props.style,]}>
{this.views}
</View>
);
}
} var styles = StyleSheet.create({
container: {
flex: 1,
overflow: 'hidden',
},
viewBase: {
position: 'absolute',
overflow: 'hidden',
left: 0,
right: 0,
bottom: 0,
top: 0,
},
viewDisabled: {
top: SCREEN_HEIGHT,
bottom: -SCREEN_HEIGHT,
},
}); module.exports = ViewStack;

so easy!

用法和简单版是一样的。

再然后,你用着用着就会发现,这切换的时候好生硬啊,秒切,略缺少点什么用户体验,比如说滚动之类的动画也要啊。

2.1版将携带动画参数和其他高级功能参数,那就要等这篇博文更新啦!

react-native学习笔记——ViewStack组件的更多相关文章

  1. React Native 学习笔记--进阶(二)--动画

    React Native 进阶(二)–动画 动画 流畅.有意义的动画对于移动应用用户体验来说是非常必要的.我们可以联合使用两个互补的系统:用于全局的布局动画LayoutAnimation,和用于创建更 ...

  2. React Native学习笔记之2

    1:如何创建一个react native工程 首先进入到指定文件夹里面,然后在终端执行react-native init ReactNativeProject :其中ReactNativeProjec ...

  3. React Native学习笔记之1

    1:运行React Native报连接错误解决 解决方式: 在终端进入项目文件里,然后执行:(cd Pods/React; npm run start) 2:组件生命周期介绍 创建阶段 1. getD ...

  4. react native 学习笔记

    假设你的机器现在还没安装任何环境. 不同的操作系统.不同的目标平台,具体的步骤也会有所不同.如果你想同时开发android和ios也没问题,只需要先选一个平台开始,另一个平台的环境搭建只是稍有不同 本 ...

  5. React Native学习笔记

    React 是使用ES6 ,支持JSX语法, 开发组件化web或native的工具. 现阶段使用Babel工具转换成ES5 代码. 组件通过props属性传递不变化的内容,UI通过state属性变动来 ...

  6. React Native学习笔记-1:JSC profiler is not supported.(转载)

    运行react-native中Example下的UIEXPLORER Project 遇到虾面报错: 2016-03-21 14:12:18.941 [trace][tid:com.facebook. ...

  7. React Native学习笔记-1:JSC profiler is not supported.

    新建React-Native工程,直接编译运行报错,控制台错误信息如下: 2016-02-22 16:49:47.317 [info][tid:com.facebook.React.JavaScrip ...

  8. React Native 开发笔记

    ReactNativeDemo 学习ReactNative开发,搭建ReactNative第一个项目 React Native 开发笔记 1.安装Homebrew $ /usr/bin/ruby -e ...

  9. iOS、swift、React Native学习常用的社区、论坛

    <!----iOS> <!----Swift>*IOS开发常用社区:http://code4app.com/ *IOS开发常用社区:http://www.cocoachina. ...

随机推荐

  1. ZJUTACM(hd1259)

    ZJUTACM 点我 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total ...

  2. Objextive-C几道小题目笔记

    //掷骰子题,掷骰子100次,输出每个号出现的次数 void one() { for (int i=1; i<=100; i++) { int a = arc4random() % 6 +1; ...

  3. 32位程序调用Oracle11gR2数据库libclntsh.so失败

    [问题描述]32位程序调用Oracle11gR2数据库的libclntsh.so库时会返回失败. [问题原因]32位程序只能调用32位的Oracle客户端实例包,而R2数据库默认安装完毕后是没有lib ...

  4. Callable,Runnable比较及用法

    http://blog.csdn.net/xtwolf008/article/details/7713580 http://www.cnblogs.com/whgw/archive/2011/09/2 ...

  5. 无法关闭的QT程序——思路开阔一下,原来这么简单!

    做一个无法关闭的QT程序(想关闭时要在任务管理器里关闭),看似很难, 其实它并不难,只要让程序在关闭时启动它自身就可以了. 上代码: #include <QtGui> class Temp ...

  6. STL set 使用小结

    这是微软帮助文档中对集合(set)的解释: “描述了一个控制变长元素序列的对象(注:set中的key和value是Key类型的,而map中的key和value是一个pair结构中的两个分 量)的模板类 ...

  7. Python网络资源 + Python Manual

    如何学习Python + 如何有效利用Python有关的网络资源 + 如何利用Python自带手册(Python Manual) 都差点忘了说了,在看下面所有的内容之前,对于python版本不了解的, ...

  8. IP defragment

    snort IP defragment 模型: BSD favors an original fragment with an offset that is less than or equal to ...

  9. Bayesian Formulation on Cooperative Tracking

    Suppose a joint state representing a set of \(N_{n}\) nodes moving in a field\[    \textbf{X}=    \b ...

  10. POJ 动态规划题目列表

    ]POJ 动态规划题目列表 容易: 1018, 1050, 1083, 1088, 1125, 1143, 1157, 1163, 1178, 1179, 1189, 1208, 1276, 1322 ...