Grow your CSS skills. Land your dream job.

Last updated on:

Support Tabs in Textareas

Normally the tab key moves to the next focusable thing. This inserts a tab character in instead.

HTMLTextAreaElement.prototype.getCaretPosition = function () { //return the caret position of the textarea
    return this.selectionStart;
};
HTMLTextAreaElement.prototype.setCaretPosition = function (position) { //change the caret position of the textarea
    this.selectionStart = position;
    this.selectionEnd = position;
    this.focus();
};
HTMLTextAreaElement.prototype.hasSelection = function () { //if the textarea has selection then return true
    if (this.selectionStart == this.selectionEnd) {
        return false;
    } else {
        return true;
    }
};
HTMLTextAreaElement.prototype.getSelectedText = function () { //return the selection text
    return this.value.substring(this.selectionStart, this.selectionEnd);
};
HTMLTextAreaElement.prototype.setSelection = function (start, end) { //change the selection area of the textarea
    this.selectionStart = start;
    this.selectionEnd = end;
    this.focus();
};

var textarea = document.getElementsByTagName('textarea')[0]; 

textarea.onkeydown = function(event) {
    
    //support tab on textarea
    if (event.keyCode == 9) { //tab was pressed
        var newCaretPosition;
        newCaretPosition = textarea.getCaretPosition() + "    ".length;
        textarea.value = textarea.value.substring(0, textarea.getCaretPosition()) + "    " + textarea.value.substring(textarea.getCaretPosition(), textarea.value.length);
        textarea.setCaretPosition(newCaretPosition);
        return false;
    }
    if(event.keyCode == 8){ //backspace
        if (textarea.value.substring(textarea.getCaretPosition() - 4, textarea.getCaretPosition()) == "    ") { //it's a tab space
            var newCaretPosition;
            newCaretPosition = textarea.getCaretPosition() - 3;
            textarea.value = textarea.value.substring(0, textarea.getCaretPosition() - 3) + textarea.value.substring(textarea.getCaretPosition(), textarea.value.length);
            textarea.setCaretPosition(newCaretPosition);
        }
    }
    if(event.keyCode == 37){ //left arrow
        var newCaretPosition;
        if (textarea.value.substring(textarea.getCaretPosition() - 4, textarea.getCaretPosition()) == "    ") { //it's a tab space
            newCaretPosition = textarea.getCaretPosition() - 3;
            textarea.setCaretPosition(newCaretPosition);
        }    
    }
    if(event.keyCode == 39){ //right arrow
        var newCaretPosition;
        if (textarea.value.substring(textarea.getCaretPosition() + 4, textarea.getCaretPosition()) == "    ") { //it's a tab space
            newCaretPosition = textarea.getCaretPosition() + 3;
            textarea.setCaretPosition(newCaretPosition);
        }
    } 
}

Reference URL

Comments

  1. Robin

    It is a cool feature, but I woudn’t recommend this.

    Most important reason: you’re changing default browser behaviour.

    How to switch to the next form element after you’re done with your textarea? Use the mouse? I personally hate it when I can’t tab through a form. When I’m on the keyboard, I’m on the keyboard. I don’t want to switch between keyboard and mouse when filling out a form.

    • Jesse
      Permalink to comment#

      Depends what you’re building. A backend custom css area for a WordPress theme or a code snippit site like snippi is a good example of where this would be useful. 2 cents.

  2. Luke
    Permalink to comment#

    @Robin
    This feature is NOT for forms with multiple inputs, but for something like a blog or a single-input-form. It´s the only element you work with, like markdown or something similar. If you use markdown really often, you will get crazy if you have to use space 4 times all the time. In all other forms you of course dont use this. Why would you use tabs in a comment window like this, makes no sense.

    btw… you could implement the feature where double-tab-press would make the initial switch to the next input

  3. The simplest:

    function enableTab(id) {
        var el = document.getElementById(id);
        el.onkeydown = function(e) {
            if (e.keyCode === 9) { // tab was pressed
    
                // get caret position/selection
                var val = this.value,
                    start = this.selectionStart,
                    end = this.selectionEnd;
    
                // set textarea value to: text before caret + tab + text after caret
                this.value = val.substring(0, start) + '\t' + val.substring(end);
    
                // put caret at right position again
                this.selectionStart = this.selectionEnd = start + 1;
    
                // prevent the focus lose
                return false;
    
            }
        };
    }

    Usage: enableTab('textarea-id');DEMO

  4. Clement
    Permalink to comment#

    @Luke, I will give you one example when tabulation is a must. Imagine you have a where you would want to let users insert/type source code, which would later be transformed and colored by CodeMirror and inserted in WYSISYG editor or something. Typing code without tabulation can really destroy your mental state.

  5. Stick
    Permalink to comment#

    Pardon my ignorance – why do we not simply insert \t? CSS can be used to set the tab-width, so unless there is a detail I’m not hip to (totally possible) it seems like we should be using escape characters…

Leave a Comment

Posting Code

Markdown is supported in the comment area, so you can write inline code in backticks like `this` or multiline blocks of code in in triple backtick fences like ```this```. You don't need to escape code in backticks, Markdown does that for you.

Sadly, it's kind of broken. WordPress only accepts a subset of HTML in comments, which makes sense, because certainly some HTML can't be allowed, like <script> tags. But this stripping happens before the comment is processed by Markdown (via Jetpack). It seems to me that would be reversed, because after Markdown processes code in backticks, it's escaped, thus safe. If you think you can fix this issue, get in touch!

If you need to make sure the code (typically HTML) you post absolutely posts correctly, escape it and put it within <pre><code> tags.

Current ye@r *

*May or may not contain any actual "CSS" or "Tricks".