乐趣区

三分钟掌握 React render props

上午 review 代码的时候,发现一些问题,关于逻辑复用的一些小技巧。然后就花点时间整理了下,做了个例子,聊一下 render props.

what is it ?
简单点讲, render props 就一种在组件间共享逻辑的技巧。把一些渲染逻辑以 prop 的形式传递给 Component, 把注意力集中在渲染逻辑上。
What do render props do?
处理组件的渲染逻辑。
When to use ?
当你发现组件中有重复的逻辑或者模式的时候。比如:

重复的 UI 结构
共享某个数据源
共享某个全局事件(比如 scroll, resize, …)

A live demo
光说不练假把式,一起看个例子。
想了想,写个表吧, 会动的那种(年会毛都没中,给个手环也好啊..)。
一番操作之后,我们花了一个表:

现在我们又想换个表带,改怎么做?重写一个吗?显然不是。
这时候就轮到 render props 登场了。
我们可以把一个个部分独立出来,把有差异的部分当作 prop 传入就可以了。
上代码:
class Watch extends Component {
state = {
date: moment(),
}

static propTypes = {
face: PropTypes.func,
}

static defaultProps = {
face: date => <DefaultFace date={date} />,
}

componentDidMount = () => (this.TICK = setInterval(this.update, 1000))

componentWillUnmount = () => clearInterval(this.TICK)

update = () => this.setState({ date: moment() })

render = () => (
<Strap>
<Bezel>
<Screen>
<Face>{this.props.face(this.state.date)}</Face>
</Screen>
</Bezel>
</Strap>
)
}
不用关注 Strap,Bezel,Screen 这些,我们只看关键点:Face.
如果我们啥也不传,得到的将是一个空空如也的表盘:

这时候可以给他加个 DefaultFace, 显示 HH:mm
static defaultProps = {
face: date => <DefaultFace date={date} />,
}

很赞。
现在给他换个样子,骚黄色:

const SecondsFace = ({date}) => {
const hours = date.format(‘HH’)
const minutes = date.format(‘mm’)
const seconds = date.format(‘ss’)
return (
<>
<Value>{hours}</Value>
<Value>{minutes}</Value>
<Value>{seconds}</Value>
</>
)
}
SecondsFace.propTypes = watchfacePropTypes;

心满意足。
这时候我们的 render 是这样的:
class App extends Component {
render() {
return (
<Watch />
<Watch face={date => <SecondsFace date={date} />} />
</div>
);
}
}

如此这般,可以把其他款式的表都写了:

舒服~
年会又又又又啥也没中的心情放佛得到了安抚。
完整代码在这里: 代码,喜欢的可以给个星星。
Live Demo : codeOpen
Tips

Dos ????
当有组件可以共享或者部分渲染逻辑重复的时候

Dont’s ????

宁可不用也不要滥用
避免在使用 PureComponents 的时候用 render Props. 除非你的 prop 是静态定义的。

Notes ⚠️

Render Prop 只是一个技巧,名字啥都可以,比如 children。
大部分可以用 Render Prop 的场景,也可以用 HOC 实现,反之亦然。

That’s it.
:)
如有纰漏,欢迎指正,谢谢。
更多参考:
https://reactjs.org/docs/rend…

退出移动版