父状态更改时,React子组件不会重新呈现

时间:2019-07-22 07:42:35

标签: reactjs

我正在编写一个React状态组件,以处理在文本框中输入的文本,并在数据库和文本框之间保存和加载文本。我可以在文本框中输入内容,也可以将文本框中的内容保存到数据库中。当我从数据库加载到文本框时,组件的状态会更新,而(子)文本框的prop会根据Chrome中的React DevTools更新处理从父组件到文本框的传递文本。问题在于该文本框的值未重新呈现以反映新的道具。

我做了一些研究,发现状态变化时应该重新渲染React组件。我尝试使用useState()向子组件添加状态,并且每次使用

更改道具时都会更新状态
useEffect(() => setText(propText), [propText])

它没有用。 React DevTools中的道具和状态显示了我加载的值,但组件未在文本框中显示它。也许它不是设计用来从props和state而不是用户输入中获取输入值的,但是它的onChange()事件处理函数会更新父状态,就像我尝试使用数据库访问组件一样,因此它是完全抽象的。

这是现在的子组件:

function InputTextComponent(props) {
  const { parentInput, textUpdate } = props;
  const [text, setText] = useState(parentInput);
  useEffect(() => setText(parentInput), [parentInput]);

  const onTextChange = event => {
    const {
      target: { value }
    } = event;
    textUpdate(value);
  };
  return (
    <TextAreaGroup
      placeholder={'Input text'}
      name={'Input text here'}
      value={text}
      info={'Input text'}
      onChange={event => onTextChange(event)}
    />
  );
}

这是父组件:

class ParentComponent extends Component {
  constructor() {
    super();
    this.state = {
      textInput: '',
    };
    this.textUpdate.bind(this);
  }

  textUpdate = textInput => this.setState({ textInput });

  render() {
    const {
      textInput,
    } = this.state;
    return (
      <div className="container mt-3">
        <InputTextComponent
          textUpdate={this.textUpdate}
          parentInput={textInput}
        />

        <LoadTextsComponent
          alias={alias} // alias is irrelevant part of the component
          aliasUpdate={this.aliasUpdate}
          skuUpdate={this.skuUpdate}
        />
      </div>
    );
  }
}

数据库加载组件使用textUpdate()函数。这是完整的组件:

function LoadTextsComponent(props) {
  const { alias, aliasUpdate, textUpdate } = props;
  const [setList, setListUpdate] = useState([]);

  useEffect(() => {
    const fetchData = async () => {
      const result = await client.get('/texts/listTexts');
      aliasUpdate(result[0].alias);
      setListUpdate(result);
    };
    fetchData();
  }, []);

  const loadTextsToInputBox = () => {
    let aliasSet;
    for (let set of setList) {
      if (set.alias === alias) {
        aliasSet = set.texts;
      }
    }
    let textString = '';
    for (let text of aliasSet) {
      textString += text + '\n';
    }
    textString = textString.slice(0, -1);
    textUpdate(textString);
  };

  return (
    <div>
      <ShowAliasesComponent
        setList={setList}
        alias={alias}
        aliasUpdate={aliasUpdate}
      />

      <button
        disabled={!alias}
        className="btn btn-primary"
        onClick={() => loadTextsToInputBox()}
      >
        Send texts of alias {alias} to input box
      </button>
    </div>
  );
}

真正令人困惑的是,当我在子文本框中键入内容时,父状态正确更新(向下传递函数以更新父状态),而新的prop反映在渲染中。但是,当我从数据库加载组件调用相同的函数时,什么也没发生。

0 个答案:

没有答案