joywok-material-components
Version:
<h1 align="center"> Joywok Material Components </h1>
370 lines (363 loc) • 12.9 kB
JavaScript
import React from 'react';
import { withStyles } from '@material-ui/core/styles';
import InputBase from "@material-ui/core/InputBase/InputBase";
import Popper from '@material-ui/core/Popper';
import Fade from '@material-ui/core/Fade';
import Paper from '@material-ui/core/Paper';
import ClickAwayListener from '@material-ui/core/ClickAwayListener';
import Chip from '@material-ui/core/Chip';
import TagFacesIcon from '@material-ui/icons/TagFaces';
import request from './../utils/request';
require('./style/customSelect.css');
const styles = theme => ({
root: {
width: '100%',
},
inputRoot: {
color: 'inherit',
marginLeft:"5px"
},
inputInput: {
transition: theme.transitions.create('width'),
color: "#333",
fontSize:14,
lineHeight:1
},
list:{
maxHeight:'300px',
overflowY:'auto'
}
});
class CustomSelect extends React.Component {
constructor(props) {
super(props);
this.state = {
open:false,
loading:false,
list:[],
check:props.checked || [],
anchorEl:null,
value:''
}
this.fetchTime = null
}
inputChange(e){
let self = this;
let value = e.target.value;
let target = this.refs.container;
self.setState({
value:value
})
clearTimeout(this.fetchTime);
if(value.length!=0){
this.fetchTime = setTimeout(function(){
self.setState({
loading:true,
anchorEl:target
})
self.setState({
open:true
})
let url = self.props.url.replace('{jw.form.search}',value)
request(url,{
method:'GET',
}).then(function(resp){
if(resp['data']['success'] && resp['data']['success'] == 0){
}else{
self.setState({
list:resp.data['list'] || resp.data['data'],
loading:false
})
}
})
},800)
$(document).off('click').one('click',function(){
self.setState({
open:false,
})
})
}else{
self.setState({
open:false,
list:[],
loading:false
})
}
}
onKeyDown(e){
let code = e.keyCode;
if(code == '38' || code == '40'){
let item = $('.custom-search-popper .search-item');
let nowActive = $('.custom-search-popper .search-item.active').eq(0);
if(nowActive.length!=0){
let nowIndex = parseInt(nowActive.attr('data-index'));
item.removeClass('active');
if(code == '38'){
nowIndex = nowIndex - 1;
if(nowIndex==-1){
$('.custom-search-popper .search-item').eq(item.length-1).addClass('active');
}else{
$('.custom-search-popper .search-item').eq(nowIndex).addClass('active');
}
}else{
nowIndex = nowIndex+ 1;
if(nowIndex==item.length){
$('.custom-search-popper .search-item').eq(0).addClass('active');
}else{
$('.custom-search-popper .search-item').eq(nowIndex).addClass('active');
}
}
}else{
item.removeClass('active');
if(code == '38'){
$('.custom-search-popper .search-item').eq(item.length-1).addClass('active');
}else{
$('.custom-search-popper .search-item').eq(0).addClass('active');
}
}
e.preventDefault()
//上下
}
if(code == '13'){
//确定
let index = $('.custom-search-popper .search-item.active').attr('data-index');
// console.log(index,'asdasdasd');
if(typeof(index) != 'undefined'){
let data = this.state.list[index];
this.choseItem(e,data);
}
e.preventDefault();
}
}
onMouseOver(index){
let item = $('.custom-search-popper .search-item');
item.removeClass('active');
item.eq(index).addClass('active');
}
onMouseOut(index){
}
handleDelete(e,data){
let self = this;
if(typeof(this.props.onDelete)!='undefined'){
this.props.onDelete(e,data)
}else{
if(typeof(this.props.sigle)!='undefined'){
this.setState({
check:{},
})
self.props.onChange && self.props.onChange({})
setTimeout(function(){
self.inputFocus();
},100)
}else{
let newList = [];
// console.log(this.state.check,data,'dsadasdasdasd');
_.each(this.state.check,function(i){
// if(i['id'] != data['id']){
// newList.push(i)
// }
if(i['id']){
if(i['id'] != data['id']){
newList.push(i)
}
}else{
if(i['key']){
if(i['key'] != data['key']){
newList.push(i)
}
}else{
if(i['value']){
if(i['value'] != data['value']){
newList.push(i)
}
}
}
}
});
this.setState({
check:newList,
})
this.inputFocus();
self.props.onChange && self.props.onChange(newList)
}
}
}
inputFocus(){
$(this.refs.container).find('input').focus();
}
customHandleDelete(e,data){
console.log(e,data,'这个是什么啊');
}
handleClickAway(){
}
choseItem(e,data){
let self = this;
let check = this.state.check;
if(typeof(this.props.sigle)!='undefined'){
check = data;
this.setState({
check:check,
open:false,
value:''
})
}else{
if(_.findWhere(check,{id:data['id'] || data['key'] || data['value']})){
this.setState({
value:''
})
}else{
check.push(data);
this.setState({
open:false,
check:check,
value:''
})
}
this.inputFocus();
}
self.props.onChange && self.props.onChange(check)
}
_initElement(){
let self = this;
const { classes } = this.props;
const { anchorEl } = this.state;
if(typeof(this.props.sigle)!='undefined'){
let chipData = {
className:"custom-select-check-i",
key:(this.state.check.id || this.state.check.key || this.state.check.value ),
onDelete:(e)=>self.handleDelete(e,this.state.check),
label:this.state.check['name']|| this.state.check['label'],
title:this.state.check['name']|| this.state.check['label']
}
if(this.props.disabled || this.props.autoShowDis){
delete chipData['onDelete']
}
return <div className="custom-select-c" ref="container" onClick={(e)=>this.inputFocus(e)}>
{
this.state.value.length!=0 || this.state.check.id || this.state.check.key || this.state.check.value ?'':<div className="custom-select-placeholder">{this.props.placeholder}</div>
}
<div className="custom-select-list">
{
this.state.check && (this.state.check.id || this.state.check.key || this.state.check.value )?<Chip
{...chipData}
/>:''
}
{
this.state.check && (this.state.check.id || this.state.check.key || this.state.check.value )?'':<InputBase
classes={{
root: classes.inputRoot,
input: classes.inputInput,
}}
className="custom-select-search-input"
value={this.state.value}
onChange={(e)=>self.inputChange(e)}
onKeyDown={(e)=>self.onKeyDown(e)}
disabled={self.props.disabled?true:false}
ref="input"
/>
}
</div>
{
typeof(chipData.autoShowDis)!='undefined'?<div className="custom-select-auto-remove" onClick={(e)=>self.handleDelete(e,this.state.check)}><svg focusable="false" viewBox="0 0 24 24" aria-hidden="true" role="presentation"><path d="M12 2C6.47 2 2 6.47 2 12s4.47 10 10 10 10-4.47 10-10S17.53 2 12 2zm5 13.59L15.59 17 12 13.41 8.41 17 7 15.59 10.59 12 7 8.41 8.41 7 12 10.59 15.59 7 17 8.41 13.41 12 17 15.59z"></path></svg></div>:""
}
</div>
}else{
return <div className="custom-select-c" ref="container" onClick={(e)=>this.inputFocus(e)}>
{
this.state.value.length!=0 || (this.state.check.length>0)?'':<div className="custom-select-placeholder">{this.props.placeholder}</div>
}
<div className="custom-select-list">
{
this.state.check && this.state.check.length!=0?_.map(this.state.check,function(i){
let chipData = {
className:"custom-select-check-i",
key:(i['id'] || i['key'] || i['value']),
onDelete:(e)=>self.handleDelete(e,i),
label:i['name']|| i['label'],
title:i['name']|| i['label']
}
if(self.props.disabled){
delete chipData['onDelete']
}
return <Chip
{...chipData}
/>
}):''
}
{
this.state.max && this.state.check.length!=0 && this.state.max <=this.state.check.length?'':<InputBase
classes={{
root: classes.inputRoot,
input: classes.inputInput,
}}
className="custom-select-search-input"
value={this.state.value}
onChange={(e)=>self.inputChange(e)}
onKeyDown={(e)=>self.onKeyDown(e)}
disabled={self.props.disabled?true:false}
ref="input"
/>
}
</div>
</div>
}
}
render(){
let self = this;
const { classes } = this.props;
const { anchorEl } = this.state;
let icon = <TagFacesIcon/>
return(<div className={"custom-select "+(this.props.className || "")} ref="main">
{self._initElement()}
<div className="custom-select-showlist">
<ClickAwayListener onClick={(e)=>self.handleClickAway(e)}>
<Popper
id="custom-search-popper"
open={this.state.open}
placement={'bottom-start'}
anchorEl={anchorEl}
modifiers={{
}}
className={'custom-search-popper custom-search-selectlist'}
style={{
width:$(this.refs.container).width()+'px',
marginTop:'10px',
marginBottom:"10px"
}}
transition
>
{({ TransitionProps }) => (
<Fade {...TransitionProps} timeout={350}>
{
self.state.loading?<Paper><div className={'custom-search-loading'}>加载中…</div></Paper>:
<Paper className={classes.list}>
{
self.state.list.length!=0?_.map(self.state.list,function(i,index){
return <div className={"search-item"} data-index={index} data-id={i['id'] || i['key']} onMouseOver={(e)=>self.onMouseOver(index)} onMouseOut={(e)=>self.onMouseOut(index)} onClick={(e)=>self.choseItem(e,i)}>
<div className={"search-item-info"}>
<div className={'search-item-info-l'}>
<div className={'search-item-info-i name ellipsis'} title={i['name'] || i['label']}>
{i['name'] || i['label']}
</div>
</div>
</div>
</div>
}):<div className={'custom-search-none'}>暂无数据</div>
}
</Paper>
}
</Fade>
)}
</Popper>
</ClickAwayListener>
</div>
</div>)
}
componentWillReceiveProps(nextProps, nextState){
// console.log(nextProps,'zzzzzz');
this.setState({
check:nextProps.checked
})
}
}
export default withStyles(styles)(CustomSelect);