I have some json data that I want to use in a leaflet map. I need to convert the json format into the geojson format used by leaflet. I also want to sort the data into Friends and Family so I can identify them separately on the map.
I have succesfuly fetch(ed) the data file and used a switch staement to sort the data into Friends case and Family case. Inside each case I handle converting the data into geojson format.
My problem is that I have not been able to figure out how to use the variables myFriends and myFamily outside of the function getData so that I can plot the points on the map.
This is all just fake data that I am using to learn how to use leaflet. Ultimately I hope to get this data through a stream to track up to the moment position data.
In my code I am able to output the data to the console by moving the console.log(myFriends); inside the function.
What I am trying to get 2 variables myFriends and myFamily each containing all of the iterated data.
Original JSON Data
[
{
"time" : 0.00,
"ID" : 51,
"name" : "John",
"relationship" : "Friend",
"Lat" : 56.166609,
"Long" : 27.157364
},
{
"time" : 0.00,
"ID" : 52,
"name" : "Sally",
"relationship" : "Friend",
"Lat" : 55.895501,
"Long" : 26.753631
},
{
"time" : 0.00,
"ID" : 50,
"name" : "Tom",
"relationship" : "Family",
"Lat" : 56.236112,
"Long" : 26.168675
}
]
var myFriends =
{
"type": "FeatureCollection",
"features": [
{
"geometry": {
"type": "Point",
"coordinates": [
56.166609, 27.157364
]
},
"type": "Feature",
"properties": {
"popupContent": "John"
},
"id": 51
},
{
"geometry": {
"type": "Point",
"coordinates": [
55.895501, 26.753631
]
},
"type": "Feature",
"properties": {
"popupContent": "Sally"
},
"id": 52
},
]
};
var myFamily =
{
"type": "FeatureCollection",
"features": [
{
"type": "Feature",
"properties": {
"popupContent": "Tom"
},
"geometry": {
"type": "Point",
"coordinates": [56.236112, 26.168675]
}
},
]
};
Program Code
async function getData() {
const response = await fetch('data.json');
var data = await response.json();
//console.log(data);
for (var i = 0; i < data.length; i++){
var unit = data[i];
var relationship = unit.relationship;
switch (relationship) {
case "Friends":
var myFriends = {
"type": "FeatureCollection",
"features": [
{
"geometry": {
"type": "Point",
"coordinates": [
unit.Lat + " , " + unit.Long
]
},
"type": "Feature",
"properties": {
"popupContent": unit.name
},
"id": unit.ID
},
]
};
break;
case "Family":
console.log("Family");
console.log(unit);
}
}
}
getData();
console.log(myFriends);
The scope of your var myFriends is limited to the function getData(). To access it outside of getData() you need to return it at the end.
Your function is an asynchronous function, which means it returns a promise. Therefore, when you call your function you need to wait for its result using await. To make it work you need to
modify your function to return the data you want.
use await where you call your getData function
var result = await getData();
Related
"type": "FeatureCollection",
"features": [
{
"type": "Feature",
"geometry": {
"type": "Polygon",
"coordinates": [
[
[
-77.155585,
40.056708,
0
],
[
-77.150315,
40.04536,
0
]
]
]
},
"id": 42001030101,
"Households": 1000,
"Income": 74597
},
I am using the google maps JS API. I cannot use the getProperty function because the data doesn't have the properties grouped together.
How can I access each of these pieces of data?
Here is what I tried before I realized that you can't use the properties function.
map.data.setStyle(
function(feature){
let income = feature.getProperty('Income');
let color = 'blue';
if (income > 10000){
color = 'red'
}
return {
fillColor: color,
//strokeColor: "green",
strokeWeight: 0.3,
};
}
);
According to the geojson spec:
A Feature object has a member with the name "properties". The value
of the properties member is an object (any JSON object or a JSON null
value).
As your feature doesn't have a properties member, you can 'repair' it so that any member that is neither type nor geometry is bundled as a member of properties.
This should enable your existing code using feature.getProperty().
const data = {
"type": "FeatureCollection",
"features": [
{
"type": "Feature",
"geometry": {
"type": "Polygon",
"coordinates": [
[
[-77.155585, 40.056708, 0],
[-77.150315, 40.04536, 0]
]
]
},
"id": 42001030101,
"Households": 1000,
"Income": 74597
}
]
}
const repairGeoJsonProps = (fc) => {
return {
"type": "FeatureCollection",
"features": fc.features.map(ftr => {
const props = Object.entries(ftr).filter(k => ["type", "geometry"].indexOf(k[0]) < 0);
return {
"type": ftr.type,
"geometry": ftr.geometry,
"properties": Object.fromEntries(props)
}
})
}
}
console.log(repairGeoJsonProps(data));
I am trying to move the element height of an entity that is loaded from a geojson file in cesium.js. I'm using the example App.js file from Cesium Workshop/
How would I modify the code below to adjust the height of the data entities so that they are pinned to the elevation of the terrain. The geojson file that I have has an altitude value of 0. This altitude needs to match the terrain at that location. When I render this data many of the points are under the terrain. I assume I also need to lookup the terrain height, convert the data to Cartesian coordinated back and forth to polar coordinates to add the offset into the entity.
var geojsonOptions = {
clampToGround : true
};
var testLinePromise = Cesium.GeoJsonDataSource.load('./Source/SampleData/testLines.geojson', geojsonOptions);
// Save an new entity collection of neighborhood data
var testLines;
testLinePromise.then(function(dataSource) {
// Add the new data as entities to the viewer
viewer.dataSources.add(dataSource);
testLines = dataSource.entities;
// Get the array of entities
var testLineEntities = dataSource.entities.values;
for (var i = 0; i < testLineEntities.length; i++) {
var entity = testLineEntities[i];
if (Cesium.defined(entity.polygon)) {
// Tells the polygon to color the terrain. ClassificationType.CESIUM_3D_TILE will color the 3D tileset, and ClassificationType.BOTH will color both the 3d tiles and terrain (BOTH is the default)
entity.polygon.classificationType = Cesium.ClassificationType.TERRAIN;
// Generate Polygon center
var polyPositions = entity.polygon.hierarchy.getValue(Cesium.JulianDate.now()).positions;
var polyCenter = Cesium.BoundingSphere.fromPoints(polyPositions).center;
polyCenter = Cesium.Ellipsoid.WGS84.scaleToGeodeticSurface(polyCenter);
entity.position = polyCenter;
// Generate labels
entity.label = {
text : entity.name,
showBackground : true,
scale : 0.6,
horizontalOrigin : Cesium.HorizontalOrigin.CENTER,
verticalOrigin : Cesium.VerticalOrigin.BOTTOM,
distanceDisplayCondition : new Cesium.DistanceDisplayCondition(10.0, 8000.0),
disableDepthTestDistance : 100.0
};
}
}
});
Here is the geojson file
{
"type": "FeatureCollection",
"features": [
{
"type": "Feature",
"properties": {
"name": "623dd9c1-26cb-4248-8e41-ebc8c3a16af5",
"description": "descr A",
"company": "ACME"
},
"geometry": {
"type": "LineString",
"coordinates": [
[
-114.5305072,
20.61238237,
0
],
[
-111.9486,
10.46916111,
0
]
]
}
},
{
"type": "Feature",
"properties": {
"name": "15966b86-26d0-4e0b-ba6e-7fa0c98bfe5e",
"description": "descr C",
"company": "ACME"
},
"geometry": {
"type": "LineString",
"coordinates": [
[
-135.9989702,
45.7677603,
0
],
[
-134.5305072,
50.61238237,
0
]
]
}
},
{
"type": "Feature",
"properties": {
"name": "00ca37f5-de78-4d5b-88b5-d39808ff8143",
"description": "descr D",
"company": "ACME"
},
"geometry": {
"type": "LineString",
"coordinates": [
[
-125.9989702,
65.7677603,
0
],
[
-129.0238961,
67.96685,
0
]
]
}
},
{
"type": "Feature",
"properties": {
"name": "22e5e02f-fa43-445e-a2eb-29ad760a964c",
"description": "descr E",
"company": "ACME"
},
"geometry": {
"type": "LineString",
"coordinates": [
[
-105.9989702,
55.7677603,
0
],
[
-100.7366501,
55.67798889,
0
]
]
}
},
{
"type": "Feature",
"properties": {
"name": "c4aefe46-a2a6-4a97-ac36-571c9e370d31",
"description": "descr A",
"company": "ACME"
},
"geometry": {
"type": "LineString",
"coordinates": [
[
-111.994653,
78.84398434,
0
],
[
-128.4816326,
16.68839404,
0
]
]
}
}
]
}
I'm trying to get some point inside multiple polygon using pointsWithinPolygon in turfjs, but the result is unexpected.
Is there any chance that pointsWithinPolygon isn't compatible with FeatureCollection?
Here is the example of my usage.
let points = {
"type": "Point",
"coordinates": [
106.866995, -6.261513
]
}
let filter = {
"type": "FeatureCollection",
"features": [
{
"type": "Feature",
"properties": {
"IdArea": 4
},
"geometry": {
"type": "Polygon",
"coordinates": [
[
[
106.314674,
-6.6348689124
],
[
107.5781628906,
-6.6348689124
],
[
107.5781628906,
-5.9742195859
],
[
106.314674,
-5.9742195859
],
[
106.314674,
-6.6348689124
]
]
]
}
}
]
}
let result = turf.pointsWithinPolygon(points, filter);
console.log(result);
You are trying to use geoJsons as inputs to turf's pointsWithinPolygons function.
The function takes a turf.points array of points, and a turf.polygon array of polygon vertices.
Based on the variables you established, you would need to call:
let result = turf.pointsWithinPolygon(turf.points([points.coordinates]), turf.polygon(filter.features.geometry.coordinates));
I'm trying to display markers on a Webpage map from a JSON object (initially Firebase).
Here is my Javascript code , how do I manage with converting JSON Object to geoson array ?
// get character (points) reference from firebase
var refPOI = '{"-KiWVsBzdJ3EW3THO7bK":{"image":"3","lat":165.440135,"lon":-21.669071},"-KiWY9hLU12ebrlH7cXS":{"image":"5","lat":167.516824,"lon":-22.619914},"-KiWY9hMggrqlTNJMWzU":{"image":"8","lat":166.59579,"lon":-20.718007},"-KiWY9mpKP8gx7i8eGpo":{"image":"8","lat":167.100445,"lon":-20.961233},"-KiWY9oqGSHS_8Sdwpda":{"image":"9","lat":167.818109,"lon":-21.460377},"-KiWYA3hGwTUJGQjYx7O":{"image":"9","lat":165.458005,"lon":-21.770834}}';
var dataPOI = JSON.parse(refPOI);
var arr = [];
for(var x in dataPOI){
arr.push(dataPOI[x]);
}
console.log(dataPOI);
console.log(arr);
var geojson = {
"type": "FeatureCollection",
"features": [
]
};
dataPOI.$loaded().then(function(results) {
for(x=0;x<results.length;x++) {
geojson.features.push({
"type": "Feature",
"properties": {
"message": results[x].points,
"image": results[x].image,
"iconSize": [50, 50],
"id": results[x].$id
},
"geometry": {
"type": "Point",
"coordinates": [
results[x].lat,
results[x].lon
]
}
});
}
})
I am using leaflet and mapbox and I use the function to print the id nuber on the screen when hovering over the line in the map.
geojson = L.geoJson(lines, {
style: style,
onEachFeature: onEachFeature
}).addTo(map);
var info = L.control();
info.onAdd = function (map) {
this._div = L.DomUtil.create('div', 'info'); // create a div with a class "info"
this.update();
return this._div;
};
info.update = function (props) {
this._div.innerHTML = '<h4><b>Links<b></h4>' + (props ?
'<b>Link' + props.id + '</b><br />'
: 'Hover over a link');
};
info.addTo(map);
The way I draw the line is by the following geoJSON file
var lines = {
"type": "FeatureCollection",
"features": [{
"type": "LineString",
"coordinates": [
[103.85, 1.28992],
[103.89, 1.294],
[103.83, 1.216]
],
"properties": { "id": "1" }
}, {
"type": "LineString",
"properties": { "id": "2" },
"coordinates": [
[103.5, 1.292],
[103.9, 1.4],
[103.3, 1.21]
]
}, {
"type": "LineString",
"properties": { "id": "3" },
"coordinates": [
[103.6, 1.291],
[103.6, 1.39],
[103.3, 1.29]
]
}]
};
but when i hover over the line it shows "undefined" instead of showing the id.Any help is appreciated
Where is the declaration of your onEachFeature? Where is update called from? Your code is incomplete.
Besides, your GeoJSON is non-conformant to the GeoJSON specifications. A FeatureCollection must contain Features, and each Feature must have a Geometry.
So instead of:
{
"type": "LineString",
"properties": { "id": "3" },
"coordinates": [[103.6,1.291],[103.6,1.39],[103.3,1.29]]
}
it should be something like:
{
"type": "Feature",
"geometry": {
"type": "LineString",
"coordinates": [[103.6,1.291],[103.6,1.39],[103.3,1.29]]
},
"properties": {
"id": "3"
},
}