Skip to content

Instantly share code, notes, and snippets.

@michelcmorel
Last active April 27, 2022 10:42
Show Gist options
  • Select an option

  • Save michelcmorel/6725279 to your computer and use it in GitHub Desktop.

Select an option

Save michelcmorel/6725279 to your computer and use it in GitHub Desktop.
add html elements inside content editable area, credits Tim Down on stackoverflow. original post at:http://stackoverflow.com/questions/6690752/insert-html-at-caret-in-a-contenteditable-div
<!DOCTYPE html>
<html>
<head>
<script src="http://ajax.googleapis.com/ajax/libs/jquery/2.0.2/jquery.min.js"></script>
<meta charset=utf-8 />
<title>JS Bin</title>
</head>
<body>
<input type="checkbox" id="selectPasted" checked> Selected pasted content
<br>
<input type="button" id="paste" value="Paste HTML" unselectable="on">
<div id="test" contenteditable="true">
Here is some nice text
</div>
</body>
</html>
function pasteHtmlAtCaret(html, selectPastedContent) {
var sel, range;
if (window.getSelection) {
// IE9 and non-IE
sel = window.getSelection();
if (sel.getRangeAt && sel.rangeCount) {
range = sel.getRangeAt(0);
range.deleteContents();
// Range.createContextualFragment() would be useful here but is
// only relatively recently standardized and is not supported in
// some browsers (IE9, for one)
var el = document.createElement("div");
el.innerHTML = html;
var frag = document.createDocumentFragment(), node, lastNode;
while ( (node = el.firstChild) ) {
lastNode = frag.appendChild(node);
}
var firstNode = frag.firstChild;
range.insertNode(frag);
// Preserve the selection
if (lastNode) {
range = range.cloneRange();
range.setStartAfter(lastNode);
if (selectPastedContent) {
range.setStartBefore(firstNode);
} else {
range.collapse(true);
}
sel.removeAllRanges();
sel.addRange(range);
}
}
} else if ( (sel = document.selection) && sel.type != "Control") {
// IE < 9
var originalRange = sel.createRange();
originalRange.collapse(true);
sel.createRange().pasteHTML(html);
var range = sel.createRange();
range.setEndPoint("StartToStart", originalRange);
range.select();
}
}
document.getElementById("paste").onclick = function() {
document.getElementById('test').focus();
var selectPastedContent = document.getElementById('selectPasted').checked;
pasteHtmlAtCaret('<b>INSERTED</b>', selectPastedContent);
return false;
};
@bahmanenayati
Copy link
Copy Markdown

How do you add to a particular input?

@JozefJarosciak
Copy link
Copy Markdown

this is quite nice, thanks

@PepeNickel
Copy link
Copy Markdown

This works fine in Firefox, Chrome and Opera, but in IE 11 and Edge the range.insertNode(frag) throws an exception... (??)

@timdown
Copy link
Copy Markdown

timdown commented Apr 3, 2019

This works fine in Firefox, Chrome and Opera, but in IE 11 and Edge the range.insertNode(frag) throws an exception... (??)

Example?

Copy link
Copy Markdown

ghost commented May 8, 2020

the new html content is being inserted at the begining..

@abhishekmatta999
Copy link
Copy Markdown

I'm having the same issue

@shoyebsheikh
Copy link
Copy Markdown

if the contenteditable element is not currently focused, the html is inserted at the beginning, how to make it insert at last ?

@unlocomqx
Copy link
Copy Markdown

unlocomqx commented Apr 27, 2022

I use this function to set the caret at then end of the element

export function setCaretAtEnd () {
    var range = document.createRange()
    var sel = window.getSelection()
    const last = editable.lastChild
    if (last) {
      range.setStartAfter(last)
      range.collapse(true)
      sel.removeAllRanges()
      sel.addRange(range)
    }
  }

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment