【问题标题】:ReactJS component textarea not updating on state changeReactJS 组件文本区域未在状态更改时更新
【发布时间】:2017-06-06 02:42:08
【问题描述】:

我正在尝试编写一个笔记/组织应用程序,但遇到了一个令人沮丧的错误。

这是我的组件:

import React from 'react';

const Note = (props) => {
  let textarea, noteForm;
  if (props.note) {
    return (
      <div>
        <button onClick={() => {
          props.handleUpdateClick(props.selectedFolderId, props.selectedNoteId, textarea.value);
        }}>
          Update
        </button>
        <textarea
          defaultValue={props.note.body}
          ref={node => {textarea = node;}}
        />
      </div>
    );
  } else {
    return <div></div>;
  }
};

export default Note;

就目前而言,每当我在便笺之间切换并使用来自 note.body 属性的新内容重新渲染便笺组件时,textarea 不会更改并保留上一个便笺中的内容。我已经尝试对文本区域使用 value 属性而不是 defaultValue 属性,这确实解决了在组件重新呈现时文本区域内容不改变的问题,但是当我这样做时,我不再能够在 textarea 字段中输入更新笔记

有谁知道一种方法,我既可以允许用户在文本字段中键入以更新笔记,又可以在我呈现不同的笔记时改变 textarea 的内容?

谢谢

【问题讨论】:

    标签: html reactjs redux textarea


    【解决方案1】:

    因为componentWillReceiveProps 现在不安全 Max Sindwani 的答案现在有点过时了。

    试试这些步骤:

    • 将您的组件转换为类
    • 现在您可以包含 shouldComponentUpdate() 生命周期挂钩
    • 创建您的事件处理程序并将其传递给 onChange
    • &lt;textarea&gt; 中,您可以将defaultValue 属性替换为value(只需在处理程序中使用 event.preventDefault() 以便用户可以在需要时继续更新文本)

          import React from 'react';
      
          export class Note extends React.Component {
      
          constructor(props) {
              super(props);
              this.state={text: this.props.note.body}
          }
      
          shouldComponentUpdate(nextProps) {
              if(nextProps.note.body !== this.state.text) {
                  this.setState({text: nextProps.note.body})
                  return true;
              }
              return false;
          }
      
          updateText = (event) => {
              event.preventDefault();
              this.setState({text: nextProps.note.body});
          }
      
       render() {
         if (this.props.note) {
           return (
             <div>
               <textarea
                 onChange={this.updateText}
                 value={this.state.text}
                 name={'display'} 
               />
             </div>
           );
        } else {
           return <div></div>;
         }
       }});
      

    【讨论】:

      【解决方案2】:

      问题在于,将值设置为您的 prop 将导致组件的所有重新渲染都使用相同的 prop,因此新文本被删除。一种解决方案是将文本保留在组件的本地状态中。要同时收听 props 的变化,您可以在收到新的 props 时设置状态。

      const Note = React.createClass({
      
        getInitialState() {
              return {
              text : this.props.note.body
          }
        },
      
        componentWillReceiveProps: function(nextProps) {
          if (typeof nextProps.note != 'undefined') {
              this.setState({text: nextProps.note.body });
          }
        },
      
        render() {
          if (this.props.note) {
            return (
              <div>
                <button onClick={(e) => {
                  // Fire a callback that re-renders the parent.
                  // render(this.textarea.value);
                }}>
                  Update
                </button>
                <textarea
                  onChange={e => this.setState({ text : e.target.value })}
                  value={this.state.text}
                  ref={node => {this.textarea = node;}}
                />
              </div>
            );
          } else {
            return <div></div>;
          }
        }
      });
      

      https://jsfiddle.net/69z2wepo/96238/

      如果您使用的是 redux,您还可以在输入的更改事件上触发一个操作以触发重新渲染。您可以将输入值保存在减速器中。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2021-06-08
        • 2018-09-21
        • 1970-01-01
        • 2022-10-15
        • 2021-12-14
        相关资源
        最近更新 更多