Parse coordinates out of XML feed - google-maps

Hello I hope I explain this correctly. I am trying to make polygons in Google Maps with coordinates from a XML feed. Problem is the cordinates in the XML feed as not shown as Lat Lon they are shown like this in the feed.
<cap:polygon>
29.66,-97.19 29.40,-97.24 29.11,-97.61 29.35,-97.85 29.57,-97.66 29.68,-97.36 29.66,-97.19
</cap:polygon>
So I need to parse the coordinates out of the XML feed, convert them into google.maps.LatLng objects, so I can push them into an array, so I can provide that array as the paths property in the google.maps.Polygon constructor.
Now this is where I am stuck as I am not sure how to go about parsing that feed element so they are properly formatted the way I need them so I can construct the polygons unless there is a way I can construct the polygons with the way it's formatted now.
Any suggestions or advice would be great!
-Thanks!

Get the content of that XML element into a string. Note that with the "cap" namespace you will have to write browser independent code (different browsers treat that differently).
split the string on spaces (" "):
var coordinates = polygonElemStr.split(" ");
split each set of coordinates on the comma (","), create a google.maps.LatLng from the two numbers and push it onto an array:
var path = [];
for (var i=0; i<coordinates.length; i++) {
var coord = coordinates[i].split(",");
path.push(new google.maps.LatLng(parseFloat(coord[0]),
parseFloat(coord[1])));
}
use that array of coordinates to create your polygon.
example

Related

GLTF file not well positioned by Cesium

I want to display a hurricane (big isosurface object) in Cesium. For this I converted an OBJ file with longitude, latitude, altitude columns for each vertex of the isosurface representing the hurricane, in a new OBJ file reprojected in ECEF (Earth Centered) projection.So the final OBJ file contains now X,Y,Z for each vertex instead of longitude, latitude, altitude. After final reformat by obj2gltf, I try to display the GLTF "hurricane" file in Cesium.JS using the code below:
console.log('loading hurricane.gltf';
var mymodel = viewer.scene.primitives.add(Cesium.Model.fromGltf({
url : 'data/hurricane.gltf',
modelMatrix : Cesium.Matrix4.IDENTITY,
asynchronous: false
}));
I can see my hurricane on the earth, but not at the good position. I suspect a problem of matrix. IDENTITY matrix seems not to be the good one. I could try to make a new matrix but I can't find enough informations about the axes orientation used by Cesium.
I verified the X,Y,Z ECEF coordinates, they are good. Does anyone already meet this problem ?
If your glTF model origin is at the center of the hurricane, you can place it using a Cesium Entity, something like this:
// Longitude degrees, Latitude degrees, height in meters
var position = Cesium.Cartesian3.fromDegrees(-123.0744619, 44.0503706, height);
var heading = Cesium.Math.toRadians(0);
var pitch = 0;
var roll = 0;
var hpr = new Cesium.HeadingPitchRoll(heading, pitch, roll);
var orientation = Cesium.Transforms.headingPitchRollQuaternion(position, hpr);
var entity = viewer.entities.add({
name : 'Hurricane',
position : position,
orientation : orientation,
model : {
uri : 'data/hurricane.gltf'
}
});
viewer.trackedEntity = entity;
There are more complete working demos of this on Sandcastle.
But, if your hurricane is visible on the surface of the Earth using the identity matrix, that likely means that the origin of that model is nowhere near the center of the hurricane. You may need to edit the glTF file, to make sure that the model is centered on its own origin, and does not have some fixed Earth location pre-baked into the model's internal transformations.

How can I scale my map to fit my svg size with d3 and geojson path data

I am trying to create a d3 SVG that draws a map of New York State and scale it so that it fits the size of my SVG, the issue I am having is that when I use .fitSize([height, width], mapObject) it only returns a NaN error in the console.
the topoJSON file of NYS I am using
I am able to get the map to display without scaling but of course, it is not optimized and needs to be scaled
I have attempted what is said in this post but I have not figured out the correct solution
var map = d3.json('./ny.json')
Promise.all([map]).then(data => {
var height = 800;
var width = 800;
var mapData = data[0]
// original geoJSON to that works without scaling
// var geoData = topojson.feature(mapData, mapData.objects["cb_2015_new_york_county_20m"]).features
//
var geoData = topojson.feature(mapData, {
type:"GeometryCollection",
geometries: mapData.objects["cb_2015_new_york_county_20m"].geometries,
})
var projection = d3.geoMercator()
.fitSize([width, height], geoData)
var path = d3.geoPath()
.projection(projection)
d3.select('svg')
.attr('height', height)
.attr('width', width)
.selectAll('.county')
.data(geoData)
.enter()
.append('path')
.classed('.county', true)
.attr('d', path)
})
I am pretty sure this is a formatting error on my part, but I am unsure of what data .fitSize() or .fitExtent() is trying to compare against.
right now the way the code site I receive no error outputted to the console but I also have no data append to the SVG
The issue is that fitSize takes a geojson object while selectAll.data() takes an array, you are using one of these two for both in geoData. This leaves two solutions:
Solution 1:
If we use
var geoData = topojson.feature(mapData, mapData.objects["cb_2015_new_york_county_20m"]).features
var projection = d3.geoMercator()
.fitSize([width, height], geoData)
We get NaN errors because the projection is not set properly as we aren't passing a geojson object, just an array of geojson objects. We could solve this by making a feature collection with geoData and passing that to fitSize:
var geoData = topojson.feature(mapData, mapData.objects["cb_2015_new_york_county_20m"]).features
var projection = d3.geoMercator()
.fitSize([width, height], {type:"FeatureCollection", features: geoData})
Now we are passing a geojson feature collection to fitSize, we're all go on the projection, and since geoData is still an array, we can pass that to selectAll.data() unchanged.
Here's a block.
Solution 2:
If we use:
var geoData = topojson.feature(mapData, {
type:"GeometryCollection",
geometries: mapData.objects["cb_2015_new_york_county_20m"].geometries,
})
We get a geojson object, projection.fitSize works, but selectAll().data(geoData) doesn't add any features as it isn't an array - the enter selection is empty. We can substitute in selectAll().data(geoData.features) to solve this and enter one path per feature (alternatively we could use .data([geoData]) to enter one feature for all the paths).
Here's a block.
Both blocks are drawn at the correct scale - the map exceeds the block bounds as I didn't alter your 800x800 dimensions

DbGeography.Distance() returning incorrect distance

I'm experimenting with System.Data.Spatial.DbGeography, that I want to use to determine the distance from one coordinate to another (going to be stored in SQL server).
My coordinates are in lat/long, and I got them from Bing Maps (I've tried with coordinates from Google Maps too, with the same result).
var osloCentralStation = DbGeography.FromText("POINT(59.9109 10.7523)", 4326);
var drammen = DbGeography.FromText("POINT(59.7378 10.2050)", 4326);
Console.WriteLine("Distance: {0}km", osloCentralStation.Distance(drammen) / 1000);
Returns:
Distance: 63,4340839088124km
The returned distance is approximately double what it should be.
https://maps.google.com/maps?saddr=59.9109+10.7523&daddr=59.7378+10.2050
Does anybody have any idea as to what's going on?
You're not declaring the element in WKT in the right order.
WKT should be in your case:
POINT(10.2050 59.7378)
See OGC standard here:
http://msdn.microsoft.com/en-us/library/bb933834.aspx
http://en.wikipedia.org/wiki/Well-known_text
And then it has to be declared like:
POINT(LONGITUDE LATITUDE)
Also keep in mind that it won't be the driving distance but the distance by air.
It turns out that lat/long are given as long/lat when creating new DbGeography objects.
I've written a little helper method so that I don't get it wrong again in the future:
private static DbGeography CreateDbGeography(double latitude, double longitude, int srid = 0)
{
var text = string.Format(CultureInfo.InvariantCulture.NumberFormat, "POINT({0} {1})", longitude, latitude);
if (srid > 0)
{
return DbGeography.FromText(text, srid);
}
return DbGeography.FromText(text);
}

Fetching all the coordinates along a route generated by Directions Service in Google Maps Apiv3

My application allows a user to select two points on the map and find a route between them using the Directions Service of the Google maps Apiv3. Then the coordinates along this route has to be saved to the database. I could successfully write all the code to accomplish this. However I am left out with an issue.
I know that there are several other questions in StackOverflow- One, Two on the same, but I think surely either they or me has missed out something here.
Sample Code:
function getCoordinates(result) {
var currentRouteArray = result.routes[0]; //Returns a complex object containing the results of the current route
var currentRoute = currentRouteArray.overview_path; //Returns a simplified version of all the coordinates on the path
obj_newPolyline = new google.maps.Polyline({ map: map }); //a polyline just to verify my code is fetching the coordinates
var path = obj_newPolyline.getPath();
for (var x = 0; x < currentRoute.length; x++) {
var pos = new google.maps.LatLng(currentRoute[x].kb, currentRoute[x].lb)
latArray[x] = currentRoute[x].kb; //Returns the latitude
lngArray[x] = currentRoute[x].lb; //Returns the longitude
path.push(pos);
}
}
The above code works perfect except that the kb and lb properties of the overview path which seem to hold the lat and lng coordinates are not always the same. The last time I made the code, it was kb and lb for few days, and later it changed to mb, nb and today jb and kb.
I dont see any other properties in the object that can provide me the latlng's other than the above. Answers to other similar questions dint mention this issue. Am I missing something here? Any reliable solutions please.
do not use kb and lb which are minified names and undocumented. Use only the documented properties .lat() and .lng()
Another option is to decode the "points" string:
http://home.provide.net/~bratliff/routes/
It is a lot faster than using the lat() / lng() methods for every individual point.

google maps : How to find if any markers inside map

I have divided the my google map display in to numbers of parts, Now I want of find it out if any markers are positioned inside a/any particulate cell.
Any Help ?
Farther Explained :
I have got the map bounds by
map.getBounds();
method and then farther divide it into numbers of sub-bounds.
also I have putted markers as
map.addOverlay(markerObject);
Now , I want find if of the cells (which I got by dividing the map by bounds) is containing any markers or not .
I have divide the entire map bounds into numbers of sub bounds
So keep all markers in array. Each marker has a method called get_position( ). After you have finished division of map bound into small sub bounds, you just need to iterate over the sub bounds and check whenever the marker within it.
PS. Also take a look on it, in some cases could be useful.
Suppose you on sub bound cell:
var sub_bounds = new Array();
// here you've pushed into an array the sub bounds
for ( var i = 0; i<sub_bounds.length; ++i)
{
for ( var j = 0; j < markers.length; ++j)
{
var lat = markers[j].get_position( ).lat;
var lng = markers[j].get_position( ).lng;
if ( sub_bounds[i].sw.lat<lat && lat<sub_bounds[i].ne.lat &&
sub_bounds[i].sw.lng<lng && lng<sub_bounds[i].ne.lng)
// marker within cell, do whatever you need to do
}
}
Here is an alternative to the above solution without re-iteration:
First - how big are your sub_bounds? Say 10 latitude and longitude degrees each.
Second - The position of the marker is (floor(marker.lat / 10), floor(marker.lng / 10))
Third - Each marker is added to the map and dropped in a bucket for that subdomain.
so (40, -78) would lie in bucket (4,7) i.e. bucket["4~7"]
Correction: would lie in bucket (4,-7) i.e. bucket["4~-7"]
which would contain all markers between 40 and 50 lat and -70 and -80 lng.
You can use GLatLngBounds as the object that holds all these markers in each bucket, which would give you a good set of methods to use, such as calculating center of the bucket depending on the markers currently in it.
Probably the best solution is given here: how to find out whether a point is inside a polygone:
How to detect that a point is inside a Polygon using Google Maps?