I'm trying to focus()
a conditionally rendered textarea in React. The code below is almost exactly identical to the example in the React docs or to this similar question.
The code below immediately shows and focuses the textarea. If the three commented lines are uncommented, the textarea gets shown after the condition
prop is set to true
(its value depends on the state of the parent and is initially false
), but the element doesn't get focused anymore.
If the condition is initially true
, the input element gets focused as expected when the component renders for the first time. The problem occurs when the condition is changed from false
to 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>
)
}
}
The console output
textarea rendered
this.textInput: [object HTMLTextAreaElement]
rules out that the element is unavailable at the time focus()
gets executed.
Furthermore:
- Setting
autoFocus
attribute doesn't seem to work, in contrast to this question - Same problem for both
<input />
and<textarea />
Edit: in response to the question below, the parent component looks as follows.
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>
)
}
}