前端车牌号的虚拟键盘实现

车牌号的虚拟键盘实现

直接上代码吧,逻辑不复杂,就是繁琐

component组件:

import React, { Component } from 'react';
import { Icon } from 'components';
class LicensePlate extends Component {
    constructor(props) {
        super(props);
        this.state = {
            value: this.props.value||"",//直接使用props.value会在点击提交时,无法保存组件状态。建议使用setValue
            showkeyboard: false,
            marking: 0,
            nowId: null,
            val0: '',
            val2: '',
            val3: '',
            val4: '',
            val5: '',
            val6: '',
            val7: '',
            chineseList: [
                { name: '京', id: 1 },
                { name: '津', id: 2 },
                { name: '冀', id: 3 },
                { name: '晋', id: 4 },
                { name: '蒙', id: 5 },
                { name: '辽', id: 6 },
                { name: '吉', id: 7 },
                { name: '黑', id: 8 },
                { name: '沪', id: 9 },
                { name: '苏', id: 10 },
                { name: '浙', id: 11 },
                { name: '皖', id: 12 },
                { name: '闽', id: 13 },
                { name: '赣', id: 14 },
                { name: '鲁', id: 15 },
                { name: '豫', id: 16 },
                { name: '鄂', id: 17 },
                { name: '湘', id: 18 },
                { name: '粤', id: 19 },
                { name: '桂', id: 20 },
                { name: '琼', id: 21 },
                { name: '渝', id: 22 },
                { name: '川', id: 23 },
                { name: '贵', id: 24 },
                { name: '云', id: 25 },
                // { name: '藏', id: 26 },
                { name: '陕', id: 27 },
                { name: '甘', id: 28 },
                { name: '青', id: 29 },
                { name: '宁', id: 30 },
                { name: '新', id: 31 },
                { name: '藏', id: 32 },
                { name: '使', id: 33 },
                { name: '领', id: 34 },
                { name: '警', id: 35 },
                { name: '学', id: 36 },
                { name: '港', id: 37 },
                { name: '澳', id: 38 },
                { name: '', id: 99 },
            ],
            englishNumber: [
                { name: '1', id: 28 },
                { name: '2', id: 29 },
                { name: '3', id: 30 },
                { name: '4', id: 31 },
                { name: '5', id: 32 },
                { name: '6', id: 33 },
                { name: '7', id: 34 },
                { name: '8', id: 35 },
                { name: '9', id: 36 },
                { name: '0', id: 37 },
                { name: 'Q', id: 38 },
                { name: 'W', id: 39 },
                { name: 'E', id: 40 },
                { name: 'R', id: 41 },
                { name: 'T', id: 42 },
                { name: 'Y', id: 43 },
                { name: 'U', id: 44 },
                { name: 'I', id: 45 },
                { name: 'O', id: 46 },
                { name: 'P', id: 47 },
                { name: 'A', id: 48 },
                { name: 'S', id: 49 },
                { name: 'D', id: 50 },
                { name: 'F', id: 51 },
                { name: 'G', id: 52 },
                { name: 'H', id: 53 },
                { name: 'J', id: 54 },
                { name: 'K', id: 55 },
                { name: 'L', id: 56 },
                { name: 'Z', id: 57 },
                { name: 'X', id: 58 },
                { name: 'C', id: 59 },
                { name: 'V', id: 60 },
                { name: 'B', id: 61 },
                { name: 'N', id: 62 },
                { name: 'M', id: 63 },
                { name: '', id: 99 },
            ],
        };
    }
    onClickFocus(e) {
        this.setState({
            marking: e.target.title*1
        })
        this.keyboardShow()
    }
    onConfirm() {
        let { val0,val1,val2,val3,val4,val5,val6,val7}=this.state
        this.keyboardHide()
        this.setState({
            value:val0+val1+val2+val3+val4+val5+val6+val7,
        })
    }
    // 清空,供外部调用
    clearValue() {
        this.setState({
            value: ''
        })
    }
    //获取,供外部调用
    getValue() {
        return this.state.value
    }
    //获取值
    setValue(val) {
        let obj = {}
        for (let i = 0; i < val.length; i++) {
            obj[`val${i}`]=val.slice(i,i+1)
        }
        this.setState({
            value: val,
            ...obj
        });
    }
    onChangeFocus(e) {
        if (e.target.title == 45 || e.target.title == 46) {//点击o和i无效化
            return
        }
        let nowId = e.target.title
        if (e.target.title == 99) {//回格
            let obj2={}
             let { marking } = this.state
            obj2[`val${marking}`] =''
            this.setState({
                value: this.state.value.substring(0, this.state.value.length - 1),
                nowId,
                marking:this.state.marking==0?this.state.marking: --marking,
                ...obj2
            })
            return
        }
        let obj = {}
        switch (this.state.marking) {//字符串转换
            case 0:
                obj.val0 = e.target.accessKey
                break;
            case 1:
                obj.val1 = e.target.accessKey
                break;
            case 2:
                obj.val2 = e.target.accessKey
                break;
            case 3:
                obj.val3 = e.target.accessKey
                break;
            case 4:
                obj.val4 = e.target.accessKey
                break;
            case 5:
                obj.val5 = e.target.accessKey
                break;
            case 6:
                obj.val6 = e.target.accessKey
                break;
            case 7:
                obj.val7 = e.target.accessKey
                break;
            default:
                break;
        }
        this.setState({
            nowId,
            marking: this.state.marking>6?this.state.marking: ++this.state.marking,
            ...obj
        })
    }
    renderPasswordGrid() {
        let length = this.props.length;
        let htmls = [];
        let marking = this.state.marking;
        for (let i = 0; i < length; i++) {
            let classN = this.state.val0==''&&i==0?"color":"";
            let el = (
                <div key={i} title={i} className={[ marking == i ? `${classN} activeColor passwordHolder` : `${classN} passwordHolder`]}>
                    { this.state.val0==''&&i==0?"省":this.state[`val${i}`]}
                </div>
            )
            //最后的新能源是否显示
            if (i == length - 1 && marking < 7 && this.state.val7=='') {
                el = (
                    <div key={i} title={i} className="last" > <div title={i}  className="last1" ></div><div  className="last2" title={i}>能源</div> </div>
                )
            }
            htmls.push(el);
        }
        return htmls;
    }
    keyboardHide() {
        this.setState({
            showkeyboard: false
        })
    }
    keyboardShow() {
        this.setState({
            showkeyboard: true
        })
    }
    render() {
        let {  chineseList, englishNumber, showkeyboard, nowId } = this.state;
        let dataList = this.state.marking==0 ? chineseList : englishNumber
        return (
            <div>
                <div className="passwordGrid" >
                    <div className="passwordGridItemWrap" onClick={(e) => this.onClickFocus(e)}>{this.renderPasswordGrid()}
                    </div>
                </div>
                {showkeyboard &&
                    <div className="keyboard-box" >
                        {
                            dataList.map((item) => {
                                let disabled = item.id == 45 || item.id == 46 ? "disabled" : ""
                                return (<div key={item.id} className={item.id == 99 ? "back cont-box " : nowId == item.id ? "cont-box active" : ` cont-box ${disabled}`}
                                    title={item.id} accessKey={item.name} onClick={(e) => this.onChangeFocus(e)} >
                                    {item.name}
                                    {item.id == 99 && <Icon name={"shanchu1"} size={22} title={99} />}
                                </div>)
                            })
                        }
                        <div className="confirm" onClick={(e) => this.onConfirm(e)} >确定</div>
                    </div>
                }
            </div>
        )
    }
}

LicensePlate.defaultProps = {
    length: 8
}

export default LicensePlate;

CSS样式:

 .passwordGrid{
            .passwordGridItemWrap{
                font-weight: 500;
                font-size: 40px;
                .passwordHolder{
                    width: 73px;
                    height: 88px;
                    background: #F0F2F5;
                    border: 1px solid #E6E7EB;
                    border-radius: 8px;
                    line-height: inherit;
                    margin-right: 5px;
                }
                .activeColor{
                    background: #FFF2F0;
                    border: 1px solid #FB5B3B;
                }
                .color{
                    color: #BABDC2;
                }
               .last{
                width: 73px;
                height: 88px; 
                position:absolute;
                background: #F0FFF0;
                border: 1px solid #79E083;
                border-radius: 8px;
                display: inline-flex;
                right: 0;
                align-items: center;
                flex-direction: column;
                font-size: 12px;
                color: #79E083;
                margin-right: 8px;
                .last1{
                    position: absolute;
                    top: -16%;
                    font-size: 24px;
                }
                .last2{
                    position: absolute;
                    top: 20%;
                    font-size: 24px;
                }
               }

            }

        }
        .keyboard-box{
            position: absolute;
            bottom: 0;
            left: 0;
            height: 480px;
            width: 100%;
            background:#E1E2E6;
            padding-left: 16px;
            padding-top: 76px;
          
            .cont-box{
                width: 61px;
                height: 88px;
                margin-right: 12px;
                display: inline-block;
                background: #FFFFFF;
                border-radius: 8px;
                text-align: center;
                margin-bottom: 16px;
            }
            .cont-box:nth-child(31){
                margin-left: 36px;
            }
            .active{
                background: #FB5B3B;
                color: #FFFFFF;
            }
            .disabled{
                color: #CCCCCC;
            }
            .confirm{
                position: absolute;
                top: 0;
                right: 50px;
            }
            .back {
                width: 134px ;
            }
        }

效果:
在这里插入图片描述
在这里插入图片描述

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值