Picker简介
在iOS和Android中选择器(Picker)是常见的控件之一,比如TimePickr(Android),pickerView(ios),并且这些基本控件可以实现诸如地址选择等效果。在RN开发中,系统也为我们提供Picker控件。应用如下:
代码语言:javascript复制<Picker
selectedValue={this.state.language}
onValueChange={(lang) => this.setState({language: lang})}>
<Picker.Item label="Java" value="java" />
<Picker.Item label="JavaScript" value="js" />
</Picker>
Picker属性
onValueChange 某一项被选中时执行此回调。调用时带有如下参数:
- itemValue: 被选中项的value属性
- itemPosition: 被选中项在picker中的索引位置
selectedValue 默认选中的值。可以是字符串或整数。
testID
用于在端对端测试中定位此视图。
enabled(Android特有) 如果设为false,则会禁用此选择器。
mode(Android特有)
在Android上,可以指定在用户点击选择器时,以怎样的形式呈现选项:
- dialog(对话框形式): 显示一个模态对话框。默认选项。
- dropdown(下拉框形式): 以选择器所在位置为锚点展开一个下拉框
prompt(Android特有)
设置选择器的提示字符串。在Android的对话框模式中用作对话框的标题。
itemStyle(ios特有)
指定应用在每项标签上的样式。
完整实例
基于上面的属性讲解,我们很容易实现一个Picker的效果。
代码:
代码语言:javascript复制<Picker
selectedValue={this.state.language}
onValueChange={lang => this.setState({language:lang})}
mode="dialog"
style={{color:'#f00'}}
>
<Picker.Item label="Java" value="Java"/>
<Picker.Item label="JavaScript" value="js"/>
<Picker.Item label="C语音" value="c"/>
<Picker.Item label="PHP开发" value="php"/>
</Picker>
综合实例
首先看一个我们在项目中常见的效果图。一般我们的picker上边是取消和确定两个按钮,用来选中或者取消Picker的值,Picker一般会固定高度,然后实现一个拨盘滚动的效果,并且上部分有遮罩层。整个界面在出现或者消失的时候往往会伴随动画(一般用Animated实现)。
显示动画:
代码语言:javascript复制in() {
Animated.parallel([
Animated.timing(
this.state.opacity,
{
easing: Easing.linear,
duration: 500,
toValue: 0.8,
}
),
Animated.timing(
this.state.offset,
{
easing: Easing.linear,
duration: 500,
toValue: 1,
}
)
]).start();
}
//隐藏动画
代码语言:javascript复制out(){
Animated.parallel([
Animated.timing(
this.state.opacity,
{
easing: Easing.linear,
duration: 500,
toValue: 0,
}
),
Animated.timing(
this.state.offset,
{
easing: Easing.linear,
duration: 500,
toValue: 0,
}
)
]).start();
this.timer = setTimeout(
() => this.setState({hide: true}),
500
);
}
完整代码:
代码语言:javascript复制'use strict';
import React, { Component } from 'react';
import {
StyleSheet,
View,
Image,
Text,
TouchableHighlight,
Animated,
Easing,
Dimensions,
Picker,
TouchableOpacity,
} from 'react-native';
const {width, height} = Dimensions.get('window');
const navigatorH = 64; // navigator height
const [aWidth, aHeight] = [width, 214];
const [left, top] = [0, 0];
const styles = StyleSheet.create({
container: {
position:"absolute",
width:width,
height:height,
left:left,
top:top,
},
mask: {
justifyContent:"center",
backgroundColor:"#383838",
opacity:0.8,
position:"absolute",
width:width,
height:height,
left:left,
top:top,
},
tip: {
width:aWidth,
height:aHeight,
// left:middleLeft,
backgroundColor:"#fff",
alignItems:"center",
justifyContent:"space-between",
},
tipTitleView: {
height:53,
width:aWidth,
flexDirection:'row',
alignItems:'center',
justifyContent:'space-between',
borderBottomWidth:0.5,
borderColor:"#f0f0f0",
},
cancelText:{
color:"#e6454a",
fontSize:16,
paddingLeft:30,
},
okText:{
color:"#e6454a",
fontSize:16,
paddingRight:27,
fontWeight:'bold',
},
picker:{
justifyContent:'center',
// height: 216,//Picker 默认高度
width:aWidth,
},
itempicker:{
color:'#e6454a',
fontSize:19,
height:161
}
});
export default class PickerWidget extends Component {
constructor(props) {
super(props);
this.state = {
offset: new Animated.Value(0),
opacity: new Animated.Value(0),
choice:this.props.defaultVal,
hide: true,
};
this.options = this.props.options;
this.callback = function () {};//回调方法
this.parent ={};
}
componentWillUnMount(){
this.timer && clearTimeout(this.timer);
}
render() {
if(this.state.hide){
return (<View />)
} else {
return (
<View style={styles.container} >
<Animated.View style={ styles.mask } >
</Animated.View>
<Animated.View style={[styles.tip , {transform: [{
translateY: this.state.offset.interpolate({
inputRange: [0, 1],
outputRange: [height, (height-aHeight)]
}),
}]
}]}>
<View style={styles.tipTitleView} >
<Text style={styles.cancelText} onPress={this.cancel.bind(this)}>取消</Text>
<Text style={styles.okText} onPress={this.ok.bind(this)} >确定</Text>
</View>
<Picker
style={styles.picker}
mode={Picker.MODE_DIALOG}
itemStyle={styles.itempicker}
selectedValue={this.state.choice}
onValueChange={choice => this.setState({choice: choice})}>
{this.options.map((aOption) => <Picker.Item color='#b5b9be' label={aOption} value={aOption} key={aOption} /> )}
</Picker>
</Animated.View>
</View>
);
}
}
componentDidMount() {
}
//显示动画
in() {
Animated.parallel([
Animated.timing(
this.state.opacity,
{
easing: Easing.linear,
duration: 500,
toValue: 0.8,
}
),
Animated.timing(
this.state.offset,
{
easing: Easing.linear,
duration: 500,
toValue: 1,
}
)
]).start();
}
//隐藏动画
out(){
Animated.parallel([
Animated.timing(
this.state.opacity,
{
easing: Easing.linear,
duration: 500,
toValue: 0,
}
),
Animated.timing(
this.state.offset,
{
easing: Easing.linear,
duration: 500,
toValue: 0,
}
)
]).start();
this.timer = setTimeout(
() => this.setState({hide: true}),
500
);
}
//取消
cancel(event) {
if(!this.state.hide){
this.out();
}
}
//选择
ok() {
if(!this.state.hide){
this.out();
this.callback.apply(this.parent,[this.state.choice]);
}
}
show(obj:Object,callback:Object) {
this.parent = obj;
this.callback = callback;
if(this.state.hide){
this.setState({ hide: false}, this.in);
}
}
}