高阶组件
(封装时钟的例子的两种方法)
eg1:
import React,from "react";
class TimeClok extends React.Component{
state = {time:new Date()}
componentDidMount(){
this.timerId=setInterval(()=>this.tick(),1000)
}
componentwillUnmount(){
clearInterval( this.timerId)
}
tick(){
this.setState({time:new Date()})
}
render(){
<div>{this.state.time}</div>
}
}
export const TimeWrapClock = WrappedComponent =>{
return class extends React.PureComponent {
render(){return <TimeClok><WrappedComponent {...this.props}/></TimeClok> }
}
}
eg2:
export default function TimeWrapClock(WrappedComponent){
return class extends React.Component{
state = {time:new Date()}
componentDidMount(){
this.timerId=setInterval(()=>this.tick(),1000)
}
componentwillUnmount(){
clearInterval(this.timerId)
}
tick(){
this.setState({time:new Date()})
}
render(){
return <WrappedComponent time={this.state.time} {...this.props}/>
}
}
}
使用时要引入:import TimeWrapClock from "./路径"
函数作为子组件
(实现更多场景的组件的复用)
class MyComponent extends React.Component{
render(){
return (
<div>
{this.props.children('nate wang')}
</div>
)
}
}
<MyComponent>
{(name)=>(<div>{name}</div>)}
</MyComponent>
Context API
(适用全局性场景)
用法:
const ThemeContext = React.createContext('light')
class App extends React.Component {
render() {
return (
<ThemeContext.Provider value="dark">
<ThemedButton />
</ThemeContext.Provider>
)
}
}
function ThemedButton(props) {
return (
<ThemeContext.Consumer >
{theme => <Button {...props} theme={theme} />}
</ThemeContext.Consumer>
)
}
eg:全局语言切换的列子
import React, {Fragment} from "react";
const en={
confirm:"Confirm",
cancel:"Cancel"
}
const cn={
confirm:"确认",
cancel:"取消",
}
const ChangeLanguage = React.createContext(en)//默认英语
class LanguageProvider extends React.Component{
state = {local:cn};
toggleLocale=()=>{
const local=this.state.local===en?cn:en
this.setState({local})
}
render(){
return(
<ChangeLanguage.Provider value={this.state.local}>
<button onClick={this.toggleLocale}>
切换语言
</button>
{this.props.children}
</ChangeLanguage.Provider>
)
}
}
class LanguageButtons extends React.Component{
render(){
return(
<ChangeLanguage.Consumer>
{
(local)=>(
<div>
<button>{local.cancel}</button>
<button>{local.confirm}</button>
</div>
)
}
</ChangeLanguage.Consumer>
)
}
}
export default ()=>{
<div>
<LanguageProvider>
<div>
<LanguageButtons/>
</div>
</LanguageProvider>
</div>
}
父组件触发子组件,子组件传值给父组件(ref)
export class Father extends Component {
constructor(props) {
this.state = {
showChildrenName:""
}
}
handleOk=()=>{
this.changeData((name)=>{
this.setState({
showChildrenName:name
})
})
}
render() {
return (
<div >
<Button onClick={this.handleOk}></Button>
<Children name={ref=> this.changeData = ref}></Children>
</div>
)
}
}
export class Children extends Component {
constructor(props) {
this.state = {
name: ""
}
}
componentDidMount() {
this.props.name(this.saveChildName)
}
saveChildName = (cb) => {
let { name } = this.state
cb(name)
}
changeName=(e)=>{
this.setState({
name:"宝宝"
})
}
render(){
return(
<Input onChange={this.changeName} value={this.state.name}/>
)
}
}