React不会有条件地渲染输入/ textarea

时间:2017-07-24 09:05:33

标签: javascript reactjs focus textarea

我正在尝试focus()在React中有条件渲染的textarea。以下代码与React docsthis similar question中的示例几乎完全相同。

下面的代码会立即显示并聚焦textarea。如果取消注释三个注释行,则在condition道具设置为true之后显示textarea(其值取决于父级的状态,最初为false),但是元素不再集中。

如果条件最初为true,则当组件首次呈现时,输入元素将按预期聚焦。当条件从false更改为true时,会出现此问题。

import React, { Component } from 'react'

class TestClass extends Component {
  constructor(props) {
    super(props)
    this.focus = this.focus.bind(this)
  }
  componentDidMount() {
    // this.props.condition &&
    this.focus()
  }
  componentDidUpdate() {
    // this.props.condition &&
    this.focus()
  }

  focus() {
    console.log(`this.textInput: ${this.textInput}`)
    this.textInput.focus()
  }

  render() {
    return (
      <div>
        {
          // this.props.condition &&
          <textarea
            ref={(input) => {this.textInput = input}}
            defaultValue="Thanks in advance for your invaluable advice">
            {console.log('textarea rendered')}
          </textarea>
        }
      </div>
    )
  }
}

控制台输出

textarea rendered
this.textInput: [object HTMLTextAreaElement]

排除该元素在focus()执行时不可用。

此外:

  • this question
  • 相比,设置autoFocus属性似乎不起作用
  • <input /><textarea />
  • 的问题相同

编辑:在回答下面的问题时,父组件如下所示。

class ParentComponent extends Component {
  constructor(props) {
  super(props)
    this.state = {
      condition: false
    }
    this.toggleCondition = this.toggleCondition.bind(this)
  }
  toggleCondition() {
    this.setState(prevState => ({
      condition: !prevState.condition
    }))
  }
  render() {
    return (
      <div>
        <TestClass condition={this.state.condition} />
        <button onMouseDown={this.toggleCondition} />
      </div>
    )
  }
}

2 个答案:

答案 0 :(得分:1)

import React, { Component } from 'react';

class TestClass extends Component {
  constructor(props) {
    super(props);
    this.focus = this.focus.bind(this);
  }
  componentDidMount() {
    this.focus();
  }
  componentWillReceiveProps(nextProps) {
    if (nextProps.condition !== this.props.condition) {
        this.focus();  
    }
  }
  focus() {
    console.log(`this.textInput: ${this.textInput}`);
    if (this.props.condition === true) {
      this.textInput.focus();
    }
  }

  render() {
    return (
      <div>
        {
          this.props.condition &&
          <textarea
            ref={(input) => { this.textInput = input; }}
            defaultValue="Thanks in advance for your invaluable advice"
          >
            {console.log('textarea rendered')}
          </textarea>
        }
      </div>
    );
  }
}
export default TestClass;

答案 1 :(得分:1)

原来问题真的很愚蠢。我实现切换按钮的方式(我在原始问题中简化为<button onClick={this.toggleCondition} />“为了清晰起见”),使用了一个自定义组件,该组件采用onClick道具并将其值附加到{{1超链接的属性。

由于超链接在其onMouseDown操作后被聚焦,因此焦点立即从textarea中删除。

我已编辑此问题以反映我对onMouseDown的使用情况。