Frank Vel
Frank Vel

Reputation: 1208

keyup event on contenteditable div

I'm attempting to format the text in an contenteditable div after Enter is pressed. The problem is that no keyups are being registered from any key, so this is making it impossible. Other events, such as 'click' does work, and if I change the element to 'document' (document.addEventListener()...) this will make it work too, but this is an extreme solution. Is there a simple solution?

window.addEventListener('load', function() {
    var editbox = document.getElementById("editable")
    editbox.addEventListener('keyup', function(e) {
        alert("this should appear");
    });
});
<main contenteditable="true">
    <div class="box" id="editable">
        text
    </div>
</main>

Upvotes: 5

Views: 9184

Answers (4)

Dennijs
Dennijs

Reputation: 11

There is another solution. You can just detect an inputType.

const divInput = document.getElementById('divInput');
const textarea = document.getElementById('inputTypePreview');

divInput.addEventListener('input', (event) => {
  const t = event.inputType;
  textarea.innerHTML = `${t} \n`;
  if (t === 'insertParagraph' || t === 'insertLineBreak') 
    textarea.innerHTML = 'Enter detected \n';
 });
#inputTypePreview {
  margin: 1em 0 0;
}
#divInput, #inputTypePreview {
  border: 1px solid #b1b0b0;
  border-radius: 3px;
  width: 100%;
  resize: none;
}
<div id="divInput" contentEditable="true"></div>
<textarea id="inputTypePreview" disabled></textarea>

Upvotes: 1

zer00ne
zer00ne

Reputation: 43880

Use keyCode event.key to detect the specific key 'Enter' = ENTER. Use event.target property to detect exactly what element was typed on. The #editable div is within the main which is contenteditable so it can't be accessed by normal means, therefore target the main instead.

To test the demo:

  1. Place the cursor within the blue outlined area.
  2. Press the ENTER key.
  3. The console should log every ENTER key pressed.
  4. Now click below the outlined area and press ENTER.
  5. The keyup event is ignored and there's nothing logged.

Demo

document.addEventListener('keyup', function(e) {
  if (e.key === 'Enter' && e.target.tagName === 'MAIN') {
    console.log('ENTER');
  }
});
#editable {
  color: red
}
<!doctype html>
<html>

<head>
  <meta charset="utf-8">
  <title>title</title>
</head>

<body>
  <main contenteditable="true">
    <div class="box" id="editable">
      text
    </div>
  </main>
</body>

</html>

Upvotes: 4

qiAlex
qiAlex

Reputation: 4346

  1. You should listen the element with contenteditable="true"
  2. there is special event for it called input.
  3. you don't need document.getElementById at almost all cases. almost every element with id has it's own variable.

window.addEventListener('load', function() {
    let enterCount = 0;
    editable.addEventListener('input', function(e) {
        console.log ("this should appear");
        if (enterCount < e.target.querySelectorAll('br').length) {    
            console.log ('enter was pressed');
        }
        enterCount = e.target.querySelectorAll('br').length;
    });
});
<!doctype html>
<html>
    <head>
        <meta charset="utf-8">
        <title>title</title>
        <script src="javascript.js"></script>
    </head>
    <body>
        <main contenteditable="true" id="editable">
            <div class="box" >
                text
            </div>
        </main>
    </body>
</html>

Upvotes: 2

smarber
smarber

Reputation: 5074

You're not attaching the listener to the right element.

window.addEventListener('load', function() {
    var editbox = document.getElementById("elm_editable")

    editbox.addEventListener('keyup', (e) => {
        // and here is how to detect the enter key
        if (13 === e.keyCode) {
            alert("this should appear");
        }        
    });
});
<main contenteditable="true" id="elm_editable">
    <div class="box" id="editable">
        text
    </div>
</main>

Upvotes: 1

Related Questions