0

I'm currently doing something this for my React textarea component:

componentDidUpdate() {
  let target = this.textBoxRef.current;

  target.style.height = 'inherit';
  target.style.height = `${target.scrollHeight + 1}px`; 
}

This works and allows the textarea to dynamically grow and shrink in height as line breaks are added and removed.

The problem is that on every text change there is a reflow occurring. This causes a lot of lag in the application. If I hold down a key in the textarea there is delay and lag as the characters are appended.

If I remove the target.style.height = 'inherit'; line the lag goes away, so I know it's being caused by this constant reflow.

I heard that setting overflow-y: hidden might get rid of the constant reflow, but it did not in my case.

My only other idea is to do a scan of the textarea on every text change for the number of \n character counts and set the height based on that count. The only problem is that it seems brittle, verbose, and is an O(n) operation for every text-change that I'd like to avoid.

Thoughts?

Edit: Alright, I ended up just counting \n's in the text change handler to predict the height. Contenteditable div's are too limited. Maybe I'll re-post this question later since I doubt it'll be re-opened.

Ryan Peschel
  • 11,087
  • 19
  • 74
  • 136
  • target.style.height = 'auto'; – Balaji Sep 16 '19 at 13:56
  • Actually, I think I want to re-open this. `contentEditable` apparently has a large host of problems. It may just be easier to continue dealing with textareas. – Ryan Peschel Sep 16 '19 at 14:04
  • Apparently doing even simple things with a `contentEditable` div is tricky and I rather not have to use a library with `dangerouslySetInnerHTML` to accommodate it: https://github.com/lovasoa/react-contenteditable – Ryan Peschel Sep 16 '19 at 14:05

1 Answers1

1

You can use contenteditable div instead:

<div name="someName" contenteditable="true">This text can be edited by the user.</div>
demkovych
  • 7,827
  • 3
  • 19
  • 25
  • I just tried this out and unfortunately it has its set of problems as well.. No placeholder text, can't set the text easily (need to use a dangerouslySetInnerHTML hack), updating the selection cursor is tricky, etc. – Ryan Peschel Sep 16 '19 at 14:06