反应。 onCopy事件的preventDefault()不起作用

时间:2018-03-08 12:48:32

标签: javascript reactjs

我正在试图弄清楚如何使onCopy事件上的剪贴板事件返回false。我用于测试onCopy处理程序和e.preventDefault()方法。但文本被无限制地复制到缓冲区!我错过了什么?

先谢谢你。

import React from 'react';
import ReactDOM from 'react-dom';
import PropTypes from 'prop-types';
import ReactDOMServer from 'react-dom/server';
import './index.css';


class Copy extends React.Component {
  constructor(props) {
    super(props);

    this.state = {
      time: '',
      timer: false,
      counter: 0
    };

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

  handlerCopy(e) {

    e.preventDefault(); // must prevent the current event

    this.setState(prevState => ({
      counter: prevState.counter + 1
    }));

    alert('Don\'t copy it!');
  }

  render() {
    return (
      <React.Fragment>
        <p onCopy={this.handlerCopy}>Copy me!</p>
        <p>Copy count: {this.state.counter}</p>
      </React.Fragment>
    );
  }
}

ReactDOM.render(
<Copy />,
document.getElementById('root'));

3 个答案:

答案 0 :(得分:6)

这是一个非常好的问题!

这是发生的,因为React的实际事件监听器也位于文档的根目录,这意味着click事件已经冒泡到根目录。您可以使用e.nativeEvent.stopImmediatePropagation()来阻止其他事件侦听器。

试一试:

import React from 'react';
import ReactDOM from 'react-dom';
import PropTypes from 'prop-types';
import ReactDOMServer from 'react-dom/server';
import './index.css';


class Copy extends React.Component {
  constructor(props) {
    super(props);

    this.state = {
      time: '',
      timer: false,
      counter: 0
    };

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

  handlerCopy(e) {
    console.log(e.target.innerHTML);
    e.preventDefault();
    e.nativeEvent.stopImmediatePropagation();

    this.setState(prevState => ({
      counter: prevState.counter + 1
    }));

    alert('Don\'t copy it!');
  }

  render() {
    return (
      <React.Fragment>
        <p onCopy={this.handlerCopy}>Copy me!</p>
        <p>Copy count: {this.state.counter}</p>
      </React.Fragment>
    );
  }
}

ReactDOM.render(
<Copy />,
document.getElementById('root'));

答案 1 :(得分:0)

这应该是评论,但我没有足够的声誉。 我认为e.preventDefault()足以(至少)React 16。

Working example on Codesandbox

答案 2 :(得分:0)

上面提到的解决方案对我来说似乎不起作用,但是如果通过以下方式编写handlerCopy(状态值的更新)来讨论状态中的计数器值,则可以正确管理。

Date/Time:           2018-03-06 09:23:25.4974 +0800
Launch Time:         2018-03-06 09:23:24.8871 +0800
OS Version:          iPhone OS 11.2.5 (15D60)
Baseband Version:    n/a
Report Version:      104

Exception Type:  EXC_BREAKPOINT (SIGTRAP)
Exception Codes: 0x0000000000000001, 0x0000000100179fe8
Termination Signal: Trace/BPT trap: 5
Termination Reason: Namespace SIGNAL, Code 0x5
Terminating Process: exc handler [0]
Triggered by Thread:  0

Filtered syslog:
None found

Thread 0 name:  Dispatch queue: com.apple.main-thread
Thread 0 Crashed:
0   simpleWeather                   0x0000000100179fe8 specialized closure #1 in LocationViewController.locationManager(_:didUpdateLocations:) + 335848 (LocationViewController.swift:0)
1   simpleWeather                   0x000000010017d550 partial apply for closure #1 in LocationViewController.locationManager(_:didUpdateLocations:) + 349520 (LocationViewController.swift:0)
2   simpleWeather                   0x00000001001332c4 specialized closure #2 in GeoRecoder.getAddress(callback:) + 45764 (struct.swift:92)
3   simpleWeather                   0x000000010012c900 closure #2 in GeoRecoder.getAddress(callback:) + 18688 (struct.swift:0)
4   simpleWeather                   0x000000010012c8c0 thunk for @callee_owned (@owned [CLPlacemark]?, @owned Error?) -> () + 18624 (struct.swift:0)
5   libdispatch.dylib               0x0000000185c52a54 _dispatch_call_block_and_release + 24
6   libdispatch.dylib               0x0000000185c52a14 _dispatch_client_callout + 16
7   libdispatch.dylib               0x0000000185c5f698 _dispatch_main_queue_callback_4CF$VARIANT$mp + 1016
8   CoreFoundation                  0x000000018627b344 __CFRUNLOOP_IS_SERVICING_THE_MAIN_DISPATCH_QUEUE__ + 12
9   CoreFoundation                  0x0000000186278f20 __CFRunLoopRun + 2012
10  CoreFoundation                  0x0000000186198c58 CFRunLoopRunSpecific + 436
11  GraphicsServices                0x0000000188044f84 GSEventRunModal + 100
12  UIKit                           0x000000018f8f15c4 UIApplicationMain + 236
13  simpleWeather                   0x00000001001304bc main + 33980 (struct.swift:13)
14  libdyld.dylib                   0x0000000185cb856c start + 4

上面提到的handlerCopy函数没有对我进行任何更改@Max Wolfen

import React from 'react';
import ReactDOM from 'react-dom';
import PropTypes from 'prop-types';
import ReactDOMServer from 'react-dom/server';

class App extends React.Component {
  constructor(props) {
    super(props);

    this.state = {
      time: '',
      timer: false,
      counter: 0
    };
  }

   handlerCopy(e) {
    var val = this.state.counter;
    val = val + 1;
    this.setState({
      counter: val
    }, function(){
      console.log('new acounter:- ', this.state.counter);
    })
    alert('Don\'t copy it!');
  }


  render() {
    return (
      <React.Fragment>
        <p onCopy={(e) => this.handlerCopy(e)}>Copy me!</p>
        <p>Copy count: {this.state.counter}</p>
      </React.Fragment>
    );
  }
}
document.addEventListener('click', function(e) {
    console.log('propagation',e)
  }, false);


export default App;