moved angle calc to util
This commit is contained in:
parent
9e64eb39c4
commit
68b7ddff5c
5 changed files with 71 additions and 61 deletions
|
@ -51,7 +51,7 @@ final class KinematicPrePath extends OsmPrePath
|
||||||
|
|
||||||
int dist = rc.calcDistance( lon1, lat1, lon2, lat2 );
|
int dist = rc.calcDistance( lon1, lat1, lon2, lat2 );
|
||||||
|
|
||||||
angle = rc.calcAngle( lon0, lat0, lon1, lat1, lon2, lat2 );
|
angle = rc.anglemeter.calcAngle( lon0, lat0, lon1, lat1, lon2, lat2 );
|
||||||
priorityclassifier = (int)rc.expctxWay.getPriorityClassifier();
|
priorityclassifier = (int)rc.expctxWay.getPriorityClassifier();
|
||||||
classifiermask = (int)rc.expctxWay.getClassifierMask();
|
classifiermask = (int)rc.expctxWay.getClassifierMask();
|
||||||
}
|
}
|
||||||
|
|
|
@ -323,8 +323,8 @@ abstract class OsmPath implements OsmLinkHolder
|
||||||
lat0 = lat1 - (lat2-lat1);
|
lat0 = lat1 - (lat2-lat1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
double angle = rc.calcAngle( lon0, lat0, lon1, lat1, lon2, lat2 );
|
double angle = rc.anglemeter.calcAngle( lon0, lat0, lon1, lat1, lon2, lat2 );
|
||||||
double cosangle = rc.getCosAngle();
|
double cosangle = rc.anglemeter.getCosAngle();
|
||||||
|
|
||||||
// *** elevation stuff
|
// *** elevation stuff
|
||||||
double delta_h = 0.;
|
double delta_h = 0.;
|
||||||
|
|
|
@ -16,6 +16,7 @@ import btools.expressions.BExpressionContextNode;
|
||||||
import btools.expressions.BExpressionContextWay;
|
import btools.expressions.BExpressionContextWay;
|
||||||
import btools.mapaccess.GeometryDecoder;
|
import btools.mapaccess.GeometryDecoder;
|
||||||
import btools.mapaccess.OsmLink;
|
import btools.mapaccess.OsmLink;
|
||||||
|
import btools.util.CheapAngleMeter;
|
||||||
import btools.util.CheapRuler;
|
import btools.util.CheapRuler;
|
||||||
|
|
||||||
public final class RoutingContext
|
public final class RoutingContext
|
||||||
|
@ -194,7 +195,8 @@ public final class RoutingContext
|
||||||
public boolean startDirectionValid;
|
public boolean startDirectionValid;
|
||||||
public boolean forceUseStartDirection;
|
public boolean forceUseStartDirection;
|
||||||
|
|
||||||
private double cosangle;
|
public CheapAngleMeter anglemeter = new CheapAngleMeter();
|
||||||
|
|
||||||
public double nogoCost = 0.;
|
public double nogoCost = 0.;
|
||||||
public boolean isEndpoint = false;
|
public boolean isEndpoint = false;
|
||||||
|
|
||||||
|
@ -412,51 +414,6 @@ public final class RoutingContext
|
||||||
return (int)(d + 1.0 );
|
return (int)(d + 1.0 );
|
||||||
}
|
}
|
||||||
|
|
||||||
public double getCosAngle()
|
|
||||||
{
|
|
||||||
return cosangle;
|
|
||||||
}
|
|
||||||
|
|
||||||
public double calcAngle( int lon0, int lat0, int lon1, int lat1, int lon2, int lat2 )
|
|
||||||
{
|
|
||||||
double[] lonlat2m = CheapRuler.getLonLatToMeterScales( lat1 );
|
|
||||||
double lon2m = lonlat2m[0];
|
|
||||||
double lat2m = lonlat2m[1];
|
|
||||||
double dx10 = (lon1 - lon0) * lon2m;
|
|
||||||
double dy10 = (lat1 - lat0) * lat2m;
|
|
||||||
double dx21 = (lon2 - lon1) * lon2m;
|
|
||||||
double dy21 = (lat2 - lat1) * lat2m;
|
|
||||||
|
|
||||||
double dd = Math.sqrt( (dx10*dx10 + dy10*dy10)*(dx21*dx21 + dy21*dy21) );
|
|
||||||
if ( dd == 0. ) { cosangle = 1.; return 0.; }
|
|
||||||
double sinp = (dy10*dx21 - dx10*dy21)/dd;
|
|
||||||
double cosp = (dy10*dy21 + dx10*dx21)/dd;
|
|
||||||
cosangle = cosp;
|
|
||||||
|
|
||||||
double offset = 0.;
|
|
||||||
double s2 = sinp*sinp;
|
|
||||||
if ( s2 > 0.5 )
|
|
||||||
{
|
|
||||||
if ( sinp > 0. )
|
|
||||||
{
|
|
||||||
offset = 90.;
|
|
||||||
sinp = -cosp;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
offset = -90.;
|
|
||||||
sinp = cosp;
|
|
||||||
}
|
|
||||||
s2 = cosp*cosp;
|
|
||||||
}
|
|
||||||
else if ( cosp < 0. )
|
|
||||||
{
|
|
||||||
sinp = -sinp;
|
|
||||||
offset = sinp > 0. ? -180. : 180.;
|
|
||||||
}
|
|
||||||
return offset + sinp * ( 57.4539 + s2 * ( 9.57565 + s2 * ( 4.30904 + s2 * 2.56491 ) ) );
|
|
||||||
}
|
|
||||||
|
|
||||||
public OsmPathModel pm;
|
public OsmPathModel pm;
|
||||||
|
|
||||||
public OsmPrePath createPrePath( OsmPath origin, OsmLink link )
|
public OsmPrePath createPrePath( OsmPath origin, OsmLink link )
|
||||||
|
|
55
brouter-util/src/main/java/btools/util/CheapAngleMeter.java
Normal file
55
brouter-util/src/main/java/btools/util/CheapAngleMeter.java
Normal file
|
@ -0,0 +1,55 @@
|
||||||
|
/**
|
||||||
|
* Calculate the angle defined by 3 points
|
||||||
|
* (and deliver it's cosine on the fly)
|
||||||
|
*/
|
||||||
|
package btools.util;
|
||||||
|
|
||||||
|
public final class CheapAngleMeter
|
||||||
|
{
|
||||||
|
private double cosangle;
|
||||||
|
|
||||||
|
public double getCosAngle()
|
||||||
|
{
|
||||||
|
return cosangle;
|
||||||
|
}
|
||||||
|
|
||||||
|
public double calcAngle( int lon0, int lat0, int lon1, int lat1, int lon2, int lat2 )
|
||||||
|
{
|
||||||
|
double[] lonlat2m = CheapRuler.getLonLatToMeterScales( lat1 );
|
||||||
|
double lon2m = lonlat2m[0];
|
||||||
|
double lat2m = lonlat2m[1];
|
||||||
|
double dx10 = (lon1 - lon0) * lon2m;
|
||||||
|
double dy10 = (lat1 - lat0) * lat2m;
|
||||||
|
double dx21 = (lon2 - lon1) * lon2m;
|
||||||
|
double dy21 = (lat2 - lat1) * lat2m;
|
||||||
|
|
||||||
|
double dd = Math.sqrt( (dx10*dx10 + dy10*dy10)*(dx21*dx21 + dy21*dy21) );
|
||||||
|
if ( dd == 0. ) { cosangle = 1.; return 0.; }
|
||||||
|
double sinp = (dy10*dx21 - dx10*dy21)/dd;
|
||||||
|
double cosp = (dy10*dy21 + dx10*dx21)/dd;
|
||||||
|
cosangle = cosp;
|
||||||
|
|
||||||
|
double offset = 0.;
|
||||||
|
double s2 = sinp*sinp;
|
||||||
|
if ( s2 > 0.5 )
|
||||||
|
{
|
||||||
|
if ( sinp > 0. )
|
||||||
|
{
|
||||||
|
offset = 90.;
|
||||||
|
sinp = -cosp;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
offset = -90.;
|
||||||
|
sinp = cosp;
|
||||||
|
}
|
||||||
|
s2 = cosp*cosp;
|
||||||
|
}
|
||||||
|
else if ( cosp < 0. )
|
||||||
|
{
|
||||||
|
sinp = -sinp;
|
||||||
|
offset = sinp > 0. ? -180. : 180.;
|
||||||
|
}
|
||||||
|
return offset + sinp * ( 57.4539 + s2 * ( 9.57565 + s2 * ( 4.30904 + s2 * 2.56491 ) ) );
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,4 +1,4 @@
|
||||||
package btools.router;
|
package btools.util;
|
||||||
|
|
||||||
import static org.junit.Assert.assertEquals;
|
import static org.junit.Assert.assertEquals;
|
||||||
import static org.junit.Assert.assertFalse;
|
import static org.junit.Assert.assertFalse;
|
||||||
|
@ -8,9 +8,7 @@ import org.junit.AfterClass;
|
||||||
import org.junit.BeforeClass;
|
import org.junit.BeforeClass;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
|
|
||||||
import btools.util.CheapRuler;
|
public class CheapAngleMeterTest {
|
||||||
|
|
||||||
public class RoutingContextTest {
|
|
||||||
static int toOsmLon(double lon) {
|
static int toOsmLon(double lon) {
|
||||||
return (int)( ( lon + 180. ) / CheapRuler.ILATLNG_TO_LATLNG + 0.5);
|
return (int)( ( lon + 180. ) / CheapRuler.ILATLNG_TO_LATLNG + 0.5);
|
||||||
}
|
}
|
||||||
|
@ -21,7 +19,7 @@ public class RoutingContextTest {
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testCalcAngle() {
|
public void testCalcAngle() {
|
||||||
RoutingContext rc = new RoutingContext();
|
CheapAngleMeter am = new CheapAngleMeter();
|
||||||
// Segment ends
|
// Segment ends
|
||||||
int lon0, lat0, lon1, lat1, lon2, lat2;
|
int lon0, lat0, lon1, lat1, lon2, lat2;
|
||||||
|
|
||||||
|
@ -34,7 +32,7 @@ public class RoutingContextTest {
|
||||||
assertEquals(
|
assertEquals(
|
||||||
"Works for an angle between -pi/4 and pi/4",
|
"Works for an angle between -pi/4 and pi/4",
|
||||||
-10.,
|
-10.,
|
||||||
rc.calcAngle(lon0, lat0, lon1, lat1, lon2, lat2),
|
am.calcAngle(lon0, lat0, lon1, lat1, lon2, lat2),
|
||||||
0.05 * 10.
|
0.05 * 10.
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -47,7 +45,7 @@ public class RoutingContextTest {
|
||||||
assertEquals(
|
assertEquals(
|
||||||
"Works for an angle between 3*pi/4 and 5*pi/4",
|
"Works for an angle between 3*pi/4 and 5*pi/4",
|
||||||
180.,
|
180.,
|
||||||
rc.calcAngle(lon0, lat0, lon1, lat1, lon2, lat2),
|
am.calcAngle(lon0, lat0, lon1, lat1, lon2, lat2),
|
||||||
0.05 * 180.
|
0.05 * 180.
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -60,7 +58,7 @@ public class RoutingContextTest {
|
||||||
assertEquals(
|
assertEquals(
|
||||||
"Works for an angle between -3*pi/4 and -pi/4",
|
"Works for an angle between -3*pi/4 and -pi/4",
|
||||||
100.,
|
100.,
|
||||||
rc.calcAngle(lon0, lat0, lon1, lat1, lon2, lat2),
|
am.calcAngle(lon0, lat0, lon1, lat1, lon2, lat2),
|
||||||
0.1 * 100.
|
0.1 * 100.
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -73,14 +71,14 @@ public class RoutingContextTest {
|
||||||
assertEquals(
|
assertEquals(
|
||||||
"Works for an angle between pi/4 and 3*pi/4",
|
"Works for an angle between pi/4 and 3*pi/4",
|
||||||
-100.,
|
-100.,
|
||||||
rc.calcAngle(lon0, lat0, lon1, lat1, lon2, lat2),
|
am.calcAngle(lon0, lat0, lon1, lat1, lon2, lat2),
|
||||||
0.1 * 100.
|
0.1 * 100.
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testCalcAngle2() {
|
public void testCalcAngle2() {
|
||||||
RoutingContext rc = new RoutingContext();
|
CheapAngleMeter am = new CheapAngleMeter();
|
||||||
int lon1 = 8500000;
|
int lon1 = 8500000;
|
||||||
int lat1 = 49500000;
|
int lat1 = 49500000;
|
||||||
|
|
||||||
|
@ -107,9 +105,9 @@ public class RoutingContextTest {
|
||||||
double a1 = afrom - ato;
|
double a1 = afrom - ato;
|
||||||
if ( a1 > 180. ) a1 -= 360.;
|
if ( a1 > 180. ) a1 -= 360.;
|
||||||
if ( a1 < -180. ) a1 += 360.;
|
if ( a1 < -180. ) a1 += 360.;
|
||||||
double a2 = rc.calcAngle( lon0, lat0, lon1, lat1, lon2, lat2 );
|
double a2 = am.calcAngle( lon0, lat0, lon1, lat1, lon2, lat2 );
|
||||||
double c1 = Math.cos( a1 * Math.PI / 180. );
|
double c1 = Math.cos( a1 * Math.PI / 180. );
|
||||||
double c2 = rc.getCosAngle();
|
double c2 = am.getCosAngle();
|
||||||
|
|
||||||
assertEquals( "angle mismatch for afrom=" + afrom + " ato=" + ato, a1, a2, 0.2 );
|
assertEquals( "angle mismatch for afrom=" + afrom + " ato=" + ato, a1, a2, 0.2 );
|
||||||
assertEquals( "cosinus mismatch for afrom=" + afrom + " ato=" + ato, c1, c2, 0.001 );
|
assertEquals( "cosinus mismatch for afrom=" + afrom + " ato=" + ato, c1, c2, 0.001 );
|
Loading…
Reference in a new issue