As noted in the search tags of this question; this is plain (valilla) JavaScript (not jQuery); here's a breakdown of the issue:
<div>
as innerHTML
onload
attribute with some JavaScript inside itsetInterval(...)
- (which does not work at all)the strange issue:
onload
attribute works fine,setInterval
& setTimeout
is completely ignored
During runtime (start-up), the SVG code is grabbed from an existing embed
element .getSVGDocument()
(after it has loaded) and prepared as plain HTML which can just be used as a template to create many others from the same source-code. I'm not using cloneNode(true)
-because: the interval is for animation (continuous slow & smooth rotation) - which could have a heavy impact on client-side resources, hence, I thought it best to grab the code and keep it as template - then remove the original from the DOM.
With all the above in mind, everything works fine:
console.log
the (inline) SVG code that is used, all looks perfectwindow.onerror == null
)onload
attribute works for things like: console.log(this)
- (which produces the SVG element in the log) - however, as mentioned: setInterval()
& setTimeout()
is just simply ignored - without any error and no warning.The following code is a very short example, and (regrettably) it works; however, in my production app it doesn't.
var html = '<svg xmlns="http://www.w3.org/2000/svg" version="1.1" onload="setInterval(function(){ console.log(\'testing\'); },500);">';
var temp = document.createElement('div'); temp.innerHTML = html;
var node = temp.getElementsByTagName('svg')[0];
document.body.appendChild(node);
If you test the above code in a new js file, it works; however, for the life of me I can't find the reason why it breaks in my app; as explained, it's quite simple really.
Does anyone know if there is some "gotcha" I'm not aware of regarding this? Maybe name-spacing?
If the source-code is required, I can load it up on JSFiddle, or CodePen -if required, but, it's a lot of code, and many files, which may not be necessary for publication.
I'm sure it's just something small; like, how timers register according to scope, and maybe how it's affected in .bind()
?
I'm really stuck with this, and I kinda need it working for a good impression for a job-interview; so if you know anything that could help, I would appreciate your input very much.
Thank you.
The following may help in related scenarios:
when targeting an asynchronous source, make sure the contentDocument
or getSVGDocument()
contains the resources you need to access. The window.onload
, or the DOMContentLoaded
event is relative to the current DOM, so it may help constructing your own listener->trigger for a cross-browser solution, because the contents you need may not be ready in a synchronous fashion.
the onload
attribute/event is not triggered when inserting dynamic content that is not asynchronously loaded, but may fire under certain circumstances, so, again, a custom:
listen->trigger will solve that.
The question is directly related to the 2nd point above, and the answer is quite simple really:
<svg onload="this.ready = true; setTinterval(...)"
onload
event was fired like so:if (!svgNode.ready){ svgNode.onload(); }
If there is an error in your code, but no error is shown, make sure window.onerror
is either null -or if it's a function, make sure it does NOT return true
- else it may suppress errors and you'll have a hard time tracking down what's wrong.
Please feel free to either improve this answer, or comment and I'll improve it accordingly; however, better answers will be appreciated.