SVG is not HTML, that's why innerHTML
doesn't work. Use textContent
instead:
var text = document.querySelector('#firstName').textContent = 'Test';
Pergunta
I am trying to use basic DOM manipulation with Javascript to change the contents of a text-node in an SVG.
Basically this is the SVG I am embedding:
<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 200 200">
<text>
<tspan x="100" y="100" fill="#000000" font-size="10">Name:
<tspan id="firstName">placeholder</tspan>
</tspan>
</text>
</svg>
And this is my javascript snippet:
document.querySelector('#firstName').innerHTML = 'Test';
This works in Chrome. It fails in IE9.
I have tried fetching the SVG as a string with AJAX, creating a JQuery
element from said string and doing the replacement before adding it to the DOM but that did not work either. IE9 did manage to render it with the placeholder text though, so I suppose I can fall back on using a regexp on the string before creating a DOM element from it, but I'd love to avoid that.
Interestingly enough, I can delete the tspan
element and IE will remove it. I can also edit the contents of the tspan
via IE's developer tools and the image gets updated.
I just can't seem to use either innerHTML
or JQuery.html()
to update it.
I've created a jsfiddle here that tries to change an already embedded DOM since that was an easier thing to turn into a fiddle than the JQuery
approach. The behaviour is the same so I am guessing the underlying problem is the same as well.
If anyone can explain to me why this does not work in IE9 that would be great.
Solução
SVG is not HTML, that's why innerHTML
doesn't work. Use textContent
instead:
var text = document.querySelector('#firstName').textContent = 'Test';
Outras dicas
Here is the workaround, basically manipulation the SVG as a string prior to injecting it into the DOM.
var svgStr = ''
+ '<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" viewBox="0 0 200 200">'
+ ' <text>'
+ ' <tspan x="100" y="100" fill="#000000" font-size="10">Name: ##PLACEHOLDER##</tspan>'
+ ' <text>'
+ '</svg>';
svgStr = svgStr.replace('##PLACEHOLDER##', 'Test');
$('body').append(svgStr);
(I'm obviously not inlining the SVG in my code, but fetching it as a resource with an AJAX request, however that is kind of irrelevant here so it's omitted).
This works in IE9, as demonstrated here.
Any kind of cleaner solution is welcome.