今天来写一个组件,相信很多人都会用到的——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. autofac使用笔记

    在之前的项目中用来解耦的使用的轻型IOC框架是unity,它的使用也是很方便的提供在之前的文章的也提到过它的使用方式,但是使用久了之后发现了它的不足之处就是需要配置xml文件来对应的接口和实现的关系. ...

  2. XML的DTD约束

    DTD约束:DTD的声明和引用 1.内部DTD文档 <!DOCTYPE 根元素 [定义内容]> 2.外部DTD文档 <!DOCTYPE 根元素 SYSTEM "DTD文件路 ...

  3. 【LeetCode练习题】First Missing Positive

    First Missing Positive Given an unsorted integer array, find the first missing positive integer. For ...

  4. C语言 EOF是什么?

    Linux中,在新的一行的开头,按下Ctrl-D,就代表EOF(如果在一行的中间按下Ctrl-D,则表示输出"标准输入"的缓存区,所以这时必须按两次Ctrl-D):Windows中 ...

  5. vs2010中看不见类视图和资源视图的解决方法

    vs2010工程中,因为删除了“vcxproj.filter”文件,所以导致资源视图看不见了. 解决方法是:先关掉工程,将工程对应的扩展名为.suo和.sdf删除,重新打开解决方案,问题解决.

  6. poj 3641 Pseudoprime numbers(快速幂)

    Description Fermat's theorem states that for any prime number p and for any integer a > 1, ap = a ...

  7. wxpython 拖放

    拖放对用户是非常直观.它在许多桌面应用程序,用户可以复制或只需用鼠标拖动和删除另一个窗口中移动对象从一个窗口到另一个中. 拖放操作包括以下步骤 - 声明拖放目标 创建数据对象 创建 wx.DropSo ...

  8. MODULE_AUTHOR、MODULE_DESCRIPTION、MODULE_LICENSE宏

    在阅读Linux Driver源码时,我们常常会在文件的结尾处看到诸如:MODULE_AUTHOR.MODULE_DESCRIPTION.MODULE_LICENSE等宏定义,这些宏主要是定义了一些模 ...

  9. JAVA File类 分析(三)

    前面两篇与大家一起研究了unix下的文件系统,本篇将和大家一起分析 文件的属性和文件夹. ok,废话不说,先来段代码 #include <stdio.h> #include <sys ...

  10. leetcode_question_102 Binary Tree Level Order Traversal

    Given a binary tree, return the level order traversal of its nodes' values. (ie, from left to right, ...