I've been getting the warning message
You have included the Google Maps API multiple times on this page.
This may cause unexpected errors.
Each time I open a different tab of my website, as each tab has its own map to show to the users.
The way I've made the code to call the google API was this:
function loadMapScript() {
var script = document.createElement("script");
script.src = "https://maps.google.com/maps/api/js";
script.type = "text/javascript";
document.getElementsByTagName("head")[0].appendChild(script);
}
And I call it here:
$(document).ready(function () {
loadMapScript();
... ... ...
The website has various tabs and when each one of them opens, the script is called, hence why it's there multiple times, I got that far.
What I didn't get is how I stop this from happening, I've tried to perform a few verification's inside the loadMapScript function but they did not work at all. I'd like to know if someone knows a way to make this verification inside the loadMapScript function, to prevent it from adding the google API script more than once.
I faced the same type of problem. This occurs if your web page including maps api more than one time.
I have checked in my case there was a .js file that was also calling maps api, so please first check if you are including maps api more than one time, if you are, remove the one.
I figured it out, it required me to do the following verification, it was simpler than I thought:
var children = document.getElementsByTagName("head")[0].childNodes;
for (i = 0; i < children.length; i++) {
if (children[i].src == script.src) {
found = true;
break;
}
}
if (found == false) { document.getElementsByTagName("head")[0].appendChild(script); }
Thanks for the attempt to help at least
Related
Problem: It seems like when loading the Google Maps script, the callback is not performed. It might be related to how to load the Google Maps script.
Context: My website displays a Map in the frontpage when certain minimum viewport conditions are met. Specifically, I avoid loading it when I'm on mobile. I do not want to use jQuery :)
Implementation: The way I'm doing it is by first loading a small handcrafted script (google-map.js), which does a bunch of things and ends with:
function dynamicallyLoadScript(url) {
var script = document.createElement("script");
script.src = url;
script.type = "text/javascript";
script.defer = true;
document.head.appendChild(script);
};
// Load Google Maps when NOT on mobile
if ( ! mobile ) {
dynamicallyLoadScript('https://maps.googleapis.com/maps/api/js?key=wIzaScChUs5NxF3Z5LZoxkAS4wca9A7Pk53I024&callback=initMap');
}
(The JS key is fake).
Outcome: This actually works when I load the site for the first time. I see that google-map.js is loaded, the Google Maps script tag is added to the head, and both resources are loaded and working well. But sometimes (!) when I refresh, the map stops loading and upon inspection I see that the script tag was added successfully, and the resource is loaded, but the initMap() callback function hasn't triggered. If I go to the console, it does fire.
Since this happens only sometimes (and never upon a fresh load without cache), I think it might have something to do with a race condition or just with how cache works. But I'm not sure how to address it. Thoughts?
Solution in a nutshell: This is not a very elegant solution imho, but I figured that what I needed to create is some retry logic for loading initMap() when it runs before it should. In other words, I'm diagnosing this as a race condition present when cache is available.
Implementation: Added a small function to check every 0.1 seconds if the DOM has an element that only exists when the map is fully loaded. When so, the timer stops, but otherwise, it runs the initMap() function.
function checkMaps() {
if (document.getElementsByClassName("gm-style").length == 0) {
initMap();
} else {
clearInterval(checker);
}
}
checker = setInterval(checkMaps, 100);
I'm trying to set a HTML input to read-only using ExecuteScriptAsync. I can make it work, but it's not an ideal scenario, so I'm wondering if anyone knows why it doesn't work the way I would expect it to.
I'm using Cef3, version 63.
I tried to see if it's a timing issue and doesn't appear to be.
I tried invalidating the view of the browser but that doesn't seem to help.
The code I currently have, which works:
public void SetReadOnly()
{
var script = #"
(function(){
var labelTags = document.getElementsByTagName('label');
var searchingText = 'Notification Initiator';
var found;
for (var i=0; i<labelTags.length; i++)
{
if(labelTags[i].textContent == searchingText)
{
found = labelTags[i]
break;
}
}
if(found)
{
found.innerHTML='Notification Initiator (Automatic)';
var input;
input = found.nextElementSibling;
if(input)
{
input.setAttribute('readonly', 'readonly');
}
}})()
";
_viewer.Browser.ExecuteScriptAsync(script);
_viewer.Browser.ExecuteScriptAsync(script);
}
now, if I remove
found.innerHTML='Notification Initiator (Automatic)';
the input is no longer shown as read-only. The HTML source of the loaded webpage does show it as read-only, but it seems like the frame doesn't get re-rendered once that property is set.
Another issue is that I'm executing the script twice. If I run it only once I don't get the desired result. I'm thinking this could be a problem with V8 Context that is required for the script to run. Apparently running the script will create the context, so that could be the reason why running it twice works.
I have been trying to figure this out for hours, haven't found anything that would explain this weird behaviour. Does anyone have a clue?
Thanks!
Prelog:
I have implemented Google maps and Geolocation as a independent widgets, Now the user have the ability to add the widget as much as he wants in a page he is owns.
I am using $.getScript(URl, callback) to load the script for that URL to work.
Problem :
When the user add both the widgets or the same widget multiple times in a same page , the check windows.google fails and the $.getScript(url, callback) gets executed twice. Due to which I get an error from the Google Script
You have included the Google Maps JavaScript API multiple times on
this page. This may cause unexpected errors. when called using
$.getScript()
if(window.google !== undefined && window.google !== null) {
onScriptLoad(null, null, 200);
} else {
$.getScript(googleUrl, onScriptLoad);
}
The above line exists in both the widget and both the widgets are independent of each other. It always goes into the else block of both the functions.
Looking forward for some work around here, like to load the script synchronously using javascript or jquery
when your code runs in the first widget, it initiates the loading of the google API, however window.google isn't created until the script completes loading. This is asynchronous
Now, the second widget tests if window.google exists, but this is still happening before the google API loads, therefore, it too thinks it needs to load google API
so, instead of this:
if(window.google !== undefined && window.google !== null) {
onScriptLoad(null, null, 200);
} else {
$.getScript(googleUrl, onScriptLoad);
}
try
window.loadingGoogleApi = window.loadingGoogleApi || $.getScript(googleUrl);
window.loadingGoogleApi.then(onScriptLoad);
the loadingGoogleApi can be any name you choose (just don't use something that will be clobbered by other code)
I've been trying to display Bing Map whenever a user clicks on a certain HTML element, but Microsoft.Maps.Map always returns undefined even after setting a timeInterval, I have also tried inserting a new scripts with onscriptload onclick event.
Below are my sample code.
$(document).ready(function(){
var script = document.createElement("script");
script.type = 'text/javascript';
script.src = 'https://ecn.dev.virtualearth.net/mapcontrol/mapcontrol.ashx?v=7.0&onscriptload=getMap';
document.head.appendChild(script);
})
$("#showMap").click(function(){
getMap();
})
function getMap(){
console.info(Microsoft.Maps.Map);
var time = "";
var map
var mapControl = Microsoft.Maps.Map;
if(mapControl == undefined){
time = setInterval(function(){ getMap() }, 8000);
}
else{
map = new Microsoft.Maps.Map(document.getElementById('address1_composite'), {credentials: 'Cred'});
clearInterval(time);
}
}
Sorry I know this question is already asked here in this link, Bing map is undefined after loading Javascript file
We have the same scenario but mine is not working as expected though i have tried the suggested answer.
What you should do instead of creating the map when an element is clicked is load the map once and then hide/show it when the button is clicked. This will significantly reduce the number of map loads which means less transactions are generated and thus lower costs.
Also, instead of loading the map script on demand like you are, use the Bing Maps V8 control and load it asynchronously: https://msdn.microsoft.com/en-us/library/mt712557.aspx
I am developing a single page web application, that has many different features and forms. When developing a deep (I mean something that is not on the home page) feature, I go through this cycle:
develop the code, editing classes and functions
refresh the whole page
clicking all the way till I get to the part that I need to test (that adds up to about a minute sometimes)
testing the new code
back to the (1) code editor doing updates
doing about 15 minor edits, can take a frustrating 30 minutes of repeated reloading and clicking
Is there any plugin, piece of javascript, or method, that allows to reload the updated javascript without reloading everything, so one can skip the 2. and 3. from the cycle above and continue doing live tests?
If there's no such thing, I am planning on developing a little javascript plugin that will reload the scripts, and probably with socket.io connection to a backend node.js server that will watch the files for any updates and push the load events to the browser.
So, I am interested in any idea about this, any thing that I should take into consideration when writing the plugin.
Thanks : )
You could do something like this.
function LoadMyJs(scriptName) {
var docHeadObj = document.getElementsByTagName("head")[0];
var dynamicScript = document.createElement("script");
dynamicScript.type = "text/javascript";
dynamicScript.src = scriptName;
docHeadObj.appendChild(newScript);
}
Call the LoadMyJs function on page load
<body onLoad="LoadMyJs()">
Then reload with the click of a button (or from your console)
<input type="button" name="reloadjs" value="Reload JavaScript" onclick="LoadMyJs('my_live_loading_script.js')">
This could be simplified using e.g jQuery
Thanks to:
http://www.philnicholas.com/2009/05/11/reloading-your-javascript-without-reloading-your-page/
Here's what I came up with: a Node.js module that watches for changes in .js & .coffee scripts, and pushes the changes to the browser upon editing the files.
It works standalone, even if you are developing on filesystem file:/// without using a web server.
It works with any framework, just launch the standalone script and point it to your js/ directory.
It has an express.js helper, that make it run using the same server instance.
It is as easy as
adding a single line of <script> tag to your existing code, and
running the live script, pointing it to the html root.
code: 🐱/etabits/live.js
That's may be not the best answer but for local developments I use that firefox plugins:
https://addons.mozilla.org/en-US/firefox/addon/auto-reload/
This reload the css, js or anything present in a directory
For dev which really needs to be remotely , I use that small js code you can adapt for reloading js.
function refreshCss(rule){
if (rule == null)
rule = /.*/;
var links = document.getElementsByTagName("link");
for(var i=0;i<links.length;i++)
{
if (!links[i].href.match(rule))
continue;
if (! links[i].href.match(/(.*)time=/)){
if (links[i].href.match(/\?/))
var glue = '&';
else
var glue = '?';
links[i].href += glue+"time="+new Date().getTime();
}
else{
links[i].href.replace(/time=\d+/, "time"+new Date().getTime());
}
}
if (!no_refresh)
{
setTimeout(function(){refreshCss(rule)}, 5000);
}
};
// and then call it refreshCss("regex to match your css, or not"); var no_refresh=false;
Edit: this is a version with "setTimeout", but you can easily made a "keypress" version of it
Replace with dynamic script.
function LoadMyJs(scriptName)
{
var docHeadObj = document.getElementsByTagName("head")[0];
var dynamicScript = document.createElement("script");
dynamicScript.type = "text/javascript";
dynamicScript.src = scriptName;
docHeadObj.appendChild(dynamicScript);
}