2016-07-04 11 views
0

私はmousemoveイベントを捕捉したい反応容器を持っています。それはかなり簡単です。さらに、実際にmousemoveイベントハンドラのロジックが存在するコンテナによってレンダリングされた反応サブコンポーネントがあります。だから私はコンテナの親から子にmousemoveイベントを渡す/委譲し、子のmousemoveハンドラを呼び出す必要があります。それはどうやって正しく行われますか?ReactJS - 子イベントハンドラで親イベントを処理する

コンテナがDOMのより大きなHTML要素であり、その全体領域内のイベントをキャプチャする必要があるため、サブコンポーネントではなくコンテナでマウスイベントをキャプチャする必要があります。

mousemove-handler-logicは、コンテナが認識してはならない機能をカプセル化するため、サブコンポーネント内に存在する必要があります。

コンテナのレンダリング方法:

render() { 
    return (
     <div data-component="MyContainer" 
      onMouseMove={(event) => this.handleMousemove(event)}> 

      <MySubComponent {// ... give some props here}> 
     </div> 
    ); 
} 

に私はMyContainerは、そのDOMノードを取得し、addEventListenerをして​​ハンドラを登録するMySubComponentのためのコールバック関数を設定しますが、それは一貫として時折DOMノードを動作しませんでしたアプローチを試してみました未定義ました:

export default class MyContainer extends Component { 
    constructor(props) { 
     super(props); 
     this.state = {}; 

     this.getContainerRef = this.getContainerRef.bind(this); 
    } 

    getContainerRef() { 
     return this.refs['containerWrap']; 
    } 

    render() { 
     return (
      <div data-component="MyContainer" 
       ref="containerWrap" 
       onMouseMove={(event) => this.handleMousemove(event)}> 

       <MySubComponent getContainerRef={this.getContainerRef} /> 
      </div> 
     ); 
    } 
} 

export default class MySubComponent extends Component { 
    constructor(props) { 
     // ... init something 

     this.handleMousemove = this.handleMousemove.bind(this); 
    } 

    componentDidMount() { 
     // add event listener for parent application frame 
     let containerDOM = this.props.getContainerRef(); 
     containerDOM.addEventListener('mousemove', this.handleMousemove, false); 
    } 

    componentWillUnmount() { 
     // remove event listener from parent application frame 
     let containerDOM= this.props.getContainerRef(); 
     containerDOM.removeEventListener('mousemove', this.handleMousemove, false); 
    } 

    handleMousemove(event) { 
     // handle the event 
    } 

    // ... more methods 
} 

は、私はまた、this.refs.SubComponent.handleMousemove経由MyContainerから直接MySubComponentでのMouseMoveイベントハンドラを呼び出すことを試みたが、それが反応し、Reduxの中に悪い習慣とみなしています。

+0

あなたの質問に「還元」はありません。あなたは 'onMouseMove'イベントを' MySubComponent'によって直接処理できますか?ロジックが「MySubComponent」によって完全に処理されているのがより理にかなっています – xiaofan2406

+0

最初のアプローチのコードを教えてもらえますか? –

+0

@ xiaofan2406:質問の編集を参照してください。非常に小さなサブコンポーネントではなく、大きなHTMLコンテナ要素でイベントをキャプチャする必要があります。 – Michbeckable

答えて

3

ください。

あなたが親コンテナにonMouseMoveをキャプチャしたい場合は、私は最高のは自分の子コンポーネントにeventの関連するプロパティを渡すことだと思います。子コンポーネントの親のcomponentWillReceivePropsshouldComponentUpdateの値が変更されたときに呼び出され、それに反応することができます。

class Container extends React.Component{ 
    constructor(props) { 
    super(props); 
     this.state = { 
     mouseX: 0, 
     mouseY: 0 
     }; 
    } 
    handleMouse(event) { 
    event.preventDefault(); 
    this.setState({ 
     mouseX: event.clientX, 
     mouseY: event.clientY 
    }); 
    } 

    render() { 
    return <div onMouseMove={(event) => this.handleMouse(event)} className="demo"> 
     <Child x={this.state.mouseX} y={this.state.mouseY} /> 
    </div>; 
    } 
} 

そして、あなたの子コンポーネント:

class Child extends React.Component { 
    shouldComponentUpdate(nextProps, nextState) { 
    return this.handleMouseMove(nextProps.x, nextProps.y); 
    } 
    handleMouseMove(x, y) { 
    if (x < 150) { // return true to invoke render for some conditions 
     // your code 
     return true; 
    } 
    return false; 
    } 

    render() { 
    return <div>Child Component</div>; 
    } 
} 

しかし、子コンポーネントで実装は次のようになります。それはそのpropsについて知っていて、その親コン​​ポーネントについては何も知りません。

反応成分ライフサイクル:https://facebook.github.io/react/docs/component-specs.html

0

あなたのMouseMoveは、サブコンポーネントにする必要がありますし、あなたのコンテナがmapDispatchtoPropsを使用する必要があり、この

const mapDispatchToProps = (dispatch) => { 
    return { 
    onmousemoveAction: (id) => { 
     dispatch(toggleTodo(id)) 
    } 
    } 
} 

とあなたのサブコンポーネントの派遣(onmousemoveAction)

のようにしかし、あなたはまだサブコンポーネントのロジックを持っているしたい場合が可能であれば避けるべきrefsでの作業

this.refs.mysubcomponent.dispatchEvent(new Event('mousedown')) 
関連する問題