反应-单击子元素时防止父元素上的onMouseDown事件

时间:2018-12-03 21:12:39

标签: javascript reactjs stoppropagation

我有一个带有onMouseDown事件的父元素,用于使它可拖动。

在其中,我有几个绝对定位的带有onClick事件的子元素。

我曾想过,通过对子元素应用更高的Z索引,onClick将运行,而不是onMouseDown,但是似乎两者都运行,并且如果div被拖动,onClick事件将无法正常运行。我试图阻止事件传播,但似乎无济于事。当子级onClick运行时,如何防止父级onMouseDown被激活?

这是代码的简化版本

export default class Day extends Component {

    constructor(props) {
    super(props);
    this.showTalks = this.showTalks.bind(this)

    this.state = {isScrolling: false};

    this.componentWillUpdate = this.componentWillUpdate.bind(this)
    this.toggleScrolling = this.toggleScrolling.bind(this)
    this.onScroll = this.onScroll.bind(this)
    this.onMouseMove = this.onMouseMove.bind(this)
    this.onMouseUp = this.onMouseUp.bind(this)    
    this.onMouseDown = this.onMouseDown.bind(this)
    this.attachScroller = this.attachScroller.bind(this)
    this.titleRef = React.createRef();

}

componentWillUpdate = (nextProps, nextState) =>{
 if(this.state.isScrolling !== nextState.isScrolling ) {
   this.toggleScrolling(nextState.isScrolling);
  }
};

toggleScrolling = (isEnable) => {
    if (isEnable) {
      window.addEventListener('mousemove', this.onMouseMove);
      window.addEventListener('mouseup', this.onMouseUp);
      window.addEventListener("drag", this.onMouseMove);
    } else {
      window.removeEventListener('mousemove', this.onMouseMove);
      window.removeEventListener("drag", this.onMouseMove);
    }
};

onScroll = (event) => {
};

onMouseMove = (event) => {

    const {clientX, scrollLeft, scrollTop, clientY} = this.state;
    this._scroller.scrollLeft = -(scrollLeft - clientX + event.clientX);
    this._scroller.scrollTop = scrollTop - clientY + event.clientY;


  };

  onMouseUp =  () => {
    this.setState(
      {
        isScrolling: false, 
        scrollLeft: 0, 
        scrollTop: 0,
        clientX: 0, 
        clientY:0
      }
    );
  };

  onMouseDown = (event) => {

    const {scrollLeft, scrollTop} = this._scroller;
    this.setState({
      isScrolling:true, 
      scrollLeft, 
      scrollTop, 
      clientX:event.clientX, 
      clientY:event.clientY
    });
  };

  attachScroller = (scroller) => {
    this._scroller = ReactDOM.findDOMNode(scroller);
  };

  showTalks(talkApi){
    this.props.showTalks( talkApi);
  }

  render() {
    let talksArray = [<Talk></Talk>] //removed code that generates an array of talks
    return (
        <div 
          onMouseDown={this.onMouseDown}
          onScroll={this.onMouseMove}
          className="multi-columns">
          {talksArray}
        </div>
      );
  }
}


export default class Talk extends Component {

  constructor(props) {
    super(props);
    this.handleFetch = this.handleFetch.bind(this);
  }

  handleFetch(e){
    e.preventDefault();
    e.stopPropagation();
    let id = e.currentTarget.dataset.id;
   this.props.showTalks(id);
  }

  render(){
    return(
        <div 
          data-id={this.props.id} 
          onClick={this.handleFetch.bind(this)}
         >
         <h2>{this.props.title}</h2>
        </div>
      )
  }
}

1 个答案:

答案 0 :(得分:0)

我意识到e.stopPropagation(); handleFetch()函数上的代码不起作用,因为我正在使用onClick事件,并且停止传播该事件对完全独立的onMouseDown事件没有影响。

现在,我将onClick切换到另一个onMouseDown事件,然后stopPropagation起作用。但是,我想知道是否有更好的方法可以让我使用onClick。