选择用户组件

仿照微信做的一个选择用户的组件,逻辑很简单。支持单选多选

import React, {
    PureComponent
} from 'react'
import {
    View,
    StyleSheet,
    TouchableOpacity,
    Image,
    Text,
    TextInput,
    ScrollView,
    InteractionManager,
    FlatList,
    Dimensions
} from 'react-native'
import ChatConfig from './ChatConfig'

const defaultUser = require('../images/avatar_contact.png')
const checkedPhto = require('../images/checked.png');
const checkPhto = require('../images/check.png');
export default class SelectUserView extends PureComponent {
    constructor(props) {
        super(props);
        this.state = {
            pageIndex: 1,
            pageSize: 30,
            selectUser: {}
        };
    }

    componentDidMount() {
        InteractionManager.runAfterInteractions(() => {
            this._loadFirstUserList();
        });
    }

    getSelectedUser(userInfo) {
        return this.state.selectUser[userInfo.uuId];
    }

    getSelectedUserArray() {
        let userArray = [];
        for (let i in this.state.selectUser) {
            userArray.push(this.state.selectUser[i]);
        }
        return userArray;
    }

    getSelectedUserAll() {
        return this.state.selectUser;
    }

    setSelectedUser(userInfo) {
        if (this.props.isMulti) {
            if (this.state.selectUser[userInfo.uuId])
                delete this.state.selectUser[userInfo.uuId];
            else
                this.state.selectUser[userInfo.uuId] = userInfo;
            this.refs['searchUserTab'].renderListView(this.state.selectUser);
            this.refs['userListView'].refreshUserList();
        }
        else {
            this.state.selectUser = {};
            this.state.selectUser[userInfo.uuId] = userInfo;
            this.refs['searchUserTab'].renderListView(this.state.selectUser);
        }
    }

    _loadFirstUserList = () => {
        this.state.pageIndex = 1;
        //查询用户
    };

    _loadNextUserList() {
        this.state.pageIndex = this.state.pageIndex + 1;
        //查询用户
    }

    render() {
        return (
            <View style={{flex: 1, backgroundColor: '#fff'}}>
                <SearchUserTab loadFirstUserList={() => this._loadFirstUserList()}
                               setSelectedUser={(userInfo) => this.setSelectedUser(userInfo)}
                               ref="searchUserTab"/>
                <UserListView isMulti={this.props.isMulti} loadNextUserList={() => this._loadNextUserList()}
                              loadFirstUserList={() => this._loadFirstUserList()}
                              getSelectedUser={(userInfo) => this.getSelectedUser(userInfo)}
                              setSelectedUser={(userInfo) => this.setSelectedUser(userInfo)} ref="userListView"/>
            </View>
        );
    }
}

class SearchUserTab extends PureComponent {
    constructor(props) {
        super(props);
        this.state = {
            userList: {},
            value: ''
        };
    }

    renderListView(list) {
        this.setState({
            userList: list
        });
    }

    getSearchValue() {
        return this.state.value;
    }

    deleteSelected(userInfo) {
        this.props.setSelectedUser(userInfo);
    }

    _renderPhoto = (userInfo) => {
        if (userInfo.photo)
            return {uri: userInfo.photo};
        else
            return defaultUser;
    };

    _renderSelectedList() {
        this._selectedView = [];
        for (let i in this.state.userList) {
            this._selectedView.push(<TouchableOpacity key={i} activeOpacity={1}
                                                      onPress={() => this.deleteSelected(this.state.userList[i])}><Image
                style={styles.selectedUserPhto}
                source={this._renderPhoto(this.state.userList[i])}/></TouchableOpacity>);
        }
        return this._selectedView;
    };

    _onContentSizeChange = () => {
        this.refs["listUser"].scrollToEnd({animated: false});
    }

    _renderSelectedUser() {
        if (Object.keys(this.state.userList).length == 0)
            return null;
        else
            return (
                <View style={{
                    height: 45,
                    width: Object.keys(this.state.userList).length > 5 ? (5 * 50) : (Object.keys(this.state.userList).length * 50)
                }}>
                    <ScrollView onContentSizeChange={() => this._onContentSizeChange()} ref="listUser"
                                style={{height: 45}} horizontal={true}>
                        {this._renderSelectedList()}
                    </ScrollView>

                </View>
            );
    };

    _onChangeText(event) {
        if (this.state.value == '' && event.nativeEvent.text == '' && Object.keys(this.state.userList).length != 0) {
            let lastUser;
            for (let i in this.state.userList) {
                lastUser = this.state.userList[i];
            }
            this.props.setSelectedUser(lastUser);
        }
        this.setState({
            value: event.nativeEvent.text
        });
        console.log(event.nativeEvent.text);
    }

    render() {
        return (
            <View style={styles.searchView}>
                {this._renderSelectedUser()}
                <TextInput ref="txt_message" placeholder={ChatConfig.SEARCH}
                           returnKeyType="search"
                           returnKeyLabel="search"
                           style={styles.textInput}
                           editable={true}
                           keyboardType='default'
                           autoCapitalize='none'
                           autoCorrect={false}
                           value={this.state.value}
                           onSubmitEditing={() => this.props.loadFirstUserList()}
                           onChange={(event) => this._onChangeText(event)}
                           underlineColorAndroid='transparent'
                />
            </View>
        );
    }
}


class UserListView extends PureComponent {
    constructor(props) {
        super(props);
        this.state = {
            isRefreshing: true,
            dataList: [],
            isLastPage: false
        };
    }

    setIsLastPage() {
        this.state.isLastPage = true;
    }

    setFirstList(list) {
        this.setState({
            dataList: list,
            isRefreshing: false
        });
    }

    setUserList(list) {
        this.setState({
            dataList: this.state.dataList.concat(list)
        });
    }

    _renderPhoto = (userInfo) => {
        if (userInfo.photo)
            return {uri: userInfo.photo};
        else
            return defaultUser;
    };
    _selectUser = (userInfo, index) => {
        this.props.setSelectedUser(userInfo);
    };

    refreshUserList() {
        this.setState(this.state);
    }

    _renderCheckBox = (userInfo) => {
        if (this.props.isMulti) {
            return (
                <View style={styles.userItemRight}>
                    <Image style={styles.checkedImage}
                           source={this.props.getSelectedUser(userInfo) ? checkedPhto : checkPhto}/>
                </View>
            );
        }
        else
            return null;
    };

    _renderItem = (item) => {
        let userInfo = item.item;
        return (
            <TouchableOpacity activeOpacity={1} onPress={() => this._selectUser(userInfo, item.index)}>
                <View style={styles.userItem}>
                    <View style={styles.userItemLeft}>
                        <Image style={styles.userPhoto} source={this._renderPhoto(userInfo)}/>
                    </View>
                    <View style={styles.userItemCenter}>
                        <Text numberOfLines={1}>{userInfo.userName}</Text>
                    </View>
                    {this._renderCheckBox(userInfo)}
                </View>
            </TouchableOpacity>
        );
    };
    _separator = () => {
        return <View style={styles.separator}/>;
    };

    _onEndReached = () => {
        if (!this.state.isLastPage && this.state.dataList.length != 0)
            this.props.loadNextUserList();
    };

    _onRefresh = () => {
        this.setState({
            isRefreshing: true
        });
        this.props.loadFirstUserList();
    };

    _keyExtractor = (item, index) => item.uuId;

    render() {
        return (
            <FlatList refreshing={this.state.isRefreshing} onRefresh={() => this._onRefresh()}
                      ItemSeparatorComponent={this._separator} ref="listMessage"
                      extraData={this.state}
                      keyExtractor={this._keyExtractor}
                      data={this.state.dataList}
                      onEndReached={this._onEndReached}
                      renderItem={this._renderItem}/>
        );
    }
}

const styles = StyleSheet.create({
    searchView: {
        height: 60,
        paddingLeft: 10,
        paddingRight: 10,
        borderColor: '#efeff4',
        borderBottomWidth: 1,
        flexDirection: 'row',
        alignItems: 'center'
    },
    textInput: {
        flex: 1,
        fontSize: 15,
        borderWidth: 0,
        height: 45,
        textAlignVertical: 'center'
    },
    separator: {
        backgroundColor: '#efeff4',
        height: 1
    },
    userItem: {
        height: 60,
        flexDirection: 'row',
        backgroundColor: '#fff',
        paddingLeft: 10,
        paddingRight: 10,
    },
    userPhoto: {
        width: 45,
        height: 45
    },
    selectedUserPhto: {
        width: 45,
        height: 45,
        marginRight: 5
    },
    userItemLeft: {
        justifyContent: 'center',
        width: 45
    },
    userItemCenter: {
        marginLeft: 10,
        justifyContent: 'center',
        flex: 1
    },
    userItemRight: {
        width: 40,
        alignItems: 'center',
        justifyContent: 'center'
    },
    checkedImage: {
        width: 20,
        height: 20
    }
});

  

posted @ 2017-12-21 11:32  不骄不傲  阅读(453)  评论(0编辑  收藏  举报