1.受控组件案例
1.1之前的影院案例改写
import React, { Component } from 'react'
import axios from 'axios'
import BetterScroll from 'better-scroll'
import './css/02_tab.css'
export default class Cinema extends Component {
constructor() {
super();
this.state = {
cinemaList: [],
mytext:''
// backcinemaList: []
}
//react中使用axios第三方的库 专门用来请求数据
// axios.get("请求地址").then(res=>{}).catch(err=>{console.log(err);})
axios({
url: "https://m.maizuo.com/gateway?cityId=110100&ticketFlag=1&k=7406159",
method: 'get',
headers: {
'X-Client-Info': '{"a":"3000","ch":"1002","v":"5.0.4","e":"16395416565231270166529","bc":"110100"}',
'X-Host': 'mall.film-ticket.cinema.list'
}
}).then(res => {
console.log(res.data)
this.setState({
cinemaList: res.data.data.cinemas,
// backcinemaList: res.data.data.cinemas
})
new BetterScroll(".wrapper")
}).catch(err => console.log(err))
}
render() {
return (
<div>
<div>
{/* <input onInput={this.handleInput}></input>实时搜索 */}
<input value={this.state.mytext} onChange={(evt)=>{
this.setState({
mytext:evt.target.value
},()=>{
console.log(this.state.mytext);
})
}}></input>实时搜索
</div>
<div className='wrapper' style={{height:'800px',overflow:'hidden'}}>
<div className='content'>
{
this.getCinemaList().map((item) =>
<dl key={item.cinemaId}>
<dt>{item.name}</dt>
<dd>{item.address}</dd>
</dl>
)
}
</div>
</div>
</div>
)
}
getCinemaList=()=>{
//return this.state.cinemaList
return this.state.cinemaList.filter(item =>
item.name.toUpperCase().includes(this.state.mytext.toUpperCase()) ||
item.address.toUpperCase().includes(this.state.mytext.toUpperCase()))
}
// handleInput = (event) => {
// console.log("input", event.target.value);
// // 数组的filter方法不会影响原数组
// var newList = this.state.backcinemaList.filter(item => item.name.toUpperCase().includes(event.target.value.toUpperCase()) ||
// item.address.toUpperCase().includes(event.target.value.toUpperCase()))
// this.setState({
// cinemaList: newList
// })
// }
}
1.2 todolist改写
import React, { Component } from 'react'
export default class App extends Component {
constructor() {
super();
this.state = {
addList: [
{
id: Math.random()*10000,
title: "张三"
}
],
mytext:''
}
}
//myref = React.createRef();
render() {
return (
<div>
<input value={this.state.mytext} onChange={(evt)=>{
this.setState({
mytext:evt.target.value
})
}}></input>
<button onClick={() => {
this.handler()
}}>增加</button>
<ul>
{
this.state.addList.map((item,index) =>
<li key={item.id}>
{/* {item.id}----{item.title} */}
<span dangerouslySetInnerHTML={
{
__html:item.id+"------"+item.title
}
}></span>
<button onClick={()=>{
this.deleteList(index)
}}>删除</button>
</li>
)
}
</ul>
{/* {this.state.addList.length===0 ?<div>暂无待办事项</div>:null} */}
{this.state.addList.length===0 && <div>暂无待办事项</div>}
</div>
)
}
handler = () => {
let newList = [...this.state.addList]
newList.push(
{
id: Math.random()*10000,
title: this.state.mytext
}
)
this.setState({
addList: newList,
mytext:''
})
}
deleteList=(index)=>{
console.log(index);
let newList = [...this.state.addList];
newList.splice(index,1);//从该下标开始删除 删除一个
this.setState({
addList: newList
})
}
}
2.父子通信
场景:比如我有一个父组件 父组件内部有1个导航组件 一个侧边栏组件 在导航栏组件中,我做了一个操作后,想让侧边栏组件隐藏与显示
这就需要子传父了 导航栏组件传递信号给父组件 父组件再去控制侧边栏组件
例如:
父组件:
通过state中的isShow来控制侧边栏组件的显示
import React, { Component } from 'react'
import Navbar from './compoent/Navbar'
import SideBar from './compoent/SideBar'
export default class App extends Component {
state={
isShow:true,
}
render() {
return (
<div>
<Navbar/>
{this.state.isShow && <SideBar/>}
</div>
)
}
}
侧边栏组件
import React, { Component } from 'react'
export default class SideBar extends Component {
render() {
return (
<div style={{background:"green",width:"300px"}}>
<ul>
<li>11111</li>
<li>11111</li>
<li>11111</li>
<li>11111</li>
<li>11111</li>
<li>11111</li>
<li>11111</li>
</ul>
</div>
)
}
}
导航栏组件
import React, { Component } from 'react'
export default class Navbar extends Component {
render() {
return (
<div style={{background:"yellow",width:"400px"}}>
<button>控制侧边栏</button>
</div>
)
}
}
现在需要去做修改,使用event属性传一个回调函数,然后子组件中调用此函数
可以发现子组件中点击按钮后,已经可以控制父组件中打印了。因此咱后面可以在父组件中修改state中的值了
export default class App extends Component {
state={
isShow:true,
}
render() {
return (
<div>
<Navbar event={()=>{
console.log("父组件中可以修改state了");
this.setState({
isShow:!this.state.isShow
})
}}/>
{this.state.isShow && <SideBar/>}
</div>
)
}
}
总结:
父传子:传属性
子传父:父给子一个函数,子执行此函数 当成回调函数
3.父子通信版:表单域组件
import React, { Component } from 'react'
import Field from './compoent/Field'
export default class App extends Component {
state={
username:"",
password:""
}
render() {
return (
<div>
<Field label="用户名" type="text" value={this.state.username} onChangeEvent={(value)=>{
// console.log("value==="+value);
this.setState({
username:value
})
}}></Field>
<Field label="密码" type="password" value={this.state.password} onChangeEvent={(value)=>{
// console.log("value==="+value);
this.setState({
password:value
})
}}></Field>
<button onClick={()=>{
console.log(this.state.username+"\t"+this.state.password+"发送给后端校验");
}}>登录</button>
<button onClick={()=>{
this.setState({
username:"",
password:""
})
}}>重置</button>
</div>
)
}
}
import React, { Component } from 'react'
export default class Field extends Component {
render() {
return (
<div>
<label>{this.props.label}</label>
<input type={this.props.type} value={this.props.value} onChange={(evt)=>{
// console.log(evt.target.value);
this.props.onChangeEvent(evt.target.value);
}}></input>
</div>
)
}
}