onKeyUp在onChange所在的React中不起作用

时间:2018-07-12 01:25:48

标签: javascript html5 reactjs onkeyup

我正在做一个React编码挑战,要求在onKeyUp上更新一个值。我最初将其设置为更新onChange,但是测试要求使用onKeyUp,因此我尝试将其更改为该值,但是我的字段不再更新,因此无法在文本区域中键入任何内容。

class MarkdownApp extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      value: ''
    };

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

  handleKeyUp(event) {
    this.setState({ value: event.target.value })
  }

  render() {
    return (
      <form>
        <label>
          Enter your markdown here:
          <br />
          <textarea value={this.state.value} onKeyUp={this.handleKeyUp} id='editor' />
          <br />
        </label>
        <label>
          Your markup will be previewed here:
          <p id='preview'>{marked(this.state.value)}</p>
        </label>
      </form>
    );
  }
}

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

就像我说的那样,当它处于onChange并且我的功能是handleChange时,它可以很好地工作,但是由于切换了它,所以我无法键入任何内容。

4 个答案:

答案 0 :(得分:3)

我只是从文本区域中删除value属性。您不需要使用React来控制它-DOM将为您保留值。

我下面所做的唯一更改是从textarea元素中删除了value={this.state.value}

import React from 'react';
import ReactDOM from 'react-dom';

class MarkdownApp extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      value: ''
    };

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

  handleKeyUp(event) {
    this.setState({ value: event.target.value })
  }

  render() {
    return (
      <form>
        <label>
          Enter your markdown here:
          <br />
          <textarea value={this.state.value} onKeyUp={this.handleKeyUp} id='editor' />
          <br />
        </label>
        <label>
          Your markup will be previewed here:
          <p id='preview'>{this.state.value}</p>
        </label>
      </form>
    );
  }
}

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

答案 1 :(得分:2)

由于该事件发生在更改文本框的实际值之前,因此event.target.value的结果为空字符串。使用空字符串设置状态,将清除文本框。

您需要从事件中获取按下的键值,并将其添加到现有的state.value中。

注意:我已从演示中删除了marked

class MarkdownApp extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      value: ''
    };

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

  handleKeyUp(event) {
    const keyValue = event.key;
    
    this.setState(({ value }) => ({
      value: value + keyValue
    }))
  }

  render() {
    return (
      <form>
        <label>
          Enter your markdown here:
          <br />
          <textarea value={this.state.value} onKeyUp={this.handleKeyUp} id='editor' />
          <br />
        </label>
        <label>
          Your markup will be previewed here:
          <p id='preview'>{this.state.value}</p>
        </label>
      </form>
    );
  }
}

ReactDOM.render(
  <MarkdownApp />,
  document.getElementById('root')
);
<script crossorigin src="https://unpkg.com/react@16/umd/react.development.js"></script>
<script crossorigin src="https://unpkg.com/react-dom@16/umd/react-dom.development.js"></script>

<div id="root"></div>

答案 2 :(得分:1)

您可以通过不给文本value而不是直接从ref存储状态来使文本区域不受控制。

示例(CodeSandbox

class MarkdownApp extends React.Component {
  ref = null;
  state = {
    value: ""
  };

  handleKeyUp = event => {
    this.setState({ value: this.ref.value });
  };

  render() {
    return (
      <form>
        <label>
          Enter your markdown here:
          <br />
          <textarea
            onKeyUp={this.handleKeyUp}
            ref={ref => (this.ref = ref)}
            id="editor"
          />
          <br />
        </label>
        <label>
          Your markup will be previewed here:
          <p id="preview">{marked(this.state.value)}</p>
        </label>
      </form>
    );
  }
}

答案 3 :(得分:1)

问题是您有两种方式,将state =绑定到文本框中的值。进行更改并触发事件后,OnChange会更新您的状态。 Onkeyup返回值onkeyup,因为您已将其映射到您的状态,它将保持为空。删除价值道具,它应该起作用。