Javascript SVG/XML中是否有一些innerHTML替换?

Javascript SVG/XML中是否有一些innerHTML替换?,javascript,xml,templates,svg,Javascript,Xml,Templates,Svg,在HTML中,我可以通过以字符串的形式提供模板来构建一个简单的模板系统,替换其中的一些部分,然后使用innerHTML将其分配给某个容器 var templ = '<span>{myText}</span>' var newContent = templ.replace( '{myText}', someVariable ); document.querySelector( '#myContainer' ).innerHTML = newContent; var tem

在HTML中,我可以通过以字符串的形式提供模板来构建一个简单的模板系统,替换其中的一些部分,然后使用
innerHTML
将其分配给某个容器

var templ = '<span>{myText}</span>'
var newContent = templ.replace( '{myText}', someVariable );
document.querySelector( '#myContainer' ).innerHTML = newContent;
var templ='{myText}'
var newContent=temp.replace('{myText}',someVariable);
document.querySelector(“#myContainer”).innerHTML=newContent;
这样我就可以利用浏览器的HTML解析器,而不必重复使用
document.createElement()
。如果模板增长超过几个元素,则后者可能会非常麻烦

但是,在SVG中,元素上没有属性,例如
innerHTML
,或者甚至没有
innerSVG

因此,我的问题是:在SVG中有什么我可以使用的方法类似于上面示例中的方法吗?或者我是否坚持使用
document.createElement()
(或者使用它的库)?


与我的问题一样:一般的JavaScript解决方案是首选,但任何指向提供解决方案的库的指针都是值得赞赏的。

使用jQuery,您可以这样做:

假设您的
svgString
包含替换操作后的svg图像

$(svgString)[0]
创建与字符串对应的svg标记。然后,可以在dom中希望绘制图像的位置附加此元素


我希望这对您有所帮助

您可以使用DOMParser来解析XML:然后您可以使用importNode将其放入您现有的文档中,如果您愿意的话:以类似这样的方式结束

var doc = new DOMParser().parseFromString(
   '<svg xmlns="http://www.w3.org/2000/svg"><circle cx="100" cy="100" r="20"/></svg>',
   'application/xml');

someElement.appendChild(
 someElement.ownerDocument.importNode(doc.documentElement, true));
var doc=new DOMParser().parseFromString(
'',
“应用程序/xml”);
someElement.appendChild(
someElement.ownerDocument.importNode(doc.documentElement,true));
简短的回答是“不,在XML世界中没有任何等价物可以让您给它一点标记,并让它在插入位置的适当名称空间中自动创建所有元素和属性。”

最直接的答案是@Robert所拥有的。正如我在评论中指出的,即使这样,您也需要在SVG文档中创建与要插入片段的文档具有相同名称空间和前缀的任何片段

相反,您可能会发现在标准DOM方法上使用便利方法同样容易(或更容易):

//在节点上创建一个带属性和可选文本的命名SVG元素
函数appendTo(节点、名称、属性、文本){
var p,ns=appendTo.ns,svg=node,doc=node.ownerDocument;
if(!ns){//按前缀缓存名称空间一次
而(svg&&svg.tagName!=“svg”)svg=svg.parentNode;
ns=appendTo.ns={svg:svg.namespaceURI};
对于(var a=svg.attributes,i=a.length;i--;){
如果(a[i].namespaceURI)ns[a[i].localName]=a[i].nodeValue;
}
}
var el=doc.createElements(ns.svg,名称);
for(属性中的var attr){
如果(!attrs.hasOwnProperty(attr))继续;
如果(!(p=attr.split(':')[1])el.setAttribute(attr,attrs[attr]);
else el.setAttributeNS(ns[p[0]| | null,p[1],attrs[attr]);
}
if(text)el.appendChild(doc.createTextNode(text));
返回节点appendChild(el);
}
功能清除(节点){
while(node.lastChild)node.removeChild(node.lastChild);
}
有了它,您可以做以下事情:

var图标={
应用程序:“/images/Apps.png”,
游戏:“/images/Games.png”
}
var wrap=document.querySelector(“#container”);
透明(包装);
用于(图标中的var标签){
如果(!icons.hasOwnProperty(标签))继续;
var icon=appendTo(wrap,'g',{'class':'icon'});
附录(图标,'image',{'xlink:href':图标[label]});
附录(图标,'text',{x:10,y:20},标签);
}
这比尝试使用字符串连接构造原始SVG标记更简洁:

var svg=[];
用于(图标中的var标签){
如果(!icons.hasOwnProperty(标签))继续;
svg.push(“”);
svg.push(“”);
svg.push(“”+标签+“”);
svg.push(“”);
}
wrap.innerssvg=svg.join(“”);//当然不行
查看javascript垫片,它提供了您想要的功能


2014更新:定义
元素
上的
innerHTML
outerHTML
,这使得这些在svg和xml元素上可用。这已经在Blink中发布了一段时间了,支持它的第一个版本是Chrome 32/Opera 19,更多详细信息可以在中找到。

我的innerSVG垫片怎么样?下面是CoffeeScript源代码,已编译的JavaScript已打开

#重要提示:您必须将页面作为XHTML提供,此垫片才能工作,
#否则,名称空间的属性和元素将变得混乱。
Object.defineProperty SVGElement.prototype“innerHTML”,
获取:()->
$temp=document.createElement“div”
$node=@cloneNode true
对于$node.children中的$child
$temp.appendChild$child
返回$temp.innerHTML
集合:(标记)->
而第一个孩子
@firstChild.parentNode.removeChild@firstChild
markup=“#{markup}”
$div=document.createElement“div”
$div.innerHTML=标记
$svg=$div.querySelector'svg#wrapper'
对于$svg.children中的$element
@追加子$element
可枚举:false
可配置:true

至少在Chrome和Safari上,您可以将SVG元素包装在HTML元素中,并请求
innerHTML
。下面的HTML文件呈现红色矩形,即使SVG源指定为绿色

<body>
<div id="wrapper">
  <svg xmlns="http://www.w3.org/2000/svg" version="1.1" width="120" height="120" viewBox="0 0 236 120">
    <rect x="14" y="23" width="250" height="50" fill="green" stroke="black" stroke-width="1" />
  </svg>
</div>
<script>
  var el = document.getElementById('wrapper');
  var t = el.innerHTML;
  t = t.replace(/green/g, "red");
  el.innerHTML = t;
</script>
</body>

var el=document.getElementById('wrapper');
var t=el.innerHTML;
t=t.替换(/green/g,“red”);
el.innerHTML=t;

这里我写了一个肮脏的方式

SVG的innerHTML解决方案


var twocircles\
'
var插座=document.createElement('div');
var svgfragment=''+twocircles+'';
receptor.innerHTML=''+svgfragment;
var节点=Array.prototype.slice.call(插座.childNode
<html>
    <body>
        <svg id="svgcanvas">
        </svg>
        <script>
            var twocircles='<circle cx="253" cy="562" r="10" stroke="black" stroke-width="2" fill="red"></circle> \
            <circle cx="353" cy="562" r="10" stroke="black" stroke-width="2" fill="red"></circle>'
            var receptacle = document.createElement('div');
            var svgfragment='<svg>'+twocircles+'</svg>';
            receptacle.innerHTML=''+svgfragment;
            var Nodes=Array.prototype.slice.call(receptacle.childNodes[0].childNodes);
            Nodes.forEach(function(el){document.getElementById('svgcanvas').appendChild(el)})
        </script>
    </body>
</html>