Cómo hacer que la tecla de tabulación insertar un carácter de tabulación en un div contentEditable?

StackOverflow https://stackoverflow.com/questions/2237497

Pregunta

Estoy construyendo un simple editor de texto mediante el establecimiento de contentEditable=true en un div (de todos modos yo creo que área de texto se comporta de la misma manera) y tengo algunos problemas con la tecla de tabulación.

Lo que quiero es que cuando el usuario presiona la tecla TAB, el foco permanece en el div y se añade un carácter de tabulación en el texto.

He resuelto la primera parte del problema llamando preventDefault() en el objeto de evento en keydown y ahora el div no perder el foco, pero no sé por qué no puedo insertar el carácter.

El código de entidad para el carbón pestaña es 	 pero si intento agregar esta cadena para el innerHTML Firefox reemplazarlo con un espacio sencillo (no   sólo un espacio en blanco). También probé con \t pero el resultado es el mismo.

Así que mi pregunta es, ¿Cómo puedo insertar un carácter de tabulación en el texto?

¿Fue útil?

Solución

La razón por la que sólo se ve un espacio sencillo es porque las secuencias de caracteres de espacio en blanco (con excepción de los espacios de no separación) se tratan como un único carácter de espacio en el interior divs. Si desea que el carácter de tabulación que se mostrará en la forma esperada que necesita para ponerlo dentro de algo así como un elemento <pre> que hace que los espacios en blanco, ya que es en el código fuente HTML, o dentro de un elemento con white-space: pre establecer a través de CSS.

Otros consejos

Sé que esto es un poco viejo, pero esto terminó trabajando lo mejor para mí ...

function onKeyDown(e) {
    if (e.keyCode === 9) { // tab key
        e.preventDefault();  // this will prevent us from tabbing out of the editor

        // now insert four non-breaking spaces for the tab key
        var editor = document.getElementById("editor");
        var doc = editor.ownerDocument.defaultView;
        var sel = doc.getSelection();
        var range = sel.getRangeAt(0);

        var tabNode = document.createTextNode("\u00a0\u00a0\u00a0\u00a0");
        range.insertNode(tabNode);

        range.setStartAfter(tabNode);
        range.setEndAfter(tabNode); 
        sel.removeAllRanges();
        sel.addRange(range);
    }
}

Dado que la respuesta que supuestamente era correcta no funcionó para mí, se me ocurrió esta solución creo que funcionaría para más personas.

$(document).on('keyup', '.editor', function(e){
  //detect 'tab' key
  if(e.keyCode == 9){
    //add tab
    document.execCommand('insertHTML', false, '&#009');
    //prevent focusing on next element
    e.preventDefault()   
  }
});

Ese código que funcionó para mí, sino también asegurarse de incluir el atributo white-space:pre-wrap en el CSS. Espero que esto ayudó!

pestañas y espacios se colapsaron en html en un espacio a menos en una etiqueta <pre> o ha white-space: pre en su estilo

puede insertar un lapso con un espacio en blanco = pre y la ficha contenido. esto se realiza mejor con rangos de esta manera:

// adapted from http://stackoverflow.com/a/25943182/460084
function insertTab() {
  if (!window.getSelection) return;
  const sel = window.getSelection();
  if (!sel.rangeCount) return;
  const range = sel.getRangeAt(0);
  range.collapse(true);
  const span = document.createElement('span');
  span.appendChild(document.createTextNode('\t'));
  span.style.whiteSpace = 'pre';
  range.insertNode(span);
  // Move the caret immediately after the inserted span
  range.setStartAfter(span);
  range.collapse(true);
  sel.removeAllRanges();
  sel.addRange(range);
}

$(document).on('keydown', '.editor', function(e) {
  if (e.keyCode == 9) {
    insertTab();
    e.preventDefault()
  }
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div contenteditable=true style="border: solid" class='editor'></div>

Yo uso esta solución:

$('[contenteditable]').on('keydown', function(e){
    if(e.keyCode == 9){
        e.preventDefault();
        document.execCommand('insertHTML', false, '&#009');
    }
}).css('white-space', 'pre-wrap');

Cuando se trabaja con código editable, un elemento <pre> no necesita la última css añadido. keyup vs keydown y la posición de e.preventDefault () puede diferir en los navegadores.

Nota: Creo que la clave de unión al evento o lo que sea de todo el documento debe ser evitada. Tenía problemas extraños con los navegadores de escritorio Safari / iOS con elementos contentEditable y eventos burbujeantes.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top