I want to select the HTML of whatever the user selects in a contenteditable div. I found some code to retrieve the HTML of the selection, but it's not limited to just the div.
What I want to do is copy the selected HTML, wrap tags around it, and then replace the selection with it. So, 'test' would become 'test' for instance.
<div contenteditable="true" class="body" id="bodydiv"></div>
function getSelectionHtml() {
var html = "";
if (typeof window.getSelection != "undefined") {
var sel = window.getSelection();
if (sel.rangeCount) {
var container = document.createElement("div");
for (var i = 0, len = sel.rangeCount; i < len; ++i) {
container.appendChild(sel.getRangeAt(i).cloneContents());
}
html = container.innerHTML;
}
} else if (typeof document.selection != "undefined") {
if (document.selection.type == "Text") {
html = document.selection.createRange().htmlText;
}
}
}
HI for getting content(text) inside a selected div I have create a little code you can check it out if it works for you :
$(document).ready(function(){
$(document).bind('mouseup', function(){
var content = getSelected();
content = "<b>"+content+"</b>";
$('#selected').html(content);
});
});
function getSelected(){
var t;
if(window.getSelection){
t = window.getSelection();
var start = t.focusOffset;
var end = t.baseOffset;
t = t.anchorNode.data;
t = t.slice(start, end);
} else if (document.selection) {
t = document.selection.createRange().text;
}
return t;
}
And
<div id="selected"></div>
Hope this helps.
Related
how i can to find selected text in a div , in html
for example we have selected from 5 to 11 in this text :
<div id="txt" >This is some <i> text </i> </div>
selected : is some ,
but in html is : id="txt
how to find this and replace between <p> or <span> that other tags to avoid loss of ?
excuse me for my bad english :)
Demo: http://jsfiddle.net/dKaJ3/2/
function getSelectionHtml() {
var html = "";
if (typeof window.getSelection != "undefined") {
var sel = window.getSelection();
if (sel.rangeCount) {
var container = document.createElement("div");
for (var i = 0, len = sel.rangeCount; i < len; ++i) {
container.appendChild(sel.getRangeAt(i).cloneContents());
}
html = container.innerHTML;
}
} else if (typeof document.selection != "undefined") {
if (document.selection.type == "Text") {
html = document.selection.createRange().htmlText;
}
}
alert(html);
}
Taken from: How to replace selected text with html in a contenteditable element?
Try to find things before you ask ;]
I had like to create an CRUD operation. I can able to create an DIV, Save the content to the Div, I'm unable to delete the DIV. I need to delete the selected DIV which i has created. I stuck how to select the DIV and delete the selected DIV.
Note: Should use only plain javaScript only.
Problem:
Need to delete that highlighted Div.
Please refer my below try code
<html>
<head>
<script>
var addid = 0;
function createJob() {
var jobList = document.getElementById("jobList");
if(document.getElementById('jobitem_' + (addid))) {
if((document.getElementById('jobitem_' + (addid)).textContent) == "") {
}else{
addid++;
jobNameCreation(jobList,addid);
}
}
if(addid == 0){
addid++;
jobNameCreation(jobList,addid);
}
}
function saveJob() {
var text_id = 'jobitem_' + addid;
var mainDiv = document.getElementById(text_id);
if(mainDiv.children[0].value == ""){
alert("please enter job name");
}else{
mainDiv.textContent =mainDiv.children[0].value;
}
}
function deleteJob() {
/*var t = '';
if(window.getSelection){
alert("1");
t = window.getSelection();
}else if(document.getSelection){
alert("2");
t = document.getSelection();
}else if(document.selection){
alert("3");
t = document.selection.createRange().text;
}
alert(t);
*/
}
function selectText(containerid) {
if (document.selection) {
var range = document.body.createTextRange();
range.moveToElementText(document.getElementById(containerid));
range.select();
} else if (window.getSelection) {
var range = document.createRange();
range.selectNode(document.getElementById(containerid));
window.getSelection().addRange(range);
}
}
function jobNameCreation(jobList,addid){
var text = document.createElement('div');
text.id = 'jobitem_' + addid;
text.innerHTML = "<input type='text' value='' style='padding:5px; width: 185px;' />";
text.onclick = function (e) {
selectText(text.id);
};
jobList.appendChild(text);
}
</script>
</head>
<body>
<button type="button" onclick="createJob();"> Create </button>
<button type="button" onclick="saveJob();"> Save </button>
<button type="button" onclick="deleteJob();"> Delete </button>
<br>
<div id="jobListContainer">
<div id="jobList">
</div>
</div>
</body>
</html>
Please help me on this. Thanks
One solution is that when your function selectText(containerid) is called store your containerid into global variable and based on that id you will remove your selected div in deleteJob() function which is call on Delete button click.
var addid = 0;
var selectedId = '';
function selectText(containerid) {
if (document.selection) {
var range = document.body.createTextRange();
range.moveToElementText(document.getElementById(containerid));
range.select();
} else if (window.getSelection) {
var range = document.createRange();
range.selectNode(document.getElementById(containerid));
window.getSelection().addRange(range);
}
selectedId = containerid;
}
function deleteJob() {
document.getElementById(selectedId).remove();
}
You can try the remove() function
var elem = document.getElementById("myDiv");
elem.parentNode.removeChild(elem);
// or
elem.remove();
Guess what you are looking for is anchorNode
Selection.anchorNode
Returns the node in which the selection begins.
-- https://developer.mozilla.org/en-US/docs/Web/API/Selection.anchorNode
… and the dynamically created ‘job'’ divs should be valid for the anchorNode to fetch them. So, use the below code to create and delete them — http://jsfiddle.net/uMhXM/2/
document.onLoad = function () {
jobListContainer = document.getElementById('jobListContainer');
jobList = document.getElementById('jobList');
}
function createJob() {
//Create an INPUT to get user input
var input = document.getElementById('input');
if (input === undefined || input === null) {
input = document.createElement('input');
input.type = 'text';
input.id = 'input';
}
//Add the created INPUT to 'jobListContainer'
jobListContainer.appendChild(input);
}
function saveJob() {
var input = document.getElementById('input');
if (input !== undefined && input !== null) {
if (input.value !== "") {
//Create the 'job' DIV enclosing INPUT value
var job = document.createElement('div');
job.setAttribute("id", "job_" +jobList.children.length);
job.textContent=input.value
//Add the created 'job' DIV to 'jobList'
jobList.appendChild(job);
//Remove the INPUT
input.remove();
} else {
alert("Please Enter Job");
}
}
}
function deleteJob(){
window.getSelection().anchorNode.remove();
}
I'm using this code to select text from the window document. This code is working fine in all browsers: it returns the selected text, but in IE8 it does not give the selected text. Instead it gives the whole HTML of the selected line. Can anybody give me solution for this?
Example:
<B><U><SPAN style="LINE-HEIGHT: 150%; FONT-FAMILY: 'Arial',
'sans-serif'; FONT-SIZE: 12pt">Summary</SPAN></U></B>
I want only Summary so all major browser return this except IE8.
<script type="text/javascript">
function getSelectionText(id) {
var html = "";
if (typeof window.getSelection != "undefined") {
var sel = window.getSelection();
if (sel.rangeCount) {
var container = document.createElement("div");
for (var i = 0, len = sel.rangeCount; i < len; ++i) {
container.appendChild(sel.getRangeAt(i).cloneContents());
}
html = container.innerHTML;
}
} else if (typeof document.selection != "undefined") {
if (document.selection.type == "Text") {
html = document.selection.createRange().htmlText;
}
}
document.getElementById(id).value = html;
//document.getElementById(id).value = html;
}
</script>
You should look into rangy - A cross-browser JavaScript range and selection library. In their own words:
It provides a simple standards-based API for performing common DOM Range and Selection tasks in all major browsers, abstracting away the wildly different implementations of this functionality between Internet Explorer up to and including version 8 and DOM-compliant browsers.
Change
html = container.innerHTML;
into
html = container.innerText;
The issue is with the following line in IE8
html = document.selection.createRange().htmlText;
Change it to this
html = document.selection.createRange().text;
Below is a nice simple function which seems to work well for me
function getSelectedText() {
var txt = '';
if (window.getSelection) {
txt = window.getSelection();
}
else if (document.getSelection) {
txt = document.getSelection();
}
else if (document.selection) {
txt = document.selection.createRange().text;
}
else return;
return txt;
}
Hope this helps
I have this function which removes selected (cursor) highlighted elements:
function deleteSelection() {
if (window.getSelection) {
// Mozilla
var selection = window.getSelection();
if (selection.rangeCount > 0) {
window.getSelection().deleteFromDocument();
window.getSelection().removeAllRanges();
}
} else if (document.selection) {
// Internet Explorer
var ranges = document.selection.createRangeCollection();
for (var i = 0; i < ranges.length; i++) {
ranges[i].text = "";
}
}
}
What I actually want to do is remove all the cursor- highlighted elements, except for the input#cursor element.
edit:
so lets say if I highlighted these elements with my cursor:
<span>a</span>
<span>b</span>
<input type='text' id = 'cursor' />
<span>c</span>
<span>d</span>
on a keyup, this function should not remove the <input> ...only the <span>
Phew, that was a little harder than expected!
Here's the code, I've tested it in IE8 and Chrome 16/FF5. The JSFiddle I used to test is available here. AFAIK, this is probably the best performance-wise you'll get.
The docs I used for Moz: Selection, Range, DocumentFragment. IE: TextRange
function deleteSelection() {
// get cursor element
var cursor = document.getElementById('cursor');
// mozilla
if(window.getSelection) {
var selection = window.getSelection();
var containsCursor = selection.containsNode(cursor, true);
if(containsCursor) {
var cursorFound = false;
for(var i=0; i < selection.rangeCount; i++) {
var range = selection.getRangeAt(i);
if(!cursorFound) {
// extracts tree from DOM and gives back a fragment
var contents = range.extractContents();
// check if tree fragment contains our cursor
cursorFound = containsChildById(contents, 'cursor');
if(cursorFound) range.insertNode(cursor); // put back in DOM
}
else {
// deletes everything in range
range.deleteContents();
}
}
}
else {
selection.deleteFromDocument();
}
// removes highlight
selection.removeAllRanges();
}
// ie
else if(document.selection) {
var ranges = document.selection.createRangeCollection();
var cursorFound = false;
for(var i=0; i < ranges.length; i++) {
if(!cursorFound) {
// hacky but it will work
cursorFound = (ranges[i].htmlText.indexOf('id=cursor') != -1);
if(cursorFound)
ranges[i].pasteHTML(cursor.outerHTML); // replaces html with parameter
else
ranges[i].text = '';
}
else {
ranges[i].text = '';
}
}
}
}
// simple BFS to find an id in a tree, not sure if you have a
// library function that does this or not
function containsChildById(source, id) {
q = [];
q.push(source);
while(q.length > 0) {
var current = q.shift();
if(current.id == id)
return true;
for(var i=0; i < current.childNodes.length; i++) {
q.push(current.childNodes[i]);
}
}
return false;
}
I would suggest removing the element you want keep, extracting the contents of the selection using Range's extractContents() method and then reinserting the element you want to keep using the range's insertNode() method.
For IE < 9, which doesn't support DOM Range, the code is trickier, so for simplicity you could use my Rangy library, which also adds convenience methods such as the containsNode() method of Range.
Live demo: http://jsfiddle.net/DFxH8/1/
Code:
function deleteSelectedExcept(node) {
var sel = rangy.getSelection();
if (!sel.isCollapsed) {
for (var i = 0, len = sel.rangeCount, range, nodeInRange; i < len; ++i) {
range = sel.getRangeAt(i);
nodeInRange = range.containsNode(node);
range.extractContents();
if (nodeInRange) {
range.insertNode(node);
}
}
}
}
deleteSelectedExcept(document.getElementById("cursor"));
it has any way for bind execcommand with a div element not for whole document , i try this :
document.getElementById('div').execcommand(...)
but it has an error :
execcommand is not a function
it has any way for bind the execcommand with just div element not whole document !!
i don't like use iframe method .
This is easier to do in IE than other browsers because IE's TextRange objects have an execCommand() method, meaning that a command can be executed on a section of the document without needing to change the selection and temporarily enable designMode (which is what you have to do in other browsers). Here's a function to do what you want cleanly:
function execCommandOnElement(el, commandName, value) {
if (typeof value == "undefined") {
value = null;
}
if (typeof window.getSelection != "undefined") {
// Non-IE case
var sel = window.getSelection();
// Save the current selection
var savedRanges = [];
for (var i = 0, len = sel.rangeCount; i < len; ++i) {
savedRanges[i] = sel.getRangeAt(i).cloneRange();
}
// Temporarily enable designMode so that
// document.execCommand() will work
document.designMode = "on";
// Select the element's content
sel = window.getSelection();
var range = document.createRange();
range.selectNodeContents(el);
sel.removeAllRanges();
sel.addRange(range);
// Execute the command
document.execCommand(commandName, false, value);
// Disable designMode
document.designMode = "off";
// Restore the previous selection
sel = window.getSelection();
sel.removeAllRanges();
for (var i = 0, len = savedRanges.length; i < len; ++i) {
sel.addRange(savedRanges[i]);
}
} else if (typeof document.body.createTextRange != "undefined") {
// IE case
var textRange = document.body.createTextRange();
textRange.moveToElementText(el);
textRange.execCommand(commandName, false, value);
}
}
Examples:
var testDiv = document.getElementById("test");
execCommandOnElement(testDiv, "Bold");
execCommandOnElement(testDiv, "ForeColor", "red");
Perhaps this helps you out:
Example code 1 on this page has the execcommand on a div by using a function. Not sure if that's what you're after? Good luck!
Edit: I figured out how to put the code here :o
<head>
<script type="text/javascript">
function SetToBold () {
document.execCommand ('bold', false, null);
}
</script>
</head>
<body>
<div contenteditable="true" onmouseup="SetToBold ();">
Select a part of this text!
</div>
</body>
Javascript:
var editableFocus = null;
window.onload = function() {
var editableElements = document.querySelectorAll("[contenteditable=true]");
for (var i = 0; i<editableElements.length; i++) {
editableElements[i].onfocus = function() {
editableFocus = this.id;
}
};
}
function setPreviewFocus(obj){
editableFocus = obj.id
}
function formatDoc(sCmd, sValue) {
if(editableFocus == "textBox"){
document.execCommand(sCmd, false, sValue);
}
}
HTML:
<div id="textBox" contenteditable="true">
Texto fora do box
</div>
<div contenteditable="true">
Texto fora do box
</div>
<button title="Bold" onclick="formatDoc('bold');">Bold</button>
You can keep it Simple, and add this to your div.
<div contenteditable="true" onmouseup="document.execCommand('bold',false,null);">