制御されたReactコンポーネントをラップして、特定のプロップ/ハンドラーのペアをコンポーネントの消費者によって省略します。制御不能を使用すると、Reactコンポーネントを最小限の状態で作成し、除外された場合はプロップ/ハンドラーの状態を管理するコンポーネントにラップできます。
npm i -S uncontrollable
このモジュールの理由が少し不明な場合は、最初に次のセクションを読んでください。実際の例をいくつか見たい場合は、この戦略を頻繁に使用するReactウィジェットをチェックしてください。
import { uncontrollable } from 'uncontrollable' ;
useUncontrolledProp(value, defaultValue, onChange) => [value, onChange]
上記の高次コンポーネントの代わりに使用できる反応フック。それは、子どもの要素に広がるのが安全なprops
の完全なセットを返します。
import { useUncontrolledProp } from 'uncontrollable' ;
const UncontrolledCombobox = ( { value , defaultValue , onChange } ) => {
// filters out defaultValue, defaultOpen and returns controlled
// versions of onChange, and onToggle.
const [ controlledValue , onControlledChange ] = useUncontrolledProp (
value ,
defaultValue ,
onChange
) ;
return < Checkbox { ... controlledProps } / > ;
} ;
useUncontrolled(props, propsHandlerHash) => controlledProps
上記の高次コンポーネントの代わりに使用できる反応フック。それは、子どもの要素に広がるのが安全なprops
の完全なセットを返します。
import { useUncontrolled } from 'uncontrollable' ;
const UncontrolledCombobox = ( props ) => {
// filters out defaultValue, defaultOpen and returns controlled
// versions of onChange, and onToggle.
const controlledProps = useUncontrolled ( props , {
value : 'onChange' ,
open : 'onToggle' ,
} ) ;
return < Checkbox { ... controlledProps } / > ;
} ;
Reactの強度の1つは、その拡張性モデルです。これは、成分状態を可能な限り高くするための一般的な慣行によって可能になります。コンポーネントについて非常に柔軟で簡単に推論しやすいことを可能にするのに最適ですが、これにより、あらゆる用途で多くのボイラープレートをワイヤするコンポーネントを生成できます。単純なコンポーネント(入力など)の場合、これは通常、入力value
プロップをonChange
ハンドラーを介して親国プロパティに結び付けることです。ここに非常に一般的なパターンがあります:
render ( ) {
return (
< input type = 'text'
value = { this . state . value }
onChange = { e => this . setState ( { value : e . target . value } ) }
/ >
)
}
このパターンは、入力からその親にvalue
管理する責任を移動し、「双方向」データバインディングを模倣します。ただし、親が入力の状態を直接管理する必要がない場合があります。その場合、私たちがしたいのは、入力の初期value
を設定し、それ以降に入力を管理させます。 Reactは、「制御されていない」入力を介してこれを扱います。ここでは、 value
Propを介して外部から入力の状態を制御したいことを示していない場合は、本の維持を行います。
これは、独自のコンポーネントで使用できる素晴らしいパターンです。親が理にかなっているすべてのものを制御したいと仮定して、各コンポーネントをできる限りステートレスにするように構築するのが最善です。例として、単純なドロップダウンコンポーネントを取ります
class SimpleDropdown extends React . Component {
static propTypes = {
value : React . PropTypes . string ,
onChange : React . PropTypes . func ,
open : React . PropTypes . bool ,
onToggle : React . PropTypes . func ,
} ;
render ( ) {
return (
< div >
< input
value = { this . props . value }
onChange = { ( e ) => this . props . onChange ( e . target . value ) }
/ >
< button onClick = { ( e ) => this . props . onToggle ( ! this . props . open ) } >
open
< / button >
{ this . props . open && (
< ul className = "open" >
< li > option 1 < / li >
< li > option 2 < / li >
< / ul >
) }
< / div >
) ;
}
}
単純なドロップダウンでどのように状態を追跡しないかに注目してください。これは素晴らしいことです。なぜなら、モジュールの消費者は、ドロップダウンの動作がどうあるべきかを決定するすべての柔軟性を持っているからです。また、パブリックAPI(PropTypes)に注意してください。これは、一般的なパターンで構成されています。セット( value
、 open
)が必要なプロパティと、セット( onChange
、 onToggle
)が必要なときを示すハンドラーのセットです。ハンドラーに応じてvalue
とopen
小道具を変更するのは親コンポーネント次第です。
このパターンは消費者に優れた柔軟性を提供しますが、おそらく使用から使用することからあまり変わらないボイラープレートコードの束を書く必要もあります。おそらく、彼らは常にonToggle
に応じてopen
設定したいと考えており、まれな場合にのみ、その動作を無効にしたいと思うでしょう。これは、制御された/制御されていないパターンが登場する場所です。
消費者がopen
小道具を提供していない場合、オープン/オントトグルケースを自分で処理したいだけです(彼らがそれを制御したいことを示します)。ドロップダウンコンポーネントをそのすべてのロジックで複雑にし、ドロップダウンのビジネスロジックを不明瞭にするのではなく、ドロップダウンを取得し、それを処理する別のコンポーネントにラップすることで、後で追加できます。
uncontrollable
/制御されていない入力を作成するために必要なロジックを分離して、完全に制御された入力を作成して後でラッピングできるようにするために必要なロジックを分離できます。これは、推論する方がはるかに簡単になる傾向があります。
import { uncontrollable } from 'uncontrollable' ;
const UncontrollableDropdown = uncontrollable ( SimpleDropdown , {
value : 'onChange' ,
open : 'onToggle'
} )
< UncontrollableDropdown
value = { this . state . val } // we can still control these props if we want
onChange = { val => this . setState ( { val } ) }
defaultOpen = { true } / > // or just let the UncontrollableDropdown handle it
// and we just set an initial value (or leave it out completely)!
今、私たちはオープンなオントグルについて心配する必要はありません!返されたコンポーネントは、 onToggle
コンポーネントopen
open
ます。心配したい場合は、 open
とonToggle
小道具を提供するだけで、制御されていない入力が通過するだけです。
上記は不自然な例ですが、さらに複雑なコンポーネントをラップすることができ、コンポーネントの消費者に提供できるAPIで多くの柔軟性を提供します。プロップ/ハンドラーのすべてのペアについて、フォーム「default [propname]」so value
> defaultValue
、およびopen
> defaultOpen
などのフォームのデフォルトプロップも取得します。ここ:https://github.com/jquense/react-widgets/blob/5d1b530cb094cdc72f577fe01abe4a02dd265400/src/multiselect.jsx#l521