私はes6クラスを使用していて、最上位の状態にいくつかの複雑なオブジェクトができてしまい、メインコンポーネントをよりモジュール化しようとしていたので、最上位のコンポーネントの状態を維持しながら、よりローカルロジックを可能にする単純なクラスラッパーを作成しました。
ラッパークラスは、メインコンポーネントの状態にプロパティを設定する関数をコンストラクターとして使用します。
export default class StateWrapper {
constructor(setState, initialProps = []) {
this.setState = props => {
this.state = {...this.state, ...props}
setState(this.state)
}
this.props = initialProps
}
render() {
return(<div>render() not defined</div>)
}
component = props => {
this.props = {...this.props, ...props}
return this.render()
}
}
次に、トップステートの複雑なプロパティごとに、StateWrappedクラスを1つ作成します。ここでコンストラクタにデフォルトの小道具を設定できます。これらはクラスの初期化時に設定され、値のローカル状態を参照してローカル状態を設定し、ローカル関数を参照して、チェーンに渡すことができます。
class WrappedFoo extends StateWrapper {
constructor(...props) {
super(...props)
this.state = {foo: "bar"}
}
render = () => <div onClick={this.props.onClick||this.onClick}>{this.state.foo}</div>
onClick = () => this.setState({foo: "baz"})
}
そのため、私の最上位コンポーネントは、各クラスをその最上位状態プロパティ、単純なレンダリング、およびコンポーネント間で通信するすべての関数に設定するコンストラクターを必要とします。
class TopComponent extends React.Component {
constructor(...props) {
super(...props)
this.foo = new WrappedFoo(
props => this.setState({
fooProps: props
})
)
this.foo2 = new WrappedFoo(
props => this.setState({
foo2Props: props
})
)
this.state = {
fooProps: this.foo.state,
foo2Props: this.foo.state,
}
}
render() {
return(
<div>
<this.foo.component onClick={this.onClickFoo} />
<this.foo2.component />
</div>
)
}
onClickFoo = () => this.foo2.setState({foo: "foo changed foo2!"})
}
私の目的には非常にうまく機能しているようですが、ラップされた各コンポーネントは独自の状態を追跡していますが、トップコンポーネントの状態を更新しているため、トップレベルのコンポーネントでラップされたコンポーネントに割り当てるプロパティの状態を変更することはできませんそれが変わるたびに。