calculate new coordinates based on Point, bearing and distance
Jo
winfixit at gmail.com
Fri Oct 26 18:11:50 UTC 2018
Hi,
If I have a node, does JOSM have the possibility to calculate how to
move/displace it a given distance in meters in the direction of a given
compass bearing in degrees?
I tried a bit, based on formulas found on the internet. But the point is
always moved the same distance along the same bearing, somewhat to the
northeast, regardless of distance or bearing.
Polyglot
from math import asin, cos, sin, atan2, radians, degrees, pi
from javax.swing import JOptionPane
from org.openstreetmap.josm.gui import MainApplication
import org.openstreetmap.josm.command as Command
def displace2(coor, bearing, distance):
_bearing = radians(float(bearing))
_lat = radians(coor.lat())
_lon = radians(coor.lon())
earthRadiusInMetres = 6371000.0
dist_over_ER = float(distance) / earthRadiusInMetres
cos_dist_over_ER = cos(dist_over_ER)
sin_dist_over_ER = sin(dist_over_ER)
lat2 = asin(sin(_lat) * cos_dist_over_ER + cos(_lat) * sin_dist_over_ER
* cos(_bearing))
a = atan2(sin(_bearing) * sin_dist_over_ER * cos(_lat),
cos_dist_over_ER - sin(_lat) * sin(lat2))
lon2 = (_lon + a + 3*pi) % (2*pi) - pi
return degrees(lon2), degrees(lat2)
def displace(coor, bearing, distance):
earth_radius = 6371000.0 # earth's radius in meter
print bearing, distance
_bearing = radians(bearing)
print _bearing, cos(_bearing), sin(_bearing)
lat1 = radians(coor.lat())
lon1 = radians(coor.lon())
distoverER = float(distance) / earth_radius
cosdistoverER = cos(distoverER)
sindistoverER = sin(distoverER)
print distoverER, cosdistoverER, sindistoverER
print sin(lat1) * cosdistoverER
print cos(lat1) * sindistoverER * cos(_bearing)
print sin(_bearing) * sindistoverER * cos(lat1)
lat2 = asin(sin(lat1) * cosdistoverER +
cos(lat1) * sindistoverER * cos(_bearing))
print cosdistoverER - sin(lat1) * sin(lat2)
print asin(sin(lat1) * cosdistoverER +
cos(lat1) * sindistoverER * cos(_bearing))
print atan2(sin(_bearing) * sindistoverER * cos(lat1),
cosdistoverER - sin(lat1) * sin(lat2))
print lon1 + atan2(sin(_bearing) * sindistoverER * cos(lat1),
cosdistoverER - sin(lat1) * sin(lat2))
lon2 = lon1 + atan2(sin(_bearing) * sindistoverER * cos(lat1),
cosdistoverER - sin(lat1) * sin(lat2))
return degrees(lon2), degrees(lat2)
editLayer = MainApplication.getLayerManager().getEditLayer()
print '==== Fresh run ===='
if editLayer and editLayer.data:
selected_nodes = editLayer.data.getSelectedNodes()
print selected_nodes
if not(selected_nodes):
JOptionPane.showMessageDialog(MainApplication.parent, "Please
select node(s) to displace")
else:
for node in selected_nodes:
b = int(node.get("bearing")) + 90
if b > 360: b = b - 360
print b
lon, lat = displace2(coor = node.getCoor(),
bearing=b,
distance = 100.0)
print node.getCoor().lon(), node.getCoor().lat()
print lon, lat
commandsList = []
commandsList.append(Command.MoveCommand(node, lon, lat))
MainApplication.undoRedo.add(Command.SequenceCommand(
"Move node", commandsList))
More information about the josm-dev
mailing list