Add circle to map with carto.js and leaflet libraries - javascript

I have to show a circle on feature click on my layer.
When I try to create the circle I have this error: Error: Invalid LatLng object: (41.961124103390674, NaN).
If I print the object before this error I can read: Array [ 41.84664960937685, 12.008056640625 ].
I tried to write values separated but it doesn't work.
How is it possible?
Someone can help me? Thanks and sorry for my english
EDIT
I tried this solution:
layer.getSubLayer(1).on('featureClick', function (event, latlon, pos, data, index) {
var coord = {lat:data.lat, lng:data.lon};
console.log(coord)
L.circle(coord, {radius: data.distance}).addTo(map);
Error and log are the same...
EDIT 2
With this code
var coord = L.latLng(42,21);
var cerchio = L.circle(coord,{radius: data.distance});
console.log(cerchio);
cerchio.addTo(map);
I noticed that circle Object is correctly created, so the problem is on addTo(map) method.

According to the Carto Docs, the latlon argument in your featureClick callback contains:
Array with the LatLng ([lat,lng]) where the layer was clicked.
Is that where you want the circle to be placed? If so, use this line:
L.circle(latlon, {radius: data.distance}).addTo(map);

SOLVED
The correct way is
L.circle([data.lat, data.lon], data.distance, {}).addTo(map);
where data.distance is the radius of circle. Official doc's example L.circle([50.5, 30.5], {radius: 200}).addTo(map); seems to be wrong.

Add 1609*3
var coord = L.latLng(42,21,1609*3);

Related

coordstoLatLng function not returning array [duplicate]

I have my geoJson format like this:
statesData.features.push({
"type":"Feature",
"id":"AFG",
"properties":{
"name":"Afghanistan"
},
"geometry":{
"type":"Polygon",
"coordinates":[
[
[
61.210817,
35.650072
],
[
62.230651,
35.270664
],
[
62.984662,
35.404041
],
I am trying to read those coordinates and set them as
var coord = statesData.features[0].geometry.coordinates;
lalo = L.GeoJSON.coordsToLatLng(coord);
map.setView(lalo, 18);
The documentation says:
coordsToLatLng( coords ) Function that will be used for
converting GeoJSON coordinates to LatLng points (if not specified,
coords will be assumed to be WGS84 — standard [longitude, latitude]
values in degrees).
But I am getting this error in console
Uncaught Error: Invalid LatLng object: (undefined,
61.210817,35.650072,62.230651,35.270664,62.984662,35.404041...
UPDATE
The first answer is correct as it solves the issue above, however, it zooms the map to the first set of coordinates while what I am really trying to achieve is to be able to load the page with the map auto zoomed to a polygon (I only load one polygon).
This example is the closest i could find
Thanks to the answer I got from here the solution is to use leaflet layerGroup.
Following leaflet example as that is what I am using, based on their code and the other answer i got, this is what worked for me. The php bit is what I use to get the country name I need as per my project. The following gets a name, compares it if there is a name in the geoJson like that and if so, centers and zooms the map to that polygon:
geojson = L.geoJson(statesData, {
style: style,
onEachFeature: onEachFeature
}).addTo(map);
<?php
$myCountry = usp_get_meta(false, 'usp-custom-3');
$fixedname = ucfirst($myCountry);
?>
geojson.eachLayer(function (layer) {
if (layer.feature.properties.name === "<?php echo $fixedname; ?>") {
// Zoom to that layer.
map.fitBounds(layer.getBounds());
}
});
You are passing an array of arrays of arrays as a parameter. coordsToLatLng doesn't expect that. It only expects one array, being it the coordinates: https://www.dartdocs.org/documentation/leaflet/0.0.1-beta.1/leaflet.layer/GeoJSON/coordsToLatLng.html
So your code has to be actually:
var coord = statesData.features[0].geometry.coordinates[0][0];
lalo = L.GeoJSON.coordsToLatLng(coord);
map.setView(lalo, 18);
This will get the coordinates of your first point inside your double-array. Btw, I'm pretty sure that double-array is not what you really want.

Input geometry is not a valid Polygon in turf.js

I try to use turf.js and its function intersect in my Leaflet project. My original question can be found here. The problem is I cannot get a proper polygon in order to call it. The idea is to get the waypoints of the calculated route make a polgyon out of them and check where they intersect with a given buffered area.
var testpoint = turf.point([9.9354, 49.799]);
var buffered = turf.buffer(testpoint, 50, {units: 'meters'});
var array = []
control._routes[0]['coordinates'].forEach(function(e){
array.push([e['lat'],e['lng']])
});
var test = turf.polygon(L.polygon([[array]]))
var intersection = turf.lineIntersect(buffered, test)
I am getting the following error message:
Uncaught Error: Input geometry is not a valid Polygon or MultiPolygon
Here I have to point out that, when using line.intersect(buffered,buffered) it is working correctly, therefore I am assuming that the buffered variable is correct.
When it comes down to the test variable, I have tried with no [], one pair and double pair. But they all result in the same problem. I also tried to pass the array to turf.polygon but it couldn`t be done.

Center of Polygon Google Maps JavaScript API v3

I looked through this thread: How to get the center of a polygon in google maps v3?, and Matthew Scharley's answer currently marked as correct does not do it for me. I am downloading corner coordinates for 50-100 polygons dynamically from the server in an array of lat/long objects, and I need a dynamic not manual solution for determining polygon centers. The answer from the same thread by furiozo comes close to fulfilling my needs, as it calculates the average center of the polygon, but the results that I see in my console.log from his function:
google.maps.Polygon.prototype.my_getBounds=function(){
var bounds = new google.maps.LatLngBounds()
this.getPath().forEach(function(element,index){bounds.extend(element)})
return bounds
}
console.log(myPolygon.my_getBounds().getCenter());
are not something that I can readily use in my program.
What I get in the console is this:
_.M {}
lat: function ()
arguments: (...)
caller: (...)
length: 0
name: ""
prototype: Object
__proto__: function ()
<function scope>
Closure
a: 45.256705626
b: -75.91270512
Closure
Global: Window
lng: function() -- contains same sub-levels as lat: function() --
__proto__: Object
What I really need right now is how to get to the a & b lat/lng values that sit under the first Closure level in in lat: function() in the object I'm getting in my console. (I have checked manually by substituting these results in code, they represent the correct center for the first of my polygons). Any help with how to get to them will be greatly appreciated.
Or, if anybody knows of any up-to-date solution for how to get average polygon center coordinate values dynamically so that the end result will be in the format of (lat, lng), this may save my day.
Thank you very much!
What you're seeing is a LatLng object.
What you can do is simply call the lat() and lng() functions on it:
var lat = myPolygon.my_getBounds().getCenter().lat();
var lng = myPolygon.my_getBounds().getCenter().lng();

mapbox fit bounds to country

i just want fit my map to my country. I saw some example from https://www.mapbox.com/mapbox-gl-js/example/fitbounds/ and it's fit to whole Kenya. It's a simple code but i don't know why this function takes two lat and longs. I just google it for what is Keyna lat and long? it's 1.2667° S, 36.8000° E. Why this is different than google's result.
function fit() {
map.fitBounds([[
32.958984,
-5.353521
], [
43.50585,
5.615985
]]);
}
How to fit to my specific area just like this.
If i search for the bounding box of Kenya, i find the following:
http://isithackday.com/geoplanet-explorer/index.php?woeid=23424863
Using those coordinates, it's looks ok:
map.fitBounds([
[-4.71712, 33.90884], // Northeast
[4.62933, 41.899059] // Southwest
]);
Example using Leaflet on Plunker: http://plnkr.co/edit/yRuTxjmQxcoqkVyFbE4q?p=preview
.fitBounds takes two latlng arguments, one for the upper-left corner of the mapview and one for the lower-right corner.
If you would like to just center the map on Kenya, you could use:
map.flyTo({center: [Lat, Lng]})
I also was looking for the answer on this question. Leaflet, for example, has a property of a layer to get its bounds (e.g.,map.fitBounds(layer.getBounds());). Mapbox GL doesn't have anything like that. At least not that I know. To handle this you may access the first and the last coordinates of the currently selected feature: map.fitBounds([feature.geometry.coordinates[0], feature.geometry.coordinates[feature.geometry.coordinates.length-1]]).
Here is the whole piece of code in case you want to have a popup with a Zoom button on it:
map.on('click', function (e) {
map.featuresAt(e.point, {layer: 'route-lines', radius: 10, includeGeometry: true}, function (err, features) {
if (err || !features.length)
return;
var feature=features[0];
new mapboxgl.Popup()
.setLngLat(e.lngLat)
.setHTML(popupTemplate)
.addTo(map);
var buttonZoomFeature = document.getElementById('button-zoom');
buttonZoomFeature.addEventListener('click', function (e) {
map.fitBounds([feature.geometry.coordinates[0], feature.geometry.coordinates[feature.geometry.coordinates.length-1]]);
});
});
});
var popupTemplate = '<div id="popup-div">\
<button id="button-zoom" class="button-zoom" type="button">Zoom to</button>\
</br>\
</div>';
PS. This approach works fine when the layer is a number of lines (roads, for example). If you want to fit the bounds to a country, which is a polygon, you may try taking the first longitude-latitude point as the one that has min latitude and for the second point the one that has max longitude. Or something like that. Just try to play around with this approach. I am sure it will work out.

removeAllFeatures is not a function

My effort is to remove the already drawn circle in Open Layers map. It's the only vector in the map so I decided to try removing all features as follows:
var vectors = map.getLayersByClass('OpenLayers.Layer.Vector');
vectors.removeAllFeatures();
I got the following error:
removeAllFeatures is not a function
What is my mistake?
Thanks.
removeAllFeatures is a function of the layer object. getLayersByClass returns an array of layers. Try this:
var vectors = map.getLayersByClass('OpenLayers.Layer.Vector');
vectors.forEach(function(vector){
vector.removeAllFeatures();
});

Categories