dangerChihuahua007
dangerChihuahua007

Reputation: 20925

How do I prevent the user from typing new lines in a contentEditable element?

I made my div element contentEditable so that the user can edit its contents:

<div contentEditable='true' id='myDiv'>
    This content can be edited.
</div>

However, I'd like to prevent the user from typing new lines into the div element. I've tried preventing the default action of keydown events to no avail:

var container = document.getElementById('myDiv');

function tryToPreventNewLines(e) {
    switch (e.keyCode) {
        case 13:
            container.blur();
            e.preventDefault();
            return false;
    }
    return true;
}

myDiv.addEventListener(
    'keydown', tryToPreventNewLines);
myDiv.addEventListener(
    'change', tryToPreventNewLines);

JSFiddle: http://jsfiddle.net/pwmspdm4/

In this case, the user can produce several new lines by hitting the enter key while within the div and not letting go of the enter key.

Upvotes: 3

Views: 3414

Answers (1)

T.J. Crowder
T.J. Crowder

Reputation: 1075925

The problem seems to be the container.blur() call; if you move that out of the handling of the event with a setTimeout, the code works (prevents the user creating a newline, and blurs the container):

function tryToPreventNewLines(e) {
    switch (e.keyCode) {
        case 13:
            e.preventDefault();
            setTimeout(function() {
                container.blur();
            }, 0);
            return false;
    }
    return true;
}

Updated Fiddle

Of course, I'm assuming you want to blur the container when they press Enter. If not, just remove that line entirely.

Tested on Chrome, Firefox, and IE11.


Below you note that on Chrome, holding down Enter continues to add newlines, even with the above. The only way I see to prevent that is to control the contentEditable property:

var container = document.getElementById('myDiv');

function tryToPreventNewLines(e) {
    switch (e.keyCode) {
        case 13:
            e.preventDefault();
            this.contentEditable = false; // No longer editable
            this.blur();                  // Remove selection box on Firefox
            return false;
    }
    // Removed the `return true;` here; it was a no-op
}

function enableEdit() {
    this.contentEditable = true;          // Make it editable
    this.focus();                         // And put the cursor in it
}

// Just for max compatibility, added the third argument below;
// some browsers still require it
myDiv.addEventListener(
    'keydown', tryToPreventNewLines, false);
myDiv.addEventListener(
    'change', tryToPreventNewLines, false);
myDiv.addEventListener(
    'click', enableEdit, false);

Updated Fiddle

Upvotes: 3

Related Questions