How do I prevent the cursor in Chrome's textarea from jumping to the top when the user inserts a newline in the middle of a long text?

quanticle

If you have a <textarea> with a lot of text (i.e. more than twice the height of the textarea), when the user inserts a newline in the middle, Chrome scrolls the text such that the cursor is at the top of the <textarea>. This behavior is disorienting for the user, as they must manually scroll the textarea in order to bring content from above back into view. Neither Firefox nor Safari has this behavior.

Steps to reproduce:

  1. Create a <textarea>
  2. Paste a lot of text into it
  3. Put the cursor in the middle of the text
  4. Press Enter

Expected behavior: The relative position of the cursor in the textarea remains the same.

Actual behavior: The text scrolls such that the cursor is at the top of the text area.

To reiterate, this behavior does not occur with Safari or Firefox. It's specific to Chrome.

Is there any way to suppress this behavior in Chrome and get it to behave more like Firefox and Safari?

sbgib

Here's a way:

  1. Detect Chrome
  2. Count how many line breaks are used in the textarea
  3. Before input, check the scroll position of the textarea
  4. After input, see if the number of line breaks has increased (i.e. has the user entered a line break). If so, then reset the scroll position.

(Note: beforeinput event is already supported by Chrome, but assumed not to be supported by Chrome for iOS, so in that case scroll event can be used. If you prefer, you can simply enable the scroll event for all cases.)

function getChromeType() {
  //source: https://stackoverflow.com/questions/4565112/javascript-how-to-find-out-if-the-user-browser-is-chrome/13348618#13348618
  // please note, 
  // that IE11 now returns undefined again for window.chrome
  // and new Opera 30 outputs true for window.chrome
  // but needs to check if window.opr is not undefined
  // and new IE Edge outputs to true now for window.chrome
  // and if not iOS Chrome check
  // so use the below updated condition
  var isChromium = window.chrome;
  var winNav = window.navigator;
  var vendorName = winNav.vendor;
  var isOpera = typeof window.opr !== "undefined";
  var isIEedge = winNav.userAgent.indexOf("Edge") > -1;
  var isIOSChrome = winNav.userAgent.match("CriOS");

  if (isIOSChrome) {
    // is Google Chrome on IOS
    return 1;
  } else if (
    isChromium !== null &&
    typeof isChromium !== "undefined" &&
    vendorName === "Google Inc." &&
    isOpera === false &&
    isIEedge === false
  ) {
    // is Google Chrome
    return 2;
  } else {
    // not Google Chrome 
    return 0;
  };
};

function handleChromeTextarea(el, useScroll) {
  let getNoLineBreaks = () => {
    //source: https://stackoverflow.com/questions/10950538/how-to-detect-line-breaks-in-a-text-area-input
    return (el.value.match(/\n/g) || []).length;
  };

  let getScrollPos = () => {
    return el.scrollTop;
  };

  let onInput = (e) => {
    const newNoLineBreaks = getNoLineBreaks();

    if (noLineBreaks < newNoLineBreaks) {
      el.scrollTop = scrollPos;
    };

    noLineBreaks = newNoLineBreaks;
  };

  let onBeforeInput = (e) => {
    scrollPos = getScrollPos();
  };

  let noLineBreaks = getNoLineBreaks();
  let scrollPos = getScrollPos();

  el.addEventListener("input", onInput);
  el.addEventListener("beforeinput", onBeforeInput); //Already supported by Chrome - you may wish to use this without the scroll event

  if (useScroll) {
    el.addEventListener("scroll", onBeforeInput);
  };
};


const chromeType = getChromeType();

if (0 < chromeType) {
  handleChromeTextarea(document.getElementById("textarea"), (chromeType === 1));
};
<textarea id="textarea">
  Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Libero justo laoreet sit amet cursus. Massa eget egestas purus viverra. Quisque id diam vel quam elementum. Amet mauris commodo quis imperdiet. Viverra aliquet eget sit amet tellus cras adipiscing enim eu. Eu non diam phasellus vestibulum lorem. Morbi leo urna molestie at elementum. Massa massa ultricies mi quis hendrerit. Augue lacus viverra vitae congue eu consequat ac felis donec. Et ligula ullamcorper malesuada proin libero nunc consequat. Tincidunt dui ut ornare lectus sit amet est placerat in. Massa tempor nec feugiat nisl. Cursus euismod quis viverra nibh.

Quam lacus suspendisse faucibus interdum posuere lorem ipsum. Ut etiam sit amet nisl purus in. Magna sit amet purus gravida quis blandit turpis cursus. Sollicitudin ac orci phasellus egestas tellus rutrum tellus pellentesque. Aliquam nulla facilisi cras fermentum odio eu. Laoreet sit amet cursus sit. Fermentum iaculis eu non diam phasellus vestibulum. Feugiat in fermentum posuere urna nec tincidunt praesent semper feugiat. Dictum fusce ut placerat orci nulla pellentesque. Eu lobortis elementum nibh tellus molestie nunc non blandit massa.

Ullamcorper malesuada proin libero nunc consequat interdum varius sit amet. Blandit massa enim nec dui nunc mattis enim ut tellus. Ac turpis egestas maecenas pharetra convallis posuere morbi leo urna. Neque gravida in fermentum et sollicitudin ac orci. Blandit volutpat maecenas volutpat blandit aliquam. Felis donec et odio pellentesque diam. In cursus turpis massa tincidunt dui ut ornare lectus. Et malesuada fames ac turpis. Amet massa vitae tortor condimentum lacinia quis vel eros. Viverra vitae congue eu consequat ac. Pretium lectus quam id leo. Malesuada fames ac turpis egestas. In est ante in nibh mauris cursus mattis molestie a. Vel pharetra vel turpis nunc eget lorem dolor sed. Donec ultrices tincidunt arcu non sodales neque sodales ut etiam. Cras adipiscing enim eu turpis egestas pretium aenean pharetra magna. Risus feugiat in ante metus dictum at. Aliquet sagittis id consectetur purus ut faucibus. Sem et tortor consequat id.

Mi sit amet mauris commodo. Senectus et netus et malesuada fames. Adipiscing commodo elit at imperdiet dui accumsan. Felis eget nunc lobortis mattis aliquam. Nunc mattis enim ut tellus elementum sagittis vitae. Vitae nunc sed velit dignissim sodales ut eu sem. Mauris nunc congue nisi vitae suscipit. Id neque aliquam vestibulum morbi blandit cursus risus at ultrices. Laoreet suspendisse interdum consectetur libero id faucibus nisl tincidunt. Sollicitudin tempor id eu nisl nunc mi ipsum faucibus vitae. In egestas erat imperdiet sed euismod nisi porta lorem mollis.

Nisl rhoncus mattis rhoncus urna neque viverra justo nec. Fames ac turpis egestas integer eget aliquet nibh. Nunc consequat interdum varius sit amet. Magna fringilla urna porttitor rhoncus dolor purus non enim. Fermentum et sollicitudin ac orci phasellus egestas tellus rutrum. Integer enim neque volutpat ac tincidunt vitae semper. Mauris vitae ultricies leo integer malesuada nunc vel risus commodo. Proin nibh nisl condimentum id venenatis a condimentum. Amet mattis vulputate enim nulla aliquet porttitor lacus luctus accumsan. Eget nunc scelerisque viverra mauris. Accumsan sit amet nulla facilisi morbi tempus. Justo eget magna fermentum iaculis eu non. Fusce id velit ut tortor pretium viverra. Quam quisque id diam vel. Ut sem viverra aliquet eget sit amet tellus. At in tellus integer feugiat scelerisque varius morbi enim nunc. Leo vel fringilla est ullamcorper eget.
</textarea>

Collected from the Internet

Please contact [email protected] to delete if infringement.

edited at
0

Comments

0 comments
Login to comment

Related

How do I prevent the browser window from jumping back to the top of the page when when I open and close my panel?

How do I prevent pointer from jumping when tapping touchpad?

How do I prevent "jumping" of a div when simultanously resizing divs?

How do I stop ENTER from adding a newline to my textarea?

How to prevent jumping the text when scroll is display?

How to center a placeholder in a textarea without the text cursor starting in the middle?

How do I prevent my cursor from changing fields when loading websites?

In vim, how do I prevent pasting on top of visually selected text from erasing the contents of the clipboard?

How to prevent a click on a '#' link from jumping to top of page?

how to prevent css div popup from jumping back to the top of the page

How do I prevent textarea maxlength from blocking submit

How do I check if the user's text cursor is between two strings?

How to prevent the cursor from moving when modifying an input's value?

How do I prevent the cursor from going to a monitor that is turned off?

How do I prevent Visual Studio Code from breaking long lines when formatting code?

How do I prevent an user from accessing another user's profile?

How do I preserve line breaks when getting text from a textarea?

How to prevent normal cursor behavior when pressing keys in a textarea

How do I prevent the browser from scrolling to the top on render

How to margin text from top border in textarea

How do I prevent chrome from scrolling when angular 5 rerenders a large list?

How do I prevent HTML from ignoring the newline that comes from JavaScript?

How do i post text from textarea to mysql database

How do I prevent a leading newline in Vim when using :r!date and other shell commands?

How can I prevent the user from entering the same text twice

How do I prevent a flexbox from becoming wider when it contains a text input field?

How do I prevent duplication in my text file when asking for registration from customer in python

how do I save the cursor position when replacing textarea with a regular expression?

How do I prevent reload when a user is going to write something?