Javascript JS:获取contentEditable div中所有选定节点的数组
嗨,我已经和contentEditable合作一段时间了,我想我对它有很好的把握。我回避的一件事是如何获得对部分或完全在用户选择范围内的所有节点的引用数组。有人有主意吗 以下是一些开始:Javascript JS:获取contentEditable div中所有选定节点的数组,javascript,html,wysiwyg,Javascript,Html,Wysiwyg,嗨,我已经和contentEditable合作一段时间了,我想我对它有很好的把握。我回避的一件事是如何获得对部分或完全在用户选择范围内的所有节点的引用数组。有人有主意吗 以下是一些开始: <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<script type="text/javascript">
function getSelectedNodes(){
var sel = window.getSelection();
try{var frag=sel.getRangeAt(0).cloneContents()}catch(e){return(false);}
var tempspan = document.createElement("span");
tempspan.appendChild(frag);
var selnodes = Array() //<<- how do I fill this array??
var output = ''
for(i in selnodes){
output += "A "+selnodes[i].tagName+" was found\n"
//do something cool with each element here...
}
return(output)
}
</script>
</head>
<body contentEditable="true" onkeypress="return(keypress(event))">
<div>This <strong>div</strong> is <em>content</em> <span class='red'>editable</span> and has a couple of <em><strong>child nodes</strong></em> within it</div>
<br />
<br />
<a href="#" onmouseover="alert(getSelectedNodes())">hover here</a>
</body>
</html>
函数getSelectedNodes(){
var sel=window.getSelection();
请尝试{var frag=sel.getRangeAt(0).cloneContents()}catch(e){return(false);}
var tempspan=document.createElement(“span”);
临时儿童(frag);
var selnodes=Array()//你太接近了!当你将文档片段
附加到临时span
元素时,你已经把它们变成了一个可管理的组,可以通过可信的childNodes
数组访问
var selnodes = tempspan.childNodes;
此外,您正在设置for(i in selnodes)
循环,该循环将返回数组中的元素,加上长度
属性、\uuuuu proto\uuu
属性以及对象可能具有的任何其他属性
当在对象中的属性上循环时,实际上应该只对
循环使用这些类型的,然后始终使用if(obj.hasOwnProperty[i])
来过滤从原型继承的属性
在阵列中循环时,请使用:
for(var i=0,u=selnodes.length;i<u;i++)
事情是这样的:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<script type="text/javascript">
function getSelectedNodes(){
var sel = window.getSelection();
try{var frag=sel.getRangeAt(0).cloneContents()}catch(e){return(false);}
var tempspan = document.createElement("span");
tempspan.appendChild(frag);
console.log(tempspan);
window.selnodes = tempspan.childNodes;
var output = ''
for(var i=0, u=selnodes.length;i<u;i++){
if (typeof selnodes[i].tagName !== 'undefined'){
output += "A "+selnodes[i].tagName+" was found\n"
}
else output += "Some text was found: '"+selnodes[i].textContent+"'\n";
//do something cool with each element here...
}
return(output)
}
</script>
</head>
<body contentEditable="true" onkeypress="return(keypress(event))">
<div>This <strong>div</strong> is <em>content</em> <span class='red'>editable</span> and has a couple of <em><strong>child nodes</strong></em> within it</div>
<br />
<br />
<a href="#" onmouseover="alert(getSelectedNodes())">hover here</a>
</body>
</html>
函数getSelectedNodes(){
var sel=window.getSelection();
请尝试{var frag=sel.getRangeAt(0).cloneContents()}catch(e){return(false);}
var tempspan=document.createElement(“span”);
临时儿童(frag);
console.log(tempspan);
window.selnodes=tempspan.childNodes;
变量输出=“”
对于(var i=0,u=selnodes.length;i这里有一个版本,它提供实际选定和部分选定的节点,而不是克隆。或者,您可以使用我的库,它有一个范围对象的getNodes()
方法,在IE<9中工作
function nextNode(node) {
if (node.hasChildNodes()) {
return node.firstChild;
} else {
while (node && !node.nextSibling) {
node = node.parentNode;
}
if (!node) {
return null;
}
return node.nextSibling;
}
}
function getRangeSelectedNodes(range) {
var node = range.startContainer;
var endNode = range.endContainer;
// Special case for a range that is contained within a single node
if (node == endNode) {
return [node];
}
// Iterate nodes until we hit the end container
var rangeNodes = [];
while (node && node != endNode) {
rangeNodes.push( node = nextNode(node) );
}
// Add partially selected nodes at the start of the range
node = range.startContainer;
while (node && node != range.commonAncestorContainer) {
rangeNodes.unshift(node);
node = node.parentNode;
}
return rangeNodes;
}
function getSelectedNodes() {
if (window.getSelection) {
var sel = window.getSelection();
if (!sel.isCollapsed) {
return getRangeSelectedNodes(sel.getRangeAt(0));
}
}
return [];
}
下面的代码是解决您的问题的示例,下面的代码返回范围内所有选定的节点
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>payam jabbari</title>
<script src="http://code.jquery.com/jquery-2.0.2.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(document).ready(function(){
var startNode = $('p.first').contents().get(0);
var endNode = $('span.second').contents().get(0);
var range = document.createRange();
range.setStart(startNode, 0);
range.setEnd(endNode, 5);
var selection = document.getSelection();
selection.addRange(range);
// below code return all nodes in selection range. this code work in all browser
var nodes = range.cloneContents().querySelectorAll("*");
for(var i=0;i<nodes.length;i++)
{
alert(nodes[i].innerHTML);
}
});
</script>
</head>
<body>
<div>
<p class="first">Even a week ago, the idea of a Russian military intervention in Ukraine seemed far-fetched if not totally alarmist. But the arrival of Russian troops in Crimea over the weekend has shown that he is not averse to reckless adventures, even ones that offer little gain. In the coming days and weeks</p>
<ol>
<li>China says military will respond to provocations.</li>
<li >This Man Has Served 20 <span class="second"> Years—and May Die—in </span> Prison for Marijuana.</li>
<li>At White House, Israel's Netanyahu pushes back against Obama diplomacy.</li>
</ol>
</div>
</body>
</html>
帕亚姆·贾巴里
$(文档).ready(函数(){
var startNode=$('p.first').contents().get(0);
var endNode=$('span.second').contents().get(0);
var range=document.createRange();
range.setStart(startNode,0);
range.setEnd(endNode,5);
var selection=document.getSelection();
选择。添加范围(范围);
//下面的代码返回选择范围内的所有节点。此代码适用于所有浏览器
var nodes=range.cloneContents().queryselectoral(“*”);
对于(var i=0;i我知道我真的很接近!childNodes真的返回DOM实节点数组吗?我无法获取标准属性来处理数组内容。例如:selnodes[i]。innerHTML='P:'+selnodes[i].innerHTML
Ah-这是在tempspan中返回节点。如何引用原始节点以更改其内容?@cronoklee您可以访问范围.commonAncestorContainer
节点并迭代其子节点,直到找到范围.startContainer
和范围.endContainer
。Tim,我该怎么做修改数组中的节点?我想通过使用outerHTML(删除第一个p节点的和第二个p节点的)合并两个特定的p节点,但它不起作用。这是amaaazing!!!!!我已经抓到我的头了,因为我必须使用cloneContents(),这会丢失对DOM的引用。这是gold Tim。
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>payam jabbari</title>
<script src="http://code.jquery.com/jquery-2.0.2.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(document).ready(function(){
var startNode = $('p.first').contents().get(0);
var endNode = $('span.second').contents().get(0);
var range = document.createRange();
range.setStart(startNode, 0);
range.setEnd(endNode, 5);
var selection = document.getSelection();
selection.addRange(range);
// below code return all nodes in selection range. this code work in all browser
var nodes = range.cloneContents().querySelectorAll("*");
for(var i=0;i<nodes.length;i++)
{
alert(nodes[i].innerHTML);
}
});
</script>
</head>
<body>
<div>
<p class="first">Even a week ago, the idea of a Russian military intervention in Ukraine seemed far-fetched if not totally alarmist. But the arrival of Russian troops in Crimea over the weekend has shown that he is not averse to reckless adventures, even ones that offer little gain. In the coming days and weeks</p>
<ol>
<li>China says military will respond to provocations.</li>
<li >This Man Has Served 20 <span class="second"> Years—and May Die—in </span> Prison for Marijuana.</li>
<li>At White House, Israel's Netanyahu pushes back against Obama diplomacy.</li>
</ol>
</div>
</body>
</html>