Wednesday, June 5, 2024
 Popular · Latest · Hot · Upcoming
20
rated 0 times [  24] [ 4]  / answers: 1 / hits: 87450  / 8 Years ago, thu, july 14, 2016, 12:00:00

I have a textarea in React that I want to turn into a notepad. Which means I want the tab key to indent instead of unfocus. I looked at this answer, but I can't get it to work with React. Here is my code:



handleKeyDown(event) {
if (event.keyCode === 9) { // tab was pressed
event.preventDefault();
var val = this.state.scriptString,
start = event.target.selectionStart,
end = event.target.selectionEnd;

this.setState({scriptString: val.substring(0, start) + 't' + val.substring(end)});
// This line doesn't work. The caret position is always at the end of the line
this.refs.input.selectionStart = this.refs.input.selectionEnd = start + 1;
}
}
onScriptChange(event) {
this.setState({scriptString: event.target.value});
}
render() {
return (
<textarea rows=30 cols=100
ref=input
onKeyDown={this.handleKeyDown.bind(this)}
onChange={this.onScriptChange.bind(this)}
value={this.state.scriptString}/>
)
}


When I run this code, even if I press the tab key in the middle of the string, my cursor always appears at the end of the string instead. Anyone knows how to correctly set the cursor position?


More From » jquery

 Answers
9

You have to change the cursor position after the state has been updated(setState() does not immediately mutate this.state)



In order to do that, you have to wrap this.refs.input.selectionStart = this.refs.input.selectionEnd = start + 1; in a function and pass it as the second argument to setState (callback).



handleKeyDown(event) {
if (event.keyCode === 9) { // tab was pressed
event.preventDefault();
var val = this.state.scriptString,
start = event.target.selectionStart,
end = event.target.selectionEnd;
this.setState(
{
scriptString: val.substring(0, start) + 't' + val.substring(end)
},
() => {
this.refs.input.selectionStart = this.refs.input.selectionEnd = start + 1
});
}
}


jsfiddle


[#61361] Wednesday, July 13, 2016, 8 Years  [reply] [flag answer]
Only authorized users can answer the question. Please sign in first, or register a free account.
jaquelineh

Total Points: 360
Total Questions: 105
Total Answers: 114

Location: Saint Pierre and Miquelon
Member since Fri, Jan 28, 2022
2 Years ago
;