例1:在页面中有一个用于输入昵称的表单元素和一个按钮。用户在文本框中输入自己的昵称,单击按钮后获取用户输入的昵称内容,并在掌握台中显示。
class App extends React.Component { constructor(props){ super(props); this.state={ nick:"" } } render(){ return ( <React.Fragment> <label htmlFor="nick">昵称</label> <input type="text" id="nick" value={this.state.nick} onChange={(event)=>{this.nickChange(event)}} /> <div><button onClick={()=>this.getNick()}>获取昵称</button></div> </React.Fragment> ) }}
从上述代码中可以看出,文本框利用value属性绑定了state区的nick数据作为文本框的默认值,即空字符串。同时又为文本框绑定了onChange事宜。该事宜只须要将文本框中用户输入的内容赋值给state区的nick数据即可。文本框中用户输入的内容可以利用onChange事宜函数中的event.tarvar.value获取。
文本框的onChange事宜代码如下所示。

onChange(event){ this.setState({ nick:event.target.value })}
按钮的单击事宜代码如下所示。
getNick(){ console.log(this.state.nick);}
从例1中可以看出,文本框中的value属性只能为文本框绑定一个初始值,当文本框中的文本内容发生变革时,还须要借助onChange事宜来将文本框的值赋给value属性当初绑定的state数据。
例2:在页面中有一个用于输入留言的多行文本域和一个按钮。用户在多行文本框中输入留言文本,单击按钮后获取用户输入的留言内容,并在掌握台中显示。同时随着用户输入文本的增多,在页面中显示已经输入了多少个字符,同时限定最多输入20个字符。
效果图如下所示。
class App extends React.Component { constructor(props){ super(props); this.state={ message:"", inputed:0, total:20 } } render(){ return ( <React.Fragment> <label htmlFor="message">留言:(已输入{this.state.inputed}/{this.state.total})</label> <textarea id="message" value={this.state.message} onChange={(event)=>{this.messageChange(event)}></textarea> <div><button onClick={()=>this.submitMessage()}>提交留言</button></div> </React.Fragment> ) }}
多行文本域的处理办法和文本域的处理办法相同,都是采取value-onChange组合来实现的。当用户在多行文本域中输入内容时,将触发onChange事宜,该事宜代码如下所示。
messageChange(event){ let message=event.target.value; this.setState({ inputed:message.length }) if(this.state.inputed<this.state.total-1){ this.setState({ message }) }}
按钮的单击事宜代码如下所示。
submitMessage(){ console.log(this.state.message);}
在state区中,message数据用来吸收用户在多行文本域中输入的内容,inputed数据用来记录已经输入的文本个数,total数据用来指定最多能够输入的文本个数。
二、单选框的受控利用方法单选框在利用时连续延续文本框和多行文本框的利用办法,唯一不同的是单选框采取的是checked-onChange组合来实现受控操作的。
例3:在页面中有一组用于选择性别的单选框和一个按钮。用户选择了某个单选项之后,单击按钮获取用户所选单选项的内容,并在掌握台中显示。
class App extends Component{ constructor(props){ super(props); this.state={ sex:'男' } } render(){ return ( <React.Fragment> <label>性别:</label> <input type="radio" value="男" checked={this.state.sex==="男"} onChange={(event)=>this.radioChange(event)} /> 男 <input type="radio" value="女" checked={this.state.sex==="女"} onChange={(event)=>this.radioChange(event)} /> 女 <div><button onClick={()=>this.getSex()}>所选性别</button></div> </React.Fragment> ) }}
在上述代码中,每一个单选框同样具备了value属性,但是这个value属性已经和文本框的value属性不一样了,这个value属性为单选框当选中后供应了与其他单选框所不同的数据。checked属性取值为逻辑值,因此绑定的是this.state.sex是不是和指定的取值相等,相等则为true,不相等则为false。
单选框的onChange事宜代码如下所示。
radioChange(event){ this.setState({ sex:event.target.value })}
按钮的单击事宜代码如下所示。
getSex(){ console.log(this.state.sex);}
代码中通过checked属性中的判断来获取哪一个单选项默认当选中,再借助onChange事宜改变state区的sex数据,以实现checked属性和sex数据的双向绑定。
三、复选框的受控利用方法复选框和单选框一样,也是用checked-onChange组合来对其进行操作,但是复选框可以选中多个复选项,而单选框只能选择一个,因此复选框的checked属性一该当绑定的是一个数组。
例4:在页面中有一组用于选择爱好的复选框和一个按钮。用户选择了某些复选项之后,单击按钮获取用户所选复选项的内容,并在掌握台中显示。
效果图如下所示。
class App extends Component{ constructor(props){ super(props); this.state={ favs:["音乐","电影","游戏","跑步","拍浮","读书"], fav:["电影"] } } render(){ return ( <React.Fragment> <label>爱好:</label> { this.state.favs.map((item,index)=>{ return ( <span key={index}> <input type="checkbox" value={item} checked={this.state.fav.includes(item)} onChange={(event)=>this.checkboxChange(event)} /> {item} </span> ) }) } <div><button onClick={()=>this.getFav()}>所选爱好</button></div> </React.Fragment> ) }}
在上述代码中,state区定义了两个数据:favs作为数组供应所有备选的爱好内容,fav作为数组用来存储用户选择的爱好内容。
复选框是由state区的favs进行遍历来实现的。复选框的checked属性取值为逻辑值,绑定的数据是判断favs数组元素item是否在fav数组中,即fav数组中是否包含favs的数组元素item。这里采取的是ES6为数组新增的includes()方法,该方法直接返回参数是否包含在指定的数值中的逻辑值。复选框的onChange事宜代码如下所示。
checkboxChange(event){ let temp=event.target.value; //用户选中的那一个复选框的value属性 let fav=[...this.state.fav]; let index=fav.findIndex(item=>item===temp); if(index!==-1){ //单击该复选框时,该复选框的value属性取值在fav数组中存在 fav.splice(index,1); }else{ //单击该复选框时,该复选框的value属性取值在fav数组中不存在 fav.push(temp); } this.setState({fav});}
按钮的单击事宜代码如下所示。
getFav(){ console.log(this.state.fav)}
该案例涉及到了大量的数组与数组元素之间的操作。虽然同样利用checked-onChange组合来完成,但是两个数组favs和fav之间要进行大量的判断,才能完成终极的效果。
四、菜单的受控利用方法<select>菜单在表单元素中表示下拉菜单,是一个单选元素,同样利用value-onChange组合来进行处理。
例5:在页面中有一组用于选择专业的下拉菜单和一个按钮。用户选择了某个专业之后,单击按钮获取用户所选专业的内容,并在掌握台中显示。
class App extends Component{ constructor(props){ super(props); this.state={ specs:["前端开拓","PHP开拓","Java开拓","UI设计","大数据开拓","人工智能"], spec:"前端开拓" } } render(){ return ( <React.Fragment> <label>专业:</label> <select value={this.state.spec} onChange={(event)=>this.specChange(event)}> { this.state.specs.map((item,index)=>{ return <option value={item} key={index}>{item}</option> }) } </select> <div><button onClick={()=>this.getSpec()}>所选专业</button></div> </React.Fragment> ) }}
在上述代码中,state区定义了两个数据:specs作为数组供应所有备选的专业内容,spec用来存储用户选择的专业内容,由于是单选,因此数据类型为字符串。
下拉菜单的菜单项(即<option>标记)是由state区的specs进行遍历来实现的。由于下拉菜单项具备容器(即<select>标记),因此<select>标记的value属性用来绑定state区的spec数据,作为默认选中项。<option>的value属性而是为下拉菜单项设置当选中后的取值。下拉菜单的onChange事宜代码如下所示。
specChange(event){ this.setState({ spec:event.target.value })}
按钮的单击事宜代码如下所示。
getSpec(){ console.log(this.state.spec)}
仔细剖析,下拉菜单的处理办法实质上和文本框是完备相同的。
五、列表的受控利用方法<select>列表在表单元素中表示列表选择框,是一个可以复选的元素,同样利用value-onChange组合来进行处理。
例6:在页面中有一组用于选择选修课程的下拉列表和一个按钮。用户选择了某些选修课程后,单击按钮获取用户所选的选修课程内容,并在掌握台中显示。
效果图如下所示。
class App extends Component{ constructor(props){ super(props); this.state={ courses:["高档数学","线性代数","概率统计","离散数学","复变函数与积分变换","关系代数"], course:[] } } render(){ return ( <React.Fragment> <label>选修:</label> <select value={this.state.course} onChange={(event)=>this.courseChange(event)} multiple size={this.state.courses.length}> { this.state.courses.map((item,index)=>{ return <option key={index} value={item}> {item} </option> }) } </select> <div><button onClick={()=>this.getCourse()}>所选选修课</button></div> </React.Fragment> ) }}
在上述代码中,state区定义了两个数据:courses作为数组供应所有备选的选修课程内容,course用来存储用户选择的选修课程内容,由于是多选,因此数据类型为数组。
这里供应两种不同的机制来完成<select>标记的onChange事宜。
1、不借助键盘快捷键实现多选。courseChange(event){ let value=event.target.value; let course=[...this.state.course]; // 判断value值是否在course数组中涌现过 let index=course.findIndex(item=>item===value); if(index>=0){ course.splice(index,1); }else{ course.push(value); } this.setState({course});}
2、借助键盘快捷键实现多选。
courseChange(event){ let options=event.target.options; let temp=[]; //盛放当选中的option项的索引值的数组 for(let i in options){ if(options[i].selected){ temp.push(i); } } let course=temp.map(item=>options[item].value); this.setState({course});}
上述事理形成的代码可以简化为以下ES6代码:
let options=event.target.options;let course=Object.keys(options).filter(item=>options[item].selected===true).map(item=>options[item].value);this.setState({course});
总结
本文是React系列教程的第六篇文章,紧张为大家讲解了React表单元素的受控组件操作。文本框、密码域、多行文本域、select列表、select菜单都是采取value-onChange组合来实现受控操作的。单选框、复选框是采取checked-onChange组合来实现受控操作的。同时具有复选功能的复选框和列表须要借助数组来吸收用户所选的内容,操作起来较为繁芜。来日诰日会为大家系统的讲解React中非受控表单元素的利用方法。
关于作者小海前端,具有18年Web项目开拓和前后台培训履历,在前端领域著有较为系统的培训教材,对Vue.js、微信小程序开拓、uniApp、React等全栈开拓领域都有较为深的成绩。入住今日头条,希望能够更多的结识Web开拓领域的同仁,将Web开拓大力的进行遍及。同时也乐意与大家进行深入的技能研讨和商业互助。