进阶组件之render props中进行公共属性的对象封装

1,291 阅读1分钟

前言

我们经常需要把一些常见的组件属性封装到一个对象里,然后在渲染属性中使用。

回顾下之前的写法

function Usage({
    onToggle = (aregs) => console.log('Ontoggle',...aregs)
}){
    return (<Toggle onToggle={onToggle}  >
        {(on,toggle)=>(
     <div>
       { on ? 'button is on' : 'button is off'}
       <Switch on={on} onClick={toggle} />
       <button onClick={toggle}>{on? 'on': 'off'}</button>
     </div>
    )   
    }
    </Toggle>)
}

发现的问题

从上面的例子中,我们可以看到onClick属性,在switch组件以及button组件都传入了一个事件属性并绑定了同一个函数。这部分可以优化为下面的方式。

// 吧需要的点击属性封装到一个对象里
getStateAndHelpers() { 
    return { 
    on: this.state.on, 
    toggle: this.toggle,
     togglerProps: {
         onClick: this.toggle, 
        'aria-pressed': this.state.on, 
    } } 
}
render(){
 return this.props.children(this.getStateAndHelpers())
}

function Usage({
    onToggle = (aregs) => console.log('Ontoggle',...aregs)
}){
    return (<Toggle onToggle={onToggle}  >
        {(on,toggle)=>(
     <div>
       { on ? 'button is on' : 'button is off'}
       <Switch on={on} {...togglerProps} />
       <button  {...togglerProps}>{on? 'on': 'off'}</button>
     </div>
    )   
    }
    </Toggle>)
}

小结

本文涉及到的技巧非常简单,主要是将render props中的部分公用属性封装为一个对象,然后进行简化操作。