I write a WordPress Plugin which provides adding scripts to header. When I try to add code snippets of our service
<script src="url/index.js"></script>
<script>
var foo = new window.Name("token");
foo.init();
</script>
to head, I got some errors.
Uncaught (in promise) TypeError: Cannot read property 'appendChild' of null
at r.<anonymous> (index.js:176)
at L (index.js:47)
at Generator._invoke (index.js:47)
at Generator.t.(:8000/anonymous function) [as next] (url/index.js:47:4580)
at r (index.js:174)
at c (index.js:174)
at index.js:174
at new Promise (<anonymous>)
at new r (index.js:36)
at r.<anonymous> (index.js:174)
and
Uncaught TypeError: Cannot read property 'appendChild' of null
at i.value (index.js:178)
at r.value (index.js:180)
at (index):41
.
The url returns our script code which is rendered by Babel.
When I add any standard html code like <html></html> or <p></p> before the script,
<p></p>
<script src="url/index.js"></script>
<script>
var foo = new window.Name("token");
foo.init();
</script>
it works clearly. What about any html code? I can't understand. I solve it by adding <html></html> without broken website. I try to learn problem.
It's hard to tell without seeing what's in your url/index.js file, but it's probably trying to append a node to the <body> element, or a child of it before it exists. It will not exist yet if you are calling this script in the <head> section.
The reason the <p></p> fixes it is that if the browser receives the following:
<head>
<script>
console.log(document.body);
</script>
</head>
It sees it is invalid HTML, and so it re-interpreted as:
<html>
<head>
<script>
console.log(document.body);
</script>
</head>
<body></body>
</html>
- the body does not exist by the time the script is run, so the console logs null.
If the browser receives:
<p>Paragraph</p>
<head>
<script>
console.log(document.body);
</script>
</head>
...it is again invalid HTML, and is re-interpreted as
<html>
<head></head>
<body>
<p>Paragraph</p>
<script>
console.log(document.body);
</script>
</body>
</html>
...and the body element exists when the script runs, so it will log the body element to the console.
In summary: You need to make sure all of your HTML is valid, and that your script only tries to append something to an element which already exists.
Related
I am trying to load an iframe function from html but I am getting an undefined on that function. I am getting a "Uncaught ReferenceError: iframeLoad is not defined". Am i missing something here?
<html>
<head>
</head>
<body onload="iframeLoad()">
<iframe id="accountroles" width="350px" height="300px"></iframe>
<script type="text/javascript">
function iframeLoad(){
var recordID = window.parent.Xrm.Page.data.entity.getId().replace(‘{‘, ”).replace(‘}’, ”).toLowerCase();
var url = "https://web.powerapps.com/webplayer/iframeapp?hideNavBar=true&source=website&appId=/providers/Microsoft.PowerApps/apps/xxxx-xxxx-xxxx-xxxx-xxxxx&da&accountID="+ recordID;
document.getElementById("accountroles").src = url;
}
</script>
</body>
</html>
Okay, that is probably due to your JS code containing syntax errors to begin with then - if the browser can’t parse the code properly, the function won’t be available at any time.
replace(‘{‘, ”).replace(‘}’, ”) - those “typographic” single quotes are wrong, you need to replace them with the correct ones, ' -04FS
I know this topic has been covered many times here but no matter which approach I take I either get a error such as "Unable to get property 'setContent' of undefined or null reference" or the line executes but nothing happens.
Here's what I know.
tinymce initializes and is a valid object.
The html variable has the propper HTML which it get from a parent window.
jQuery is loaded and functional.
In addition to the code below I have also tried.
tinyMCE.activeEditor.setContent(html);
tinymce.editors[0].setContent(html);
$('textarea#XRMeditor').val(html); * Before initialization
I have tried all methods before and after tinymce intializes (just in case).
<!DOCTYPE html>
<html>
<head>
<script src="sage_jquery.min.js" type="text/javascript"></script>
<script src="tinymce_/tinymce.min.js" type="text/javascript"></script>
<script>
var html = window.parent.document.getElementById("descriptionIFrame").contentDocument.getElementsByTagName('body')[0].innerHTML;
debugger;
//$('textarea#XRMeditor').val(html);
tinymce.init({
selector: 'textarea#XRMeditor'
});
tinymce.get('XRMeditor').setContent(html);
</script>
</head>
<body>
<textarea id="XRMeditor">Easy (and free!) You should check out our premium features.</textarea>
</body>
</html>
I suspect this issue is that you are trying to talk to TinyMCE before its initialized on the page.
Your get() call is in the head of your page and I would doubt that when the browser processes your script that TinyMCE has initialized. You can use an "init" handler to delay when this call happens:
tinyMCE.init({
//your regular init parameters here...
setup: function(editor) {
editor.on('init', function() {
//load your content here!
tinymce.activeEditor.setContent(html);
//or
tinymce.editors[0].setContent(html);
});
}
});
I'm trying to understand how to modularize the Backbone ToDo tutorial
Originally everything is inside the same file, but if I try to extract to another file:
var TodoView = Backbone.View.extend({
...
});
then this throws an error:
var view = new TodoView({model: todo});
**Uncaught TypeError: undefined is not a function**
It's probably due to a scope issue, but I don't know how to create a reference inside the $(function() so I can create this new object inside the main function.
Assuming that your first code part is TodoView.js,
and your second code part is app.js.
Write your html file like this,
<html>
<head>
<script type="text/javascript" src="js/TodoView.js"></script>
<script type="text/javascript" src="js/app.js"></script>
</head>
<body>
// your dom
</body>
</html>
(Edited, at 2015-07-27)
sorry for my late reply.
how about this?
<html>
<head></head>
<body>
<!-- your dom -->
<script type="text/javascript" src="js/TodoView.js"></script>
<script type="text/javascript" src="js/app.js"></script>
</body>
</html>
In many case, most javascript codes are appended to just before </body>, so that javascript can use your dom!
You can use something like require.js to load your external files and manage dependancies.
Ok, the solution was to move the script references to the end of the body instead of inside the head tags.
I think that the reason is that TodoView.js is making use of templates that were defined in the body, and since the js file was being loaded before the body, the templates were not yet available.
I'm trying several WYSIWYG HTML5/JQuery editors. However, with both Bootstrap WISWYG and Summernote, I get 'cannot read property 'fn' of undefined' or 'cannot read property 'Editor' of undefined. I'm just using the standard files out there on GitHub. Anyone familiar with these errors using JQuery plugins?
EDIT
I'm now trying Bootstrap WISWYG
Within my body I have
<div id="editor">Editor</div>
In my js, I have
$(document).ready(function() {
$('#editor').wysihtml5();
});
However, the error I get is:
Cannot read property 'Editor' of undefined (line 157)
Line 157:
var editor = new wysi.Editor(this.el[0], options);
JSFiddle: http://jsfiddle.net/MgcDU/8125/
EDIT 2
I forgot to include one JS file. However, after including it I get a new error:
Uncaught TypeError: Cannot read property 'firstChild' of undefined
The lines of code that the error refers to:
if (isString) {
element = wysihtml5.dom.getAsDom(elementOrHtml, context);
} else {
element = elementOrHtml;
}
while (element.firstChild) <<<Error
The thing is you are using a DIV element instead of a textarea there are also dependencies missing. Checking the Bootstrap WYSIHTML5 page it says:
Dependencies:
bootstrap-wysihtml5.js
bootstrap-wysihtml5.css
wysihtml5
Twitter Bootstrap
Then your document should look something like:
<!DOCTYPE html>
<header>
<title>HTML5 Editor</title>
<script type="text/javascript" src="//ajax.googleapis.com/ajax/libs/jquery/1.10.2/jquery.min.js"></script>
<!-- Of course place sources in your own server, do not leech bandwidth -->
<script type="text/javascript" src="http://jhollingworth.github.io/bootstrap-wysihtml5/lib/js/wysihtml5-0.3.0.js"></script>
<script type="text/javascript" src="http://jhollingworth.github.io/bootstrap-wysihtml5/lib/js/bootstrap.min.js"></script>
<script type="text/javascript" src="http://jhollingworth.github.io/bootstrap-wysihtml5/src/bootstrap-wysihtml5.js"></script>
<link rel="stylesheet" type="text/css" href="http://jhollingworth.github.io/lib/css/bootstrap.min.css">
<link rel="stylesheet" type="text/css" href="http://jhollingworth.github.io/src/bootstrap-wysihtml5.css">
</header>
<body>
<textarea class="editor"></textarea>
<script type="text/javascript">
$(document).ready(function(){
$('.editor').wysihtml5();
});
</script>
</body>
For further reference, please check: Wysihtml5 #Usage
"cannot read property 'fn' of undefined"
usually means that the script does not have script being loaded into DOM. You might are missing jQuery file? I have often noticed that it is becoming a practice for jQuery scripts to be loaded right in the bottom of HTML, right before
</body>
But, it always works so well if I loaded only one Jquery file in header meanwhile the rest of other jquery plugin scripts loaded in the bottom of the html file.
I'm trying to use kartograph.js to display a svg map located in /public in a rails application and cannot figure out how to load the map. Here's my .js.coffee.erb file:
$ ->
map = $K.map('#map')
# map.loadMap("#{Rails.root}/public/Blank_US_Map.svg", loaded) # attempt 1
map.loadMap("Blank_US_Map.svg", loaded) # attempt 2
loaded = () ->
map.addLayer('baseLayer')
The error thrown in the console is Uncaught TypeError: Cannot call method 'getAttribute' of undefined, though I believe the problem is that no file is being loaded.
The issue comes from the library you're using, Kartograph. It needs a SVG file with absolute coordinate, or you'll most likely get this error.
You can confirm that by trying a pure-HTML-and-js version, e.g. :
<html>
<head>
<script src="jquery.min.js"></script>
<script src="raphael-min.js"></script>
<script src="kartograph.min.js"></script>
</head>
<body>
<div id="map"></div>
</body>
</html>
<script>
$(document).ready(function() {
var map = kartograph.map('#map');
function callback(mymap) {
// Stuff
}
map.loadMap('Blank_US_Map.svg', callback);
})
</script>
And see if you get the same error.