Leaflet + GeoJson converted from OSM Data - Relations - javascript

I'm trying to display bicycle relations which I downloaded from geofabrik, converted with osmconvert, filtered with osmfilter and converted to geojson. At the moment Leaflet displays line strings and nodes correctly on the map. The problem is with data from relations that are included in the file. Here is a part of my GeoJson file (I won't include whole file because it's just too big):
var rower = {
"type": "FeatureCollection",
"features": [{
"type": "Feature",
"id": "way/27149688",
"properties": {
"type": "way",
"id": "27149688",
"tags": {
"agricultural": "no",
"bicycle": "yes",
"highway": "residential",
"maxweightrating:hgv": "24",
"maxweightrating:hgv:condtitional": "none # marked",
"name": "Mikołaja Reja",
"source:maxweightrating:hgv": "PL:sign_B-5-note"
},
"relations": [{
"role": "",
"rel": "4046118",
"reltags": {
"colour": "blue",
"description": "Leśna trasa rowerowa, preferowany rower górski / Forest track, Mountain Bike preferred",
"lcn_ref": "niebieski",
"name": "Szlak Trójmiejski",
"network": "rcn",
"route": "bicycle",
"type": "route"
}
}],
"meta": {
"timestamp": "2014-04-17T11:58:45Z",
"version": "20",
"changeset": "21747999",
"user": "wojtas82",
"uid": "729745"
},
"tainted": true
},
"geometry": {
"type": "LineString",
"coordinates": [[
18.5024141,
54.4354139
],[
18.503622,
54.4353485
],[
18.5053714,
54.4352858
]]
}
}]
};
As you can see relations are in square brackets. I wish to display different colours of tracks depending on relations>reltags>colour tag. Here is my main html file (actually the party that doesn't work):
var rower2 = L.geoJson(rower, {
style: function (feature) {
switch (feature.properties.relations) {
case 'blue':
return {color: "#ff0000"};
case 'red':
return {color: "#0000ff"};
}
}
}).addTo(map);
I tried to modify this part (feature.properties.relations) to (feature.properties.relations.reltags.colour) but it doesn't work. Is there any way to fix this problem?

This isn't working because feature.properties.relations is an array (hence the surrounding brackets) containing objects. To access the objects stored in that array you can use array notation like this: feature.properties.relations[0] for the first object in the array, feature.properties.relations[1] for the second object in the array and so forth. So if you want to access the colour property of the reltags object in the first relation object in the array you should use feature.properties.relations[0].reltags.colour
var rower2 = L.geoJson(rower, {
style: function (feature) {
switch (feature.properties.relations[0].reltags.colour) {
case 'blue':
return {color: "#ff0000"};
case 'red':
return {color: "#0000ff"};
}
}
}).addTo(map);
But my guess is that you're gonna be running into trouble because OSM did use an array for relations with a purpose. My guess is that there can be multiple relations for a feature, and thus it could have multiple colors.
Here's a working example on Plunker: http://plnkr.co/edit/EjCCsb?p=preview
PS. I'm wondering why you're returning '#FF0000' when the case is blue, because that's the code for red, same thing with case red, you're returning '#0000FF' which is the code for blue. Other than that the code is working fine when you use feature.properties.relations[0].reltags.colour as you can see in the example i supplied.

Related

GeoJSON formats for Leaflet -- certain GeoJSON not displaying, while others are

I am modifying an example Leaflet script for my custom purposes.
The original had an associated GeoJSON file with the following format (this is just an excerpt):
{"type":"FeatureCollection","features":[{"type":"Feature","properties":{"OBJECTID":1,"NAME":"Alpha Terrace","TYPE":"CHD"},"geometry":{"type":"Polygon","coordinates":[[[-79.9222757299766,40.4687885729535],[-79.922601544034,40.4688999202888],[-79.9227665690647,40.4689585131248],[-79.9231802736014,40.4691056186529],[-79.9228362255,40.4696697431611],[-79.9224234733987,40.4695244210813],[-79.9222570954656,40.4694656801973],[-79.9222259241735,40.4695164633706],[-79.9219035919843,40.4694017028541],[-79.9222757299766,40.4687885729535]]]}},{"type":"Feature","properties":{"OBJECTID":2,"NAME":"Manchester","TYPE":"CHD"},"geometry":{"type":"Polygon","coordinates":[[[-80.0271753891687,40.4506598454243],[-80.0271940086199,40.4507189442263],[-80.0272105946986,40.4507710471721],[-80.0272579314302,40.4509221686618],[-80.0273032612578,40.4510537660432],[-80.0273193174278,40.451103476753],[-80.0273338296879,40.451147381945],[-80.0273478698275,40.451190610864],[-80.0273633786279,40.4512374152857],[-80.0273793914473,40.4512858394759],[-80.0273919427229,40.4513248923929],[-80.0274084625005,40.4513750227769],[-80.0274174596111,40.451401961247],
I made my own GeoJSON with this format (again, just an excerpt):
{
"type": "FeatureCollection",
"name": "testmap1",
"features": [
{ "type": "Feature", "properties": { "land_val": 16290.0, "imprv_val": 0.0, "land_acres": 0.31, "land_sqft": 13503.6, "situs_stre": null, "situs_st_1": "LAKE BREEZE", "situs_st_2": "DR", "situs_city": "BROWNWOOD", "Deed_Date": "2014\/10\/14", "Mkt_Land_S": "FBINT" }, "geometry": { "type": "MultiPolygon", "coordinates": [ [ [ [ 2695178.255351334810257, 10617843.194646343588829 ], [ 2695245.314272344112396, 10618016.961359173059464 ], [ 2695316.911570087075233, 10617988.845273673534393 ], [ 2695251.204024344682693, 10617828.19828525185585 ], [ 2695196.89442166686058, 10617839.362961083650589 ], [ 2695178.255351334810257, 10617843.194646343588829 ] ] ] ] } },
I'm aware that these are in different locations -- I edited the coordinates of the map so that they display the area covered by the new GeoJSON.
When the map displays with my GeoJSON nothing shows up. But when I use the original GeoJSON (and move the window back to that area), it overlays polygons onto the OSM map.
Does anyone know why this might be? Is there a hyper-specific GeoJSON format needed for Leaflet?
Your coordinates are completely off (e.g [ 2695178.255351334810257, 10617843.194646343588829]).
First value (i.e. longitude) should be 0 to 360
Second value (i.e. latitude) should be -90 to 90

parse string from webAPI into multiple variables for openlayers GeoJSON

currently my webAPI method returns to me a long string for a GeoJSON layer that i need to parse through and separate out into mutliple variables that allows for me to create my necessary GeoJSON layer. Can i accomplish this easily through the str.split function or is a there another route that i need to take
The returned string from the webAPI looks like this:
{"type":"FeatureCollection","bbox":[1108864.9370570681,507099.9482870581,1109064.5346246646,507455.89728260477],"features":[{"type":"Feature","geometry":{"type":"Polygon","coordinates":[[[1109035.4443840273,507308.60334444791],[1108893.4509952962,507307.23951566964],[1108893.1628068388,507337.23816090077],[1109035.1562700756,507338.60198967904],[1109035.4443840273,507308.60334444791]]]},"properties":{"twp":"01","map_num":"8.0","sec":"33.00","qtr_sec":"003","map_block":"007","parcel":"008.00","pid":"018.033.00003007008.00","gis_acres":"0.0977962","debbie_ac":"0.10c","misc":"","scan_deeds":"T:\\Images\\Hyperlinked_Deeds\\00203","latitude":"37.2227488237","longitude":"-89.5082666075","name":"O'RILEY PROPERTIES LLC","site_addre":"519 MADISON ST","shape_leng":"344.000009295","shape_area":"4260.00340015","card_ac":"0.00c 0.00d","date":"1/1/0001 12:00:00 AM","ParcelId":"203","ParcelNumber":"0180330000300700800","_hg_layer":"PARCELS"}}
The features section of the string has an array of features but for use in this example i only copied of one specific feature that. the format I'm looking to set this up in is as follows:
var geojsonObject = {
'type': 'FeatureCollection',
'crs': {
'type': 'name',
'properties': {
//'name': 'EPSG:3857'
}
},
'features': [
{
"type": "Feature", "geometry":
{
"type": "Polygon", "coordinates": [[[1109035.4443840273, 507308.60334444791],
[1108893.4509952962, 507307.23951566964],
[1108893.1628068388, 507337.23816090077],
[1109035.1562700756, 507338.60198967904],
[1109035.4443840273, 507308.60334444791]]]
, "properties": {
"twp": "01",
"map_num": "8.0",
"sec": "33.00",
"qtr_sec": "003",
"map_block": "007",
"parcel": "008.00",
"pid": "018.033.00003007008.00",
"gis_acres": "0.0977962",
"debbie_ac": "0.10c",
"misc": "",
"scan_deeds": "T:\\Images\\Hyperlinked_Deeds\\00203",
"latitude": "37.2227488237",
"longitude": "-89.5082666075",
"name": "O'RILEY PROPERTIES LLC",
"site_addre": "519 MADISON ST",
"shape_leng": "344.000009295",
"shape_area": "4260.00340015",
"card_ac": "0.00c 0.00d",
"date": "1/1/0001 12:00:00 AM",
"ParcelId": "203",
"ParcelNumber": "0180330000300700800",
"_hg_layer": "PARCELS"
}
}
}
Again the features section of this code in my example just shows one specific feature but i will actually have several features that i need to display.
is parsing through this long string the easiest route to go or do i need to restructure the string that my WebAPI actually sends back to me

GeoJSON - Display all features in a table

I am trying to list all my features from a GeoJSON file in a table on a website and i am stuck figuring out how to achieve this.
As a first step i built a Leaflet map showing all locations loaded from the GeoJSON file which works pretty good.
What i would like to have in addition to the map is a rating system on a second page, which features all the locations from the GeoJSON in a table (I only need names for now, the rating system would be a different problem...).
Note that i am an absolute beginner and need a very detailed "tutorial" for this.
My GeoJSON looks like this:
{
"type": "FeatureCollection",
"features": [
{
"type": "Feature",
"geometry": {
"type": "Point",
"coordinates": [ x,y ]
},
"properties": {
"FID":0,
"Shape *":"Point",
"Name":"XXX",
"Ditrict":"Dist1",
"Str_No":"Street 1",
"ZIP":"Some ZIP",
"Phone":"Some Number",
"Rating":4.5
}
},
{
"type": "Feature",
"geometry": {
"type": "Point",
"coordinates": [ x,y ]
}, and so on
I hope that there is a simple solution for this.
Thank you in advance!
If your GeoJSON object is var geoJSON, you can get all the names for each feature by doing the following:
var featureNames = [];
for (var i = 0; i < geoJSON.features.length; i++) {
var currentFeature = geoJSON.features[i];
var featureName = currentFeature.properties.Name;
var featureId = currentFeature.properties.FID;
console.log(featureName);
featureNames.push({ featureId: featureId, featureName : featureName });
}
So featureNames will have each feature object with it's name in an array.
To put them all in a table, I'm going to use jQuery DataTables. If I have a <div id="myTable">, then:
$('#myTable').DataTable( {
"columnDefs": [
{ "title": "Feature Names", "targets": 0 }
]
data: featureNames,
scrollY: 300,
paging: false
} );

Javascript looping through elements and adding to table

I'm having trouble finding a solution that will help me loop through a bunch of elements and putting the chosen values into a table. I've been able to withdraw some values but the method isn't dynamic.
Here is an example:
var Table = {
"credit": {
"link": "site link",
"logoUrl": "logo url",
"message": "message"
},
"groups": [
{
"labels": [
{
"name": "Western Conference",
"type": "conference"
},
{
"name": "Central Division",
"type": "division"
}
],
"standings": [
{
"stats": [
{
"name": "gp",
"value": 20
},
{
"name": "w",
"value": 17
},
{
"name": "l",
"value": 0
},
{
"name": "gf",
"value": 64
},
{
"name": "ga",
"value": 37
},
{
"name": "gd",
"value": 27
},
{
"name": "pts",
"value": 37
}
],
"team": {
"id": 12345,
"link": "team link",
"name": "team name",
"shortName": "team"
}
},
This is the structure of the elements. So far I've used this:
document.getElementById("sGamesPlayed").innerHTML=Table.groups[0].standings[0].stats[0].value;
to withdraw values. However there are more teams, stats and divisions so I would need some kind of loop to go through the elements and put the into a dynamic table.
I would consider you to look at http://underscorejs.org/.
it provides a bunch of utility functions that could help you,
for example, _.each() helps you loop through JSON properties.
for the sample objects you've given (after completing the missing brackets at the end),
_.each(Table.groups[0].standings[0].stats, function(stats){
console.log(stats['name']+","+stats['value'])
})
gives me:
gp,20
w,17
l,0
gf,64
ga,37
gd,27
pts,37
how it works is that you provide the object you want as the first argument and the function that you give as the second argument will be called with each element of the first argument (Assuming it is a list).
I would also urge you to look at underscore templating that you can use to render your table where i put the console.log :
http://net.tutsplus.com/tutorials/javascript-ajax/getting-cozy-with-underscore-js/
http://scriptble.com/2011/01/28/underscore-js-templates/
I guess your question is about filtering the values of the array standings. In order to do that you can use the jQuery grep function (if you want to use jQuery).
For example you can write:
var arr = $.grep(Table.groups[0].standings[0].stats, function(d){return d.value>25})
Which will give
arr = [{"name": "gf","value": 64}, {"name": "ga", "value": 37},{"name": "gd", "value": 27},{"name": "pts", "value": 37}]
If this is not what you meant, can you please create a jsFiddle with a sample of what you want?
Depending on what you want to do with the results, you can go over the object using a scheme like:
var groups, standings, stats, value;
groups = Table.groups;
// Do stuff with groups
for (var i=0, iLen=groups.length; i<iLen; i++) {
standings = groups[i].standings;
// Do stuff with standings
for (var j=0, jLen=standings.length; j<jLen; j++) {
stats = standings[j];
// Do stuff with stats
for (var k=0, kLen=stats.length; k<kLen; k++) {
value = stats[k].value;
// Do stuff with value
}
}
}
Of course I have no idea what the data is for, what the overall structure is or how you want to present it. But if you have deeply nested data, all you can do is dig into it. You might be able to write a recursive function, but it might also become very difficult to maintain if the data structure is complex.

JSON parsing in JS

I am getting a JSON in response from server:
{
"width": "765",
"height": "990",
"srcPath": "http://192.168.5.13:8888/ebook/user_content/_ADMIN_/_MERGED_/1273.pdf",
"coverPage": "",
"documents": [
{
"index": "1",
"text": "Archiving Microsoft® Office SharePoint® Server 2007 Data with the Hitachi Content Archive Platform and Hitachi Data Discovery for Microsoft SharePoint",
"type": "doc",
"id": "HDS_054227~201106290029",
"children": [
{
"text": "Page 1",
"leaf": "true",
"pageLocation": "http://192.168.5.13:8888/ebook/user_content/_ADMIN_/_IMAGES_/HDS_054227~201106290029/image_1.png"
},
{
"text": "Page 2",
"leaf": "true",
"pageLocation": "http://192.168.5.13:8888/ebook/user_content/_ADMIN_/_IMAGES_/HDS_054227~201106290029/image_2.png"
}
]
},
{
"index": "11",
"text": "Brocade FCoE Enabling Server I/O Consolidation",
"type": "doc",
"id": "HDS_053732~201105261741",
"children": [
{
"text": "Page 1",
"leaf": "true",
"pageLocation": "http://192.168.5.13:8888/ebook/user_content/_ADMIN_/_IMAGES_/HDS_053732~201105261741/image_1.png"
},
{
"text": "Page 2",
"leaf": "true",
"pageLocation": "http://192.168.5.13:8888/ebook/user_content/_ADMIN_/_IMAGES_/HDS_053732~201105261741/image_2.png"
}
]
}
]
}
And I want to get pagelocation of the children.
Can anyone tell me how to do this?
Hi
i also want to get indexes from this and then want to get pagelocations of that particular children. Can you tell me how would i do that?
And also when i when i am getting indexes array it is returning me ,, only and not the index nos.
I am using following code for that :
indexes=response.documents.map(function(e){ return e.children.index; })
Thanks & Regards
If you're interested in simply retrieving all the page locations, you can do it using filter:
var locations = [];
json.documents.forEach(function(e,i) {
e.children.forEach(function(e2,i2) {
locations.push(e2.pageLocation);
)}
});
// returns flat array like [item1,item2,item3,item4]
You can get an array of arrays using map:
var locations = [];
var locations = json.documents.map(function(e) {
return e.children.map(function(e2) {
return e2.pageLocation;
});
});
// returns 2-dimensional array like [[item1,item2],[item1,item2]]
Your json response is an appropriate javascript object So you can access all elements of the object like you do as in back end.
here, you have an array of object of the type documents and each document object has array of objects of the type children. so
syntax would be
myjson.documents[0].children[0].pagelocation
( = http://192.168.5.13:8888/ebook/user_content/_ADMIN_/_IMAGES_/HDS_054227~201106290029/image_1.png)
will give you the very first page location..
and so on

Categories

Resources