Google Maps Distance API is undefined in react - javascript

I am trying to use the Google Maps Distance Matrix Service (https://developers.google.com/maps/documentation/javascript/distancematrix).
I put this line in my public/index.html: <script src="https://maps.googleapis.com/maps/api/js?key=MY_API_KEY"></script>
In a react's js file, I can print window.google and see the global variable. I can also see that it has a function window.google.maps.DistanceMatrixService() to create the service. However, when I create that service with var service = window.google.maps.DistanceMatrixService(), service is undefined. Any idea why?

As Jaromanda X pointed out, I missed the new keyword.
Full line is now: var service = new window.google.map.DistanceMatrixService().

Related

Get KML style in OpenLayers 5

I have some code in an application that access the style of a selected feature in a KML layer. It was working in OpenLayers 3.1. I have now upgraded to 5.3.0 and it stopped working. See the relevant lines below:
var featStyle = feature.getStyleFunction().call(feature, map.getView().getResolution());
var strokeWidth = featStyle[0].getStroke().getWidth();
var strokeColor = featStyle[0].getStroke().getColor();
var fillColor = featStyle[0].getFill().getColor();
var fillOpacity = (Math.round(fillColor[3] * 100));
The line:
var featStyle = feature.getStyleFunction().call(feature, map.getView().getResolution());
Produces an error visible in the developer console:
TypeError: o.getGeometry is not a function[Learn More] KML.js:943
a KML.js:943
myFunctionName file.php:5371
onclick file.php:1
I can't find anything in the documentation or examples that shows how to properly access the KML style data for a given feature (not an entire layer/source). Is there a new way to do this or did I miss something?
Could it have to do with this?: https://github.com/IGNF/geoportal-sdk/issues/2 Plugged into Google translate it seems to say something about no longer storing style properties inside each feature but it does not seem to say where they are stored...
The KML is valid and displays on the map properly. I just can't seem to find a way to access the style data anymore.
In OpenLayers 3 and 4 a feature style function takes only a resolution argument but internally uses this so the function or call must be bound to the feature:
feature.getStyleFunction().bind(feature)(map.getView().getResolution());
or
feature.getStyleFunction().call(feature, map.getView().getResolution());
In OpenLayers 5 feature style function are similar to layer style functions and require the feature to be passed as an argument:
feature.getStyleFunction()(feature, map.getView().getResolution());

Get JSON WebMap from ArcGIS JavaScript API Map object

I'm trying to get a WebMap object (as JSON) from a JavaScript Map object in the ArcGIS JavaScript API. Is there any way to do this within the API, without using ArcGIS.com? Ideally something like:
webMapAsJSON = map.toWebMap();
From the "Export Web Map Task" documentation in the REST API, there's this line that suggests it should exist:
"The ArcGIS web APIs (for JavaScript, Flex, Silverlight, etc.) allow developers to easily get this JSON string from the map."
However, I don't see anything in the Map object or elsewhere in the API that would do this.
You can't. At least not officially. The steps outlined below are not recommended. They use part of the ArcGIS JS library that is not part of the public API and therefore this behavior may not work in the next version of the API or they may back-patch a previous version of the API and this could stop working even on something that previously did work.
That said, sometimes you need some "future" functionality right now and this is actually a pretty straightforward way of getting what you want using the common proxy pattern
Use the undocumented "private" function _getPrintDefinition
var proxy_getPrintDefinition = printTask._getPrintDefinition;
printTask._getPrintDefinition = function() {
var getPrintDefResult = proxy_getPrintDefinition.apply(this, arguments);
//Now you can do what you want with getPrintDefResults
//which should contain the Web_Map_as_JSON
console.log(Json.stringify(getPrintDefResult));
//make sure you return the result or you'll break this print task.
return getPrintDefResult;
}
_getPrintDefinition takes the map as the first argument and a PrintParameters object as the second.
so you'll have to create a PrintTask, redefine the _getPrintDefinition function on the newly created print task as outlined above, create a PrintParameters and then run:
myPrintTask._getPrintDefinition(myMap,myPrintParameters);
The results of this on my little test are:
{"mapOptions":{"showAttribution":false,"extent":{"xmin":-7967955.990468411,"ymin":5162705.099750506,"xmax":-7931266.216891576,"ymax":5184470.54355468,
"spatialReference":{"wkid":102100,"latestWkid":3857}},"spatialReference":{"wkid":102100,"latestWkid":3857}},
"operationalLayers":[
{"id":"layer0","title":"layer0","opacity":1,"minScale":591657527.591555,"maxScale":70.5310735,"url":"http://services.arcgisonline.com/ArcGIS/rest/services/World_Street_Map/MapServer"},
{"id":"XXX-Redacted-XXX","title":"serviceTitle","opacity":1,"minScale":0,"maxScale":0,"token":"XXX-Redacted-XXX","url":"http://XXX-Redacted-XXX/arcgis/rest/services/TestService/MapServer"},
{"id":"XXX-Redacted-XXX","opacity":1,"minScale":0,"maxScale":0,"featureCollection":{"layers":[]}},
{"id":"featureGraphics","opacity":1,"minScale":0,"maxScale":0,"featureCollection":{"layers":[]}},
{"id":"map_graphics","opacity":1,"minScale":0,"maxScale":0,"featureCollection":{"layers":[]}}
]}
if you don't need to do any operations on the web map json and just need the output then you don't even need to use the proxy pattern.
#Suttikeat Witchayakul's answer above should work if your goal is to print the map using a print service.
However, if you are trying to export the map to the web map JSON spec so that you can save it to ArcGIS Online/Portal, or re-instantiate a map object from it later, you may have some problems. This is because the web map specification is not the same as the export web map specification, which what the print task generates and sends to printing services.
Unfortunately, the ArcGIS API for JavaScript does not provide any methods to export a map object to web map JSON. This is supposed to be coming in version 4... at some point. Until then, you can use the all but abandoned cereal library. However, if your map uses layer types that are not fully supported by cereal, it may not work for you as is and you would have to extend it.
If you want to use "esri/tasks/PrintTask" to export your map, you must use "esri/tasks/PrintParameters" for execute the printTask. Just set your map object directly to printParameter.
require([
"esri/map", "esri/tasks/PrintTemplate", "esri/tasks/PrintParameters", ...
], function(Map, PrintTemplate, PrintParameters, ... ) {
var map = new Map( ... );
var template = new PrintTemplate();
template.exportOptions = {
width: 500,
height: 400,
dpi: 96
};
template.format = "PDF";
template.layout = "MAP_ONLY";
template.preserveScale = false;
var params = new PrintParameters();
params.map = map;
params.template = template;
printTask.execute(params, printResult);
});

add namespace to your javascript

I have worked on google map api few years ago and wrote a little reusable utility. At that time adding google map api reference does add all the api classses in your page's global namespace. As this is working sample
<script src="http://maps.google.com/maps?SOMEPARAMETERS">
<script>
var map= new GMap2(document.getElementById("map_canvas"));
var point= new LatLng(31,75);
var line= new Polyline(OPTIONS);
</script>
In v3, all Google Maps JavaScript API code is stored in the google.maps.* namespace instead of the global namespace. Most objects have also been renamed as part of this process and some more changes are done.
Now you have to write the above code as follows
<script src="APIURL">
<script>
var map= new google.map.Map(document.getElementById("map_canvas"));
var point= new google.mapLatLng(31,75);
var line= new google.map.Polyline(OPTIONS);
</script>
ISSUE
I wrote a library back in Google v2 API time and used in number of projects and was working great. But now I am working on a new project and using Google V3 API and want to reuse that old v2 library. But adding v3 library doesn't add the API classes in global namespace and my library doesn't work. Is there any way we can add namespace to our JavaScript file like we did in C# on top and it allows us to write the classes without appending the namespace
You might be able to just use references:
(function() { // A scoping function to avoid creating glboals
var GMap2 = google.map.Map;
var LatLng = google.map.LatLng;
var Polyline = googlemap.Polyline;
// ...your code using the above here...
})();
This assumes, though, that the arguments haven't changed.
Alternately, you could use the Facade pattern:
function GMap2(/*...relevant args...*/)
return new google.map.Map(/*...relevant args here, possibly modified...*/);
}
(And similar for others.)
(That works even if you use new with GMap2 because the result of the new expression will be the object you return from the constructor function if you return an object.)

Pass javascript data from view into coffeescript function

I have a view that generates a map for a specific district (available in #district). My map plotting code is coffeescript available to every page but it needs data available as a set of json files (district1.json, district2.json, etc). The first way I got this working was to load this variable in my view, making it globally available.
# in my view
<script type="text/javascript">
var d_data = <%= render file: "#{Rails.root}/data/district_data/#{#district}.json" %>
&lt/script>
Then I use the following coffeescript accepting this global variable:
$(document).ready ->
if $("#users-district-display")
myLatLng = new google.maps.LatLng(d_data.centroid.lat,d_data.centroid.lon)
This works well for this page, but I now throw errors on all pages that don't define d_data. Also, I made these json files available at mysite.com/district_data and was thinking of using .get to bring in the data from ajax (and let the view load quickly), but I still have to the the #district parameter in there.
I know I could just render the js as a partial, and am going to do that unless I can find a way to make this coffeescript work.
Any thoughts appreciated.
Regards,
Tim
Why don't you just check to see if the data was defined?
$(document).ready ->
if $("#users-district-display") and d_data
myLatLng = new google.maps.LatLng(d_data.centroid.lat,d_data.centroid.lon)
Also, if you want to create a new LatLng object with zero parameters, you can always use the existential operator (?):
$(document).ready ->
if $("#users-district-display")
myLatLng = new google.maps.LatLng(
d_data?.centroid.lat || 0
d_data?.centroid.lon || 0
)

Get Map Object in Javascript after using CodeIgniter Google Maps API

I'm using the codeigniter library for the google maps api. I load the map using the library located on the CI Wiki: http://www.phpinsider.com/php/code/GoogleMapAPI/
I want to then use javascript on the map object after loading the page. How can I get the map object in javascript? Can I use GMap2 on the same div? Won't that recreate the map?
The reason I want to do this is to bind an event to the map.
Thanks!
Hope this works:
var myMap;
function getMap()
{
if(myMap == null)
myMap = new GMap2(document.getElementById("map"));
return myMap;
}
and then refer to this function to get reference to the GMap2 object.

Categories

Resources