loading script after google map api has been loaded?
Added by Arjan Vermeij about 13 years ago
I downloaded markerwithlabel.js from http://google-maps-utility-library-v3.googlecode.com/svn/trunk to see if I can add markers with a label to a Google Map. The examples work in my browser, chrome. The examples do something like:
<script type="text/javascript" src="http://maps.google.com/maps/api/js?v=3&sensor=false"></script>
<script type="text/javascript" src="../src/markerwithlabel.js"></script>
But in a Wt application, where/when do I load the markerwithlabel.js script? For example, if I change src/Wt/WGoogleMap.C, line 178, into (really, just as an example to show what the problem is):
const std::string gmuri = "http://www.google.com/jsapi?key=" + googlekey;
app->require(gmuri, "google");
app->require("resources/scripts/markerwithlabel.js");
then I get the following JavaScript error:
Uncaught TypeError: Cannot read property 'OverlayView' of undefined
The culprit is line 70 of markerwithlabel.js, where it says:
MarkerLabel_.prototype = new google.maps.OverlayView();
It is as if the google map api has not been loaded. I tried several other things, always with a similar result.
Perhaps I need to wait loading markerwithlabel.js until the google map api has been loaded?
The fact that I'm not fluent in JavaScript may be a compromising factor ...
Any help would be greatly appreciated. Thanks, Arjan.
Replies (5)
RE: loading script after google map api has been loaded? - Added by Bradley Looy almost 9 years ago
I'm having the exact same problem.
RE: loading script after google map api has been loaded? - Added by Bradley Looy almost 9 years ago
Perhaps a jQuery getScript after the google api load?
RE: loading script after google map api has been loaded? - Added by Koen Deforche almost 9 years ago
Hey,
Google API itself loads libraries asynchronously. So you need to react to a load event when asking google to load a particular library: see for example how it's done further down in WGoogleMap.
If you want to load additional libraries conditionally, then you need to use a JSignal to get back to the server to do the subsequent require().
<< "google.load(\"maps\", \"" << (apiVersion_ == Version2 ? '2' : '3')
<< "\", {other_params:\"sensor=false\", callback: "
<< initFunction << "});"
<< "}";
RE: loading script after google map api has been loaded? - Added by Bradley Looy almost 9 years ago
Thank you. I was able to do just as you suggested. I added a JSignal to the WGoogleMap widget and emitted as follows in the initFunction (for when the api loads):
strm << "{ " << initFunction << " = function() {"
"""var self = " << jsRef() << ";"
"""if (!self) { "
"" "setTimeout(" << initFunction << ", 0);"
"" "return;"
"} else { " << googleApiLoaded_.createCall() << " }";
Then in my app I connect to the signal and load the MarkerWithLabel javascript:
std::cout << "VcsWebPageMap::googleApiLoaded" << std::endl;
// load marker label script for map
WApplication::instance()->require("js/markerwithlabel.js");
Thanks again.
RE: loading script after google map api has been loaded? - Added by yvan vander sanden over 8 years ago
I was struggling with the same, but I still trouble filling in the blanks with the information above. Eventually I came up with this solution. I think it might be easier this way. The main difference is the use of doGmJavaScript, which is triggered when google maps has been loaded.
// GoogleMaps.h
#pragma once
#include <Wt/WGoogleMap>
#include <Wt/WJavaScript>
class GoogleMap : public Wt::WGoogleMap
{
public:
GoogleMap(Wt::WContainerWidget * parent);
private:
void loadScripts();
Wt::JSignal<void> mapsLoaded;
};
// GoogleMaps.cpp
#include "GoogleMap.h"
#include <Wt/WContainerWidget>
#include <Wt/WApplication>
GoogleMap::GoogleMap(Wt::WContainerWidget * parent) : Wt::WGoogleMap(Wt::WGoogleMap::Version3, parent), mapsLoaded(this, "mapsLoaded")
{
setPositionScheme(Wt::PositionScheme::Absolute);
resize("100%", "100%");
mapsLoaded.connect(this, &GoogleMap::loadScripts);
this->doGmJavaScript(mapsLoaded.createCall());
}
void GoogleMap::loadScripts() {
Wt::WApplication::instance()->require("js/googleplaces.js");
}