I encountered a problem of dynamic editing a content in a XHTML. Since document.write cannot be used there, one needs to use a different approach. An ideal solution would be
<script type="text/javascript"> var element_to_insert = ... var the_element = thisElement(); the_element.parentNode.insertBefore(element_to_insert, the_element); </script>Now, we need to define function thisElement properly. I came up with this solution
function thisElement(){
var obj = document.documentElement;
while (obj.lastChild) obj = obj.lastChild;
return obj.parentNode;
}
Assuming that the script is executed at the time when it appears, function thisElement finds the very last element at that time. That element is the text element of the javascript being executed. The parent of this text element is the corresponding script element.
When it does not work
- If you defer the execution of the script using option defer.
- If you add an element after your script element and then call thisElement(). For example,
<script type="text/javascript"> var obj = thisElement(); obj.parentNode.appendChild(another_element); var obj2 = thisElement(); // obj2 is not the script element! </script>
Other solutions
After having spent a day looking for a solution on the web I found solutions that use id or src properties. For example, here. The idea is the following:
<script type="text/javascript" id="the_element">
var element_to_insert = ...
var script = document.getElementById("the_element");
script.parentNode.insertBefore(element_to_insert, script);
</script>
and this one
<script type="text/javascript" src="the_script.js"/>where the file the_script.js is
var element_to_insert = ...
var all_scripts = document.getElementsByTagName("script");
for (var s = 0; s < all_scripts.length; s++)
if (all_scripts[s].src == "the_script.js"){
all_scripts[s].parentNode.insertBefore(element_to_insert, all_scripts[s]);
break;
}