Add netcore
This commit is contained in:
parent
2b0fbff159
commit
3843109a62
File diff suppressed because it is too large
Load Diff
@ -1,8 +1,7 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
|
|
||||||
namespace CoordinateSharp
|
namespace CoordinateSharp {
|
||||||
{
|
|
||||||
//CURRENT ALTITUDE IS SET CONSTANT AT 100M. POSSIBLY NEED TO ADJUST TO ALLOW USER PASS.
|
//CURRENT ALTITUDE IS SET CONSTANT AT 100M. POSSIBLY NEED TO ADJUST TO ALLOW USER PASS.
|
||||||
//Altitude adjustments appear to have minimal effect on eclipse timing. These were mainly used
|
//Altitude adjustments appear to have minimal effect on eclipse timing. These were mainly used
|
||||||
//to signify eclipses that had already started during rise and set times on the NASA calculator
|
//to signify eclipses that had already started during rise and set times on the NASA calculator
|
||||||
@ -15,80 +14,51 @@ namespace CoordinateSharp
|
|||||||
//This can be modified if need to allow users to pass custom number with the Coordinate SetDatum() functions.
|
//This can be modified if need to allow users to pass custom number with the Coordinate SetDatum() functions.
|
||||||
|
|
||||||
//CURRENT RANGE 1601-2600.
|
//CURRENT RANGE 1601-2600.
|
||||||
internal class LunarEclipseCalc
|
internal class LunarEclipseCalc {
|
||||||
{
|
public static List<List<String>> CalculateLunarEclipse(DateTime d, Double latRad, Double longRad) => Calculate(d, latRad, longRad);
|
||||||
public static List<List<string>> CalculateLunarEclipse(DateTime d, double latRad, double longRad)
|
public static List<LunarEclipseDetails> CalculateLunarEclipse(DateTime d, Double latRad, Double longRad, Double[] events) {
|
||||||
{
|
List<List<String>> evs = Calculate(d, latRad, longRad, events);
|
||||||
return Calculate(d, latRad, longRad);
|
|
||||||
}
|
|
||||||
public static List<LunarEclipseDetails> CalculateLunarEclipse(DateTime d, double latRad, double longRad, double[] events)
|
|
||||||
{
|
|
||||||
List<List<string>> evs = Calculate(d, latRad, longRad, events);
|
|
||||||
List<LunarEclipseDetails> deetsList = new List<LunarEclipseDetails>();
|
List<LunarEclipseDetails> deetsList = new List<LunarEclipseDetails>();
|
||||||
foreach (List<string> ls in evs)
|
foreach (List<String> ls in evs) {
|
||||||
{
|
|
||||||
LunarEclipseDetails deets = new LunarEclipseDetails(ls);
|
LunarEclipseDetails deets = new LunarEclipseDetails(ls);
|
||||||
deetsList.Add(deets);
|
deetsList.Add(deets);
|
||||||
}
|
}
|
||||||
return deetsList;
|
return deetsList;
|
||||||
}
|
}
|
||||||
public static List<List<string>> CalculateLunarEclipse(DateTime d, Coordinate coord)
|
public static List<List<String>> CalculateLunarEclipse(DateTime d, Coordinate coord) => Calculate(d, coord.Latitude.ToRadians(), coord.Longitude.ToRadians());
|
||||||
{
|
|
||||||
return Calculate(d, coord.Latitude.ToRadians(), coord.Longitude.ToRadians());
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// CALCULATE!
|
// CALCULATE!
|
||||||
private static List<List<string>> Calculate(DateTime d, double latRad, double longRad, double[] ev = null)
|
private static List<List<String>> Calculate(DateTime d, Double latRad, Double longRad, Double[] ev = null) {
|
||||||
{
|
|
||||||
//DECLARE ARRAYS
|
//DECLARE ARRAYS
|
||||||
double[] obsvconst = new double[6];
|
Double[] obsvconst = new Double[6];
|
||||||
double[] mid = new double[41];
|
Double[] mid = new Double[41];
|
||||||
double[] p1 = new double[41];
|
Double[] p1 = new Double[41];
|
||||||
double[] u1 = new double[41];
|
Double[] u1 = new Double[41];
|
||||||
double[] u2 = new double[41];
|
Double[] u2 = new Double[41];
|
||||||
double[] u3 = new double[41];
|
Double[] u3 = new Double[41];
|
||||||
double[] u4 = new double[41];
|
Double[] u4 = new Double[41];
|
||||||
double[] p4 = new double[41];
|
Double[] p4 = new Double[41];
|
||||||
|
|
||||||
List<List<string>> events = new List<List<string>>();
|
Double[] el = ev ?? Eclipse.LunarData.LunarDateData(d);
|
||||||
|
List<List<String>> events = new List<List<String>>();
|
||||||
double[] el;
|
|
||||||
if (ev == null)
|
|
||||||
{
|
|
||||||
el = Eclipse.LunarData.LunarDateData(d);//Get 100 year solar data;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
el = ev;
|
|
||||||
}
|
|
||||||
|
|
||||||
events = new List<List<string>>();
|
|
||||||
ReadData(latRad, longRad, obsvconst);
|
ReadData(latRad, longRad, obsvconst);
|
||||||
|
|
||||||
for (int i = 0; i < el.Length; i += 22)
|
for (Int32 i = 0; i < el.Length; i += 22) {
|
||||||
{
|
if (el[5 + i] <= obsvconst[5]) {
|
||||||
if (el[5 + i] <= obsvconst[5])
|
List<String> values = new List<String>();
|
||||||
{
|
|
||||||
List<string> values = new List<string>();
|
|
||||||
obsvconst[4] = i;
|
obsvconst[4] = i;
|
||||||
GetAll(el, obsvconst, mid, p1, u1, u2, u3, u4, p4);
|
GetAll(el, obsvconst, mid, p1, u1, u2, u3, u4, p4);
|
||||||
// Is there an event...
|
// Is there an event...
|
||||||
if (mid[5] != 1)
|
if (mid[5] != 1) {
|
||||||
{
|
|
||||||
|
|
||||||
values.Add(GetDate(el, p1, obsvconst));
|
values.Add(GetDate(el, p1, obsvconst));
|
||||||
|
|
||||||
if (el[5 + i] == 1)
|
if (el[5 + i] == 1) {
|
||||||
{
|
|
||||||
values.Add("T");
|
values.Add("T");
|
||||||
}
|
} else if (el[5 + i] == 2) {
|
||||||
else if (el[5 + i] == 2)
|
|
||||||
{
|
|
||||||
values.Add("P");
|
values.Add("P");
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
values.Add("N");
|
values.Add("N");
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -104,26 +74,20 @@ namespace CoordinateSharp
|
|||||||
// P1 alt
|
// P1 alt
|
||||||
values.Add(GetAlt(p1));
|
values.Add(GetAlt(p1));
|
||||||
|
|
||||||
if (u1[5] == 1)
|
if (u1[5] == 1) {
|
||||||
{
|
|
||||||
values.Add("-");
|
values.Add("-");
|
||||||
values.Add("-");
|
values.Add("-");
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
// U1
|
// U1
|
||||||
values.Add(GetTime(el, u1, obsvconst));
|
values.Add(GetTime(el, u1, obsvconst));
|
||||||
|
|
||||||
// U1 alt
|
// U1 alt
|
||||||
values.Add(GetAlt(u1));
|
values.Add(GetAlt(u1));
|
||||||
}
|
}
|
||||||
if (u2[5] == 1)
|
if (u2[5] == 1) {
|
||||||
{
|
|
||||||
values.Add("-");
|
values.Add("-");
|
||||||
values.Add("-");
|
values.Add("-");
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
// U2
|
// U2
|
||||||
values.Add(GetTime(el, u2, obsvconst));
|
values.Add(GetTime(el, u2, obsvconst));
|
||||||
|
|
||||||
@ -138,26 +102,20 @@ namespace CoordinateSharp
|
|||||||
|
|
||||||
values.Add(GetAlt(mid));
|
values.Add(GetAlt(mid));
|
||||||
|
|
||||||
if (u3[5] == 1)
|
if (u3[5] == 1) {
|
||||||
{
|
|
||||||
values.Add("-");
|
values.Add("-");
|
||||||
values.Add("-");
|
values.Add("-");
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
// u3
|
// u3
|
||||||
values.Add(GetTime(el, u3, obsvconst));
|
values.Add(GetTime(el, u3, obsvconst));
|
||||||
|
|
||||||
// u3 alt
|
// u3 alt
|
||||||
values.Add(GetAlt(u3));
|
values.Add(GetAlt(u3));
|
||||||
}
|
}
|
||||||
if (u4[5] == 1)
|
if (u4[5] == 1) {
|
||||||
{
|
|
||||||
values.Add("-");
|
values.Add("-");
|
||||||
values.Add("-");
|
values.Add("-");
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
// u4
|
// u4
|
||||||
values.Add(GetTime(el, u4, obsvconst));
|
values.Add(GetTime(el, u4, obsvconst));
|
||||||
|
|
||||||
@ -177,8 +135,7 @@ namespace CoordinateSharp
|
|||||||
return events;
|
return events;
|
||||||
}
|
}
|
||||||
// Read the data that's in the form, and populate the obsvconst array
|
// Read the data that's in the form, and populate the obsvconst array
|
||||||
private static void ReadData(double latRad, double longRad, double[] obsvconst)
|
private static void ReadData(Double latRad, Double longRad, Double[] obsvconst) {
|
||||||
{
|
|
||||||
|
|
||||||
// Get the latitude
|
// Get the latitude
|
||||||
obsvconst[0] = latRad;
|
obsvconst[0] = latRad;
|
||||||
@ -199,53 +156,44 @@ namespace CoordinateSharp
|
|||||||
|
|
||||||
}
|
}
|
||||||
// Populate the p1, u1, u2, mid, u3, u4 and p4 arrays
|
// Populate the p1, u1, u2, mid, u3, u4 and p4 arrays
|
||||||
private static void GetAll(double[] elements, double[] obsvconst, double[] mid, double[] p1, double[] u1, double[] u2, double[] u3, double[] u4, double[] p4)
|
private static void GetAll(Double[] elements, Double[] obsvconst, Double[] mid, Double[] p1, Double[] u1, Double[] u2, Double[] u3, Double[] u4, Double[] p4) {
|
||||||
{
|
Int32 index = (Int32)obsvconst[4];
|
||||||
int index = (int)obsvconst[4];
|
|
||||||
p1[1] = elements[index + 9];
|
p1[1] = elements[index + 9];
|
||||||
PopulateCircumstances(elements, p1, obsvconst);
|
PopulateCircumstances(elements, p1, obsvconst);
|
||||||
mid[1] = elements[index + 12];
|
mid[1] = elements[index + 12];
|
||||||
PopulateCircumstances(elements, mid, obsvconst);
|
PopulateCircumstances(elements, mid, obsvconst);
|
||||||
p4[1] = elements[index + 15];
|
p4[1] = elements[index + 15];
|
||||||
PopulateCircumstances(elements, p4, obsvconst);
|
PopulateCircumstances(elements, p4, obsvconst);
|
||||||
if (elements[index + 5] < 3)
|
if (elements[index + 5] < 3) {
|
||||||
{
|
|
||||||
u1[1] = elements[index + 10];
|
u1[1] = elements[index + 10];
|
||||||
PopulateCircumstances(elements, u1, obsvconst);
|
PopulateCircumstances(elements, u1, obsvconst);
|
||||||
u4[1] = elements[index + 14];
|
u4[1] = elements[index + 14];
|
||||||
PopulateCircumstances(elements, u4, obsvconst);
|
PopulateCircumstances(elements, u4, obsvconst);
|
||||||
if (elements[index + 5] < 2)
|
if (elements[index + 5] < 2) {
|
||||||
{
|
|
||||||
u2[1] = elements[index + 11];
|
u2[1] = elements[index + 11];
|
||||||
u3[1] = elements[index + 13];
|
u3[1] = elements[index + 13];
|
||||||
PopulateCircumstances(elements, u2, obsvconst);
|
PopulateCircumstances(elements, u2, obsvconst);
|
||||||
PopulateCircumstances(elements, u3, obsvconst);
|
PopulateCircumstances(elements, u3, obsvconst);
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
u2[5] = 1;
|
u2[5] = 1;
|
||||||
u3[5] = 1;
|
u3[5] = 1;
|
||||||
}
|
}
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
u1[5] = 1;
|
u1[5] = 1;
|
||||||
u2[5] = 1;
|
u2[5] = 1;
|
||||||
u3[5] = 1;
|
u3[5] = 1;
|
||||||
u4[5] = 1;
|
u4[5] = 1;
|
||||||
}
|
}
|
||||||
if ((p1[5] != 0) && (u1[5] != 0) && (u2[5] != 0) && (mid[5] != 0) && (u3[5] != 0) && (u4[5] != 0) && (p4[5] != 0))
|
if (p1[5] != 0 && u1[5] != 0 && u2[5] != 0 && mid[5] != 0 && u3[5] != 0 && u4[5] != 0 && p4[5] != 0) {
|
||||||
{
|
|
||||||
mid[5] = 1;
|
mid[5] = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// Populate the circumstances array
|
// Populate the circumstances array
|
||||||
// entry condition - circumstances[1] must contain the correct value
|
// entry condition - circumstances[1] must contain the correct value
|
||||||
private static void PopulateCircumstances(double[] elements, double[] circumstances, double[] obsvconst)
|
private static void PopulateCircumstances(Double[] elements, Double[] circumstances, Double[] obsvconst) {
|
||||||
{
|
Double t, ra, dec, h;
|
||||||
double t, ra, dec, h;
|
|
||||||
|
|
||||||
int index = (int)obsvconst[4];
|
Int32 index = (Int32)obsvconst[4];
|
||||||
t = circumstances[1];
|
t = circumstances[1];
|
||||||
ra = elements[18 + index] * t + elements[17 + index];
|
ra = elements[18 + index] * t + elements[17 + index];
|
||||||
ra = ra * t + elements[16 + index];
|
ra = ra * t + elements[16 + index];
|
||||||
@ -258,47 +206,35 @@ namespace CoordinateSharp
|
|||||||
circumstances[2] = h;
|
circumstances[2] = h;
|
||||||
circumstances[4] = Math.Asin(Math.Sin(obsvconst[0]) * Math.Sin(dec) + Math.Cos(obsvconst[0]) * Math.Cos(dec) * Math.Cos(h));
|
circumstances[4] = Math.Asin(Math.Sin(obsvconst[0]) * Math.Sin(dec) + Math.Cos(obsvconst[0]) * Math.Cos(dec) * Math.Cos(h));
|
||||||
circumstances[4] -= Math.Asin(Math.Sin(elements[7 + index] * Math.PI / 180.0) * Math.Cos(circumstances[4]));
|
circumstances[4] -= Math.Asin(Math.Sin(elements[7 + index] * Math.PI / 180.0) * Math.Cos(circumstances[4]));
|
||||||
if (circumstances[4] * 180.0 / Math.PI < elements[8 + index] - 0.5667)
|
if (circumstances[4] * 180.0 / Math.PI < elements[8 + index] - 0.5667) {
|
||||||
{
|
|
||||||
circumstances[5] = 2;
|
circumstances[5] = 2;
|
||||||
}
|
} else if (circumstances[4] < 0.0) {
|
||||||
else if (circumstances[4] < 0.0)
|
|
||||||
{
|
|
||||||
circumstances[4] = 0.0;
|
circumstances[4] = 0.0;
|
||||||
circumstances[5] = 0;
|
circumstances[5] = 0;
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
circumstances[5] = 0;
|
circumstances[5] = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// Get the date of an event
|
// Get the date of an event
|
||||||
private static string GetDate(double[] elements, double[] circumstances, double[] obsvconst)
|
private static String GetDate(Double[] elements, Double[] circumstances, Double[] obsvconst) {
|
||||||
{
|
String[] month = new String[] { "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" };//Month string array
|
||||||
string[] month = new string[] { "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" };//Month string array
|
Double t, jd, a, b, c, d, e;
|
||||||
double t, jd, a, b, c, d, e;
|
Int32 index = (Int32)obsvconst[4];
|
||||||
string ans = "";
|
|
||||||
int index = (int)obsvconst[4];
|
|
||||||
// Calculate the JD for noon (TDT) the day before the day that contains T0
|
// Calculate the JD for noon (TDT) the day before the day that contains T0
|
||||||
jd = Math.Floor(elements[index] - (elements[1 + index] / 24.0));
|
jd = Math.Floor(elements[index] - elements[1 + index] / 24.0);
|
||||||
// Calculate the local time (ie the offset in hours since midnight TDT on the day containing T0).
|
// Calculate the local time (ie the offset in hours since midnight TDT on the day containing T0).
|
||||||
t = circumstances[1] + elements[1 + index] - obsvconst[3] - (elements[2 + index] - 30.0) / 3600.0;
|
t = circumstances[1] + elements[1 + index] - obsvconst[3] - (elements[2 + index] - 30.0) / 3600.0;
|
||||||
|
|
||||||
if (t < 0.0)
|
if (t < 0.0) {
|
||||||
{
|
|
||||||
jd--;
|
jd--;
|
||||||
}
|
}
|
||||||
if (t >= 24.0)
|
if (t >= 24.0) {
|
||||||
{
|
|
||||||
jd++;
|
jd++;
|
||||||
}
|
}
|
||||||
if (jd >= 2299160.0)
|
if (jd >= 2299160.0) {
|
||||||
{
|
|
||||||
a = Math.Floor((jd - 1867216.25) / 36524.25);
|
a = Math.Floor((jd - 1867216.25) / 36524.25);
|
||||||
a = jd + 1 + a - Math.Floor(a / 4.0);
|
a = jd + 1 + a - Math.Floor(a / 4.0);
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
a = jd;
|
a = jd;
|
||||||
}
|
}
|
||||||
b = a + 1525.0;
|
b = a + 1525.0;
|
||||||
@ -306,104 +242,77 @@ namespace CoordinateSharp
|
|||||||
d = Math.Floor(365.25 * c);
|
d = Math.Floor(365.25 * c);
|
||||||
e = Math.Floor((b - d) / 30.6001);
|
e = Math.Floor((b - d) / 30.6001);
|
||||||
d = b - d - Math.Floor(30.6001 * e);
|
d = b - d - Math.Floor(30.6001 * e);
|
||||||
if (e < 13.5)
|
e = e < 13.5 ? e - 1 : e - 13;
|
||||||
{
|
Double year;
|
||||||
e = e - 1;
|
String ans;
|
||||||
}
|
if (e > 2.5) {
|
||||||
else
|
|
||||||
{
|
|
||||||
e = e - 13;
|
|
||||||
}
|
|
||||||
double year;
|
|
||||||
if (e > 2.5)
|
|
||||||
{
|
|
||||||
ans = c - 4716 + "-";
|
ans = c - 4716 + "-";
|
||||||
year = c - 4716;
|
year = c - 4716;
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
ans = c - 4715 + "-";
|
ans = c - 4715 + "-";
|
||||||
year = c - 4715;
|
year = c - 4715;
|
||||||
}
|
}
|
||||||
string m = month[(int)e - 1];
|
String m = month[(Int32)e - 1];
|
||||||
ans += m + "-";
|
ans += m + "-";
|
||||||
if (d < 10)
|
if (d < 10) {
|
||||||
{
|
ans += "0";
|
||||||
ans = ans + "0";
|
|
||||||
}
|
}
|
||||||
ans = ans + d;
|
ans += d;
|
||||||
//Leap Year Integrity Check
|
//Leap Year Integrity Check
|
||||||
|
|
||||||
if (m == "Feb" && d == 29 && !DateTime.IsLeapYear((int)year))
|
if (m == "Feb" && d == 29 && !DateTime.IsLeapYear((Int32)year)) {
|
||||||
{
|
|
||||||
ans = year.ToString() + "-Mar-01";
|
ans = year.ToString() + "-Mar-01";
|
||||||
}
|
}
|
||||||
return ans;
|
return ans;
|
||||||
}
|
}
|
||||||
// Get the time of an event
|
// Get the time of an event
|
||||||
private static string GetTime(double[] elements, double[] circumstances, double[] obsvconst)
|
private static String GetTime(Double[] elements, Double[] circumstances, Double[] obsvconst) {
|
||||||
{
|
Double t;
|
||||||
double t;
|
String ans = "";
|
||||||
string ans = "";
|
|
||||||
|
|
||||||
int index = (int)obsvconst[4];
|
Int32 index = (Int32)obsvconst[4];
|
||||||
t = circumstances[1] + elements[1 + index] - obsvconst[3] - (elements[2 + index] - 30.0) / 3600.0;
|
t = circumstances[1] + elements[1 + index] - obsvconst[3] - (elements[2 + index] - 30.0) / 3600.0;
|
||||||
if (t < 0.0)
|
if (t < 0.0) {
|
||||||
{
|
t += 24.0;
|
||||||
t = t + 24.0;
|
|
||||||
}
|
}
|
||||||
if (t >= 24.0)
|
if (t >= 24.0) {
|
||||||
{
|
t -= 24.0;
|
||||||
t = t - 24.0;
|
|
||||||
}
|
}
|
||||||
if (t < 10.0)
|
if (t < 10.0) {
|
||||||
{
|
ans += "0";
|
||||||
ans = ans + "0";
|
|
||||||
}
|
}
|
||||||
ans = ans + Math.Floor(t) + ":";
|
ans = ans + Math.Floor(t) + ":";
|
||||||
t = (t * 60.0) - 60.0 * Math.Floor(t);
|
t = t * 60.0 - 60.0 * Math.Floor(t);
|
||||||
if (t < 10.0)
|
if (t < 10.0) {
|
||||||
{
|
ans += "0";
|
||||||
ans = ans + "0";
|
|
||||||
}
|
}
|
||||||
ans = ans + Math.Floor(t);
|
ans += Math.Floor(t);
|
||||||
if (circumstances[5] == 2)
|
if (circumstances[5] == 2) {
|
||||||
{
|
|
||||||
return ans; //RETURNED IN ITAL DETERMINE WHY
|
return ans; //RETURNED IN ITAL DETERMINE WHY
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
return ans;
|
return ans;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// Get the altitude
|
// Get the altitude
|
||||||
private static string GetAlt(double[] circumstances)
|
private static String GetAlt(Double[] circumstances) {
|
||||||
{
|
Double t;
|
||||||
double t;
|
|
||||||
string ans = "";
|
|
||||||
t = circumstances[4] * 180.0 / Math.PI;
|
t = circumstances[4] * 180.0 / Math.PI;
|
||||||
t = Math.Floor(t + 0.5);
|
t = Math.Floor(t + 0.5);
|
||||||
if (t < 0.0)
|
String ans;
|
||||||
{
|
if (t < 0.0) {
|
||||||
ans = "-";
|
ans = "-";
|
||||||
t = -t;
|
t = -t;
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
ans = "+";
|
ans = "+";
|
||||||
}
|
}
|
||||||
if (t < 10.0)
|
if (t < 10.0) {
|
||||||
{
|
ans += "0";
|
||||||
ans = ans + "0";
|
|
||||||
}
|
}
|
||||||
ans = ans + t;
|
ans += t;
|
||||||
if (circumstances[5] == 2)
|
if (circumstances[5] == 2) {
|
||||||
{
|
|
||||||
return ans; //returned in italics determine why
|
return ans; //returned in italics determine why
|
||||||
|
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
return ans;
|
return ans;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,14 +1,9 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
|
|
||||||
namespace CoordinateSharp
|
namespace CoordinateSharp {
|
||||||
{
|
internal partial class MeeusTables {
|
||||||
internal partial class MeeusTables
|
|
||||||
{
|
|
||||||
//Ch 47
|
//Ch 47
|
||||||
private static double[] Table47A_Arguments = new double[]
|
private static readonly Double[] Table47A_Arguments = new Double[]
|
||||||
{
|
{
|
||||||
0,0,1,0,
|
0,0,1,0,
|
||||||
2,0,-1,0,
|
2,0,-1,0,
|
||||||
@ -72,7 +67,7 @@ namespace CoordinateSharp
|
|||||||
2,0,3,0,
|
2,0,3,0,
|
||||||
2,0,-1,-2
|
2,0,-1,-2
|
||||||
};
|
};
|
||||||
private static double[] Table47B_Arguments = new double[]
|
private static readonly Double[] Table47B_Arguments = new Double[]
|
||||||
{
|
{
|
||||||
0,0,0,1,
|
0,0,0,1,
|
||||||
0,0,1,1,
|
0,0,1,1,
|
||||||
@ -136,7 +131,7 @@ namespace CoordinateSharp
|
|||||||
4,-1,0,-1,
|
4,-1,0,-1,
|
||||||
2,-2,0,1,
|
2,-2,0,1,
|
||||||
};
|
};
|
||||||
private static double[] Table47A_El_Er = new double[]
|
private static readonly Double[] Table47A_El_Er = new Double[]
|
||||||
{
|
{
|
||||||
//El
|
//El
|
||||||
6288774, 1274027,658314,213618,-185116,-114332,58793,57066,53322,45758,
|
6288774, 1274027,658314,213618,-185116,-114332,58793,57066,53322,45758,
|
||||||
@ -151,7 +146,7 @@ namespace CoordinateSharp
|
|||||||
2616,-1897,-2117,2354,0,0,-1423,-1117,-1571,-1739,0,-4421,0,0,0,0,1165,0,0,8752
|
2616,-1897,-2117,2354,0,0,-1423,-1117,-1571,-1739,0,-4421,0,0,0,0,1165,0,0,8752
|
||||||
|
|
||||||
};
|
};
|
||||||
private static double[] Table47B_Eb = new double[]
|
private static readonly Double[] Table47B_Eb = new Double[]
|
||||||
{
|
{
|
||||||
5128122,280602,277693,173237,55413,46271,32573,17198,9266,8822,
|
5128122,280602,277693,173237,55413,46271,32573,17198,9266,8822,
|
||||||
8216,4324,4200,-3359,2463,2211,2065,-1870,1828,-1794,-1749,-1565,-1491,
|
8216,4324,4200,-3359,2463,2211,2065,-1870,1828,-1794,-1749,-1565,-1491,
|
||||||
@ -160,62 +155,48 @@ namespace CoordinateSharp
|
|||||||
777,671,607,596,491,-451,439,422,421,-366,-351,331,315,302,-283,-229,
|
777,671,607,596,491,-451,439,422,421,-366,-351,331,315,302,-283,-229,
|
||||||
223,223,-220,-220,-185,181,-177,176,166,-164,132,-119,115,107
|
223,223,-220,-220,-185,181,-177,176,166,-164,132,-119,115,107
|
||||||
};
|
};
|
||||||
private static double Get_Table47A_Values(double[] values, int l, double t, bool sine)
|
private static Double Get_Table47A_Values(Double[] values, Int32 l, Double t, Boolean sine) {
|
||||||
{
|
|
||||||
//sine true returns El
|
//sine true returns El
|
||||||
//sine false return Er
|
//sine false return Er
|
||||||
//Er values start at 60 in the Table47A_El_Er array.
|
//Er values start at 60 in the Table47A_El_Er array.
|
||||||
|
|
||||||
int nl = l * 4;
|
Int32 nl = l * 4;
|
||||||
|
|
||||||
if (sine)
|
if (sine) {
|
||||||
{
|
Double e = 1;
|
||||||
double e = 1;
|
|
||||||
|
|
||||||
if (Table47A_Arguments[nl + 1] != 0)
|
if (Table47A_Arguments[nl + 1] != 0) {
|
||||||
{
|
|
||||||
e = 1 - .002516 * t - .0000074 * Math.Pow(t, 2);
|
e = 1 - .002516 * t - .0000074 * Math.Pow(t, 2);
|
||||||
|
|
||||||
if (Math.Abs(Table47A_Arguments[nl + 1]) == 2)
|
if (Math.Abs(Table47A_Arguments[nl + 1]) == 2) {
|
||||||
{
|
|
||||||
e *= e;
|
e *= e;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return (Table47A_El_Er[l] * e) * Math.Sin(Table47A_Arguments[nl] * values[0] + Table47A_Arguments[nl + 1] * values[1] +
|
return Table47A_El_Er[l] * e * Math.Sin(Table47A_Arguments[nl] * values[0] + Table47A_Arguments[nl + 1] * values[1] + Table47A_Arguments[nl + 2] * values[2] + Table47A_Arguments[nl + 3] * values[3]);
|
||||||
Table47A_Arguments[nl + 2] * values[2] + Table47A_Arguments[nl + 3] * values[3]);
|
} else {
|
||||||
}
|
Double e = 1;
|
||||||
else
|
if (Table47A_Arguments[nl + 1] != 0) {
|
||||||
{
|
|
||||||
double e = 1;
|
|
||||||
if (Table47A_Arguments[nl + 1] != 0)
|
|
||||||
{
|
|
||||||
e = 1 - .002516 * t - .0000074 * Math.Pow(t, 2);
|
e = 1 - .002516 * t - .0000074 * Math.Pow(t, 2);
|
||||||
|
|
||||||
if (Math.Abs(Table47A_Arguments[nl + 1]) == 2)
|
if (Math.Abs(Table47A_Arguments[nl + 1]) == 2) {
|
||||||
{
|
|
||||||
e *= e;
|
e *= e;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return (Table47A_El_Er[l + 60] * e) * Math.Cos(Table47A_Arguments[nl] * values[0] + Table47A_Arguments[nl + 1] * values[1] +
|
return Table47A_El_Er[l + 60] * e * Math.Cos(Table47A_Arguments[nl] * values[0] + Table47A_Arguments[nl + 1] * values[1] + Table47A_Arguments[nl + 2] * values[2] + Table47A_Arguments[nl + 3] * values[3]);
|
||||||
Table47A_Arguments[nl + 2] * values[2] + Table47A_Arguments[nl + 3] * values[3]);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
private static double Get_Table47B_Values(double[] values, int l, double t)
|
private static Double Get_Table47B_Values(Double[] values, Int32 l, Double t) {
|
||||||
{
|
Int32 nl = l * 4;
|
||||||
int nl = l * 4;
|
Double e = 1;
|
||||||
double e = 1;
|
|
||||||
|
|
||||||
if (Table47B_Arguments[nl + 1] != 0)
|
if (Table47B_Arguments[nl + 1] != 0) {
|
||||||
{
|
|
||||||
e = 1 - .002516 * t - .0000074 * Math.Pow(t, 2);
|
e = 1 - .002516 * t - .0000074 * Math.Pow(t, 2);
|
||||||
|
|
||||||
if (Math.Abs(Table47B_Arguments[nl + 1]) == 2)
|
if (Math.Abs(Table47B_Arguments[nl + 1]) == 2) {
|
||||||
{
|
|
||||||
e *= e;
|
e *= e;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return (Table47B_Eb[l] * e) * Math.Sin(Table47B_Arguments[nl] * values[0] + Table47B_Arguments[nl + 1] * values[1] +
|
return Table47B_Eb[l] * e * Math.Sin(Table47B_Arguments[nl] * values[0] + Table47B_Arguments[nl + 1] * values[1] + Table47B_Arguments[nl + 2] * values[2] + Table47B_Arguments[nl + 3] * values[3]);
|
||||||
Table47B_Arguments[nl + 2] * values[2] + Table47B_Arguments[nl + 3] * values[3]);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -1,19 +1,17 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
namespace CoordinateSharp
|
|
||||||
{
|
namespace CoordinateSharp {
|
||||||
internal class SunCalc
|
internal class SunCalc {
|
||||||
{
|
public static void CalculateSunTime(Double lat, Double longi, DateTime date, Celestial c, Double _ = 0) {
|
||||||
public static void CalculateSunTime(double lat, double longi, DateTime date, Celestial c,double offset = 0)
|
|
||||||
{
|
|
||||||
if (date.Year == 0001) { return; } //Return if date vaue hasn't been established.
|
if (date.Year == 0001) { return; } //Return if date vaue hasn't been established.
|
||||||
DateTime actualDate = new DateTime(date.Year, date.Month, date.Day, 0, 0, 0, DateTimeKind.Utc);
|
DateTime actualDate = new DateTime(date.Year, date.Month, date.Day, 0, 0, 0, DateTimeKind.Utc);
|
||||||
|
|
||||||
////Sun Time Calculations
|
////Sun Time Calculations
|
||||||
|
|
||||||
//Get Julian
|
//Get Julian
|
||||||
double lw = rad * -longi;
|
Double lw = rad * -longi;
|
||||||
double phi = rad * lat;
|
Double phi = rad * lat;
|
||||||
|
|
||||||
//Rise Set
|
//Rise Set
|
||||||
DateTime?[] evDate = Get_Event_Time(lw, phi, -.8333, actualDate);
|
DateTime?[] evDate = Get_Event_Time(lw, phi, -.8333, actualDate);
|
||||||
@ -24,28 +22,16 @@ namespace CoordinateSharp
|
|||||||
//Azimuth and Altitude
|
//Azimuth and Altitude
|
||||||
CalculateSunAngle(date, longi, lat, c);
|
CalculateSunAngle(date, longi, lat, c);
|
||||||
// neither sunrise nor sunset
|
// neither sunrise nor sunset
|
||||||
if ((!c.SunRise.HasValue) && (!c.SunSet.HasValue))
|
if (!c.SunRise.HasValue && !c.SunSet.HasValue) {
|
||||||
{
|
c.sunCondition = c.SunAltitude < 0 ? CelestialStatus.DownAllDay : CelestialStatus.UpAllDay;
|
||||||
if (c.SunAltitude < 0)
|
|
||||||
{
|
|
||||||
c.sunCondition = CelestialStatus.DownAllDay;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
c.sunCondition = CelestialStatus.UpAllDay;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
// sunrise or sunset
|
// sunrise or sunset
|
||||||
else
|
else {
|
||||||
{
|
if (!c.SunRise.HasValue) {
|
||||||
if (!c.SunRise.HasValue)
|
|
||||||
{
|
|
||||||
// No sunrise this date
|
// No sunrise this date
|
||||||
c.sunCondition = CelestialStatus.NoRise;
|
c.sunCondition = CelestialStatus.NoRise;
|
||||||
|
|
||||||
}
|
} else if (!c.SunSet.HasValue) {
|
||||||
else if (!c.SunSet.HasValue)
|
|
||||||
{
|
|
||||||
// No sunset this date
|
// No sunset this date
|
||||||
c.sunCondition = CelestialStatus.NoSet;
|
c.sunCondition = CelestialStatus.NoSet;
|
||||||
}
|
}
|
||||||
@ -86,34 +72,32 @@ namespace CoordinateSharp
|
|||||||
/// <param name="h">Angle in Degrees</param>
|
/// <param name="h">Angle in Degrees</param>
|
||||||
/// <param name="date">Date of Event</param>
|
/// <param name="date">Date of Event</param>
|
||||||
/// <returns>DateTime?[]{rise, set}</returns>
|
/// <returns>DateTime?[]{rise, set}</returns>
|
||||||
private static DateTime?[] Get_Event_Time(double lw, double phi, double h,DateTime date)
|
private static DateTime?[] Get_Event_Time(Double lw, Double phi, Double h, DateTime date) {
|
||||||
{
|
|
||||||
//Create arrays. Index 0 = Day -1, 1 = Day, 2 = Day + 1;
|
//Create arrays. Index 0 = Day -1, 1 = Day, 2 = Day + 1;
|
||||||
//These will be used to find exact day event occurs for comparison
|
//These will be used to find exact day event occurs for comparison
|
||||||
DateTime?[] sets = new DateTime?[] { null, null, null, null, null };
|
DateTime?[] sets = new DateTime?[] { null, null, null, null, null };
|
||||||
DateTime?[] rises = new DateTime?[] { null, null, null, null, null };
|
DateTime?[] rises = new DateTime?[] { null, null, null, null, null };
|
||||||
|
|
||||||
//Iterate starting with day -1;
|
//Iterate starting with day -1;
|
||||||
for (int x = 0; x < 5; x++)
|
for (Int32 x = 0; x < 5; x++) {
|
||||||
{
|
Double d = JulianConversions.GetJulian(date.AddDays(x - 2)) - j2000 + .5; //LESS PRECISE JULIAN NEEDED
|
||||||
double d = JulianConversions.GetJulian(date.AddDays(x-2)) - j2000 + .5; //LESS PRECISE JULIAN NEEDED
|
|
||||||
|
|
||||||
double n = julianCycle(d, lw);
|
Double n = JulianCycle(d, lw);
|
||||||
double ds = approxTransit(0, lw, n);
|
Double ds = ApproxTransit(0, lw, n);
|
||||||
|
|
||||||
double M = solarMeanAnomaly(ds);
|
Double M = SolarMeanAnomaly(ds);
|
||||||
double L = eclipticLongitude(M);
|
Double L = EclipticLongitude(M);
|
||||||
|
|
||||||
double dec = declination(L, 0);
|
Double dec = Declination(L, 0);
|
||||||
|
|
||||||
double Jnoon = solarTransitJ(ds, M, L);
|
Double Jnoon = SolarTransitJ(ds, M, L);
|
||||||
|
|
||||||
double Jset;
|
Double Jset;
|
||||||
double Jrise;
|
Double Jrise;
|
||||||
|
|
||||||
|
|
||||||
DateTime? solarNoon = JulianConversions.GetDate_FromJulian(Jnoon);
|
//DateTime? solarNoon = JulianConversions.GetDate_FromJulian(Jnoon);
|
||||||
DateTime? nadir = JulianConversions.GetDate_FromJulian(Jnoon - 0.5);
|
//DateTime? nadir = JulianConversions.GetDate_FromJulian(Jnoon - 0.5);
|
||||||
|
|
||||||
//Rise Set
|
//Rise Set
|
||||||
Jset = GetTime(h * rad, lw, phi, dec, n, M, L);
|
Jset = GetTime(h * rad, lw, phi, dec, n, M, L);
|
||||||
@ -128,24 +112,18 @@ namespace CoordinateSharp
|
|||||||
|
|
||||||
//Compare and send
|
//Compare and send
|
||||||
DateTime? tRise = null;
|
DateTime? tRise = null;
|
||||||
for(int x=0;x<5;x++)
|
for (Int32 x = 0; x < 5; x++) {
|
||||||
{
|
if (rises[x].HasValue) {
|
||||||
if(rises[x].HasValue)
|
if (rises[x].Value.Day == date.Day) {
|
||||||
{
|
|
||||||
if(rises[x].Value.Day == date.Day)
|
|
||||||
{
|
|
||||||
tRise = rises[x];
|
tRise = rises[x];
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
DateTime? tSet = null;
|
DateTime? tSet = null;
|
||||||
for (int x = 0; x < 5; x++)
|
for (Int32 x = 0; x < 5; x++) {
|
||||||
{
|
if (sets[x].HasValue) {
|
||||||
if (sets[x].HasValue)
|
if (sets[x].Value.Day == date.Day) {
|
||||||
{
|
|
||||||
if (sets[x].Value.Day == date.Day)
|
|
||||||
{
|
|
||||||
tSet = sets[x];
|
tSet = sets[x];
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -154,8 +132,7 @@ namespace CoordinateSharp
|
|||||||
return new DateTime?[] { tRise, tSet };
|
return new DateTime?[] { tRise, tSet };
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void CalculateZodiacSign(DateTime date, Celestial c)
|
public static void CalculateZodiacSign(DateTime date, Celestial c) {
|
||||||
{
|
|
||||||
//Aquarius (January 20 to February 18)
|
//Aquarius (January 20 to February 18)
|
||||||
//Pisces (February 19 to March 20)
|
//Pisces (February 19 to March 20)
|
||||||
//Aries (March 21-April 19)
|
//Aries (March 21-April 19)
|
||||||
@ -168,89 +145,74 @@ namespace CoordinateSharp
|
|||||||
//Scorpio (October 23-November 21)
|
//Scorpio (October 23-November 21)
|
||||||
//Sagittarius (November 22-December 21)
|
//Sagittarius (November 22-December 21)
|
||||||
//Capricorn (December 22-January 19)
|
//Capricorn (December 22-January 19)
|
||||||
if (date >= new DateTime(date.Year, 1, 1) && date <= new DateTime(date.Year, 1, 19, 23, 59, 59))
|
if (date >= new DateTime(date.Year, 1, 1) && date <= new DateTime(date.Year, 1, 19, 23, 59, 59)) {
|
||||||
{
|
|
||||||
c.AstrologicalSigns.ZodiacSign = "Capricorn";
|
c.AstrologicalSigns.ZodiacSign = "Capricorn";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (date >= new DateTime(date.Year, 1, 20) && date <= new DateTime(date.Year, 2, 18, 23, 59, 59))
|
if (date >= new DateTime(date.Year, 1, 20) && date <= new DateTime(date.Year, 2, 18, 23, 59, 59)) {
|
||||||
{
|
|
||||||
c.AstrologicalSigns.ZodiacSign = "Aquarius";
|
c.AstrologicalSigns.ZodiacSign = "Aquarius";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (date >= new DateTime(date.Year, 2, 19) && date <= new DateTime(date.Year, 3, 20, 23, 59, 59))
|
if (date >= new DateTime(date.Year, 2, 19) && date <= new DateTime(date.Year, 3, 20, 23, 59, 59)) {
|
||||||
{
|
|
||||||
c.AstrologicalSigns.ZodiacSign = "Pisces";
|
c.AstrologicalSigns.ZodiacSign = "Pisces";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (date >= new DateTime(date.Year, 3, 21) && date <= new DateTime(date.Year, 4, 19, 23, 59, 59))
|
if (date >= new DateTime(date.Year, 3, 21) && date <= new DateTime(date.Year, 4, 19, 23, 59, 59)) {
|
||||||
{
|
|
||||||
c.AstrologicalSigns.ZodiacSign = "Aries";
|
c.AstrologicalSigns.ZodiacSign = "Aries";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (date >= new DateTime(date.Year, 4, 20) && date <= new DateTime(date.Year, 5, 20, 23, 59, 59))
|
if (date >= new DateTime(date.Year, 4, 20) && date <= new DateTime(date.Year, 5, 20, 23, 59, 59)) {
|
||||||
{
|
|
||||||
c.AstrologicalSigns.ZodiacSign = "Taurus";
|
c.AstrologicalSigns.ZodiacSign = "Taurus";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (date >= new DateTime(date.Year, 5, 21) && date <= new DateTime(date.Year, 6, 20,23,59,59))
|
if (date >= new DateTime(date.Year, 5, 21) && date <= new DateTime(date.Year, 6, 20, 23, 59, 59)) {
|
||||||
{
|
|
||||||
c.AstrologicalSigns.ZodiacSign = "Gemini";
|
c.AstrologicalSigns.ZodiacSign = "Gemini";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (date >= new DateTime(date.Year, 6, 21) && date <= new DateTime(date.Year, 7, 22, 23, 59, 59))
|
if (date >= new DateTime(date.Year, 6, 21) && date <= new DateTime(date.Year, 7, 22, 23, 59, 59)) {
|
||||||
{
|
|
||||||
c.AstrologicalSigns.ZodiacSign = "Cancer";
|
c.AstrologicalSigns.ZodiacSign = "Cancer";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (date >= new DateTime(date.Year, 7, 23) && date <= new DateTime(date.Year, 8, 22, 23, 59, 59))
|
if (date >= new DateTime(date.Year, 7, 23) && date <= new DateTime(date.Year, 8, 22, 23, 59, 59)) {
|
||||||
{
|
|
||||||
c.AstrologicalSigns.ZodiacSign = "Leo";
|
c.AstrologicalSigns.ZodiacSign = "Leo";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (date >= new DateTime(date.Year, 8, 23) && date <= new DateTime(date.Year, 9, 22, 23, 59, 59))
|
if (date >= new DateTime(date.Year, 8, 23) && date <= new DateTime(date.Year, 9, 22, 23, 59, 59)) {
|
||||||
{
|
|
||||||
c.AstrologicalSigns.ZodiacSign = "Virgo";
|
c.AstrologicalSigns.ZodiacSign = "Virgo";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (date >= new DateTime(date.Year, 9, 23) && date <= new DateTime(date.Year, 10, 22, 23, 59, 59))
|
if (date >= new DateTime(date.Year, 9, 23) && date <= new DateTime(date.Year, 10, 22, 23, 59, 59)) {
|
||||||
{
|
|
||||||
c.AstrologicalSigns.ZodiacSign = "Libra";
|
c.AstrologicalSigns.ZodiacSign = "Libra";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (date >= new DateTime(date.Year, 9, 23) && date <= new DateTime(date.Year, 11, 21, 23, 59, 59))
|
if (date >= new DateTime(date.Year, 9, 23) && date <= new DateTime(date.Year, 11, 21, 23, 59, 59)) {
|
||||||
{
|
|
||||||
c.AstrologicalSigns.ZodiacSign = "Scorpio";
|
c.AstrologicalSigns.ZodiacSign = "Scorpio";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (date >= new DateTime(date.Year, 11, 21) && date <= new DateTime(date.Year, 12, 21, 23, 59, 59))
|
if (date >= new DateTime(date.Year, 11, 21) && date <= new DateTime(date.Year, 12, 21, 23, 59, 59)) {
|
||||||
{
|
|
||||||
c.AstrologicalSigns.ZodiacSign = "Sagittarius";
|
c.AstrologicalSigns.ZodiacSign = "Sagittarius";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (date >= new DateTime(date.Year, 12, 22) && date <= new DateTime(date.Year, 12, 31, 23, 59, 59))
|
if (date >= new DateTime(date.Year, 12, 22) && date <= new DateTime(date.Year, 12, 31, 23, 59, 59)) {
|
||||||
{
|
|
||||||
c.AstrologicalSigns.ZodiacSign = "Capricorn";
|
c.AstrologicalSigns.ZodiacSign = "Capricorn";
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
public static void CalculateSolarEclipse(DateTime date, double lat, double longi, Celestial c)
|
public static void CalculateSolarEclipse(DateTime date, Double lat, Double longi, Celestial c) {
|
||||||
{
|
|
||||||
//Convert to Radian
|
//Convert to Radian
|
||||||
double latR = lat * Math.PI / 180;
|
Double latR = lat * Math.PI / 180;
|
||||||
double longR = longi * Math.PI / 180;
|
Double longR = longi * Math.PI / 180;
|
||||||
List<List<string>> se = SolarEclipseCalc.CalculateSolarEclipse(date, latR, longR);
|
List<List<String>> se = SolarEclipseCalc.CalculateSolarEclipse(date, latR, longR);
|
||||||
//RETURN FIRST AND LAST
|
//RETURN FIRST AND LAST
|
||||||
if (se.Count == 0) { return; }
|
if (se.Count == 0) { return; }
|
||||||
//FIND LAST AND NEXT ECLIPSE
|
//FIND LAST AND NEXT ECLIPSE
|
||||||
int lastE = -1;
|
Int32 lastE = -1;
|
||||||
int nextE = -1;
|
Int32 nextE = -1;
|
||||||
int currentE = 0;
|
Int32 currentE = 0;
|
||||||
DateTime lastDate = new DateTime();
|
DateTime lastDate = new DateTime();
|
||||||
DateTime nextDate = new DateTime(3300, 1, 1);
|
DateTime nextDate = new DateTime(3300, 1, 1);
|
||||||
//Iterate to get last and next eclipse
|
//Iterate to get last and next eclipse
|
||||||
foreach(List<string> values in se)
|
foreach (List<String> values in se) {
|
||||||
{
|
|
||||||
DateTime ld = DateTime.ParseExact(values[0], "yyyy-MMM-dd", System.Globalization.CultureInfo.InvariantCulture);
|
DateTime ld = DateTime.ParseExact(values[0], "yyyy-MMM-dd", System.Globalization.CultureInfo.InvariantCulture);
|
||||||
|
|
||||||
if (ld < date && ld > lastDate) { lastDate = ld; lastE = currentE; }
|
if (ld < date && ld > lastDate) { lastDate = ld; lastE = currentE; }
|
||||||
@ -258,112 +220,94 @@ namespace CoordinateSharp
|
|||||||
currentE++;
|
currentE++;
|
||||||
}
|
}
|
||||||
//SET ECLIPSE DATA
|
//SET ECLIPSE DATA
|
||||||
if (lastE >= 0)
|
if (lastE >= 0) {
|
||||||
{
|
|
||||||
c.SolarEclipse.LastEclipse = new SolarEclipseDetails(se[lastE]);
|
c.SolarEclipse.LastEclipse = new SolarEclipseDetails(se[lastE]);
|
||||||
}
|
}
|
||||||
if (nextE >= 0)
|
if (nextE >= 0) {
|
||||||
{
|
|
||||||
c.SolarEclipse.NextEclipse = new SolarEclipseDetails(se[nextE]);
|
c.SolarEclipse.NextEclipse = new SolarEclipseDetails(se[nextE]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#region Private Suntime Members
|
#region Private Suntime Members
|
||||||
private static readonly double dayMS = 1000 * 60 * 60 * 24, j1970 = 2440588, j2000 = 2451545;
|
private static readonly Double dayMS = 1000 * 60 * 60 * 24, j1970 = 2440588, j2000 = 2451545;
|
||||||
private static readonly double rad = Math.PI / 180;
|
private static readonly Double rad = Math.PI / 180;
|
||||||
|
|
||||||
private static double LocalSiderealTimeForTimeZone(double lon, double jd, double z)
|
/*private static Double LocalSiderealTimeForTimeZone(Double lon, Double jd, Double z)
|
||||||
{
|
{
|
||||||
double s = 24110.5 + 8640184.812999999 * jd / 36525 + 86636.6 * z + 86400 * lon;
|
Double s = 24110.5 + 8640184.812999999 * jd / 36525 + 86636.6 * z + 86400 * lon;
|
||||||
s = s / 86400;
|
s = s / 86400;
|
||||||
s = s - Math.Truncate(s);
|
s = s - Math.Truncate(s);
|
||||||
double lst = s * 360 *rad;
|
Double lst = s * 360 *rad;
|
||||||
|
|
||||||
return lst;
|
return lst;
|
||||||
}
|
}*/
|
||||||
private static double SideRealTime(double d, double lw)
|
private static Double SideRealTime(Double d, Double lw) {
|
||||||
{
|
Double s = rad * (280.16 + 360.9856235 * d) - lw;
|
||||||
double s = rad * (280.16 + 360.9856235 * d) - lw;
|
|
||||||
return s;
|
return s;
|
||||||
}
|
}
|
||||||
private static double solarTransitJ(double ds, double M, double L)
|
private static Double SolarTransitJ(Double ds, Double M, Double L) => j2000 + ds + 0.0053 * Math.Sin(M) - 0.0069 * Math.Sin(2 * L);
|
||||||
{
|
|
||||||
return j2000 + ds + 0.0053 * Math.Sin(M) - 0.0069 * Math.Sin(2 * L);
|
|
||||||
}
|
|
||||||
|
|
||||||
//CH15
|
//CH15
|
||||||
//Formula 15.1
|
//Formula 15.1
|
||||||
//Returns Approximate Time
|
//Returns Approximate Time
|
||||||
private static double hourAngle(double h, double phi, double d)
|
private static Double HourAngle(Double h, Double phi, Double d) {
|
||||||
{
|
|
||||||
//NUMBER RETURNING > and < 1 NaN;
|
//NUMBER RETURNING > and < 1 NaN;
|
||||||
double d1 = Math.Sin(h) - Math.Sin(phi) * Math.Sin(d);
|
Double d1 = Math.Sin(h) - Math.Sin(phi) * Math.Sin(d);
|
||||||
double d2 = Math.Cos(phi) * Math.Cos(d);
|
Double d2 = Math.Cos(phi) * Math.Cos(d);
|
||||||
double d3 = (d1 / d2);
|
Double d3 = d1 / d2;
|
||||||
|
|
||||||
return Math.Acos(d3);
|
return Math.Acos(d3);
|
||||||
}
|
}
|
||||||
private static double approxTransit(double Ht, double lw, double n)
|
private static Double ApproxTransit(Double Ht, Double lw, Double n) => 0.0009 + (Ht + lw) / (2 * Math.PI) + n;
|
||||||
{
|
|
||||||
return 0.0009 + (Ht + lw) / (2 * Math.PI) + n;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static double julianCycle(double d, double lw) { return Math.Round(d - 0.0009 - lw / (2 * Math.PI)); }
|
private static Double JulianCycle(Double d, Double lw) => Math.Round(d - 0.0009 - lw / (2 * Math.PI));
|
||||||
|
|
||||||
//Returns Time of specified event based on suns angle
|
//Returns Time of specified event based on suns angle
|
||||||
private static double GetTime(double h, double lw, double phi, double dec, double n,double M, double L)
|
private static Double GetTime(Double h, Double lw, Double phi, Double dec, Double n, Double M, Double L) {
|
||||||
{
|
Double approxTime = HourAngle(h, phi, dec); //Ch15 Formula 15.1
|
||||||
double approxTime = hourAngle(h, phi, dec); //Ch15 Formula 15.1
|
|
||||||
|
|
||||||
double a = approxTransit(approxTime, lw, n);
|
Double a = ApproxTransit(approxTime, lw, n);
|
||||||
double st = solarTransitJ(a, M, L);
|
Double st = SolarTransitJ(a, M, L);
|
||||||
|
|
||||||
return st;
|
return st;
|
||||||
}
|
}
|
||||||
private static double declination(double l, double b)
|
private static Double Declination(Double l, Double b) {
|
||||||
{
|
Double e = Math.PI / 180 * 23.4392911; // obliquity of the Earth
|
||||||
double e = (Math.PI/180) * 23.4392911; // obliquity of the Earth
|
|
||||||
|
|
||||||
return Math.Asin(Math.Sin(b) * Math.Cos(e) + Math.Cos(b) * Math.Sin(e) * Math.Sin(l));
|
return Math.Asin(Math.Sin(b) * Math.Cos(e) + Math.Cos(b) * Math.Sin(e) * Math.Sin(l));
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void CalculateSunAngle(DateTime date, double longi, double lat, Celestial c)
|
private static void CalculateSunAngle(DateTime date, Double longi, Double lat, Celestial c) {
|
||||||
{
|
|
||||||
TimeSpan ts = date - new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc);
|
TimeSpan ts = date - new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc);
|
||||||
double dms = (ts.TotalMilliseconds / dayMS -.5 + j1970)-j2000;
|
Double dms = ts.TotalMilliseconds / dayMS - .5 + j1970 - j2000;
|
||||||
|
|
||||||
double lw = rad * -longi;
|
Double lw = rad * -longi;
|
||||||
double phi = rad * lat;
|
Double phi = rad * lat;
|
||||||
double e = rad * 23.4397;
|
//Double e = rad * 23.4397;
|
||||||
|
|
||||||
double[] sc = sunCoords(dms);
|
Double[] sc = SunCoords(dms);
|
||||||
|
|
||||||
double H = SideRealTime(dms, lw) - sc[1];
|
Double H = SideRealTime(dms, lw) - sc[1];
|
||||||
|
|
||||||
c.sunAzimuth = Math.Atan2(Math.Sin(H), Math.Cos(H) * Math.Sin(phi) - Math.Tan(sc[0]) * Math.Cos(phi)) * 180 / Math.PI + 180;
|
c.sunAzimuth = Math.Atan2(Math.Sin(H), Math.Cos(H) * Math.Sin(phi) - Math.Tan(sc[0]) * Math.Cos(phi)) * 180 / Math.PI + 180;
|
||||||
c.sunAltitude = Math.Asin(Math.Sin(phi) * Math.Sin(sc[0]) + Math.Cos(phi) * Math.Cos(sc[0]) * Math.Cos(H)) * 180 / Math.PI;
|
c.sunAltitude = Math.Asin(Math.Sin(phi) * Math.Sin(sc[0]) + Math.Cos(phi) * Math.Cos(sc[0]) * Math.Cos(H)) * 180 / Math.PI;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static double solarMeanAnomaly(double d)
|
private static Double SolarMeanAnomaly(Double d) => rad * (357.5291 + 0.98560028 * d);
|
||||||
{
|
|
||||||
return rad * (357.5291 + 0.98560028 * d);
|
|
||||||
}
|
|
||||||
|
|
||||||
private static double eclipticLongitude(double m)
|
private static Double EclipticLongitude(Double m) {
|
||||||
{
|
Double c = rad * (1.9148 * Math.Sin(m) + 0.02 * Math.Sin(2 * m) + 0.0003 * Math.Sin(3 * m)); // equation of center
|
||||||
double c = rad * (1.9148 * Math.Sin(m) + 0.02 * Math.Sin(2 * m) + 0.0003 * Math.Sin(3 * m)); // equation of center
|
Double p = rad * 102.9372; // perihelion of the Earth
|
||||||
double p = rad * 102.9372; // perihelion of the Earth
|
|
||||||
|
|
||||||
return m + c + p + Math.PI;
|
return m + c + p + Math.PI;
|
||||||
}
|
}
|
||||||
private static double[] sunCoords(double d)
|
private static Double[] SunCoords(Double d) {
|
||||||
{
|
|
||||||
|
|
||||||
double m = solarMeanAnomaly(d);
|
Double m = SolarMeanAnomaly(d);
|
||||||
double l = eclipticLongitude(m);
|
Double l = EclipticLongitude(m);
|
||||||
double[] sc = new double[2];
|
Double[] sc = new Double[2];
|
||||||
double b = 0;
|
Double b = 0;
|
||||||
double e = rad * 23.4397; // obliquity of the Earth
|
Double e = rad * 23.4397; // obliquity of the Earth
|
||||||
sc[0] = Math.Asin(Math.Sin(b) * Math.Cos(e) + Math.Cos(b) * Math.Sin(e) * Math.Sin(l)); //declination
|
sc[0] = Math.Asin(Math.Sin(b) * Math.Cos(e) + Math.Cos(b) * Math.Sin(e) * Math.Sin(l)); //declination
|
||||||
sc[1] = Math.Atan2(Math.Sin(l) * Math.Cos(e) - Math.Tan(b) * Math.Sin(e), Math.Cos(l)); //rightAscension
|
sc[1] = Math.Atan2(Math.Sin(l) * Math.Cos(e) - Math.Tan(b) * Math.Sin(e), Math.Cos(l)); //rightAscension
|
||||||
return sc;
|
return sc;
|
||||||
|
@ -1,8 +1,7 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.ComponentModel;
|
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
namespace CoordinateSharp
|
|
||||||
{
|
namespace CoordinateSharp {
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// The main class for handling location based celestial information.
|
/// The main class for handling location based celestial information.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -10,29 +9,26 @@ namespace CoordinateSharp
|
|||||||
/// This class can calculate various pieces of solar and lunar data, based on location and date
|
/// This class can calculate various pieces of solar and lunar data, based on location and date
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public class Celestial
|
public class Celestial {
|
||||||
{
|
|
||||||
|
|
||||||
//When a rise or a set does not occur, the DateTime will return null
|
//When a rise or a set does not occur, the DateTime will return null
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Creates an empty Celestial.
|
/// Creates an empty Celestial.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public Celestial()
|
public Celestial() {
|
||||||
{
|
this.astrologicalSigns = new AstrologicalSigns();
|
||||||
astrologicalSigns = new AstrologicalSigns();
|
this.lunarEclipse = new LunarEclipse();
|
||||||
lunarEclipse = new LunarEclipse();
|
this.solarEclipse = new SolarEclipse();
|
||||||
solarEclipse = new SolarEclipse();
|
this.CalculateCelestialTime(0, 0, new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc));
|
||||||
CalculateCelestialTime(0, 0, new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private Celestial(bool hasCalcs)
|
private Celestial(Boolean hasCalcs) {
|
||||||
{
|
|
||||||
|
|
||||||
astrologicalSigns = new AstrologicalSigns();
|
this.astrologicalSigns = new AstrologicalSigns();
|
||||||
lunarEclipse = new LunarEclipse();
|
this.lunarEclipse = new LunarEclipse();
|
||||||
solarEclipse = new SolarEclipse();
|
this.solarEclipse = new SolarEclipse();
|
||||||
if (hasCalcs) { CalculateCelestialTime(0, 0, new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc)); }
|
if (hasCalcs) { this.CalculateCelestialTime(0, 0, new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc)); }
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@ -41,13 +37,12 @@ namespace CoordinateSharp
|
|||||||
/// <param name="lat">latitude</param>
|
/// <param name="lat">latitude</param>
|
||||||
/// <param name="longi">longitude</param>
|
/// <param name="longi">longitude</param>
|
||||||
/// <param name="geoDate">DateTime (UTC)</param>
|
/// <param name="geoDate">DateTime (UTC)</param>
|
||||||
public Celestial(double lat, double longi, DateTime geoDate)
|
public Celestial(Double lat, Double longi, DateTime geoDate) {
|
||||||
{
|
|
||||||
DateTime d = new DateTime(geoDate.Year, geoDate.Month, geoDate.Day, geoDate.Hour, geoDate.Minute, geoDate.Second, DateTimeKind.Utc);
|
DateTime d = new DateTime(geoDate.Year, geoDate.Month, geoDate.Day, geoDate.Hour, geoDate.Minute, geoDate.Second, DateTimeKind.Utc);
|
||||||
astrologicalSigns = new AstrologicalSigns();
|
this.astrologicalSigns = new AstrologicalSigns();
|
||||||
lunarEclipse = new LunarEclipse();
|
this.lunarEclipse = new LunarEclipse();
|
||||||
solarEclipse = new SolarEclipse();
|
this.solarEclipse = new SolarEclipse();
|
||||||
CalculateCelestialTime(lat, longi, d);
|
this.CalculateCelestialTime(lat, longi, d);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@ -55,11 +50,10 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="c">Coordinate</param>
|
/// <param name="c">Coordinate</param>
|
||||||
/// <returns>Celestial</returns>
|
/// <returns>Celestial</returns>
|
||||||
public static Celestial LoadCelestial(Coordinate c)
|
public static Celestial LoadCelestial(Coordinate c) {
|
||||||
{
|
//DateTime geoDate = c.GeoDate;
|
||||||
DateTime geoDate = c.GeoDate;
|
|
||||||
|
|
||||||
DateTime d = new DateTime(geoDate.Year, geoDate.Month, geoDate.Day, geoDate.Hour, geoDate.Minute, geoDate.Second, DateTimeKind.Utc);
|
//DateTime d = new DateTime(geoDate.Year, geoDate.Month, geoDate.Day, geoDate.Hour, geoDate.Minute, geoDate.Second, DateTimeKind.Utc);
|
||||||
Celestial cel = new Celestial(c.Latitude.ToDouble(), c.Longitude.ToDouble(), c.GeoDate);
|
Celestial cel = new Celestial(c.Latitude.ToDouble(), c.Longitude.ToDouble(), c.GeoDate);
|
||||||
|
|
||||||
return cel;
|
return cel;
|
||||||
@ -71,8 +65,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="c">Coordinate</param>
|
/// <param name="c">Coordinate</param>
|
||||||
/// <param name="offset">UTC offset</param>
|
/// <param name="offset">UTC offset</param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
public static Celestial Celestial_LocalTime(Coordinate c, double offset)
|
public static Celestial Celestial_LocalTime(Coordinate c, Double offset) {
|
||||||
{
|
|
||||||
if (offset < -12 || offset > 12) { throw new ArgumentOutOfRangeException("Time offsets cannot be greater 12 or less than -12."); }
|
if (offset < -12 || offset > 12) { throw new ArgumentOutOfRangeException("Time offsets cannot be greater 12 or less than -12."); }
|
||||||
//Probably need to offset initial UTC date so user can op in local
|
//Probably need to offset initial UTC date so user can op in local
|
||||||
//Determine best way to do this.
|
//Determine best way to do this.
|
||||||
@ -89,7 +82,7 @@ namespace CoordinateSharp
|
|||||||
celPost.Local_Convert(c, offset);
|
celPost.Local_Convert(c, offset);
|
||||||
|
|
||||||
//Get SunSet
|
//Get SunSet
|
||||||
int i = Determine_Slipped_Event_Index(cel.SunSet, celPre.SunSet, celPost.SunSet, d);
|
Int32 i = Determine_Slipped_Event_Index(cel.SunSet, celPre.SunSet, celPost.SunSet, d);
|
||||||
cel.sunSet = Get_Correct_Slipped_Date(cel.SunSet, celPre.SunSet, celPost.SunSet, i);
|
cel.sunSet = Get_Correct_Slipped_Date(cel.SunSet, celPre.SunSet, celPost.SunSet, i);
|
||||||
cel.AdditionalSolarTimes.CivilDusk = Get_Correct_Slipped_Date(cel.AdditionalSolarTimes.CivilDusk,
|
cel.AdditionalSolarTimes.CivilDusk = Get_Correct_Slipped_Date(cel.AdditionalSolarTimes.CivilDusk,
|
||||||
celPre.AdditionalSolarTimes.CivilDusk, celPost.AdditionalSolarTimes.CivilDusk, i);
|
celPre.AdditionalSolarTimes.CivilDusk, celPost.AdditionalSolarTimes.CivilDusk, i);
|
||||||
@ -129,15 +122,12 @@ namespace CoordinateSharp
|
|||||||
return cel;
|
return cel;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static CelestialStatus GetStatus(DateTime? rise, DateTime? set, CelestialStatus[] cels)
|
private static CelestialStatus GetStatus(DateTime? rise, DateTime? set, CelestialStatus[] cels) {
|
||||||
{
|
|
||||||
if (set.HasValue && rise.HasValue) { return CelestialStatus.RiseAndSet; }
|
if (set.HasValue && rise.HasValue) { return CelestialStatus.RiseAndSet; }
|
||||||
if (set.HasValue && !rise.HasValue) { return CelestialStatus.NoRise; }
|
if (set.HasValue && !rise.HasValue) { return CelestialStatus.NoRise; }
|
||||||
if (!set.HasValue && rise.HasValue) { return CelestialStatus.NoSet; }
|
if (!set.HasValue && rise.HasValue) { return CelestialStatus.NoSet; }
|
||||||
for (int x=0; x < 3;x++)
|
for (Int32 x = 0; x < 3; x++) {
|
||||||
{
|
if (cels[x] == CelestialStatus.DownAllDay || cels[x] == CelestialStatus.UpAllDay) {
|
||||||
if(cels[x] == CelestialStatus.DownAllDay || cels[x] == CelestialStatus.UpAllDay)
|
|
||||||
{
|
|
||||||
return cels[x];
|
return cels[x];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -149,31 +139,30 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="c">Coordinate</param>
|
/// <param name="c">Coordinate</param>
|
||||||
/// <param name="offset">hour offset</param>
|
/// <param name="offset">hour offset</param>
|
||||||
private void Local_Convert(Coordinate c, double offset)
|
private void Local_Convert(Coordinate c, Double offset) {
|
||||||
{
|
|
||||||
//Find new lunar set rise times
|
//Find new lunar set rise times
|
||||||
if (MoonSet.HasValue) { moonSet = moonSet.Value.AddHours(offset); }
|
if (this.MoonSet.HasValue) { this.moonSet = this.moonSet.Value.AddHours(offset); }
|
||||||
if (MoonRise.HasValue) { moonRise = moonRise.Value.AddHours(offset); }
|
if (this.MoonRise.HasValue) { this.moonRise = this.moonRise.Value.AddHours(offset); }
|
||||||
//Perigee
|
//Perigee
|
||||||
Perigee.ConvertTo_Local_Time(offset);
|
this.Perigee.ConvertTo_Local_Time(offset);
|
||||||
//Apogee
|
//Apogee
|
||||||
Apogee.ConvertTo_Local_Time(offset);
|
this.Apogee.ConvertTo_Local_Time(offset);
|
||||||
//Eclipse
|
//Eclipse
|
||||||
LunarEclipse.ConvertTo_LocalTime(offset);
|
this.LunarEclipse.ConvertTo_LocalTime(offset);
|
||||||
|
|
||||||
////Solar
|
////Solar
|
||||||
if (sunSet.HasValue) { sunSet = sunSet.Value.AddHours(offset); }
|
if (this.sunSet.HasValue) { this.sunSet = this.sunSet.Value.AddHours(offset); }
|
||||||
if (SunRise.HasValue) { sunRise = SunRise.Value.AddHours(offset); }
|
if (this.SunRise.HasValue) { this.sunRise = this.SunRise.Value.AddHours(offset); }
|
||||||
AdditionalSolarTimes.Convert_To_Local_Time(offset);
|
this.AdditionalSolarTimes.Convert_To_Local_Time(offset);
|
||||||
|
|
||||||
//Eclipse
|
//Eclipse
|
||||||
SolarEclipse.ConvertTo_LocalTime(offset);
|
this.SolarEclipse.ConvertTo_LocalTime(offset);
|
||||||
SunCalc.CalculateZodiacSign(c.GeoDate.AddHours(offset), this);
|
SunCalc.CalculateZodiacSign(c.GeoDate.AddHours(offset), this);
|
||||||
MoonCalc.GetMoonSign(c.GeoDate.AddHours(offset), this);
|
MoonCalc.GetMoonSign(c.GeoDate.AddHours(offset), this);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private PerigeeApogee Get_Correct_Slipped_Date(PerigeeApogee actual, PerigeeApogee pre, PerigeeApogee post, int i)
|
/*private PerigeeApogee Get_Correct_Slipped_Date(PerigeeApogee actual, PerigeeApogee pre, PerigeeApogee post, Int32 i)
|
||||||
{
|
{
|
||||||
switch (i)
|
switch (i)
|
||||||
{
|
{
|
||||||
@ -186,47 +175,31 @@ namespace CoordinateSharp
|
|||||||
default:
|
default:
|
||||||
return actual;
|
return actual;
|
||||||
}
|
}
|
||||||
}
|
}*/
|
||||||
private static DateTime? Get_Correct_Slipped_Date(DateTime? actual, DateTime? pre, DateTime? post, int i)
|
private static DateTime? Get_Correct_Slipped_Date(DateTime? actual, DateTime? pre, DateTime? post, Int32 i) => i switch
|
||||||
{
|
|
||||||
switch(i)
|
|
||||||
{
|
|
||||||
case 0:
|
|
||||||
return pre;
|
|
||||||
case 1:
|
|
||||||
return actual;
|
|
||||||
case 2:
|
|
||||||
return post;
|
|
||||||
default:
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
private static int Determine_Slipped_Event_Index(DateTime? actual, DateTime? pre, DateTime? post, DateTime d)
|
|
||||||
{
|
{
|
||||||
|
0 => pre,
|
||||||
|
1 => actual,
|
||||||
|
2 => post,
|
||||||
|
_ => null,
|
||||||
|
};
|
||||||
|
private static Int32 Determine_Slipped_Event_Index(DateTime? actual, DateTime? pre, DateTime? post, DateTime d) {
|
||||||
|
|
||||||
if (actual.HasValue)
|
if (actual.HasValue) {
|
||||||
{
|
if (actual.Value.Day != d.Day) {
|
||||||
if (actual.Value.Day != d.Day)
|
if (pre.HasValue) {
|
||||||
{
|
|
||||||
if (pre.HasValue)
|
|
||||||
{
|
|
||||||
if (pre.Value.Day == d.Day) { return 0; }
|
if (pre.Value.Day == d.Day) { return 0; }
|
||||||
}
|
}
|
||||||
if (post.HasValue)
|
if (post.HasValue) {
|
||||||
{
|
|
||||||
if (post.Value.Day == d.Day) { return 2; }
|
if (post.Value.Day == d.Day) { return 2; }
|
||||||
}
|
}
|
||||||
return 3;
|
return 3;
|
||||||
}
|
}
|
||||||
}
|
} else {
|
||||||
else
|
if (pre.HasValue) {
|
||||||
{
|
|
||||||
if (pre.HasValue)
|
|
||||||
{
|
|
||||||
if (pre.Value.Day == d.Day) { return 0; }
|
if (pre.Value.Day == d.Day) { return 0; }
|
||||||
}
|
}
|
||||||
if (post.HasValue)
|
if (post.HasValue) {
|
||||||
{
|
|
||||||
if (post.Value.Day == d.Day) { return 2; }
|
if (post.Value.Day == d.Day) { return 2; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -238,18 +211,18 @@ namespace CoordinateSharp
|
|||||||
internal DateTime? moonSet;
|
internal DateTime? moonSet;
|
||||||
internal DateTime? moonRise;
|
internal DateTime? moonRise;
|
||||||
|
|
||||||
internal double sunAltitude;
|
internal Double sunAltitude;
|
||||||
internal double sunAzimuth;
|
internal Double sunAzimuth;
|
||||||
internal double moonAltitude;
|
internal Double moonAltitude;
|
||||||
internal double moonAzimuth;
|
internal Double moonAzimuth;
|
||||||
|
|
||||||
internal Distance moonDistance;
|
internal Distance moonDistance;
|
||||||
|
|
||||||
internal CelestialStatus sunCondition;
|
internal CelestialStatus sunCondition;
|
||||||
internal CelestialStatus moonCondition;
|
internal CelestialStatus moonCondition;
|
||||||
|
|
||||||
internal bool isSunUp;
|
internal Boolean isSunUp;
|
||||||
internal bool isMoonUp;
|
internal Boolean isMoonUp;
|
||||||
|
|
||||||
internal MoonIllum moonIllum;
|
internal MoonIllum moonIllum;
|
||||||
internal Perigee perigee;
|
internal Perigee perigee;
|
||||||
@ -262,59 +235,59 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Sunset time.
|
/// Sunset time.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public DateTime? SunSet { get { return sunSet; } }
|
public DateTime? SunSet => this.sunSet;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Sunrise time.
|
/// Sunrise time.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public DateTime? SunRise { get { return sunRise; } }
|
public DateTime? SunRise => this.sunRise;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Moonset time.
|
/// Moonset time.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public DateTime? MoonSet { get { return moonSet; } }
|
public DateTime? MoonSet => this.moonSet;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Moonrise time.
|
/// Moonrise time.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public DateTime? MoonRise { get { return moonRise; } }
|
public DateTime? MoonRise => this.moonRise;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Sun altitude in degrees (E of N).
|
/// Sun altitude in degrees (E of N).
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double SunAltitude { get { return sunAltitude; } }
|
public Double SunAltitude => this.sunAltitude;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Sun azimuth in degrees (E of N).
|
/// Sun azimuth in degrees (E of N).
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double SunAzimuth { get { return sunAzimuth; } }
|
public Double SunAzimuth => this.sunAzimuth;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Moon altitude in degrees (corrected for parallax and refraction).
|
/// Moon altitude in degrees (corrected for parallax and refraction).
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double MoonAltitude { get { return moonAltitude; } }
|
public Double MoonAltitude => this.moonAltitude;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Moon azimuth in degrees (E of N).
|
/// Moon azimuth in degrees (E of N).
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double MoonAzimuth { get { return moonAzimuth; } }
|
public Double MoonAzimuth => this.moonAzimuth;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Estimated moon distance from the earth.
|
/// Estimated moon distance from the earth.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public Distance MoonDistance { get { return moonDistance; } }
|
public Distance MoonDistance => this.moonDistance;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Sun's Condition based on the provided date.
|
/// Sun's Condition based on the provided date.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public CelestialStatus SunCondition { get { return sunCondition; } }
|
public CelestialStatus SunCondition => this.sunCondition;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Moon's condition based on the provided date.
|
/// Moon's condition based on the provided date.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public CelestialStatus MoonCondition { get { return moonCondition; } }
|
public CelestialStatus MoonCondition => this.moonCondition;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Determine if the sun is currently up, based on sunset and sunrise time at the provided location and date.
|
/// Determine if the sun is currently up, based on sunset and sunrise time at the provided location and date.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool IsSunUp{ get { return isSunUp; } }
|
public Boolean IsSunUp => this.isSunUp;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Determine if the moon is currently up, based on moonset and moonrise time at the provided location and date.
|
/// Determine if the moon is currently up, based on moonset and moonrise time at the provided location and date.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool IsMoonUp { get { return isMoonUp; } }
|
public Boolean IsMoonUp => this.isMoonUp;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Moon ilumination details based on the provided date.
|
/// Moon ilumination details based on the provided date.
|
||||||
@ -322,37 +295,37 @@ namespace CoordinateSharp
|
|||||||
/// <remarks>
|
/// <remarks>
|
||||||
/// Contains phase, phase name, fraction and angle
|
/// Contains phase, phase name, fraction and angle
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
public MoonIllum MoonIllum { get { return moonIllum; } }
|
public MoonIllum MoonIllum => this.moonIllum;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Moons perigee details based on the provided date.
|
/// Moons perigee details based on the provided date.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public Perigee Perigee { get { return perigee; } }
|
public Perigee Perigee => this.perigee;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Moons apogee details based on the provided date.
|
/// Moons apogee details based on the provided date.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public Apogee Apogee { get { return apogee; } }
|
public Apogee Apogee => this.apogee;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Additional solar event times based on the provided date and location.
|
/// Additional solar event times based on the provided date and location.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <remarks>Contains civil and nautical dawn and dusk times.</remarks>
|
/// <remarks>Contains civil and nautical dawn and dusk times.</remarks>
|
||||||
public AdditionalSolarTimes AdditionalSolarTimes { get { return additionalSolarTimes; } }
|
public AdditionalSolarTimes AdditionalSolarTimes => this.additionalSolarTimes;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Astrological signs based on the provided date.
|
/// Astrological signs based on the provided date.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <remarks>
|
/// <remarks>
|
||||||
/// Contains zodiac, moon sign and moon name during full moon events
|
/// Contains zodiac, moon sign and moon name during full moon events
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
public AstrologicalSigns AstrologicalSigns { get { return astrologicalSigns; } }
|
public AstrologicalSigns AstrologicalSigns => this.astrologicalSigns;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Returns a SolarEclipse.
|
/// Returns a SolarEclipse.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public SolarEclipse SolarEclipse { get { return solarEclipse; } }
|
public SolarEclipse SolarEclipse => this.solarEclipse;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Returns a LunarEclipse.
|
/// Returns a LunarEclipse.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public LunarEclipse LunarEclipse { get { return lunarEclipse; } }
|
public LunarEclipse LunarEclipse => this.lunarEclipse;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Calculates all celestial data. Coordinates will notify as changes occur
|
/// Calculates all celestial data. Coordinates will notify as changes occur
|
||||||
@ -360,8 +333,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="lat">Decimal format latitude</param>
|
/// <param name="lat">Decimal format latitude</param>
|
||||||
/// <param name="longi">Decimal format longitude</param>
|
/// <param name="longi">Decimal format longitude</param>
|
||||||
/// <param name="date">Geographic DateTime</param>
|
/// <param name="date">Geographic DateTime</param>
|
||||||
internal void CalculateCelestialTime(double lat, double longi, DateTime date)
|
internal void CalculateCelestialTime(Double lat, Double longi, DateTime date) {
|
||||||
{
|
|
||||||
date = new DateTime(date.Year, date.Month, date.Day, date.Hour, date.Minute, date.Second, DateTimeKind.Utc);
|
date = new DateTime(date.Year, date.Month, date.Day, date.Hour, date.Minute, date.Second, DateTimeKind.Utc);
|
||||||
SunCalc.CalculateSunTime(lat, longi, date, this);
|
SunCalc.CalculateSunTime(lat, longi, date, this);
|
||||||
MoonCalc.GetMoonTimes(date, lat, longi, this);
|
MoonCalc.GetMoonTimes(date, lat, longi, this);
|
||||||
@ -373,8 +345,8 @@ namespace CoordinateSharp
|
|||||||
MoonCalc.GetMoonIllumination(date, this, lat, longi);
|
MoonCalc.GetMoonIllumination(date, this, lat, longi);
|
||||||
|
|
||||||
|
|
||||||
perigee = MoonCalc.GetPerigeeEvents(date);
|
this.perigee = MoonCalc.GetPerigeeEvents(date);
|
||||||
apogee = MoonCalc.GetApogeeEvents(date);
|
this.apogee = MoonCalc.GetApogeeEvents(date);
|
||||||
|
|
||||||
Calculate_Celestial_IsUp_Booleans(date, this);
|
Calculate_Celestial_IsUp_Booleans(date, this);
|
||||||
|
|
||||||
@ -386,8 +358,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="longi">Decimal format longitude</param>
|
/// <param name="longi">Decimal format longitude</param>
|
||||||
/// <param name="date">Geographic DateTime</param>
|
/// <param name="date">Geographic DateTime</param>
|
||||||
/// <returns>Fully populated Celestial object</returns>
|
/// <returns>Fully populated Celestial object</returns>
|
||||||
public static Celestial CalculateCelestialTimes(double lat, double longi, DateTime date)
|
public static Celestial CalculateCelestialTimes(Double lat, Double longi, DateTime date) {
|
||||||
{
|
|
||||||
date = new DateTime(date.Year, date.Month, date.Day, date.Hour, date.Minute, date.Second, DateTimeKind.Utc);
|
date = new DateTime(date.Year, date.Month, date.Day, date.Hour, date.Minute, date.Second, DateTimeKind.Utc);
|
||||||
|
|
||||||
Celestial c = new Celestial(false);
|
Celestial c = new Celestial(false);
|
||||||
@ -414,8 +385,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="longi">longitude</param>
|
/// <param name="longi">longitude</param>
|
||||||
/// <param name="date">DateTime</param>
|
/// <param name="date">DateTime</param>
|
||||||
/// <returns>Celestial (Partially Populated)</returns>
|
/// <returns>Celestial (Partially Populated)</returns>
|
||||||
public static Celestial CalculateSunData(double lat, double longi, DateTime date)
|
public static Celestial CalculateSunData(Double lat, Double longi, DateTime date) {
|
||||||
{
|
|
||||||
date = new DateTime(date.Year, date.Month, date.Day, date.Hour, date.Minute, date.Second, DateTimeKind.Utc);
|
date = new DateTime(date.Year, date.Month, date.Day, date.Hour, date.Minute, date.Second, DateTimeKind.Utc);
|
||||||
|
|
||||||
Celestial c = new Celestial(false);
|
Celestial c = new Celestial(false);
|
||||||
@ -431,8 +401,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="longi">longitude</param>
|
/// <param name="longi">longitude</param>
|
||||||
/// <param name="date">DateTime</param>
|
/// <param name="date">DateTime</param>
|
||||||
/// <returns>Celestial (Partially Populated)</returns>
|
/// <returns>Celestial (Partially Populated)</returns>
|
||||||
public static Celestial CalculateMoonData(double lat, double longi, DateTime date)
|
public static Celestial CalculateMoonData(Double lat, Double longi, DateTime date) {
|
||||||
{
|
|
||||||
date = new DateTime(date.Year, date.Month, date.Day, date.Hour, date.Minute, date.Second, DateTimeKind.Utc);
|
date = new DateTime(date.Year, date.Month, date.Day, date.Hour, date.Minute, date.Second, DateTimeKind.Utc);
|
||||||
|
|
||||||
Celestial c = new Celestial(false);
|
Celestial c = new Celestial(false);
|
||||||
@ -456,13 +425,12 @@ namespace CoordinateSharp
|
|||||||
/// <param name="longi">longitude</param>
|
/// <param name="longi">longitude</param>
|
||||||
/// <param name="date">DateTime</param>
|
/// <param name="date">DateTime</param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
public static List<SolarEclipseDetails> Get_Solar_Eclipse_Table(double lat, double longi, DateTime date)
|
public static List<SolarEclipseDetails> Get_Solar_Eclipse_Table(Double lat, Double longi, DateTime date) {
|
||||||
{
|
|
||||||
//Convert to Radians
|
//Convert to Radians
|
||||||
double latR = lat * Math.PI / 180;
|
Double latR = lat * Math.PI / 180;
|
||||||
double longR = longi * Math.PI / 180;
|
Double longR = longi * Math.PI / 180;
|
||||||
//Get solar data based on date
|
//Get solar data based on date
|
||||||
double[] events = Eclipse.SolarData.SolarDateData_100Year(date);
|
Double[] events = Eclipse.SolarData.SolarDateData_100Year(date);
|
||||||
//Return list of solar data.
|
//Return list of solar data.
|
||||||
return SolarEclipseCalc.CalculateSolarEclipse(date, latR, longR, events);
|
return SolarEclipseCalc.CalculateSolarEclipse(date, latR, longR, events);
|
||||||
}
|
}
|
||||||
@ -474,13 +442,12 @@ namespace CoordinateSharp
|
|||||||
/// <param name="longi">longitude</param>
|
/// <param name="longi">longitude</param>
|
||||||
/// <param name="date">DateTime</param>
|
/// <param name="date">DateTime</param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
public static List<LunarEclipseDetails> Get_Lunar_Eclipse_Table(double lat, double longi, DateTime date)
|
public static List<LunarEclipseDetails> Get_Lunar_Eclipse_Table(Double lat, Double longi, DateTime date) {
|
||||||
{
|
|
||||||
//Convert to Radians
|
//Convert to Radians
|
||||||
double latR = lat * Math.PI / 180;
|
Double latR = lat * Math.PI / 180;
|
||||||
double longR = longi * Math.PI / 180;
|
Double longR = longi * Math.PI / 180;
|
||||||
//Get solar data based on date
|
//Get solar data based on date
|
||||||
double[] events = Eclipse.LunarData.LunarDateData_100Year(date);
|
Double[] events = Eclipse.LunarData.LunarDateData_100Year(date);
|
||||||
//Return list of solar data.
|
//Return list of solar data.
|
||||||
return LunarEclipseCalc.CalculateLunarEclipse(date, latR, longR, events);
|
return LunarEclipseCalc.CalculateLunarEclipse(date, latR, longR, events);
|
||||||
}
|
}
|
||||||
@ -490,11 +457,9 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="date">Coordinate GeoDate</param>
|
/// <param name="date">Coordinate GeoDate</param>
|
||||||
/// <param name="cel">Celestial Object</param>
|
/// <param name="cel">Celestial Object</param>
|
||||||
private static void Calculate_Celestial_IsUp_Booleans(DateTime date, Celestial cel)
|
private static void Calculate_Celestial_IsUp_Booleans(DateTime date, Celestial cel) {
|
||||||
{
|
|
||||||
//SUN
|
//SUN
|
||||||
switch (cel.SunCondition)
|
switch (cel.SunCondition) {
|
||||||
{
|
|
||||||
case CelestialStatus.DownAllDay:
|
case CelestialStatus.DownAllDay:
|
||||||
cel.isSunUp = false;
|
cel.isSunUp = false;
|
||||||
break;
|
break;
|
||||||
@ -502,42 +467,13 @@ namespace CoordinateSharp
|
|||||||
cel.isSunUp = true;
|
cel.isSunUp = true;
|
||||||
break;
|
break;
|
||||||
case CelestialStatus.NoRise:
|
case CelestialStatus.NoRise:
|
||||||
if(date<cel.SunSet)
|
cel.isSunUp = date < cel.SunSet;
|
||||||
{
|
|
||||||
cel.isSunUp = true;
|
|
||||||
}
|
|
||||||
else { cel.isSunUp = false; }
|
|
||||||
break;
|
break;
|
||||||
case CelestialStatus.NoSet:
|
case CelestialStatus.NoSet:
|
||||||
if (date > cel.SunRise)
|
cel.isSunUp = date > cel.SunRise;
|
||||||
{
|
|
||||||
cel.isSunUp = true;
|
|
||||||
}
|
|
||||||
else { cel.isSunUp = false; }
|
|
||||||
break;
|
break;
|
||||||
case CelestialStatus.RiseAndSet:
|
case CelestialStatus.RiseAndSet:
|
||||||
if (cel.SunRise < cel.SunSet)
|
cel.isSunUp = cel.SunRise < cel.SunSet ? date > cel.SunRise && date < cel.SunSet : date > cel.SunRise || date < cel.SunSet;
|
||||||
{
|
|
||||||
if (date > cel.SunRise && date < cel.SunSet)
|
|
||||||
{
|
|
||||||
cel.isSunUp = true;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
cel.isSunUp = false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (date > cel.SunRise || date < cel.SunSet)
|
|
||||||
{
|
|
||||||
cel.isSunUp = true;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
cel.isSunUp = false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
//Should never be reached. If reached, previous calculations failed somewhere.
|
//Should never be reached. If reached, previous calculations failed somewhere.
|
||||||
@ -545,8 +481,7 @@ namespace CoordinateSharp
|
|||||||
}
|
}
|
||||||
|
|
||||||
//MOON
|
//MOON
|
||||||
switch (cel.MoonCondition)
|
switch (cel.MoonCondition) {
|
||||||
{
|
|
||||||
case CelestialStatus.DownAllDay:
|
case CelestialStatus.DownAllDay:
|
||||||
cel.isMoonUp = false;
|
cel.isMoonUp = false;
|
||||||
break;
|
break;
|
||||||
@ -554,42 +489,13 @@ namespace CoordinateSharp
|
|||||||
cel.isMoonUp = true;
|
cel.isMoonUp = true;
|
||||||
break;
|
break;
|
||||||
case CelestialStatus.NoRise:
|
case CelestialStatus.NoRise:
|
||||||
if (date < cel.MoonSet)
|
cel.isMoonUp = date < cel.MoonSet;
|
||||||
{
|
|
||||||
cel.isMoonUp = true;
|
|
||||||
}
|
|
||||||
else { cel.isMoonUp = false; }
|
|
||||||
break;
|
break;
|
||||||
case CelestialStatus.NoSet:
|
case CelestialStatus.NoSet:
|
||||||
if (date > cel.MoonRise)
|
cel.isMoonUp = date > cel.MoonRise;
|
||||||
{
|
|
||||||
cel.isMoonUp = true;
|
|
||||||
}
|
|
||||||
else { cel.isMoonUp = false; }
|
|
||||||
break;
|
break;
|
||||||
case CelestialStatus.RiseAndSet:
|
case CelestialStatus.RiseAndSet:
|
||||||
if (cel.MoonRise < cel.MoonSet)
|
cel.isMoonUp = cel.MoonRise < cel.MoonSet ? date > cel.MoonRise && date < cel.MoonSet : date > cel.MoonRise || date < cel.MoonSet;
|
||||||
{
|
|
||||||
if (date > cel.MoonRise && date < cel.MoonSet)
|
|
||||||
{
|
|
||||||
cel.isMoonUp = true;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
cel.isMoonUp = false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (date > cel.MoonRise || date < cel.MoonSet)
|
|
||||||
{
|
|
||||||
cel.isMoonUp = true;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
cel.isMoonUp = false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
//Should never be reached. If reached, previous calculations failed somewhere.
|
//Should never be reached. If reached, previous calculations failed somewhere.
|
||||||
@ -602,19 +508,13 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="d">DateTime</param>
|
/// <param name="d">DateTime</param>
|
||||||
/// <returns>Apogee</returns>
|
/// <returns>Apogee</returns>
|
||||||
public static Apogee GetApogees(DateTime d)
|
public static Apogee GetApogees(DateTime d) => MoonCalc.GetApogeeEvents(d);
|
||||||
{
|
|
||||||
return MoonCalc.GetApogeeEvents(d);
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Returns Perigee object containing last and next perigee based on the specified date.
|
/// Returns Perigee object containing last and next perigee based on the specified date.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="d">DateTime</param>
|
/// <param name="d">DateTime</param>
|
||||||
/// <returns>Perigee</returns>
|
/// <returns>Perigee</returns>
|
||||||
public static Perigee GetPerigees(DateTime d)
|
public static Perigee GetPerigees(DateTime d) => MoonCalc.GetPerigeeEvents(d);
|
||||||
{
|
|
||||||
return MoonCalc.GetPerigeeEvents(d);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -2,8 +2,7 @@
|
|||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
|
||||||
namespace CoordinateSharp
|
namespace CoordinateSharp {
|
||||||
{
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@ -11,87 +10,78 @@ namespace CoordinateSharp
|
|||||||
/// Used for UTM/MGRS Conversions
|
/// Used for UTM/MGRS Conversions
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
internal class LatZones
|
internal class LatZones {
|
||||||
{
|
public static List<String> longZongLetters = new List<String>(new String[]{"C", "D", "E", "F", "G", "H", "J", "K", "L", "M", "N", "P", "Q", "R", "S", "T",
|
||||||
public static List<string> longZongLetters = new List<string>(new string[]{"C", "D", "E", "F", "G", "H", "J", "K", "L", "M", "N", "P", "Q", "R", "S", "T",
|
|
||||||
"U", "V", "W", "X"});
|
"U", "V", "W", "X"});
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Used for handling diagraph determination
|
/// Used for handling diagraph determination
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
internal class Digraphs
|
internal class Digraphs {
|
||||||
{
|
private readonly List<Digraph> digraph1;
|
||||||
private List<Digraph> digraph1;
|
private readonly List<Digraph> digraph2;
|
||||||
private List<Digraph> digraph2;
|
|
||||||
|
|
||||||
private String[] digraph1Array = { "A", "B", "C", "D", "E", "F", "G", "H",
|
private readonly String[] digraph1Array = { "A", "B", "C", "D", "E", "F", "G", "H", "J", "K", "L", "M", "N", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z" };
|
||||||
"J", "K", "L", "M", "N", "P", "Q", "R", "S", "T", "U", "V", "W", "X",
|
|
||||||
"Y", "Z" };
|
|
||||||
|
|
||||||
private String[] digraph2Array = { "V", "A", "B", "C", "D", "E", "F", "G",
|
private readonly String[] digraph2Array = { "V", "A", "B", "C", "D", "E", "F", "G", "H", "J", "K", "L", "M", "N", "P", "Q", "R", "S", "T", "U", "V" };
|
||||||
"H", "J", "K", "L", "M", "N", "P", "Q", "R", "S", "T", "U", "V" };
|
|
||||||
|
|
||||||
public Digraphs()
|
public Digraphs() {
|
||||||
{
|
this.digraph1 = new List<Digraph>();
|
||||||
digraph1 = new List<Digraph>();
|
this.digraph2 = new List<Digraph>();
|
||||||
digraph2 = new List<Digraph>();
|
|
||||||
|
|
||||||
digraph1.Add(new Digraph() { Zone = 1, Letter = "A" });
|
this.digraph1.Add(new Digraph() { Zone = 1, Letter = "A" });
|
||||||
digraph1.Add(new Digraph() { Zone = 2, Letter = "B" });
|
this.digraph1.Add(new Digraph() { Zone = 2, Letter = "B" });
|
||||||
digraph1.Add(new Digraph() { Zone = 3, Letter = "C" });
|
this.digraph1.Add(new Digraph() { Zone = 3, Letter = "C" });
|
||||||
digraph1.Add(new Digraph() { Zone = 4, Letter = "D" });
|
this.digraph1.Add(new Digraph() { Zone = 4, Letter = "D" });
|
||||||
digraph1.Add(new Digraph() { Zone = 5, Letter = "E" });
|
this.digraph1.Add(new Digraph() { Zone = 5, Letter = "E" });
|
||||||
digraph1.Add(new Digraph() { Zone = 6, Letter = "F" });
|
this.digraph1.Add(new Digraph() { Zone = 6, Letter = "F" });
|
||||||
digraph1.Add(new Digraph() { Zone = 7, Letter = "G" });
|
this.digraph1.Add(new Digraph() { Zone = 7, Letter = "G" });
|
||||||
digraph1.Add(new Digraph() { Zone = 8, Letter = "H" });
|
this.digraph1.Add(new Digraph() { Zone = 8, Letter = "H" });
|
||||||
digraph1.Add(new Digraph() { Zone = 9, Letter = "J" });
|
this.digraph1.Add(new Digraph() { Zone = 9, Letter = "J" });
|
||||||
digraph1.Add(new Digraph() { Zone = 10, Letter = "K" });
|
this.digraph1.Add(new Digraph() { Zone = 10, Letter = "K" });
|
||||||
digraph1.Add(new Digraph() { Zone = 11, Letter = "L" });
|
this.digraph1.Add(new Digraph() { Zone = 11, Letter = "L" });
|
||||||
digraph1.Add(new Digraph() { Zone = 12, Letter = "M" });
|
this.digraph1.Add(new Digraph() { Zone = 12, Letter = "M" });
|
||||||
digraph1.Add(new Digraph() { Zone = 13, Letter = "N" });
|
this.digraph1.Add(new Digraph() { Zone = 13, Letter = "N" });
|
||||||
digraph1.Add(new Digraph() { Zone = 14, Letter = "P" });
|
this.digraph1.Add(new Digraph() { Zone = 14, Letter = "P" });
|
||||||
digraph1.Add(new Digraph() { Zone = 15, Letter = "Q" });
|
this.digraph1.Add(new Digraph() { Zone = 15, Letter = "Q" });
|
||||||
digraph1.Add(new Digraph() { Zone = 16, Letter = "R" });
|
this.digraph1.Add(new Digraph() { Zone = 16, Letter = "R" });
|
||||||
digraph1.Add(new Digraph() { Zone = 17, Letter = "S" });
|
this.digraph1.Add(new Digraph() { Zone = 17, Letter = "S" });
|
||||||
digraph1.Add(new Digraph() { Zone = 18, Letter = "T" });
|
this.digraph1.Add(new Digraph() { Zone = 18, Letter = "T" });
|
||||||
digraph1.Add(new Digraph() { Zone = 19, Letter = "U" });
|
this.digraph1.Add(new Digraph() { Zone = 19, Letter = "U" });
|
||||||
digraph1.Add(new Digraph() { Zone = 20, Letter = "V" });
|
this.digraph1.Add(new Digraph() { Zone = 20, Letter = "V" });
|
||||||
digraph1.Add(new Digraph() { Zone = 21, Letter = "W" });
|
this.digraph1.Add(new Digraph() { Zone = 21, Letter = "W" });
|
||||||
digraph1.Add(new Digraph() { Zone = 22, Letter = "X" });
|
this.digraph1.Add(new Digraph() { Zone = 22, Letter = "X" });
|
||||||
digraph1.Add(new Digraph() { Zone = 23, Letter = "Y" });
|
this.digraph1.Add(new Digraph() { Zone = 23, Letter = "Y" });
|
||||||
digraph1.Add(new Digraph() { Zone = 24, Letter = "Z" });
|
this.digraph1.Add(new Digraph() { Zone = 24, Letter = "Z" });
|
||||||
digraph1.Add(new Digraph() { Zone = 1, Letter = "A" });
|
this.digraph1.Add(new Digraph() { Zone = 1, Letter = "A" });
|
||||||
|
|
||||||
digraph2.Add(new Digraph() { Zone = 0, Letter = "V"});
|
this.digraph2.Add(new Digraph() { Zone = 0, Letter = "V" });
|
||||||
digraph2.Add(new Digraph() { Zone = 1, Letter = "A" });
|
this.digraph2.Add(new Digraph() { Zone = 1, Letter = "A" });
|
||||||
digraph2.Add(new Digraph() { Zone = 2, Letter = "B" });
|
this.digraph2.Add(new Digraph() { Zone = 2, Letter = "B" });
|
||||||
digraph2.Add(new Digraph() { Zone = 3, Letter = "C" });
|
this.digraph2.Add(new Digraph() { Zone = 3, Letter = "C" });
|
||||||
digraph2.Add(new Digraph() { Zone = 4, Letter = "D" });
|
this.digraph2.Add(new Digraph() { Zone = 4, Letter = "D" });
|
||||||
digraph2.Add(new Digraph() { Zone = 5, Letter = "E" });
|
this.digraph2.Add(new Digraph() { Zone = 5, Letter = "E" });
|
||||||
digraph2.Add(new Digraph() { Zone = 6, Letter = "F" });
|
this.digraph2.Add(new Digraph() { Zone = 6, Letter = "F" });
|
||||||
digraph2.Add(new Digraph() { Zone = 7, Letter = "G" });
|
this.digraph2.Add(new Digraph() { Zone = 7, Letter = "G" });
|
||||||
digraph2.Add(new Digraph() { Zone = 8, Letter = "H" });
|
this.digraph2.Add(new Digraph() { Zone = 8, Letter = "H" });
|
||||||
digraph2.Add(new Digraph() { Zone = 9, Letter = "J" });
|
this.digraph2.Add(new Digraph() { Zone = 9, Letter = "J" });
|
||||||
digraph2.Add(new Digraph() { Zone = 10, Letter = "K" });
|
this.digraph2.Add(new Digraph() { Zone = 10, Letter = "K" });
|
||||||
digraph2.Add(new Digraph() { Zone = 11, Letter = "L" });
|
this.digraph2.Add(new Digraph() { Zone = 11, Letter = "L" });
|
||||||
digraph2.Add(new Digraph() { Zone = 12, Letter = "M" });
|
this.digraph2.Add(new Digraph() { Zone = 12, Letter = "M" });
|
||||||
digraph2.Add(new Digraph() { Zone = 13, Letter = "N" });
|
this.digraph2.Add(new Digraph() { Zone = 13, Letter = "N" });
|
||||||
digraph2.Add(new Digraph() { Zone = 14, Letter = "P" });
|
this.digraph2.Add(new Digraph() { Zone = 14, Letter = "P" });
|
||||||
digraph2.Add(new Digraph() { Zone = 15, Letter = "Q" });
|
this.digraph2.Add(new Digraph() { Zone = 15, Letter = "Q" });
|
||||||
digraph2.Add(new Digraph() { Zone = 16, Letter = "R" });
|
this.digraph2.Add(new Digraph() { Zone = 16, Letter = "R" });
|
||||||
digraph2.Add(new Digraph() { Zone = 17, Letter = "S" });
|
this.digraph2.Add(new Digraph() { Zone = 17, Letter = "S" });
|
||||||
digraph2.Add(new Digraph() { Zone = 18, Letter = "T" });
|
this.digraph2.Add(new Digraph() { Zone = 18, Letter = "T" });
|
||||||
digraph2.Add(new Digraph() { Zone = 19, Letter = "U" });
|
this.digraph2.Add(new Digraph() { Zone = 19, Letter = "U" });
|
||||||
digraph2.Add(new Digraph() { Zone = 20, Letter = "V" });
|
this.digraph2.Add(new Digraph() { Zone = 20, Letter = "V" });
|
||||||
}
|
}
|
||||||
|
|
||||||
internal int getDigraph1Index(String letter)
|
internal Int32 GetDigraph1Index(String letter) {
|
||||||
{
|
for (Int32 i = 0; i < this.digraph1Array.Length; i++) {
|
||||||
for (int i = 0; i < digraph1Array.Length; i++)
|
if (this.digraph1Array[i].Equals(letter)) {
|
||||||
{
|
|
||||||
if (digraph1Array[i].Equals(letter))
|
|
||||||
{
|
|
||||||
return i + 1;
|
return i + 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -99,12 +89,9 @@ namespace CoordinateSharp
|
|||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
internal int getDigraph2Index(String letter)
|
internal Int32 GetDigraph2Index(String letter) {
|
||||||
{
|
for (Int32 i = 0; i < this.digraph2Array.Length; i++) {
|
||||||
for (int i = 0; i < digraph2Array.Length; i++)
|
if (this.digraph2Array[i].Equals(letter)) {
|
||||||
{
|
|
||||||
if (digraph2Array[i].Equals(letter))
|
|
||||||
{
|
|
||||||
return i;
|
return i;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -112,29 +99,26 @@ namespace CoordinateSharp
|
|||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
internal String getDigraph1(int longZone, double easting)
|
internal String GetDigraph1(Int32 longZone, Double easting) {
|
||||||
{
|
Int32 a1 = longZone;
|
||||||
int a1 = longZone;
|
Double a2 = 8 * ((a1 - 1) % 3) + 1;
|
||||||
double a2 = 8 * ((a1 - 1) % 3) + 1;
|
|
||||||
|
|
||||||
double a3 = easting;
|
Double a3 = easting;
|
||||||
double a4 = a2 + ((int)(a3 / 100000)) - 1;
|
Double a4 = a2 + (Int32)(a3 / 100000) - 1;
|
||||||
return digraph1.Where(x=>x.Zone == Math.Floor(a4)).FirstOrDefault().Letter;
|
return this.digraph1.Where(x => x.Zone == Math.Floor(a4)).FirstOrDefault().Letter;
|
||||||
}
|
}
|
||||||
|
|
||||||
internal String getDigraph2(int longZone, double northing)
|
internal String GetDigraph2(Int32 longZone, Double northing) {
|
||||||
{
|
Int32 a1 = longZone;
|
||||||
int a1 = longZone;
|
Double a2 = 1 + 5 * ((a1 - 1) % 2);
|
||||||
double a2 = 1 + 5 * ((a1 - 1) % 2);
|
Double a3 = northing;
|
||||||
double a3 = northing;
|
Double a4 = a2 + (Int32)(a3 / 100000);
|
||||||
double a4 = (a2 + ((int)(a3 / 100000)));
|
a4 = (a2 + (Int32)(a3 / 100000.0)) % 20;
|
||||||
a4 = (a2 + ((int)(a3 / 100000.0))) % 20;
|
|
||||||
a4 = Math.Floor(a4);
|
a4 = Math.Floor(a4);
|
||||||
if (a4 < 0)
|
if (a4 < 0) {
|
||||||
{
|
a4 += 19;
|
||||||
a4 = a4 + 19;
|
|
||||||
}
|
}
|
||||||
return digraph2.Where(x => x.Zone == Math.Floor(a4)).FirstOrDefault().Letter;
|
return this.digraph2.Where(x => x.Zone == Math.Floor(a4)).FirstOrDefault().Letter;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
@ -142,17 +126,15 @@ namespace CoordinateSharp
|
|||||||
/// Diagraph model
|
/// Diagraph model
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
internal class Digraph
|
internal class Digraph {
|
||||||
{
|
public Int32 Zone { get; set; }
|
||||||
public int Zone { get; set; }
|
public String Letter { get; set; }
|
||||||
public string Letter { get; set; }
|
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Used for setting whether a coordinate part is latitudinal or longitudinal.
|
/// Used for setting whether a coordinate part is latitudinal or longitudinal.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public enum CoordinateType
|
public enum CoordinateType {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Latitude
|
/// Latitude
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -166,8 +148,7 @@ namespace CoordinateSharp
|
|||||||
/// Used to set a coordinate part position.
|
/// Used to set a coordinate part position.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public enum CoordinatesPosition :int
|
public enum CoordinatesPosition : Int32 {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// North
|
/// North
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -192,8 +173,7 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
[Flags]
|
[Flags]
|
||||||
public enum Coordinate_Datum
|
public enum Coordinate_Datum {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Lat Long GeoDetic
|
/// Lat Long GeoDetic
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -211,8 +191,7 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Cartesian Coordinate Type
|
/// Cartesian Coordinate Type
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public enum CartesianType
|
public enum CartesianType {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Spherical Cartesian
|
/// Spherical Cartesian
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -226,35 +205,21 @@ namespace CoordinateSharp
|
|||||||
/// Used for easy read math functions
|
/// Used for easy read math functions
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
internal static class ModM
|
internal static class ModM {
|
||||||
{
|
public static Double Mod(Double x, Double y) => x - y * Math.Floor(x / y);
|
||||||
public static double Mod(double x, double y)
|
|
||||||
{
|
|
||||||
return x - y * Math.Floor(x / y);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static double ModLon(double x)
|
public static Double ModLon(Double x) => Mod(x + Math.PI, 2 * Math.PI) - Math.PI;
|
||||||
{
|
|
||||||
return Mod(x + Math.PI, 2 * Math.PI) - Math.PI;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static double ModCrs(double x)
|
public static Double ModCrs(Double x) => Mod(x, 2 * Math.PI);
|
||||||
{
|
|
||||||
return Mod(x, 2 * Math.PI);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static double ModLat(double x)
|
public static Double ModLat(Double x) => Mod(x + Math.PI / 2, 2 * Math.PI) - Math.PI / 2;
|
||||||
{
|
|
||||||
return Mod(x + Math.PI / 2, 2 * Math.PI) - Math.PI / 2;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Earth Shape for Calculations.
|
/// Earth Shape for Calculations.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public enum Shape
|
public enum Shape {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Calculate as sphere (less accurate, more efficient).
|
/// Calculate as sphere (less accurate, more efficient).
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
@ -1,23 +1,21 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.ComponentModel;
|
using System.ComponentModel;
|
||||||
namespace CoordinateSharp
|
|
||||||
{
|
namespace CoordinateSharp {
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Cartesian (X, Y, Z) Coordinate
|
/// Cartesian (X, Y, Z) Coordinate
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public class Cartesian : INotifyPropertyChanged
|
public class Cartesian : INotifyPropertyChanged {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Create a Cartesian Object
|
/// Create a Cartesian Object
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="c"></param>
|
/// <param name="c"></param>
|
||||||
public Cartesian(Coordinate c)
|
public Cartesian(Coordinate c) {
|
||||||
{
|
|
||||||
//formulas:
|
//formulas:
|
||||||
x = Math.Cos(c.Latitude.ToRadians()) * Math.Cos(c.Longitude.ToRadians());
|
this.x = Math.Cos(c.Latitude.ToRadians()) * Math.Cos(c.Longitude.ToRadians());
|
||||||
y = Math.Cos(c.Latitude.ToRadians()) * Math.Sin(c.Longitude.ToRadians());
|
this.y = Math.Cos(c.Latitude.ToRadians()) * Math.Sin(c.Longitude.ToRadians());
|
||||||
z = Math.Sin(c.Latitude.ToRadians());
|
this.z = Math.Sin(c.Latitude.ToRadians());
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Create a Cartesian Object
|
/// Create a Cartesian Object
|
||||||
@ -25,69 +23,58 @@ namespace CoordinateSharp
|
|||||||
/// <param name="xc">X</param>
|
/// <param name="xc">X</param>
|
||||||
/// <param name="yc">Y</param>
|
/// <param name="yc">Y</param>
|
||||||
/// <param name="zc">Z</param>
|
/// <param name="zc">Z</param>
|
||||||
public Cartesian(double xc, double yc, double zc)
|
public Cartesian(Double xc, Double yc, Double zc) {
|
||||||
{
|
|
||||||
//formulas:
|
//formulas:
|
||||||
x = xc;
|
this.x = xc;
|
||||||
y = yc;
|
this.y = yc;
|
||||||
z = zc;
|
this.z = zc;
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Updates Cartesian Values
|
/// Updates Cartesian Values
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="c"></param>
|
/// <param name="c"></param>
|
||||||
public void ToCartesian(Coordinate c)
|
public void ToCartesian(Coordinate c) {
|
||||||
{
|
this.x = Math.Cos(c.Latitude.ToRadians()) * Math.Cos(c.Longitude.ToRadians());
|
||||||
x = Math.Cos(c.Latitude.ToRadians()) * Math.Cos(c.Longitude.ToRadians());
|
this.y = Math.Cos(c.Latitude.ToRadians()) * Math.Sin(c.Longitude.ToRadians());
|
||||||
y = Math.Cos(c.Latitude.ToRadians()) * Math.Sin(c.Longitude.ToRadians());
|
this.z = Math.Sin(c.Latitude.ToRadians());
|
||||||
z = Math.Sin(c.Latitude.ToRadians());
|
|
||||||
}
|
}
|
||||||
private double x;
|
private Double x;
|
||||||
private double y;
|
private Double y;
|
||||||
private double z;
|
private Double z;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// X Coordinate
|
/// X Coordinate
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double X
|
public Double X {
|
||||||
{
|
get => this.x;
|
||||||
get { return x; }
|
set {
|
||||||
set
|
if (this.x != value) {
|
||||||
{
|
this.x = value;
|
||||||
if(x != value)
|
this.NotifyPropertyChanged("X");
|
||||||
{
|
|
||||||
x = value;
|
|
||||||
NotifyPropertyChanged("X");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// y Coordinate
|
/// y Coordinate
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Y
|
public Double Y {
|
||||||
{
|
get => this.y;
|
||||||
get { return y; }
|
set {
|
||||||
set
|
if (this.y != value) {
|
||||||
{
|
this.y = value;
|
||||||
if (y != value)
|
this.NotifyPropertyChanged("Y");
|
||||||
{
|
|
||||||
y = value;
|
|
||||||
NotifyPropertyChanged("Y");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Z Coordinate
|
/// Z Coordinate
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Z
|
public Double Z {
|
||||||
{
|
get => this.z;
|
||||||
get { return z; }
|
set {
|
||||||
set
|
if (this.z != value) {
|
||||||
{
|
this.z = value;
|
||||||
if (z != value)
|
this.NotifyPropertyChanged("Z");
|
||||||
{
|
|
||||||
z = value;
|
|
||||||
NotifyPropertyChanged("Z");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -98,14 +85,13 @@ namespace CoordinateSharp
|
|||||||
/// <param name="y">Y</param>
|
/// <param name="y">Y</param>
|
||||||
/// <param name="z">Z</param>
|
/// <param name="z">Z</param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
public static Coordinate CartesianToLatLong(double x, double y, double z)
|
public static Coordinate CartesianToLatLong(Double x, Double y, Double z) {
|
||||||
{
|
Double lon = Math.Atan2(y, x);
|
||||||
double lon = Math.Atan2(y, x);
|
Double hyp = Math.Sqrt(x * x + y * y);
|
||||||
double hyp = Math.Sqrt(x * x + y * y);
|
Double lat = Math.Atan2(z, hyp);
|
||||||
double lat = Math.Atan2(z, hyp);
|
|
||||||
|
|
||||||
double Lat = lat * (180 / Math.PI);
|
Double Lat = lat * (180 / Math.PI);
|
||||||
double Lon = lon * (180 / Math.PI);
|
Double Lon = lon * (180 / Math.PI);
|
||||||
return new Coordinate(Lat, Lon);
|
return new Coordinate(Lat, Lon);
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@ -113,18 +99,17 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="cart">Cartesian Coordinate</param>
|
/// <param name="cart">Cartesian Coordinate</param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
public static Coordinate CartesianToLatLong(Cartesian cart)
|
public static Coordinate CartesianToLatLong(Cartesian cart) {
|
||||||
{
|
Double x = cart.X;
|
||||||
double x = cart.X;
|
Double y = cart.Y;
|
||||||
double y = cart.Y;
|
Double z = cart.Z;
|
||||||
double z = cart.Z;
|
|
||||||
|
|
||||||
double lon = Math.Atan2(y, x);
|
Double lon = Math.Atan2(y, x);
|
||||||
double hyp = Math.Sqrt(x * x + y * y);
|
Double hyp = Math.Sqrt(x * x + y * y);
|
||||||
double lat = Math.Atan2(z, hyp);
|
Double lat = Math.Atan2(z, hyp);
|
||||||
|
|
||||||
double Lat = lat * (180 / Math.PI);
|
Double Lat = lat * (180 / Math.PI);
|
||||||
double Lon = lon * (180 / Math.PI);
|
Double Lon = lon * (180 / Math.PI);
|
||||||
return new Coordinate(Lat, Lon);
|
return new Coordinate(Lat, Lon);
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@ -132,10 +117,7 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <returns>Cartesian Formatted Coordinate String</returns>
|
/// <returns>Cartesian Formatted Coordinate String</returns>
|
||||||
/// <returns>Values rounded to the 8th place</returns>
|
/// <returns>Values rounded to the 8th place</returns>
|
||||||
public override string ToString()
|
public override String ToString() => Math.Round(this.x, 8).ToString() + " " + Math.Round(this.y, 8).ToString() + " " + Math.Round(this.z, 8).ToString();
|
||||||
{
|
|
||||||
return Math.Round(x,8).ToString() + " " + Math.Round(y, 8).ToString() + " " + Math.Round(z, 8).ToString();
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Property changed event
|
/// Property changed event
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -144,10 +126,8 @@ namespace CoordinateSharp
|
|||||||
/// Notify property changed
|
/// Notify property changed
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="propName">Property name</param>
|
/// <param name="propName">Property name</param>
|
||||||
public void NotifyPropertyChanged(string propName)
|
public void NotifyPropertyChanged(String propName) {
|
||||||
{
|
if (this.PropertyChanged != null) {
|
||||||
if (this.PropertyChanged != null)
|
|
||||||
{
|
|
||||||
PropertyChanged(this, new PropertyChangedEventArgs(propName));
|
PropertyChanged(this, new PropertyChangedEventArgs(propName));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,46 +1,40 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
using System.ComponentModel;
|
using System.ComponentModel;
|
||||||
namespace CoordinateSharp
|
|
||||||
{
|
namespace CoordinateSharp {
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Earth Centered - Earth Fixed (X,Y,Z) Coordinate
|
/// Earth Centered - Earth Fixed (X,Y,Z) Coordinate
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public class ECEF : INotifyPropertyChanged
|
public class ECEF : INotifyPropertyChanged {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Create an ECEF Object
|
/// Create an ECEF Object
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="c">Coordinate</param>
|
/// <param name="c">Coordinate</param>
|
||||||
public ECEF(Coordinate c)
|
public ECEF(Coordinate c) {
|
||||||
{
|
this.equatorial_radius = 6378137.0;
|
||||||
equatorial_radius = 6378137.0;
|
this.inverse_flattening = 298.257223563;
|
||||||
inverse_flattening = 298.257223563;
|
this.WGS84();
|
||||||
WGS84();
|
this.geodetic_height = new Distance(0);
|
||||||
geodetic_height = new Distance(0);
|
Double[] ecef = this.LatLong_To_ECEF(c.Latitude.DecimalDegree, c.Longitude.DecimalDegree, this.geodetic_height.Kilometers);
|
||||||
double[] ecef = LatLong_To_ECEF(c.Latitude.DecimalDegree, c.Longitude.DecimalDegree, geodetic_height.Kilometers);
|
this.x = ecef[0];
|
||||||
x = ecef[0];
|
this.y = ecef[1];
|
||||||
y = ecef[1];
|
this.z = ecef[2];
|
||||||
z = ecef[2];
|
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Create an ECEF Object
|
/// Create an ECEF Object
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="c">Coordinate</param>
|
/// <param name="c">Coordinate</param>
|
||||||
/// <param name="height">Coordinate</param>
|
/// <param name="height">Coordinate</param>
|
||||||
public ECEF(Coordinate c, Distance height)
|
public ECEF(Coordinate c, Distance height) {
|
||||||
{
|
this.equatorial_radius = 6378137.0;
|
||||||
equatorial_radius = 6378137.0;
|
this.inverse_flattening = 298.257223563;
|
||||||
inverse_flattening = 298.257223563;
|
this.WGS84();
|
||||||
WGS84();
|
this.geodetic_height = height;
|
||||||
geodetic_height = height;
|
Double[] ecef = this.LatLong_To_ECEF(c.Latitude.DecimalDegree, c.Longitude.DecimalDegree, this.geodetic_height.Kilometers);
|
||||||
double[] ecef = LatLong_To_ECEF(c.Latitude.DecimalDegree, c.Longitude.DecimalDegree, geodetic_height.Kilometers);
|
this.x = ecef[0];
|
||||||
x = ecef[0];
|
this.y = ecef[1];
|
||||||
y = ecef[1];
|
this.z = ecef[2];
|
||||||
z = ecef[2];
|
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Create an ECEF Object
|
/// Create an ECEF Object
|
||||||
@ -48,106 +42,89 @@ namespace CoordinateSharp
|
|||||||
/// <param name="xc">X</param>
|
/// <param name="xc">X</param>
|
||||||
/// <param name="yc">Y</param>
|
/// <param name="yc">Y</param>
|
||||||
/// <param name="zc">Z</param>
|
/// <param name="zc">Z</param>
|
||||||
public ECEF(double xc, double yc, double zc)
|
public ECEF(Double xc, Double yc, Double zc) {
|
||||||
{
|
this.equatorial_radius = 6378137.0;
|
||||||
equatorial_radius = 6378137.0;
|
this.inverse_flattening = 298.257223563;
|
||||||
inverse_flattening = 298.257223563;
|
this.WGS84();
|
||||||
WGS84();
|
this.geodetic_height = new Distance(0);
|
||||||
geodetic_height = new Distance(0);
|
this.x = xc;
|
||||||
x = xc;
|
this.y = yc;
|
||||||
y = yc;
|
this.z = zc;
|
||||||
z = zc;
|
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Updates ECEF Values
|
/// Updates ECEF Values
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="c">Coordinate</param>
|
/// <param name="c">Coordinate</param>
|
||||||
public void ToECEF(Coordinate c)
|
public void ToECEF(Coordinate c) {
|
||||||
{
|
this.equatorial_radius = 6378137.0;
|
||||||
equatorial_radius = 6378137.0;
|
this.inverse_flattening = 298.257223563;
|
||||||
inverse_flattening = 298.257223563;
|
this.WGS84();
|
||||||
WGS84();
|
Double[] ecef = this.LatLong_To_ECEF(c.Latitude.DecimalDegree, c.Longitude.DecimalDegree, this.geodetic_height.Kilometers);
|
||||||
double[] ecef = LatLong_To_ECEF(c.Latitude.DecimalDegree, c.Longitude.DecimalDegree, geodetic_height.Kilometers);
|
this.x = ecef[0];
|
||||||
x = ecef[0];
|
this.y = ecef[1];
|
||||||
y = ecef[1];
|
this.z = ecef[2];
|
||||||
z = ecef[2];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
//Globals for calucations
|
//Globals for calucations
|
||||||
private double EARTH_A;
|
private Double EARTH_A;
|
||||||
private double EARTH_B;
|
private Double EARTH_B;
|
||||||
private double EARTH_F;
|
//private Double EARTH_F;
|
||||||
private double EARTH_Ecc;
|
private Double EARTH_Ecc;
|
||||||
private double EARTH_Esq;
|
private Double EARTH_Esq;
|
||||||
|
|
||||||
//ECEF Values
|
//ECEF Values
|
||||||
private double x;
|
private Double x;
|
||||||
private double y;
|
private Double y;
|
||||||
private double z;
|
private Double z;
|
||||||
private Distance geodetic_height;
|
private Distance geodetic_height;
|
||||||
|
|
||||||
//Datum
|
//Datum
|
||||||
internal double equatorial_radius;
|
internal Double equatorial_radius;
|
||||||
internal double inverse_flattening;
|
internal Double inverse_flattening;
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Datum Equatorial Radius / Semi Major Axis
|
/// Datum Equatorial Radius / Semi Major Axis
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Equatorial_Radius
|
public Double Equatorial_Radius => this.equatorial_radius;
|
||||||
{
|
|
||||||
get { return equatorial_radius; }
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Datum Flattening
|
/// Datum Flattening
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Inverse_Flattening
|
public Double Inverse_Flattening => this.inverse_flattening;
|
||||||
{
|
|
||||||
get { return inverse_flattening; }
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// X Coordinate
|
/// X Coordinate
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double X
|
public Double X {
|
||||||
{
|
get => this.x;
|
||||||
get { return x; }
|
set {
|
||||||
set
|
if (this.x != value) {
|
||||||
{
|
this.x = value;
|
||||||
if (x != value)
|
this.NotifyPropertyChanged("X");
|
||||||
{
|
|
||||||
x = value;
|
|
||||||
NotifyPropertyChanged("X");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// y Coordinate
|
/// y Coordinate
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Y
|
public Double Y {
|
||||||
{
|
get => this.y;
|
||||||
get { return y; }
|
set {
|
||||||
set
|
if (this.y != value) {
|
||||||
{
|
this.y = value;
|
||||||
if (y != value)
|
this.NotifyPropertyChanged("Y");
|
||||||
{
|
|
||||||
y = value;
|
|
||||||
NotifyPropertyChanged("Y");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Z Coordinate
|
/// Z Coordinate
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Z
|
public Double Z {
|
||||||
{
|
get => this.z;
|
||||||
get { return z; }
|
set {
|
||||||
set
|
if (this.z != value) {
|
||||||
{
|
this.z = value;
|
||||||
if (z != value)
|
this.NotifyPropertyChanged("Z");
|
||||||
{
|
|
||||||
z = value;
|
|
||||||
NotifyPropertyChanged("Z");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -157,15 +134,12 @@ namespace CoordinateSharp
|
|||||||
/// Used for converting Lat Long / ECEF.
|
/// Used for converting Lat Long / ECEF.
|
||||||
/// Default value is 0. Adjust as needed.
|
/// Default value is 0. Adjust as needed.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public Distance GeoDetic_Height
|
public Distance GeoDetic_Height {
|
||||||
{
|
get => this.geodetic_height;
|
||||||
get { return geodetic_height; }
|
internal set {
|
||||||
internal set
|
if (this.geodetic_height != value) {
|
||||||
{
|
this.geodetic_height = value;
|
||||||
if (geodetic_height != value)
|
this.NotifyPropertyChanged("Height");
|
||||||
{
|
|
||||||
geodetic_height = value;
|
|
||||||
NotifyPropertyChanged("Height");
|
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -177,13 +151,12 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="c">Coordinate</param>
|
/// <param name="c">Coordinate</param>
|
||||||
/// <param name="dist">Height</param>
|
/// <param name="dist">Height</param>
|
||||||
public void Set_GeoDetic_Height(Coordinate c, Distance dist)
|
public void Set_GeoDetic_Height(Coordinate c, Distance dist) {
|
||||||
{
|
this.geodetic_height = dist;
|
||||||
geodetic_height = dist;
|
Double[] values = this.LatLong_To_ECEF(c.Latitude.DecimalDegree, c.Longitude.DecimalDegree, dist.Kilometers);
|
||||||
double[] values = LatLong_To_ECEF(c.Latitude.DecimalDegree, c.Longitude.DecimalDegree, dist.Kilometers);
|
this.x = values[0];
|
||||||
x = values[0];
|
this.y = values[1];
|
||||||
y = values[1];
|
this.z = values[2];
|
||||||
z = values[2];
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -194,14 +167,14 @@ namespace CoordinateSharp
|
|||||||
/// <param name="y">Y</param>
|
/// <param name="y">Y</param>
|
||||||
/// <param name="z">Z</param>
|
/// <param name="z">Z</param>
|
||||||
/// <returns>Coordinate</returns>
|
/// <returns>Coordinate</returns>
|
||||||
public static Coordinate ECEFToLatLong(double x, double y, double z)
|
public static Coordinate ECEFToLatLong(Double x, Double y, Double z) {
|
||||||
{
|
|
||||||
ECEF ecef = new ECEF(x, y, z);
|
ECEF ecef = new ECEF(x, y, z);
|
||||||
double[] values = ecef.ECEF_To_LatLong(x, y, z);
|
Double[] values = ecef.ECEF_To_LatLong(x, y, z);
|
||||||
ecef.geodetic_height = new Distance(values[2]);
|
ecef.geodetic_height = new Distance(values[2]);
|
||||||
|
|
||||||
Coordinate c = new Coordinate(values[0], values[1]);
|
Coordinate c = new Coordinate(values[0], values[1]) {
|
||||||
c.ECEF = ecef;
|
ECEF = ecef
|
||||||
|
};
|
||||||
return c;
|
return c;
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@ -209,12 +182,11 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="ecef">ECEF Coordinate</param>
|
/// <param name="ecef">ECEF Coordinate</param>
|
||||||
/// <returns>Coordinate</returns>
|
/// <returns>Coordinate</returns>
|
||||||
public static Coordinate ECEFToLatLong(ECEF ecef)
|
public static Coordinate ECEFToLatLong(ECEF ecef) {
|
||||||
{
|
Double[] values = ecef.ECEF_To_LatLong(ecef.X, ecef.Y, ecef.Z);
|
||||||
double[] values = ecef.ECEF_To_LatLong(ecef.X, ecef.Y, ecef.Z);
|
|
||||||
|
|
||||||
Coordinate c = new Coordinate(values[0], values[1]);
|
Coordinate c = new Coordinate(values[0], values[1]);
|
||||||
Distance height = new Distance(values[2]);
|
//Distance height = new Distance(values[2]);
|
||||||
|
|
||||||
ecef.geodetic_height = new Distance(values[2]);
|
ecef.geodetic_height = new Distance(values[2]);
|
||||||
c.ECEF = ecef;
|
c.ECEF = ecef;
|
||||||
@ -226,10 +198,7 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <returns>ECEF Formatted Coordinate String</returns>
|
/// <returns>ECEF Formatted Coordinate String</returns>
|
||||||
/// <returns>Values rounded to the 3rd place</returns>
|
/// <returns>Values rounded to the 3rd place</returns>
|
||||||
public override string ToString()
|
public override String ToString() => Math.Round(this.x, 3).ToString() + " km, " + Math.Round(this.y, 3).ToString() + " km, " + Math.Round(this.z, 3).ToString() + " km";
|
||||||
{
|
|
||||||
return Math.Round(x, 3).ToString() + " km, " + Math.Round(y, 3).ToString() + " km, " + Math.Round(z, 3).ToString() + " km";
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Property changed event
|
/// Property changed event
|
||||||
@ -239,25 +208,18 @@ namespace CoordinateSharp
|
|||||||
/// Notify property changed
|
/// Notify property changed
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="propName">Property name</param>
|
/// <param name="propName">Property name</param>
|
||||||
public void NotifyPropertyChanged(string propName)
|
public void NotifyPropertyChanged(String propName) => PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propName));
|
||||||
{
|
|
||||||
if (PropertyChanged != null)
|
|
||||||
{
|
|
||||||
PropertyChanged(this, new PropertyChangedEventArgs(propName));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//CONVERSION LOGIC
|
//CONVERSION LOGIC
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Initialize EARTH global variables based on the Datum
|
/// Initialize EARTH global variables based on the Datum
|
||||||
/// </summary>
|
/// </summary>
|
||||||
private void WGS84()
|
private void WGS84() {
|
||||||
{
|
Double wgs84a = this.equatorial_radius / 1000;
|
||||||
double wgs84a = equatorial_radius / 1000;
|
Double wgs84f = 1.0 / this.inverse_flattening;
|
||||||
double wgs84f = 1.0 / inverse_flattening;
|
Double wgs84b = wgs84a * (1.0 - wgs84f);
|
||||||
double wgs84b = wgs84a * (1.0 - wgs84f);
|
|
||||||
|
|
||||||
EarthCon(wgs84a, wgs84b);
|
this.EarthCon(wgs84a, wgs84b);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@ -265,17 +227,16 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="a">a</param>
|
/// <param name="a">a</param>
|
||||||
/// <param name="b">b</param>
|
/// <param name="b">b</param>
|
||||||
private void EarthCon(double a, double b)
|
private void EarthCon(Double a, Double b) {
|
||||||
{
|
//Double f = 1 - b / a;
|
||||||
double f = 1 - b / a;
|
Double eccsq = 1 - b * b / (a * a);
|
||||||
double eccsq = 1 - b * b / (a * a);
|
Double ecc = Math.Sqrt(eccsq);
|
||||||
double ecc = Math.Sqrt(eccsq);
|
|
||||||
|
|
||||||
EARTH_A = a;
|
this.EARTH_A = a;
|
||||||
EARTH_B = b;
|
this.EARTH_B = b;
|
||||||
EARTH_F = f;
|
//this.EARTH_F = f;
|
||||||
EARTH_Ecc = ecc;
|
this.EARTH_Ecc = ecc;
|
||||||
EARTH_Esq = eccsq;
|
this.EARTH_Esq = eccsq;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@ -283,39 +244,38 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="lat">Latitude in degres</param>
|
/// <param name="lat">Latitude in degres</param>
|
||||||
/// <returns>double[]</returns>
|
/// <returns>double[]</returns>
|
||||||
private double[] radcur(double lat)
|
private Double[] Radcur(Double lat) {
|
||||||
{
|
Double[] rrnrm = new Double[3];
|
||||||
double[] rrnrm = new double[3];
|
|
||||||
|
|
||||||
double dtr = Math.PI / 180.0;
|
Double dtr = Math.PI / 180.0;
|
||||||
|
|
||||||
double a = EARTH_A;
|
Double a = this.EARTH_A;
|
||||||
double b = EARTH_B;
|
Double b = this.EARTH_B;
|
||||||
|
|
||||||
double asq = a * a;
|
Double asq = a * a;
|
||||||
double bsq = b * b;
|
Double bsq = b * b;
|
||||||
double eccsq = 1 - bsq / asq;
|
Double eccsq = 1 - bsq / asq;
|
||||||
double ecc = Math.Sqrt(eccsq);
|
//Double ecc = Math.Sqrt(eccsq);
|
||||||
|
|
||||||
double clat = Math.Cos(dtr * lat);
|
Double clat = Math.Cos(dtr * lat);
|
||||||
double slat = Math.Sin(dtr * lat);
|
Double slat = Math.Sin(dtr * lat);
|
||||||
|
|
||||||
double dsq = 1.0 - eccsq * slat * slat;
|
Double dsq = 1.0 - eccsq * slat * slat;
|
||||||
double d = Math.Sqrt(dsq);
|
Double d = Math.Sqrt(dsq);
|
||||||
|
|
||||||
double rn = a / d;
|
Double rn = a / d;
|
||||||
double rm = rn * (1.0 - eccsq) / dsq;
|
Double rm = rn * (1.0 - eccsq) / dsq;
|
||||||
|
|
||||||
double rho = rn * clat;
|
Double rho = rn * clat;
|
||||||
double z = (1.0 - eccsq) * rn * slat;
|
Double z = (1.0 - eccsq) * rn * slat;
|
||||||
double rsq = rho * rho + z * z;
|
Double rsq = rho * rho + z * z;
|
||||||
double r = Math.Sqrt(rsq);
|
Double r = Math.Sqrt(rsq);
|
||||||
|
|
||||||
rrnrm[0] = r;
|
rrnrm[0] = r;
|
||||||
rrnrm[1] = rn;
|
rrnrm[1] = rn;
|
||||||
rrnrm[2] = rm;
|
rrnrm[2] = rm;
|
||||||
|
|
||||||
return (rrnrm);
|
return rrnrm;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -324,11 +284,10 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="lat">Latidude in degrees</param>
|
/// <param name="lat">Latidude in degrees</param>
|
||||||
/// <returns>double</returns>
|
/// <returns>double</returns>
|
||||||
private double rearth(double lat)
|
private Double Rearth(Double lat) {
|
||||||
{
|
Double[] rrnrm;
|
||||||
double[] rrnrm;
|
rrnrm = this.Radcur(lat);
|
||||||
rrnrm = radcur(lat);
|
Double r = rrnrm[0];
|
||||||
double r = rrnrm[0];
|
|
||||||
|
|
||||||
return r;
|
return r;
|
||||||
}
|
}
|
||||||
@ -339,30 +298,29 @@ namespace CoordinateSharp
|
|||||||
/// <param name="flatgc">Geocentric latitude</param>
|
/// <param name="flatgc">Geocentric latitude</param>
|
||||||
/// <param name="altkm">Altitude in KM</param>
|
/// <param name="altkm">Altitude in KM</param>
|
||||||
/// <returns>double</returns>
|
/// <returns>double</returns>
|
||||||
private double gc2gd(double flatgc, double altkm)
|
private Double Gc2gd(Double flatgc, Double altkm) {
|
||||||
{
|
Double dtr = Math.PI / 180.0;
|
||||||
var dtr = Math.PI / 180.0;
|
Double rtd = 1 / dtr;
|
||||||
var rtd = 1 / dtr;
|
|
||||||
|
|
||||||
double ecc = EARTH_Ecc;
|
Double ecc = this.EARTH_Ecc;
|
||||||
double esq = ecc * ecc;
|
Double esq = ecc * ecc;
|
||||||
|
|
||||||
//approximation by stages
|
//approximation by stages
|
||||||
//1st use gc-lat as if is gd, then correct alt dependence
|
//1st use gc-lat as if is gd, then correct alt dependence
|
||||||
|
|
||||||
double altnow = altkm;
|
Double altnow = altkm;
|
||||||
|
|
||||||
double[] rrnrm = radcur(flatgc);
|
Double[] rrnrm = this.Radcur(flatgc);
|
||||||
double rn = rrnrm[1];
|
Double rn = rrnrm[1];
|
||||||
|
|
||||||
double ratio = 1 - esq * rn / (rn + altnow);
|
Double ratio = 1 - esq * rn / (rn + altnow);
|
||||||
|
|
||||||
double tlat = Math.Tan(dtr * flatgc) / ratio;
|
Double tlat = Math.Tan(dtr * flatgc) / ratio;
|
||||||
double flatgd = rtd * Math.Atan(tlat);
|
Double flatgd = rtd * Math.Atan(tlat);
|
||||||
|
|
||||||
//now use this approximation for gd-lat to get rn etc.
|
//now use this approximation for gd-lat to get rn etc.
|
||||||
|
|
||||||
rrnrm = radcur(flatgd);
|
rrnrm = this.Radcur(flatgd);
|
||||||
rn = rrnrm[1];
|
rn = rrnrm[1];
|
||||||
|
|
||||||
ratio = 1 - esq * rn / (rn + altnow);
|
ratio = 1 - esq * rn / (rn + altnow);
|
||||||
@ -378,26 +336,25 @@ namespace CoordinateSharp
|
|||||||
/// <param name="flatgd">Geodetic latitude tp geocentric latitide</param>
|
/// <param name="flatgd">Geodetic latitude tp geocentric latitide</param>
|
||||||
/// <param name="altkm">Altitude in KM</param>
|
/// <param name="altkm">Altitude in KM</param>
|
||||||
/// <returns>double</returns>
|
/// <returns>double</returns>
|
||||||
private double gd2gc(double flatgd, double altkm)
|
/*private Double gd2gc(Double flatgd, Double altkm) {
|
||||||
{
|
Double dtr = Math.PI / 180.0;
|
||||||
double dtr = Math.PI / 180.0;
|
Double rtd = 1 / dtr;
|
||||||
double rtd = 1 / dtr;
|
|
||||||
|
|
||||||
double ecc = EARTH_Ecc;
|
Double ecc = this.EARTH_Ecc;
|
||||||
double esq = ecc * ecc;
|
Double esq = ecc * ecc;
|
||||||
|
|
||||||
double altnow = altkm;
|
Double altnow = altkm;
|
||||||
|
|
||||||
double[] rrnrm = radcur(flatgd);
|
Double[] rrnrm = this.Radcur(flatgd);
|
||||||
double rn = rrnrm[1];
|
Double rn = rrnrm[1];
|
||||||
|
|
||||||
double ratio = 1 - esq * rn / (rn + altnow);
|
Double ratio = 1 - esq * rn / (rn + altnow);
|
||||||
|
|
||||||
double tlat = Math.Tan(dtr * flatgd) * ratio;
|
Double tlat = Math.Tan(dtr * flatgd) * ratio;
|
||||||
double flatgc = rtd * Math.Atan(tlat);
|
Double flatgc = rtd * Math.Atan(tlat);
|
||||||
|
|
||||||
return flatgc;
|
return flatgc;
|
||||||
}
|
}*/
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Converts lat / long to east, north, up vectors
|
/// Converts lat / long to east, north, up vectors
|
||||||
@ -405,16 +362,15 @@ namespace CoordinateSharp
|
|||||||
/// <param name="flat">Latitude</param>
|
/// <param name="flat">Latitude</param>
|
||||||
/// <param name="flon">Longitude</param>
|
/// <param name="flon">Longitude</param>
|
||||||
/// <returns>Array[] of double[]</returns>
|
/// <returns>Array[] of double[]</returns>
|
||||||
private Array[] llenu(double flat, double flon)
|
/*private Array[] llenu(Double flat, Double flon) {
|
||||||
{
|
Double clat, slat, clon, slon;
|
||||||
double clat, slat, clon, slon;
|
Double[] ee = new Double[3];
|
||||||
double[] ee = new double[3];
|
Double[] en = new Double[3];
|
||||||
double[] en = new double[3];
|
Double[] eu = new Double[3];
|
||||||
double[] eu = new double[3];
|
|
||||||
|
|
||||||
Array[] enu = new Array[3];
|
Array[] enu = new Array[3];
|
||||||
|
|
||||||
double dtr = Math.PI / 180.0;
|
Double dtr = Math.PI / 180.0;
|
||||||
|
|
||||||
clat = Math.Cos(dtr * flat);
|
clat = Math.Cos(dtr * flat);
|
||||||
slat = Math.Sin(dtr * flat);
|
slat = Math.Sin(dtr * flat);
|
||||||
@ -438,7 +394,7 @@ namespace CoordinateSharp
|
|||||||
enu[2] = eu;
|
enu[2] = eu;
|
||||||
|
|
||||||
return enu;
|
return enu;
|
||||||
}
|
}*/
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Gets ECEF vector in KM
|
/// Gets ECEF vector in KM
|
||||||
@ -447,27 +403,26 @@ namespace CoordinateSharp
|
|||||||
/// <param name="longi">Longitude</param>
|
/// <param name="longi">Longitude</param>
|
||||||
/// <param name="altkm">Altitude in KM</param>
|
/// <param name="altkm">Altitude in KM</param>
|
||||||
/// <returns>double[]</returns>
|
/// <returns>double[]</returns>
|
||||||
private double[] LatLong_To_ECEF(double lat, double longi, double altkm)
|
private Double[] LatLong_To_ECEF(Double lat, Double longi, Double altkm) {
|
||||||
{
|
Double dtr = Math.PI / 180.0;
|
||||||
double dtr = Math.PI / 180.0;
|
|
||||||
|
|
||||||
double clat = Math.Cos(dtr * lat);
|
Double clat = Math.Cos(dtr * lat);
|
||||||
double slat = Math.Sin(dtr * lat);
|
Double slat = Math.Sin(dtr * lat);
|
||||||
double clon = Math.Cos(dtr * longi);
|
Double clon = Math.Cos(dtr * longi);
|
||||||
double slon = Math.Sin(dtr * longi);
|
Double slon = Math.Sin(dtr * longi);
|
||||||
|
|
||||||
double[] rrnrm = radcur(lat);
|
Double[] rrnrm = this.Radcur(lat);
|
||||||
double rn = rrnrm[1];
|
Double rn = rrnrm[1];
|
||||||
double re = rrnrm[0];
|
//Double re = rrnrm[0];
|
||||||
|
|
||||||
double ecc = EARTH_Ecc;
|
Double ecc = this.EARTH_Ecc;
|
||||||
double esq = ecc * ecc;
|
Double esq = ecc * ecc;
|
||||||
|
|
||||||
double x = (rn + altkm) * clat * clon;
|
Double x = (rn + altkm) * clat * clon;
|
||||||
double y = (rn + altkm) * clat * slon;
|
Double y = (rn + altkm) * clat * slon;
|
||||||
double z = ((1 - esq) * rn + altkm) * slat;
|
Double z = ((1 - esq) * rn + altkm) * slat;
|
||||||
|
|
||||||
double[] xvec = new double[3];
|
Double[] xvec = new Double[3];
|
||||||
|
|
||||||
xvec[0] = x;
|
xvec[0] = x;
|
||||||
xvec[1] = y;
|
xvec[1] = y;
|
||||||
@ -483,39 +438,34 @@ namespace CoordinateSharp
|
|||||||
/// <param name="y"></param>
|
/// <param name="y"></param>
|
||||||
/// <param name="z"></param>
|
/// <param name="z"></param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
private double[] ECEF_To_LatLong(double x, double y, double z)
|
private Double[] ECEF_To_LatLong(Double x, Double y, Double z) {
|
||||||
{
|
Double dtr = Math.PI / 180.0;
|
||||||
var dtr = Math.PI / 180.0;
|
|
||||||
|
|
||||||
double[] rrnrm = new double[3];
|
//_ = new Double[3];
|
||||||
double[] llhvec = new double[3];
|
Double[] llhvec = new Double[3];
|
||||||
double slat, tangd, flatn, dlat, clat;
|
Double slat, tangd, flatn, dlat, clat;
|
||||||
double flat;
|
Double flat;
|
||||||
double altkm;
|
Double altkm;
|
||||||
|
|
||||||
double esq = EARTH_Esq;
|
Double esq = this.EARTH_Esq;
|
||||||
|
|
||||||
double rp = Math.Sqrt(x * x + y * y + z * z);
|
Double rp = Math.Sqrt(x * x + y * y + z * z);
|
||||||
|
|
||||||
double flatgc = Math.Asin(z / rp) / dtr;
|
Double flatgc = Math.Asin(z / rp) / dtr;
|
||||||
double flon;
|
Double flon;
|
||||||
double testval = Math.Abs(x) + Math.Abs(y);
|
Double testval = Math.Abs(x) + Math.Abs(y);
|
||||||
if (testval < 1.0e-10)
|
flon = testval < 1.0e-10 ? 0.0 : Math.Atan2(y, x) / dtr;
|
||||||
{ flon = 0.0; }
|
if (flon < 0.0) { flon += 360.0; }
|
||||||
else
|
|
||||||
{ flon = Math.Atan2(y, x) / dtr; }
|
|
||||||
if (flon < 0.0) { flon = flon + 360.0; }
|
|
||||||
|
|
||||||
double p = Math.Sqrt(x * x + y * y);
|
Double p = Math.Sqrt(x * x + y * y);
|
||||||
|
|
||||||
//Pole special case
|
//Pole special case
|
||||||
|
|
||||||
if (p < 1.0e-10)
|
if (p < 1.0e-10) {
|
||||||
{
|
|
||||||
flat = 90.0;
|
flat = 90.0;
|
||||||
if (z < 0.0) { flat = -90.0; }
|
if (z < 0.0) { flat = -90.0; }
|
||||||
|
|
||||||
altkm = rp - rearth(flat);
|
altkm = rp - this.Rearth(flat);
|
||||||
llhvec[0] = flat;
|
llhvec[0] = flat;
|
||||||
llhvec[1] = flon;
|
llhvec[1] = flon;
|
||||||
llhvec[2] = altkm;
|
llhvec[2] = altkm;
|
||||||
@ -526,15 +476,14 @@ namespace CoordinateSharp
|
|||||||
//first iteration, use flatgc to get altitude
|
//first iteration, use flatgc to get altitude
|
||||||
//and alt needed to convert gc to gd lat.
|
//and alt needed to convert gc to gd lat.
|
||||||
|
|
||||||
double rnow = rearth(flatgc);
|
Double rnow = this.Rearth(flatgc);
|
||||||
altkm = rp - rnow;
|
altkm = rp - rnow;
|
||||||
flat = gc2gd(flatgc, altkm);
|
flat = this.Gc2gd(flatgc, altkm);
|
||||||
|
|
||||||
rrnrm = radcur(flat);
|
Double[] rrnrm = this.Radcur(flat);
|
||||||
double rn = rrnrm[1];
|
Double rn = rrnrm[1];
|
||||||
|
|
||||||
for (int kount = 0; kount < 5; kount++)
|
for (Int32 kount = 0; kount < 5; kount++) {
|
||||||
{
|
|
||||||
slat = Math.Sin(dtr * flat);
|
slat = Math.Sin(dtr * flat);
|
||||||
tangd = (z + rn * esq * slat) / p;
|
tangd = (z + rn * esq * slat) / p;
|
||||||
flatn = Math.Atan(tangd) / dtr;
|
flatn = Math.Atan(tangd) / dtr;
|
||||||
@ -543,17 +492,17 @@ namespace CoordinateSharp
|
|||||||
flat = flatn;
|
flat = flatn;
|
||||||
clat = Math.Cos(dtr * flat);
|
clat = Math.Cos(dtr * flat);
|
||||||
|
|
||||||
rrnrm = radcur(flat);
|
rrnrm = this.Radcur(flat);
|
||||||
rn = rrnrm[1];
|
rn = rrnrm[1];
|
||||||
|
|
||||||
altkm = (p / clat) - rn;
|
altkm = p / clat - rn;
|
||||||
|
|
||||||
if (Math.Abs(dlat) < 1.0e-12) { break; }
|
if (Math.Abs(dlat) < 1.0e-12) { break; }
|
||||||
|
|
||||||
}
|
}
|
||||||
//CONVERTER WORKS IN E LAT ONLY, IF E LAT > 180 LAT IS WEST SO IT MUCST BE CONVERTED TO Decimal
|
//CONVERTER WORKS IN E LAT ONLY, IF E LAT > 180 LAT IS WEST SO IT MUCST BE CONVERTED TO Decimal
|
||||||
|
|
||||||
if (flon > 180) { flon = flon - 360; }
|
if (flon > 180) { flon -= 360; }
|
||||||
llhvec[0] = flat;
|
llhvec[0] = flat;
|
||||||
llhvec[1] = flon;
|
llhvec[1] = flon;
|
||||||
llhvec[2] = altkm;
|
llhvec[2] = altkm;
|
||||||
|
@ -1,65 +1,53 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
|
|
||||||
namespace CoordinateSharp
|
namespace CoordinateSharp {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Turn on/off eager loading of certain properties.
|
/// Turn on/off eager loading of certain properties.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public class EagerLoad
|
public class EagerLoad {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Create an EagerLoad object
|
/// Create an EagerLoad object
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public EagerLoad()
|
public EagerLoad() {
|
||||||
{
|
this.Celestial = true;
|
||||||
Celestial = true;
|
this.UTM_MGRS = true;
|
||||||
UTM_MGRS = true;
|
this.Cartesian = true;
|
||||||
Cartesian = true;
|
this.ECEF = true;
|
||||||
ECEF = true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Create an EagerLoad object with all options on or off
|
/// Create an EagerLoad object with all options on or off
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="isOn">Turns EagerLoad on or off</param>
|
/// <param name="isOn">Turns EagerLoad on or off</param>
|
||||||
public EagerLoad(bool isOn)
|
public EagerLoad(Boolean isOn) {
|
||||||
{
|
this.Celestial = isOn;
|
||||||
Celestial = isOn;
|
this.UTM_MGRS = isOn;
|
||||||
UTM_MGRS = isOn;
|
this.Cartesian = isOn;
|
||||||
Cartesian = isOn;
|
this.ECEF = isOn;
|
||||||
ECEF = isOn;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Create an EagerLoad object with only the specified flag options turned on.
|
/// Create an EagerLoad object with only the specified flag options turned on.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="et">EagerLoadType</param>
|
/// <param name="et">EagerLoadType</param>
|
||||||
public EagerLoad(EagerLoadType et)
|
public EagerLoad(EagerLoadType et) {
|
||||||
{
|
this.Cartesian = false;
|
||||||
Cartesian = false;
|
this.Celestial = false;
|
||||||
Celestial = false;
|
this.UTM_MGRS = false;
|
||||||
UTM_MGRS = false;
|
this.ECEF = false;
|
||||||
ECEF = false;
|
|
||||||
|
|
||||||
if (et.HasFlag(EagerLoadType.Cartesian))
|
if (et.HasFlag(EagerLoadType.Cartesian)) {
|
||||||
{
|
this.Cartesian = true;
|
||||||
Cartesian = true;
|
|
||||||
}
|
}
|
||||||
if (et.HasFlag(EagerLoadType.Celestial))
|
if (et.HasFlag(EagerLoadType.Celestial)) {
|
||||||
{
|
this.Celestial = true;
|
||||||
Celestial = true;
|
|
||||||
}
|
}
|
||||||
if (et.HasFlag(EagerLoadType.UTM_MGRS))
|
if (et.HasFlag(EagerLoadType.UTM_MGRS)) {
|
||||||
{
|
this.UTM_MGRS = true;
|
||||||
UTM_MGRS = true;
|
|
||||||
}
|
}
|
||||||
if (et.HasFlag(EagerLoadType.ECEF))
|
if (et.HasFlag(EagerLoadType.ECEF)) {
|
||||||
{
|
this.ECEF = true;
|
||||||
ECEF = true;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -68,8 +56,7 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="et">EagerLoadType</param>
|
/// <param name="et">EagerLoadType</param>
|
||||||
/// <returns>EagerLoad</returns>
|
/// <returns>EagerLoad</returns>
|
||||||
public static EagerLoad Create(EagerLoadType et)
|
public static EagerLoad Create(EagerLoadType et) {
|
||||||
{
|
|
||||||
EagerLoad el = new EagerLoad(et);
|
EagerLoad el = new EagerLoad(et);
|
||||||
return el;
|
return el;
|
||||||
}
|
}
|
||||||
@ -77,27 +64,26 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Eager load celestial information.
|
/// Eager load celestial information.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool Celestial { get; set; }
|
public Boolean Celestial { get; set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Eager load UTM and MGRS information
|
/// Eager load UTM and MGRS information
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool UTM_MGRS { get; set; }
|
public Boolean UTM_MGRS { get; set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Eager load Cartesian information
|
/// Eager load Cartesian information
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool Cartesian { get; set; }
|
public Boolean Cartesian { get; set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Eager load ECEF information
|
/// Eager load ECEF information
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool ECEF { get; set; }
|
public Boolean ECEF { get; set; }
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// EagerLoad Enumerator
|
/// EagerLoad Enumerator
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
[Flags]
|
[Flags]
|
||||||
public enum EagerLoadType
|
public enum EagerLoadType {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// UTM and MGRS
|
/// UTM and MGRS
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
@ -1,31 +1,25 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Text;
|
|
||||||
|
|
||||||
namespace CoordinateSharp
|
namespace CoordinateSharp {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Coordinate formatting options for a Coordinate object.
|
/// Coordinate formatting options for a Coordinate object.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public class CoordinateFormatOptions
|
public class CoordinateFormatOptions {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Set default values with the constructor.
|
/// Set default values with the constructor.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public CoordinateFormatOptions()
|
public CoordinateFormatOptions() {
|
||||||
{
|
this.Format = CoordinateFormatType.Degree_Minutes_Seconds;
|
||||||
Format = CoordinateFormatType.Degree_Minutes_Seconds;
|
this.Round = 3;
|
||||||
Round = 3;
|
this.Display_Leading_Zeros = false;
|
||||||
Display_Leading_Zeros = false;
|
this.Display_Trailing_Zeros = false;
|
||||||
Display_Trailing_Zeros = false;
|
this.Display_Symbols = true;
|
||||||
Display_Symbols = true;
|
this.Display_Degree_Symbol = true;
|
||||||
Display_Degree_Symbol = true;
|
this.Display_Minute_Symbol = true;
|
||||||
Display_Minute_Symbol = true;
|
this.Display_Seconds_Symbol = true;
|
||||||
Display_Seconds_Symbol = true;
|
this.Display_Hyphens = false;
|
||||||
Display_Hyphens = false;
|
this.Position_First = true;
|
||||||
Position_First = true;
|
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Coordinate format type.
|
/// Coordinate format type.
|
||||||
@ -34,47 +28,46 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Rounds Coordinates to the set value.
|
/// Rounds Coordinates to the set value.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public int Round { get; set; }
|
public Int32 Round { get; set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Displays leading zeros.
|
/// Displays leading zeros.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool Display_Leading_Zeros { get; set; }
|
public Boolean Display_Leading_Zeros { get; set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Display trailing zeros.
|
/// Display trailing zeros.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool Display_Trailing_Zeros { get; set; }
|
public Boolean Display_Trailing_Zeros { get; set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Allow symbols to display.
|
/// Allow symbols to display.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool Display_Symbols { get; set; }
|
public Boolean Display_Symbols { get; set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Display degree symbols.
|
/// Display degree symbols.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool Display_Degree_Symbol { get; set; }
|
public Boolean Display_Degree_Symbol { get; set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Display minute symbols.
|
/// Display minute symbols.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool Display_Minute_Symbol { get; set; }
|
public Boolean Display_Minute_Symbol { get; set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Display secons symbol.
|
/// Display secons symbol.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool Display_Seconds_Symbol { get; set; }
|
public Boolean Display_Seconds_Symbol { get; set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Display hyphens between values.
|
/// Display hyphens between values.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool Display_Hyphens { get; set; }
|
public Boolean Display_Hyphens { get; set; }
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Show coordinate position first.
|
/// Show coordinate position first.
|
||||||
/// Will show last if set 'false'.
|
/// Will show last if set 'false'.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool Position_First { get; set; }
|
public Boolean Position_First { get; set; }
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Coordinate Format Types.
|
/// Coordinate Format Types.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public enum CoordinateFormatType
|
public enum CoordinateFormatType {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Decimal Degree Format
|
/// Decimal Degree Format
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
@ -1,17 +1,15 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Linq;
|
|
||||||
using System.Diagnostics;
|
|
||||||
using System.ComponentModel;
|
using System.ComponentModel;
|
||||||
|
using System.Diagnostics;
|
||||||
|
using System.Linq;
|
||||||
|
|
||||||
namespace CoordinateSharp
|
namespace CoordinateSharp {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Military Grid Reference System (MGRS). Uses the WGS 84 Datum.
|
/// Military Grid Reference System (MGRS). Uses the WGS 84 Datum.
|
||||||
/// Relies upon values from the UniversalTransverseMercator class
|
/// Relies upon values from the UniversalTransverseMercator class
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public class MilitaryGridReferenceSystem : INotifyPropertyChanged
|
public class MilitaryGridReferenceSystem : INotifyPropertyChanged {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Create an MGRS object with WGS84 datum
|
/// Create an MGRS object with WGS84 datum
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -20,24 +18,23 @@ namespace CoordinateSharp
|
|||||||
/// <param name="d">Digraph</param>
|
/// <param name="d">Digraph</param>
|
||||||
/// <param name="e">Easting</param>
|
/// <param name="e">Easting</param>
|
||||||
/// <param name="n">Northing</param>
|
/// <param name="n">Northing</param>
|
||||||
public MilitaryGridReferenceSystem(string latz, int longz, string d, double e, double n)
|
public MilitaryGridReferenceSystem(String latz, Int32 longz, String d, Double e, Double n) {
|
||||||
{
|
String digraphLettersE = "ABCDEFGHJKLMNPQRSTUVWXYZ";
|
||||||
string digraphLettersE = "ABCDEFGHJKLMNPQRSTUVWXYZ";
|
String digraphLettersN = "ABCDEFGHJKLMNPQRSTUV";
|
||||||
string digraphLettersN = "ABCDEFGHJKLMNPQRSTUV";
|
|
||||||
if (longz < 1 || longz > 60) { Debug.WriteLine("Longitudinal zone out of range", "UTM longitudinal zones must be between 1-60."); }
|
if (longz < 1 || longz > 60) { Debug.WriteLine("Longitudinal zone out of range", "UTM longitudinal zones must be between 1-60."); }
|
||||||
if (!Verify_Lat_Zone(latz)) { throw new ArgumentException("Latitudinal zone invalid", "UTM latitudinal zone was unrecognized."); }
|
if (!this.Verify_Lat_Zone(latz)) { throw new ArgumentException("Latitudinal zone invalid", "UTM latitudinal zone was unrecognized."); }
|
||||||
if (n < 0 || n > 10000000) { throw new ArgumentOutOfRangeException("Northing out of range", "Northing must be between 0-10,000,000."); }
|
if (n < 0 || n > 10000000) { throw new ArgumentOutOfRangeException("Northing out of range", "Northing must be between 0-10,000,000."); }
|
||||||
if (d.Count() < 2 || d.Count() > 2) { throw new ArgumentException("Digraph invalid", "MGRS Digraph was unrecognized."); }
|
if (d.Count() < 2 || d.Count() > 2) { throw new ArgumentException("Digraph invalid", "MGRS Digraph was unrecognized."); }
|
||||||
if (digraphLettersE.ToCharArray().ToList().Where(x => x.ToString() == d.ToUpper()[0].ToString()).Count() == 0) { throw new ArgumentException("Digraph invalid", "MGRS Digraph was unrecognized."); }
|
if (digraphLettersE.ToCharArray().ToList().Where(x => x.ToString() == d.ToUpper()[0].ToString()).Count() == 0) { throw new ArgumentException("Digraph invalid", "MGRS Digraph was unrecognized."); }
|
||||||
if (digraphLettersN.ToCharArray().ToList().Where(x => x.ToString() == d.ToUpper()[1].ToString()).Count() == 0) { throw new ArgumentException("Digraph invalid", "MGRS Digraph was unrecognized."); }
|
if (digraphLettersN.ToCharArray().ToList().Where(x => x.ToString() == d.ToUpper()[1].ToString()).Count() == 0) { throw new ArgumentException("Digraph invalid", "MGRS Digraph was unrecognized."); }
|
||||||
latZone = latz;
|
this.LatZone = latz;
|
||||||
longZone = longz;
|
this.LongZone = longz;
|
||||||
digraph = d;
|
this.Digraph = d;
|
||||||
easting = e;
|
this.Easting = e;
|
||||||
northing = n;
|
this.Northing = n;
|
||||||
//WGS84
|
//WGS84
|
||||||
equatorialRadius = 6378137.0;
|
this.equatorialRadius = 6378137.0;
|
||||||
inverseFlattening = 298.257223563;
|
this.inverseFlattening = 298.257223563;
|
||||||
|
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@ -50,132 +47,89 @@ namespace CoordinateSharp
|
|||||||
/// <param name="n">Northing</param>
|
/// <param name="n">Northing</param>
|
||||||
/// <param name="rad">Equatorial Radius</param>
|
/// <param name="rad">Equatorial Radius</param>
|
||||||
/// <param name="flt">Inverse Flattening</param>
|
/// <param name="flt">Inverse Flattening</param>
|
||||||
public MilitaryGridReferenceSystem(string latz, int longz, string d, double e, double n,double rad, double flt)
|
public MilitaryGridReferenceSystem(String latz, Int32 longz, String d, Double e, Double n, Double rad, Double flt) {
|
||||||
{
|
String digraphLettersE = "ABCDEFGHJKLMNPQRSTUVWXYZ";
|
||||||
string digraphLettersE = "ABCDEFGHJKLMNPQRSTUVWXYZ";
|
String digraphLettersN = "ABCDEFGHJKLMNPQRSTUV";
|
||||||
string digraphLettersN = "ABCDEFGHJKLMNPQRSTUV";
|
|
||||||
if (longz < 1 || longz > 60) { Debug.WriteLine("Longitudinal zone out of range", "UTM longitudinal zones must be between 1-60."); }
|
if (longz < 1 || longz > 60) { Debug.WriteLine("Longitudinal zone out of range", "UTM longitudinal zones must be between 1-60."); }
|
||||||
if (!Verify_Lat_Zone(latz)) { throw new ArgumentException("Latitudinal zone invalid", "UTM latitudinal zone was unrecognized."); }
|
if (!this.Verify_Lat_Zone(latz)) { throw new ArgumentException("Latitudinal zone invalid", "UTM latitudinal zone was unrecognized."); }
|
||||||
if (n < 0 || n > 10000000) { throw new ArgumentOutOfRangeException("Northing out of range", "Northing must be between 0-10,000,000."); }
|
if (n < 0 || n > 10000000) { throw new ArgumentOutOfRangeException("Northing out of range", "Northing must be between 0-10,000,000."); }
|
||||||
if (d.Count() < 2 || d.Count() > 2) { throw new ArgumentException("Digraph invalid", "MGRS Digraph was unrecognized."); }
|
if (d.Count() < 2 || d.Count() > 2) { throw new ArgumentException("Digraph invalid", "MGRS Digraph was unrecognized."); }
|
||||||
if (digraphLettersE.ToCharArray().ToList().Where(x => x.ToString() == d.ToUpper()[0].ToString()).Count() == 0) { throw new ArgumentException("Digraph invalid", "MGRS Digraph was unrecognized."); }
|
if (digraphLettersE.ToCharArray().ToList().Where(x => x.ToString() == d.ToUpper()[0].ToString()).Count() == 0) { throw new ArgumentException("Digraph invalid", "MGRS Digraph was unrecognized."); }
|
||||||
if (digraphLettersN.ToCharArray().ToList().Where(x => x.ToString() == d.ToUpper()[1].ToString()).Count() == 0) { throw new ArgumentException("Digraph invalid", "MGRS Digraph was unrecognized."); }
|
if (digraphLettersN.ToCharArray().ToList().Where(x => x.ToString() == d.ToUpper()[1].ToString()).Count() == 0) { throw new ArgumentException("Digraph invalid", "MGRS Digraph was unrecognized."); }
|
||||||
latZone = latz;
|
this.LatZone = latz;
|
||||||
longZone = longz;
|
this.LongZone = longz;
|
||||||
digraph = d;
|
this.Digraph = d;
|
||||||
easting = e;
|
this.Easting = e;
|
||||||
northing = n;
|
this.Northing = n;
|
||||||
|
|
||||||
equatorialRadius = rad;
|
this.equatorialRadius = rad;
|
||||||
inverseFlattening = flt;
|
this.inverseFlattening = flt;
|
||||||
}
|
}
|
||||||
|
|
||||||
private double equatorialRadius;
|
private Double equatorialRadius;
|
||||||
private double inverseFlattening;
|
private Double inverseFlattening;
|
||||||
private string latZone;
|
|
||||||
private int longZone;
|
|
||||||
private double easting;
|
|
||||||
private double northing;
|
|
||||||
private string digraph;
|
|
||||||
|
|
||||||
private bool withinCoordinateSystemBounds=true;
|
private Boolean Verify_Lat_Zone(String l) => LatZones.longZongLetters.Where(x => x == l.ToUpper()).Count() == 1;
|
||||||
|
|
||||||
private bool Verify_Lat_Zone(string l)
|
|
||||||
{
|
|
||||||
if (LatZones.longZongLetters.Where(x => x == l.ToUpper()).Count() != 1)
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// MGRS Zone Letter
|
/// MGRS Zone Letter
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public string LatZone
|
public String LatZone { get; private set; }
|
||||||
{
|
|
||||||
get { return latZone; }
|
|
||||||
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// MGRS Zone Number
|
/// MGRS Zone Number
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public int LongZone
|
public Int32 LongZone { get; private set; }
|
||||||
{
|
|
||||||
get { return longZone; }
|
|
||||||
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// MGRS Easting
|
/// MGRS Easting
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Easting
|
public Double Easting { get; private set; }
|
||||||
{
|
|
||||||
get { return easting; }
|
|
||||||
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// MGRS Northing
|
/// MGRS Northing
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Northing
|
public Double Northing { get; private set; }
|
||||||
{
|
|
||||||
get { return northing; }
|
|
||||||
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// MGRS Digraph
|
/// MGRS Digraph
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public string Digraph
|
public String Digraph { get; private set; }
|
||||||
{
|
|
||||||
get { return digraph; }
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Is MGRS conversion within the coordinate system's accurate boundaries after conversion from Lat/Long.
|
/// Is MGRS conversion within the coordinate system's accurate boundaries after conversion from Lat/Long.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool WithinCoordinateSystemBounds
|
public Boolean WithinCoordinateSystemBounds { get; private set; } = true;
|
||||||
{
|
|
||||||
get { return withinCoordinateSystemBounds; }
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
internal MilitaryGridReferenceSystem(UniversalTransverseMercator utm)
|
internal MilitaryGridReferenceSystem(UniversalTransverseMercator utm) => this.ToMGRS(utm);
|
||||||
{
|
internal void ToMGRS(UniversalTransverseMercator utm) {
|
||||||
ToMGRS(utm);
|
|
||||||
}
|
|
||||||
internal void ToMGRS(UniversalTransverseMercator utm)
|
|
||||||
{
|
|
||||||
Digraphs digraphs = new Digraphs();
|
Digraphs digraphs = new Digraphs();
|
||||||
|
|
||||||
string digraph1 = digraphs.getDigraph1(utm.LongZone, utm.Easting);
|
String digraph1 = digraphs.GetDigraph1(utm.LongZone, utm.Easting);
|
||||||
string digraph2 = digraphs.getDigraph2(utm.LongZone, utm.Northing);
|
String digraph2 = digraphs.GetDigraph2(utm.LongZone, utm.Northing);
|
||||||
|
|
||||||
digraph = digraph1 + digraph2;
|
this.Digraph = digraph1 + digraph2;
|
||||||
latZone = utm.LatZone;
|
this.LatZone = utm.LatZone;
|
||||||
longZone = utm.LongZone;
|
this.LongZone = utm.LongZone;
|
||||||
|
|
||||||
//String easting = String.valueOf((int)_easting);
|
//String easting = String.valueOf((int)_easting);
|
||||||
string e = ((int)utm.Easting).ToString();
|
String e = ((Int32)utm.Easting).ToString();
|
||||||
if (e.Length < 5)
|
if (e.Length < 5) {
|
||||||
{
|
e = "00000" + ((Int32)utm.Easting).ToString();
|
||||||
e = "00000" + ((int)utm.Easting).ToString();
|
|
||||||
}
|
}
|
||||||
e = e.Substring(e.Length - 5);
|
e = e.Substring(e.Length - 5);
|
||||||
|
|
||||||
easting = Convert.ToInt32(e);
|
this.Easting = Convert.ToInt32(e);
|
||||||
|
|
||||||
string n = ((int)utm.Northing).ToString();
|
String n = ((Int32)utm.Northing).ToString();
|
||||||
if (n.Length < 5)
|
if (n.Length < 5) {
|
||||||
{
|
n = "0000" + ((Int32)utm.Northing).ToString();
|
||||||
n = "0000" + ((int)utm.Northing).ToString();
|
|
||||||
}
|
}
|
||||||
n = n.Substring(n.Length - 5);
|
n = n.Substring(n.Length - 5);
|
||||||
|
|
||||||
northing = Convert.ToInt32(n);
|
this.Northing = Convert.ToInt32(n);
|
||||||
equatorialRadius = utm.equatorial_radius;
|
this.equatorialRadius = utm.equatorial_radius;
|
||||||
inverseFlattening = utm.inverse_flattening;
|
this.inverseFlattening = utm.inverse_flattening;
|
||||||
|
|
||||||
withinCoordinateSystemBounds = utm.WithinCoordinateSystemBounds;
|
this.WithinCoordinateSystemBounds = utm.WithinCoordinateSystemBounds;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@ -183,81 +137,64 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="mgrs">MilitaryGridReferenceSystem</param>
|
/// <param name="mgrs">MilitaryGridReferenceSystem</param>
|
||||||
/// <returns>Coordinate object</returns>
|
/// <returns>Coordinate object</returns>
|
||||||
public static Coordinate MGRStoLatLong(MilitaryGridReferenceSystem mgrs)
|
public static Coordinate MGRStoLatLong(MilitaryGridReferenceSystem mgrs) {
|
||||||
{
|
String latz = mgrs.LatZone;
|
||||||
string latz = mgrs.LatZone;
|
String digraph = mgrs.Digraph;
|
||||||
string digraph = mgrs.Digraph;
|
|
||||||
|
|
||||||
char eltr = digraph[0];
|
Char eltr = digraph[0];
|
||||||
char nltr = digraph[1];
|
Char nltr = digraph[1];
|
||||||
|
|
||||||
string digraphLettersE = "ABCDEFGHJKLMNPQRSTUVWXYZ";
|
String digraphLettersE = "ABCDEFGHJKLMNPQRSTUVWXYZ";
|
||||||
string digraphLettersN = "ABCDEFGHJKLMNPQRSTUV";
|
//String digraphLettersN = "ABCDEFGHJKLMNPQRSTUV";
|
||||||
string digraphLettersAll="";
|
String digraphLettersAll = "";
|
||||||
for (int lt = 1; lt < 25; lt++)
|
for (Int32 lt = 1; lt < 25; lt++) {
|
||||||
{
|
|
||||||
digraphLettersAll += "ABCDEFGHJKLMNPQRSTUV";
|
digraphLettersAll += "ABCDEFGHJKLMNPQRSTUV";
|
||||||
}
|
}
|
||||||
|
|
||||||
var eidx = digraphLettersE.IndexOf(eltr);
|
Int32 eidx = digraphLettersE.IndexOf(eltr);
|
||||||
var nidx = digraphLettersN.IndexOf(nltr);
|
//Int32 nidx = digraphLettersN.IndexOf(nltr);
|
||||||
if (mgrs.LongZone / 2.0 == Math.Floor(mgrs.LongZone / 2.0))
|
if (mgrs.LongZone / 2.0 == Math.Floor(mgrs.LongZone / 2.0)) {
|
||||||
{
|
//nidx -= 5; // correction for even numbered zones
|
||||||
nidx -= 5; // correction for even numbered zones
|
|
||||||
}
|
}
|
||||||
|
|
||||||
var ebase = 100000 * (1 + eidx - 8 * Math.Floor(Convert.ToDouble(eidx) / 8));
|
Double ebase = 100000 * (1 + eidx - 8 * Math.Floor(Convert.ToDouble(eidx) / 8));
|
||||||
var latBand = digraphLettersE.IndexOf(latz);
|
Int32 latBand = digraphLettersE.IndexOf(latz);
|
||||||
var latBandLow = 8 * latBand - 96;
|
Int32 latBandLow = 8 * latBand - 96;
|
||||||
var latBandHigh = 8 * latBand - 88;
|
Int32 latBandHigh = 8 * latBand - 88;
|
||||||
|
|
||||||
if (latBand < 2)
|
if (latBand < 2) {
|
||||||
{
|
|
||||||
latBandLow = -90;
|
latBandLow = -90;
|
||||||
latBandHigh = -80;
|
latBandHigh = -80;
|
||||||
}
|
} else if (latBand == 21) {
|
||||||
else if (latBand == 21)
|
|
||||||
{
|
|
||||||
latBandLow = 72;
|
latBandLow = 72;
|
||||||
latBandHigh = 84;
|
latBandHigh = 84;
|
||||||
}
|
} else if (latBand > 21) {
|
||||||
else if (latBand > 21)
|
|
||||||
{
|
|
||||||
latBandLow = 84;
|
latBandLow = 84;
|
||||||
latBandHigh = 90;
|
latBandHigh = 90;
|
||||||
}
|
}
|
||||||
|
|
||||||
var lowLetter = Math.Floor(100 + 1.11 * latBandLow);
|
Double lowLetter = Math.Floor(100 + 1.11 * latBandLow);
|
||||||
var highLetter = Math.Round(100 + 1.11 * latBandHigh);
|
Double highLetter = Math.Round(100 + 1.11 * latBandHigh);
|
||||||
|
Int32 l = Convert.ToInt32(lowLetter);
|
||||||
|
Int32 h = Convert.ToInt32(highLetter);
|
||||||
|
|
||||||
string latBandLetters = null;
|
String latBandLetters = mgrs.LongZone / 2.0 == Math.Floor(mgrs.LongZone / 2.0) ? digraphLettersAll.Substring(l + 5, h + 5).ToString() : digraphLettersAll.Substring(l, h).ToString();
|
||||||
int l = Convert.ToInt32(lowLetter);
|
Double nbase = 100000 * (lowLetter + latBandLetters.IndexOf(nltr));
|
||||||
int h = Convert.ToInt32(highLetter);
|
|
||||||
if (mgrs.LongZone / 2.0 == Math.Floor(mgrs.LongZone / 2.0))
|
|
||||||
{
|
|
||||||
latBandLetters = digraphLettersAll.Substring(l + 5, h + 5).ToString();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
latBandLetters = digraphLettersAll.Substring(l, h).ToString();
|
|
||||||
}
|
|
||||||
var nbase = 100000 * (lowLetter + latBandLetters.IndexOf(nltr));
|
|
||||||
//latBandLetters.IndexOf(nltr) value causing incorrect Northing below -80
|
//latBandLetters.IndexOf(nltr) value causing incorrect Northing below -80
|
||||||
var x = ebase + mgrs.Easting;
|
Double x = ebase + mgrs.Easting;
|
||||||
var y = nbase + mgrs.Northing;
|
Double y = nbase + mgrs.Northing;
|
||||||
if (y > 10000000)
|
if (y > 10000000) {
|
||||||
{
|
y -= 10000000;
|
||||||
y = y - 10000000;
|
|
||||||
}
|
}
|
||||||
if (nbase >= 10000000)
|
if (nbase >= 10000000) {
|
||||||
{
|
y = nbase + mgrs.Northing - 10000000;
|
||||||
y = nbase + mgrs.northing - 10000000;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
var southern = nbase < 10000000;
|
_ = nbase < 10000000;
|
||||||
UniversalTransverseMercator utm = new UniversalTransverseMercator(mgrs.LatZone, mgrs.LongZone, x, y);
|
UniversalTransverseMercator utm = new UniversalTransverseMercator(mgrs.LatZone, mgrs.LongZone, x, y) {
|
||||||
utm.equatorial_radius = mgrs.equatorialRadius;
|
equatorial_radius = mgrs.equatorialRadius,
|
||||||
utm.inverse_flattening = mgrs.inverseFlattening;
|
inverse_flattening = mgrs.inverseFlattening
|
||||||
|
};
|
||||||
Coordinate c = UniversalTransverseMercator.ConvertUTMtoLatLong(utm);
|
Coordinate c = UniversalTransverseMercator.ConvertUTMtoLatLong(utm);
|
||||||
|
|
||||||
c.Set_Datum(mgrs.equatorialRadius, mgrs.inverseFlattening);
|
c.Set_Datum(mgrs.equatorialRadius, mgrs.inverseFlattening);
|
||||||
@ -269,11 +206,8 @@ namespace CoordinateSharp
|
|||||||
/// MGRS Default String Format
|
/// MGRS Default String Format
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <returns>MGRS Formatted Coordinate String</returns>
|
/// <returns>MGRS Formatted Coordinate String</returns>
|
||||||
public override string ToString()
|
public override String ToString() => !this.WithinCoordinateSystemBounds ? "" : this.LongZone.ToString() + this.LatZone + " " + this.Digraph + " " + ((Int32)this.Easting).ToString("00000") + " " + ((Int32)this.Northing).ToString("00000");
|
||||||
{
|
//MGRS Coordinate is outside its reliable boundaries. Return empty.
|
||||||
if (!withinCoordinateSystemBounds) { return ""; }//MGRS Coordinate is outside its reliable boundaries. Return empty.
|
|
||||||
return longZone.ToString() + LatZone + " " + digraph + " " + ((int)easting).ToString("00000") + " " + ((int)northing).ToString("00000");
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Property changed event
|
/// Property changed event
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -282,12 +216,6 @@ namespace CoordinateSharp
|
|||||||
/// Notify property changed
|
/// Notify property changed
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="propName">Property name</param>
|
/// <param name="propName">Property name</param>
|
||||||
public void NotifyPropertyChanged(string propName)
|
public void NotifyPropertyChanged(String propName) => PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propName));
|
||||||
{
|
|
||||||
if (PropertyChanged != null)
|
|
||||||
{
|
|
||||||
PropertyChanged(this, new PropertyChangedEventArgs(propName));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -1,16 +1,14 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Linq;
|
|
||||||
using System.Diagnostics;
|
|
||||||
using System.ComponentModel;
|
using System.ComponentModel;
|
||||||
|
using System.Diagnostics;
|
||||||
|
using System.Linq;
|
||||||
|
|
||||||
namespace CoordinateSharp
|
namespace CoordinateSharp {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Universal Transverse Mercator (UTM) coordinate system. Uses the WGS 84 Datum.
|
/// Universal Transverse Mercator (UTM) coordinate system. Uses the WGS 84 Datum.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public class UniversalTransverseMercator : INotifyPropertyChanged
|
public class UniversalTransverseMercator : INotifyPropertyChanged {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Creates a UniversalTransverMercator object with a WGS84 Datum.
|
/// Creates a UniversalTransverMercator object with a WGS84 Datum.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -18,20 +16,19 @@ namespace CoordinateSharp
|
|||||||
/// <param name="longz">Longitude zone</param>
|
/// <param name="longz">Longitude zone</param>
|
||||||
/// <param name="est">Easting</param>
|
/// <param name="est">Easting</param>
|
||||||
/// <param name="nrt">Northing</param>
|
/// <param name="nrt">Northing</param>
|
||||||
public UniversalTransverseMercator(string latz, int longz, double est, double nrt)
|
public UniversalTransverseMercator(String latz, Int32 longz, Double est, Double nrt) {
|
||||||
{
|
|
||||||
if (longz < 1 || longz > 60) { Debug.WriteLine("Longitudinal zone out of range", "UTM longitudinal zones must be between 1-60."); }
|
if (longz < 1 || longz > 60) { Debug.WriteLine("Longitudinal zone out of range", "UTM longitudinal zones must be between 1-60."); }
|
||||||
if (!Verify_Lat_Zone(latz)) { Debug.WriteLine("Latitudinal zone invalid", "UTM latitudinal zone was unrecognized."); }
|
if (!this.Verify_Lat_Zone(latz)) { Debug.WriteLine("Latitudinal zone invalid", "UTM latitudinal zone was unrecognized."); }
|
||||||
if (est < 160000 || est > 834000) { Debug.WriteLine("The Easting value provided is outside the max allowable range. Use with caution."); }
|
if (est < 160000 || est > 834000) { Debug.WriteLine("The Easting value provided is outside the max allowable range. Use with caution."); }
|
||||||
if (nrt < 0 || nrt > 10000000) { Debug.WriteLine("Northing out of range", "Northing must be between 0-10,000,000."); }
|
if (nrt < 0 || nrt > 10000000) { Debug.WriteLine("Northing out of range", "Northing must be between 0-10,000,000."); }
|
||||||
|
|
||||||
latZone = latz;
|
this.latZone = latz;
|
||||||
longZone =longz;
|
this.longZone = longz;
|
||||||
easting = est;
|
this.easting = est;
|
||||||
northing = nrt;
|
this.northing = nrt;
|
||||||
|
|
||||||
equatorial_radius = 6378137.0;
|
this.equatorial_radius = 6378137.0;
|
||||||
inverse_flattening = 298.257223563;
|
this.inverse_flattening = 298.257223563;
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Creates a UniversalTransverMercator object with a custom Datum.
|
/// Creates a UniversalTransverMercator object with a custom Datum.
|
||||||
@ -42,87 +39,72 @@ namespace CoordinateSharp
|
|||||||
/// <param name="nrt">Northing</param>
|
/// <param name="nrt">Northing</param>
|
||||||
/// <param name="radius">Equatorial Radius</param>
|
/// <param name="radius">Equatorial Radius</param>
|
||||||
/// <param name="flaten">Inverse Flattening</param>
|
/// <param name="flaten">Inverse Flattening</param>
|
||||||
public UniversalTransverseMercator(string latz, int longz, double est, double nrt, double radius, double flaten)
|
public UniversalTransverseMercator(String latz, Int32 longz, Double est, Double nrt, Double radius, Double flaten) {
|
||||||
{
|
|
||||||
if (longz < 1 || longz > 60) { Debug.WriteLine("Longitudinal zone out of range", "UTM longitudinal zones must be between 1-60."); }
|
if (longz < 1 || longz > 60) { Debug.WriteLine("Longitudinal zone out of range", "UTM longitudinal zones must be between 1-60."); }
|
||||||
if (!Verify_Lat_Zone(latz)) { Debug.WriteLine("Latitudinal zone invalid", "UTM latitudinal zone was unrecognized."); }
|
if (!this.Verify_Lat_Zone(latz)) { Debug.WriteLine("Latitudinal zone invalid", "UTM latitudinal zone was unrecognized."); }
|
||||||
if (est < 160000 || est > 834000) { Debug.WriteLine("The Easting value provided is outside the max allowable range. Use with caution."); }
|
if (est < 160000 || est > 834000) { Debug.WriteLine("The Easting value provided is outside the max allowable range. Use with caution."); }
|
||||||
if (nrt < 0 || nrt > 10000000) { Debug.WriteLine("Northing out of range", "Northing must be between 0-10,000,000."); }
|
if (nrt < 0 || nrt > 10000000) { Debug.WriteLine("Northing out of range", "Northing must be between 0-10,000,000."); }
|
||||||
|
|
||||||
latZone = latz;
|
this.latZone = latz;
|
||||||
longZone = longz;
|
this.longZone = longz;
|
||||||
easting = est;
|
this.easting = est;
|
||||||
northing = nrt;
|
this.northing = nrt;
|
||||||
|
|
||||||
equatorial_radius = radius;
|
this.equatorial_radius = radius;
|
||||||
inverse_flattening = flaten;
|
this.inverse_flattening = flaten;
|
||||||
}
|
}
|
||||||
|
|
||||||
private Coordinate coordinate;
|
//private readonly Coordinate coordinate;
|
||||||
|
|
||||||
internal double equatorial_radius;
|
internal Double equatorial_radius;
|
||||||
internal double inverse_flattening;
|
internal Double inverse_flattening;
|
||||||
private string latZone;
|
private String latZone;
|
||||||
private int longZone;
|
private Int32 longZone;
|
||||||
|
|
||||||
private double easting;
|
private Double easting;
|
||||||
private double northing;
|
private Double northing;
|
||||||
|
|
||||||
private bool withinCoordinateSystemBounds = true;
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// UTM Zone Letter
|
/// UTM Zone Letter
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public string LatZone
|
public String LatZone {
|
||||||
{
|
get => this.latZone;
|
||||||
get { return latZone; }
|
set {
|
||||||
set
|
if (this.latZone != value) {
|
||||||
{
|
this.latZone = value;
|
||||||
if (latZone != value)
|
|
||||||
{
|
|
||||||
latZone = value;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// UTM Zone Number
|
/// UTM Zone Number
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public int LongZone
|
public Int32 LongZone {
|
||||||
{
|
get => this.longZone;
|
||||||
get { return longZone; }
|
set {
|
||||||
set
|
if (this.longZone != value) {
|
||||||
{
|
this.longZone = value;
|
||||||
if (longZone != value)
|
|
||||||
{
|
|
||||||
longZone = value;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// UTM Easting
|
/// UTM Easting
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Easting
|
public Double Easting {
|
||||||
{
|
get => this.easting;
|
||||||
get { return easting; }
|
set {
|
||||||
set
|
if (this.easting != value) {
|
||||||
{
|
this.easting = value;
|
||||||
if (easting != value)
|
|
||||||
{
|
|
||||||
easting = value;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// UTM Northing
|
/// UTM Northing
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Northing
|
public Double Northing {
|
||||||
{
|
get => this.northing;
|
||||||
get { return northing; }
|
set {
|
||||||
set
|
if (this.northing != value) {
|
||||||
{
|
this.northing = value;
|
||||||
if (northing != value)
|
|
||||||
{
|
|
||||||
northing = value;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -130,25 +112,16 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Datum Equatorial Radius / Semi Major Axis
|
/// Datum Equatorial Radius / Semi Major Axis
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Equatorial_Radius
|
public Double Equatorial_Radius => this.equatorial_radius;
|
||||||
{
|
|
||||||
get { return equatorial_radius; }
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Datum Flattening
|
/// Datum Flattening
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Inverse_Flattening
|
public Double Inverse_Flattening => this.inverse_flattening;
|
||||||
{
|
|
||||||
get { return inverse_flattening; }
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Is the UTM conversion within the coordinate system's accurate boundaries after conversion from Lat/Long.
|
/// Is the UTM conversion within the coordinate system's accurate boundaries after conversion from Lat/Long.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool WithinCoordinateSystemBounds
|
public Boolean WithinCoordinateSystemBounds { get; private set; } = true;
|
||||||
{
|
|
||||||
get { return withinCoordinateSystemBounds; }
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Constructs a UTM object based off DD Lat/Long
|
/// Constructs a UTM object based off DD Lat/Long
|
||||||
@ -156,8 +129,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="lat">DD Latitude</param>
|
/// <param name="lat">DD Latitude</param>
|
||||||
/// <param name="longi">DD Longitide</param>
|
/// <param name="longi">DD Longitide</param>
|
||||||
/// <param name="c">Parent Coordinate Object</param>
|
/// <param name="c">Parent Coordinate Object</param>
|
||||||
internal UniversalTransverseMercator(double lat, double longi, Coordinate c)
|
internal UniversalTransverseMercator(Double lat, Double longi, Coordinate _) {
|
||||||
{
|
|
||||||
//validate coords
|
//validate coords
|
||||||
|
|
||||||
//if (lat > 180) { throw new ArgumentOutOfRangeException("Degrees out of range", "Longitudinal coordinate decimal cannot be greater than 180."); }
|
//if (lat > 180) { throw new ArgumentOutOfRangeException("Degrees out of range", "Longitudinal coordinate decimal cannot be greater than 180."); }
|
||||||
@ -165,11 +137,11 @@ namespace CoordinateSharp
|
|||||||
|
|
||||||
//if (longi > 90) { throw new ArgumentOutOfRangeException("Degrees out of range", "Latitudinal coordinate decimal cannot be greater than 90."); }
|
//if (longi > 90) { throw new ArgumentOutOfRangeException("Degrees out of range", "Latitudinal coordinate decimal cannot be greater than 90."); }
|
||||||
//if (longi < -90) { throw new ArgumentOutOfRangeException("Degrees out of range", "Latitudinal coordinate decimal cannot be less than 90."); }
|
//if (longi < -90) { throw new ArgumentOutOfRangeException("Degrees out of range", "Latitudinal coordinate decimal cannot be less than 90."); }
|
||||||
equatorial_radius = 6378137.0;
|
this.equatorial_radius = 6378137.0;
|
||||||
inverse_flattening = 298.257223563;
|
this.inverse_flattening = 298.257223563;
|
||||||
ToUTM(lat, longi, this);
|
this.ToUTM(lat, longi, this);
|
||||||
|
|
||||||
coordinate = c;
|
//this.coordinate = c;
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Constructs a UTM object based off DD Lat/Long
|
/// Constructs a UTM object based off DD Lat/Long
|
||||||
@ -179,13 +151,12 @@ namespace CoordinateSharp
|
|||||||
/// <param name="c">Parent Coordinate Object</param>
|
/// <param name="c">Parent Coordinate Object</param>
|
||||||
/// <param name="rad">Equatorial Radius</param>
|
/// <param name="rad">Equatorial Radius</param>
|
||||||
/// <param name="flt">Flattening</param>
|
/// <param name="flt">Flattening</param>
|
||||||
internal UniversalTransverseMercator(double lat, double longi, Coordinate c,double rad,double flt)
|
internal UniversalTransverseMercator(Double lat, Double longi, Coordinate _, Double rad, Double flt) {
|
||||||
{
|
this.equatorial_radius = rad;
|
||||||
equatorial_radius = rad;
|
this.inverse_flattening = flt;
|
||||||
inverse_flattening = flt;
|
this.ToUTM(lat, longi, this);
|
||||||
ToUTM(lat, longi, this);
|
|
||||||
|
|
||||||
coordinate = c;
|
//this.coordinate = c;
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Constructs a UTM object based off a UTM coordinate
|
/// Constructs a UTM object based off a UTM coordinate
|
||||||
@ -198,24 +169,22 @@ namespace CoordinateSharp
|
|||||||
/// <param name="c">Parent Coordinate Object</param>
|
/// <param name="c">Parent Coordinate Object</param>
|
||||||
/// <param name="rad">Equatorial Radius</param>
|
/// <param name="rad">Equatorial Radius</param>
|
||||||
/// <param name="flt">Inverse Flattening</param>
|
/// <param name="flt">Inverse Flattening</param>
|
||||||
internal UniversalTransverseMercator(string latz, int longz, double e, double n, Coordinate c, double rad, double flt)
|
internal UniversalTransverseMercator(String latz, Int32 longz, Double e, Double n, Coordinate c, Double rad, Double flt) {
|
||||||
{
|
|
||||||
//validate utm
|
//validate utm
|
||||||
if (longz < 1 || longz > 60) { Debug.WriteLine("Longitudinal zone out of range", "UTM longitudinal zones must be between 1-60."); }
|
if (longz < 1 || longz > 60) { Debug.WriteLine("Longitudinal zone out of range", "UTM longitudinal zones must be between 1-60."); }
|
||||||
if (!Verify_Lat_Zone(latz)) { throw new ArgumentException("Latitudinal zone invalid", "UTM latitudinal zone was unrecognized."); }
|
if (!this.Verify_Lat_Zone(latz)) { throw new ArgumentException("Latitudinal zone invalid", "UTM latitudinal zone was unrecognized."); }
|
||||||
if (e < 160000 || e > 834000) { Debug.WriteLine("The Easting value provided is outside the max allowable range. If this is intentional, use with caution."); }
|
if (e < 160000 || e > 834000) { Debug.WriteLine("The Easting value provided is outside the max allowable range. If this is intentional, use with caution."); }
|
||||||
if (n < 0 || n > 10000000) { throw new ArgumentOutOfRangeException("Northing out of range", "Northing must be between 0-10,000,000."); }
|
if (n < 0 || n > 10000000) { throw new ArgumentOutOfRangeException("Northing out of range", "Northing must be between 0-10,000,000."); }
|
||||||
equatorial_radius = rad;
|
this.equatorial_radius = rad;
|
||||||
inverse_flattening = flt;
|
this.inverse_flattening = flt;
|
||||||
latZone = latz;
|
this.latZone = latz;
|
||||||
longZone = longz;
|
this.longZone = longz;
|
||||||
|
|
||||||
easting = e;
|
this.easting = e;
|
||||||
northing = n;
|
this.northing = n;
|
||||||
|
|
||||||
coordinate = c;
|
//this.coordinate = c;
|
||||||
if (c.Latitude.DecimalDegree <= -80 || c.Latitude.DecimalDegree >= 84) { withinCoordinateSystemBounds = false; }
|
this.WithinCoordinateSystemBounds = c.Latitude.DecimalDegree > -80 && c.Latitude.DecimalDegree < 84;
|
||||||
else { withinCoordinateSystemBounds = true; }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@ -223,160 +192,115 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="l">Zone Letter</param>
|
/// <param name="l">Zone Letter</param>
|
||||||
/// <returns>boolean</returns>
|
/// <returns>boolean</returns>
|
||||||
private bool Verify_Lat_Zone(string l)
|
private Boolean Verify_Lat_Zone(String l) => LatZones.longZongLetters.Where(x => x == l.ToUpper()).Count() == 1;
|
||||||
{
|
//private Double degreeToRadian(Double degree) => degree * Math.PI / 180;
|
||||||
if (LatZones.longZongLetters.Where(x => x == l.ToUpper()).Count() != 1)
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
private double degreeToRadian(double degree)
|
|
||||||
{
|
|
||||||
return degree * Math.PI / 180;
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Assigns UTM values based of Lat/Long
|
/// Assigns UTM values based of Lat/Long
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="lat">DD Latitude</param>
|
/// <param name="lat">DD Latitude</param>
|
||||||
/// <param name="longi">DD longitude</param>
|
/// <param name="longi">DD longitude</param>
|
||||||
/// <param name="utm">UTM Object to modify</param>
|
/// <param name="utm">UTM Object to modify</param>
|
||||||
internal void ToUTM(double lat, double longi, UniversalTransverseMercator utm)
|
internal void ToUTM(Double lat, Double longi, UniversalTransverseMercator utm) {
|
||||||
{
|
Int32 zone = (Int32)Math.Floor(longi / 6 + 31);
|
||||||
string letter = "";
|
String letter = lat < -72 ? "C"
|
||||||
double easting = 0;
|
: lat < -64 ? "D"
|
||||||
double northing = 0;
|
: lat < -56 ? "E"
|
||||||
int zone = (int)Math.Floor(longi / 6 + 31);
|
: lat < -48 ? "F"
|
||||||
if (lat < -72)
|
: lat < -40 ? "G"
|
||||||
letter = "C";
|
: lat < -32 ? "H"
|
||||||
else if (lat < -64)
|
: lat < -24 ? "J"
|
||||||
letter = "D";
|
: lat < -16 ? "K"
|
||||||
else if (lat < -56)
|
: lat < -8 ? "L"
|
||||||
letter = "E";
|
: lat < 0 ? "M"
|
||||||
else if (lat < -48)
|
: lat < 8 ? "N"
|
||||||
letter = "F";
|
: lat < 16 ? "P"
|
||||||
else if (lat < -40)
|
: lat < 24 ? "Q"
|
||||||
letter = "G";
|
: lat < 32 ? "R"
|
||||||
else if (lat < -32)
|
: lat < 40 ? "S"
|
||||||
letter = "H";
|
: lat < 48 ? "T"
|
||||||
else if (lat < -24)
|
: lat < 56 ? "U"
|
||||||
letter = "J";
|
: lat < 64 ? "V"
|
||||||
else if (lat < -16)
|
: lat < 72 ? "W" : "X";
|
||||||
letter = "K";
|
Double a = utm.equatorial_radius;
|
||||||
else if (lat < -8)
|
Double f = 1.0 / utm.inverse_flattening;
|
||||||
letter = "L";
|
Double b = a * (1 - f); // polar radius
|
||||||
else if (lat < 0)
|
|
||||||
letter = "M";
|
|
||||||
else if (lat < 8)
|
|
||||||
letter = "N";
|
|
||||||
else if (lat < 16)
|
|
||||||
letter = "P";
|
|
||||||
else if (lat < 24)
|
|
||||||
letter = "Q";
|
|
||||||
else if (lat < 32)
|
|
||||||
letter = "R";
|
|
||||||
else if (lat < 40)
|
|
||||||
letter = "S";
|
|
||||||
else if (lat < 48)
|
|
||||||
letter = "T";
|
|
||||||
else if (lat < 56)
|
|
||||||
letter = "U";
|
|
||||||
else if (lat < 64)
|
|
||||||
letter = "V";
|
|
||||||
else if (lat < 72)
|
|
||||||
letter = "W";
|
|
||||||
else
|
|
||||||
letter = "X";
|
|
||||||
|
|
||||||
double a = utm.equatorial_radius;
|
Double e = Math.Sqrt(1 - Math.Pow(b, 2) / Math.Pow(a, 2));
|
||||||
double f = 1.0 / utm.inverse_flattening;
|
_ = e / Math.Sqrt(1 - Math.Pow(e, 1));
|
||||||
double b = a * (1 - f); // polar radius
|
|
||||||
|
|
||||||
double e = Math.Sqrt(1 - Math.Pow(b, 2) / Math.Pow(a, 2));
|
Double drad = Math.PI / 180;
|
||||||
double e0 = e / Math.Sqrt(1 - Math.Pow(e, 1));
|
Double k0 = 0.9996;
|
||||||
|
|
||||||
double drad = Math.PI / 180;
|
Double phi = lat * drad; // convert latitude to radians
|
||||||
double k0 = 0.9996;
|
_ = longi * drad; // convert longitude to radians
|
||||||
|
Double utmz = 1 + Math.Floor((longi + 180) / 6.0); // longitude to utm zone
|
||||||
double phi = lat * drad; // convert latitude to radians
|
Double zcm = 3 + 6.0 * (utmz - 1) - 180; // central meridian of a zone
|
||||||
double lng = longi * drad; // convert longitude to radians
|
|
||||||
double utmz = 1 + Math.Floor((longi + 180) / 6.0); // longitude to utm zone
|
|
||||||
double zcm = 3 + 6.0 * (utmz - 1) - 180; // central meridian of a zone
|
|
||||||
// this gives us zone A-B for below 80S
|
// this gives us zone A-B for below 80S
|
||||||
double esq = (1 - (b / a) * (b / a));
|
Double esq = 1 - b / a * (b / a);
|
||||||
double e0sq = e * e / (1 - Math.Pow(e, 2));
|
Double e0sq = e * e / (1 - Math.Pow(e, 2));
|
||||||
double M = 0;
|
Double N = a / Math.Sqrt(1 - Math.Pow(e * Math.Sin(phi), 2));
|
||||||
|
Double T = Math.Pow(Math.Tan(phi), 2);
|
||||||
double N = a / Math.Sqrt(1 - Math.Pow(e * Math.Sin(phi), 2));
|
Double C = e0sq * Math.Pow(Math.Cos(phi), 2);
|
||||||
double T = Math.Pow(Math.Tan(phi), 2);
|
Double A = (longi - zcm) * drad * Math.Cos(phi);
|
||||||
double C = e0sq * Math.Pow(Math.Cos(phi), 2);
|
|
||||||
double A = (longi - zcm) * drad * Math.Cos(phi);
|
|
||||||
|
|
||||||
// calculate M (USGS style)
|
// calculate M (USGS style)
|
||||||
M = phi * (1 - esq * (1.0 / 4.0 + esq * (3.0 / 64.0 + 5.0 * esq / 256.0)));
|
Double M = phi * (1 - esq * (1.0 / 4.0 + esq * (3.0 / 64.0 + 5.0 * esq / 256.0)));
|
||||||
M = M - Math.Sin(2.0 * phi) * (esq * (3.0 / 8.0 + esq * (3.0 / 32.0 + 45.0 * esq / 1024.0)));
|
M -= Math.Sin(2.0 * phi) * (esq * (3.0 / 8.0 + esq * (3.0 / 32.0 + 45.0 * esq / 1024.0)));
|
||||||
M = M + Math.Sin(4.0 * phi) * (esq * esq * (15.0 / 256.0 + esq * 45.0 / 1024.0));
|
M += Math.Sin(4.0 * phi) * (esq * esq * (15.0 / 256.0 + esq * 45.0 / 1024.0));
|
||||||
M = M - Math.Sin(6.0 * phi) * (esq * esq * esq * (35.0 / 3072.0));
|
M -= Math.Sin(6.0 * phi) * (esq * esq * esq * (35.0 / 3072.0));
|
||||||
M = M * a;//Arc length along standard meridian
|
M *= a;//Arc length along standard meridian
|
||||||
|
|
||||||
double M0 = 0;// if another point of origin is used than the equator
|
Double M0 = 0;// if another point of origin is used than the equator
|
||||||
|
|
||||||
// Calculate the UTM values...
|
// Calculate the UTM values...
|
||||||
// first the easting
|
// first the easting
|
||||||
var x = k0 * N * A * (1 + A * A * ((1 - T + C) / 6 + A * A * (5 - 18 * T + T * T + 72.0 * C - 58 * e0sq) / 120.0)); //Easting relative to CM
|
Double x = k0 * N * A * (1 + A * A * ((1 - T + C) / 6 + A * A * (5 - 18 * T + T * T + 72.0 * C - 58 * e0sq) / 120.0)); //Easting relative to CM
|
||||||
x = x + 500000; // standard easting
|
x += 500000; // standard easting
|
||||||
|
|
||||||
// Northing
|
// Northing
|
||||||
|
|
||||||
double y = k0 * (M - M0 + N * Math.Tan(phi) * (A * A * (1 / 2.0 + A * A * ((5 - T + 9 * C + 4 * C * C) / 24.0 + A * A * (61 - 58 * T + T * T + 600 * C - 330 * e0sq) / 720.0)))); // first from the equator
|
Double y = k0 * (M - M0 + N * Math.Tan(phi) * (A * A * (1 / 2.0 + A * A * ((5 - T + 9 * C + 4 * C * C) / 24.0 + A * A * (61 - 58 * T + T * T + 600 * C - 330 * e0sq) / 720.0)))); // first from the equator
|
||||||
double yg = y + 10000000; //yg = y global, from S. Pole
|
_ = y + 10000000; //yg = y global, from S. Pole
|
||||||
if (y < 0)
|
if (y < 0) {
|
||||||
{
|
|
||||||
y = 10000000 + y; // add in false northing if south of the equator
|
y = 10000000 + y; // add in false northing if south of the equator
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
easting = Math.Round(10 * (x)) / 10.0;
|
Double easting = Math.Round(10 * x) / 10.0;
|
||||||
northing = Math.Round(10 * y) / 10.0;
|
Double northing = Math.Round(10 * y) / 10.0;
|
||||||
|
|
||||||
utm.latZone = letter;
|
utm.latZone = letter;
|
||||||
utm.longZone = zone;
|
utm.longZone = zone;
|
||||||
utm.easting = easting;
|
utm.easting = easting;
|
||||||
utm.northing = northing;
|
utm.northing = northing;
|
||||||
|
|
||||||
if(lat<=-80 || lat >= 84) { withinCoordinateSystemBounds = false; }
|
this.WithinCoordinateSystemBounds = lat > -80 && lat < 84;
|
||||||
else { withinCoordinateSystemBounds = true; }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// UTM Default String Format
|
/// UTM Default String Format
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <returns>UTM Formatted Coordinate String</returns>
|
/// <returns>UTM Formatted Coordinate String</returns>
|
||||||
public override string ToString()
|
public override String ToString() => !this.WithinCoordinateSystemBounds ? "" : this.longZone.ToString() + this.LatZone + " " + (Int32)this.easting + "mE " + (Int32)this.northing + "mN";
|
||||||
{
|
//MGRS Coordinate is outside its reliable boundaries. Return empty.
|
||||||
if (!withinCoordinateSystemBounds) { return ""; }//MGRS Coordinate is outside its reliable boundaries. Return empty.
|
|
||||||
return longZone.ToString() + LatZone + " " + (int)easting + "mE " + (int)northing + "mN";
|
|
||||||
}
|
|
||||||
|
|
||||||
private static Coordinate UTMtoLatLong(double x, double y, double zone, double equatorialRadius, double flattening)
|
private static Coordinate UTMtoLatLong(Double x, Double y, Double zone, Double equatorialRadius, Double flattening) {
|
||||||
{
|
|
||||||
//x easting
|
//x easting
|
||||||
//y northing
|
//y northing
|
||||||
|
|
||||||
//http://home.hiwaay.net/~taylorc/toolbox/geography/geoutm.html
|
//http://home.hiwaay.net/~taylorc/toolbox/geography/geoutm.html
|
||||||
double phif, Nf, Nfpow, nuf2, ep2, tf, tf2, tf4, cf;
|
Double phif, Nf, Nfpow, nuf2, ep2, tf, tf2, tf4, cf;
|
||||||
double x1frac, x2frac, x3frac, x4frac, x5frac, x6frac, x7frac, x8frac;
|
Double x1frac, x2frac, x3frac, x4frac, x5frac, x6frac, x7frac, x8frac;
|
||||||
double x2poly, x3poly, x4poly, x5poly, x6poly, x7poly, x8poly;
|
Double x2poly, x3poly, x4poly, x5poly, x6poly, x7poly, x8poly;
|
||||||
|
|
||||||
double sm_a = equatorialRadius;
|
Double sm_a = equatorialRadius;
|
||||||
double sm_b = equatorialRadius * (1 - (1.0 / flattening)); //Polar Radius
|
Double sm_b = equatorialRadius * (1 - 1.0 / flattening); //Polar Radius
|
||||||
|
|
||||||
/* Get the value of phif, the footpoint latitude. */
|
/* Get the value of phif, the footpoint latitude. */
|
||||||
phif = FootpointLatitude(y, equatorialRadius, flattening);
|
phif = FootpointLatitude(y, equatorialRadius, flattening);
|
||||||
|
|
||||||
/* Precalculate ep2 */
|
/* Precalculate ep2 */
|
||||||
ep2 = (Math.Pow(sm_a, 2.0) - Math.Pow(sm_b, 2.0))
|
ep2 = (Math.Pow(sm_a, 2.0) - Math.Pow(sm_b, 2.0)) / Math.Pow(sm_b, 2.0);
|
||||||
/ Math.Pow(sm_b, 2.0);
|
|
||||||
|
|
||||||
/* Precalculate cos (phif) */
|
/* Precalculate cos (phif) */
|
||||||
cf = Math.Cos(phif);
|
cf = Math.Cos(phif);
|
||||||
@ -424,32 +348,24 @@ namespace CoordinateSharp
|
|||||||
|
|
||||||
x3poly = -1.0 - 2 * tf2 - nuf2;
|
x3poly = -1.0 - 2 * tf2 - nuf2;
|
||||||
|
|
||||||
x4poly = 5.0 + 3.0 * tf2 + 6.0 * nuf2 - 6.0 * tf2 * nuf2
|
x4poly = 5.0 + 3.0 * tf2 + 6.0 * nuf2 - 6.0 * tf2 * nuf2 - 3.0 * (nuf2 * nuf2) - 9.0 * tf2 * (nuf2 * nuf2);
|
||||||
- 3.0 * (nuf2 * nuf2) - 9.0 * tf2 * (nuf2 * nuf2);
|
|
||||||
|
|
||||||
x5poly = 5.0 + 28.0 * tf2 + 24.0 * tf4 + 6.0 * nuf2 + 8.0 * tf2 * nuf2;
|
x5poly = 5.0 + 28.0 * tf2 + 24.0 * tf4 + 6.0 * nuf2 + 8.0 * tf2 * nuf2;
|
||||||
|
|
||||||
x6poly = -61.0 - 90.0 * tf2 - 45.0 * tf4 - 107.0 * nuf2
|
x6poly = -61.0 - 90.0 * tf2 - 45.0 * tf4 - 107.0 * nuf2 + 162.0 * tf2 * nuf2;
|
||||||
+ 162.0 * tf2 * nuf2;
|
|
||||||
|
|
||||||
x7poly = -61.0 - 662.0 * tf2 - 1320.0 * tf4 - 720.0 * (tf4 * tf2);
|
x7poly = -61.0 - 662.0 * tf2 - 1320.0 * tf4 - 720.0 * (tf4 * tf2);
|
||||||
|
|
||||||
x8poly = 1385.0 + 3633.0 * tf2 + 4095.0 * tf4 + 1575 * (tf4 * tf2);
|
x8poly = 1385.0 + 3633.0 * tf2 + 4095.0 * tf4 + 1575 * (tf4 * tf2);
|
||||||
|
|
||||||
/* Calculate latitude */
|
/* Calculate latitude */
|
||||||
double nLat = phif + x2frac * x2poly * (x * x)
|
Double nLat = phif + x2frac * x2poly * (x * x) + x4frac * x4poly * Math.Pow(x, 4.0) + x6frac * x6poly * Math.Pow(x, 6.0) + x8frac * x8poly * Math.Pow(x, 8.0);
|
||||||
+ x4frac * x4poly * Math.Pow(x, 4.0)
|
|
||||||
+ x6frac * x6poly * Math.Pow(x, 6.0)
|
|
||||||
+ x8frac * x8poly * Math.Pow(x, 8.0);
|
|
||||||
|
|
||||||
/* Calculate longitude */
|
/* Calculate longitude */
|
||||||
double nLong = zone + x1frac * x
|
Double nLong = zone + x1frac * x + x3frac * x3poly * Math.Pow(x, 3.0) + x5frac * x5poly * Math.Pow(x, 5.0) + x7frac * x7poly * Math.Pow(x, 7.0);
|
||||||
+ x3frac * x3poly * Math.Pow(x, 3.0)
|
|
||||||
+ x5frac * x5poly * Math.Pow(x, 5.0)
|
|
||||||
+ x7frac * x7poly * Math.Pow(x, 7.0);
|
|
||||||
|
|
||||||
double dLat = RadToDeg(nLat);
|
Double dLat = RadToDeg(nLat);
|
||||||
double dLong = RadToDeg(nLong);
|
Double dLong = RadToDeg(nLong);
|
||||||
if (dLat > 90) { dLat = 90; }
|
if (dLat > 90) { dLat = 90; }
|
||||||
if (dLat < -90) { dLat = -90; }
|
if (dLat < -90) { dLat = -90; }
|
||||||
if (dLong > 180) { dLong = 180; }
|
if (dLong > 180) { dLong = 180; }
|
||||||
@ -465,25 +381,22 @@ namespace CoordinateSharp
|
|||||||
return c;
|
return c;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static double RadToDeg(double rad)
|
private static Double RadToDeg(Double rad) {
|
||||||
{
|
Double pi = 3.14159265358979;
|
||||||
double pi = 3.14159265358979;
|
return rad / pi * 180.0;
|
||||||
return (rad / pi * 180.0);
|
|
||||||
}
|
}
|
||||||
private static double DegToRad(double deg)
|
private static Double DegToRad(Double deg) {
|
||||||
{
|
Double pi = 3.14159265358979;
|
||||||
double pi = 3.14159265358979;
|
return deg / 180.0 * pi;
|
||||||
return (deg / 180.0 * pi);
|
|
||||||
}
|
}
|
||||||
private static double FootpointLatitude(double y, double equatorialRadius, double flattening)
|
private static Double FootpointLatitude(Double y, Double equatorialRadius, Double flattening) {
|
||||||
{
|
Double y_, alpha_, beta_, gamma_, delta_, epsilon_, n;
|
||||||
double y_, alpha_, beta_, gamma_, delta_, epsilon_, n;
|
Double result;
|
||||||
double result;
|
|
||||||
|
|
||||||
|
|
||||||
/* Ellipsoid model constants (actual values here are for WGS84) */
|
/* Ellipsoid model constants (actual values here are for WGS84) */
|
||||||
double sm_a = equatorialRadius;
|
Double sm_a = equatorialRadius;
|
||||||
double sm_b = equatorialRadius * (1 - (1.0 / flattening));
|
Double sm_b = equatorialRadius * (1 - 1.0 / flattening);
|
||||||
|
|
||||||
|
|
||||||
/* Precalculate n (Eq. 10.18) */
|
/* Precalculate n (Eq. 10.18) */
|
||||||
@ -491,31 +404,25 @@ namespace CoordinateSharp
|
|||||||
|
|
||||||
/* Precalculate alpha_ (Eq. 10.22) */
|
/* Precalculate alpha_ (Eq. 10.22) */
|
||||||
/* (Same as alpha in Eq. 10.17) */
|
/* (Same as alpha in Eq. 10.17) */
|
||||||
alpha_ = ((sm_a + sm_b) / 2.0) * (1 + (Math.Pow(n, 2.0) / 4) + (Math.Pow(n, 4.0) / 64));
|
alpha_ = (sm_a + sm_b) / 2.0 * (1 + Math.Pow(n, 2.0) / 4 + Math.Pow(n, 4.0) / 64);
|
||||||
|
|
||||||
/* Precalculate y_ (Eq. 10.23) */
|
/* Precalculate y_ (Eq. 10.23) */
|
||||||
y_ = y / alpha_;
|
y_ = y / alpha_;
|
||||||
|
|
||||||
/* Precalculate beta_ (Eq. 10.22) */
|
/* Precalculate beta_ (Eq. 10.22) */
|
||||||
beta_ = (3.0 * n / 2.0) + (-27.0 * Math.Pow(n, 3.0) / 32.0)
|
beta_ = 3.0 * n / 2.0 + -27.0 * Math.Pow(n, 3.0) / 32.0 + 269.0 * Math.Pow(n, 5.0) / 512.0;
|
||||||
+ (269.0 * Math.Pow(n, 5.0) / 512.0);
|
|
||||||
|
|
||||||
/* Precalculate gamma_ (Eq. 10.22) */
|
/* Precalculate gamma_ (Eq. 10.22) */
|
||||||
gamma_ = (21.0 * Math.Pow(n, 2.0) / 16.0)
|
gamma_ = 21.0 * Math.Pow(n, 2.0) / 16.0 + -55.0 * Math.Pow(n, 4.0) / 32.0;
|
||||||
+ (-55.0 * Math.Pow(n, 4.0) / 32.0);
|
|
||||||
|
|
||||||
/* Precalculate delta_ (Eq. 10.22) */
|
/* Precalculate delta_ (Eq. 10.22) */
|
||||||
delta_ = (151.0 * Math.Pow(n, 3.0) / 96.0)
|
delta_ = 151.0 * Math.Pow(n, 3.0) / 96.0 + -417.0 * Math.Pow(n, 5.0) / 128.0;
|
||||||
+ (-417.0 * Math.Pow(n, 5.0) / 128.0);
|
|
||||||
|
|
||||||
/* Precalculate epsilon_ (Eq. 10.22) */
|
/* Precalculate epsilon_ (Eq. 10.22) */
|
||||||
epsilon_ = (1097.0 * Math.Pow(n, 4.0) / 512.0);
|
epsilon_ = 1097.0 * Math.Pow(n, 4.0) / 512.0;
|
||||||
|
|
||||||
/* Now calculate the sum of the series (Eq. 10.21) */
|
/* Now calculate the sum of the series (Eq. 10.21) */
|
||||||
result = y_ + (beta_ * Math.Sin(2.0 * y_))
|
result = y_ + beta_ * Math.Sin(2.0 * y_) + gamma_ * Math.Sin(4.0 * y_) + delta_ * Math.Sin(6.0 * y_) + epsilon_ * Math.Sin(8.0 * y_);
|
||||||
+ (gamma_ * Math.Sin(4.0 * y_))
|
|
||||||
+ (delta_ * Math.Sin(6.0 * y_))
|
|
||||||
+ (epsilon_ * Math.Sin(8.0 * y_));
|
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@ -525,26 +432,22 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="utm">utm</param>
|
/// <param name="utm">utm</param>
|
||||||
/// <returns>Coordinate object</returns>
|
/// <returns>Coordinate object</returns>
|
||||||
public static Coordinate ConvertUTMtoLatLong(UniversalTransverseMercator utm)
|
public static Coordinate ConvertUTMtoLatLong(UniversalTransverseMercator utm) {
|
||||||
{
|
|
||||||
|
|
||||||
bool southhemi = false;
|
Boolean southhemi = false;
|
||||||
if (utm.latZone == "A" || utm.latZone == "B" || utm.latZone == "C" || utm.latZone == "D" || utm.latZone == "E" || utm.latZone == "F" || utm.latZone == "G" || utm.latZone == "H" || utm.latZone == "J" ||
|
if (utm.latZone == "A" || utm.latZone == "B" || utm.latZone == "C" || utm.latZone == "D" || utm.latZone == "E" || utm.latZone == "F" || utm.latZone == "G" || utm.latZone == "H" || utm.latZone == "J" || utm.latZone == "K" || utm.latZone == "L" || utm.latZone == "M") {
|
||||||
utm.latZone == "K" || utm.latZone == "L" || utm.latZone == "M")
|
|
||||||
{
|
|
||||||
southhemi = true;
|
southhemi = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
double cmeridian;
|
Double cmeridian;
|
||||||
|
|
||||||
double x = utm.Easting - 500000.0;
|
Double x = utm.Easting - 500000.0;
|
||||||
double UTMScaleFactor = 0.9996;
|
Double UTMScaleFactor = 0.9996;
|
||||||
x /= UTMScaleFactor;
|
x /= UTMScaleFactor;
|
||||||
|
|
||||||
/* If in southern hemisphere, adjust y accordingly. */
|
/* If in southern hemisphere, adjust y accordingly. */
|
||||||
double y = utm.Northing;
|
Double y = utm.Northing;
|
||||||
if (southhemi)
|
if (southhemi) {
|
||||||
{
|
|
||||||
y -= 10000000.0;
|
y -= 10000000.0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -554,8 +457,7 @@ namespace CoordinateSharp
|
|||||||
|
|
||||||
Coordinate c = UTMtoLatLong(x, y, cmeridian, utm.equatorial_radius, utm.inverse_flattening);
|
Coordinate c = UTMtoLatLong(x, y, cmeridian, utm.equatorial_radius, utm.inverse_flattening);
|
||||||
|
|
||||||
if (c.Latitude.ToDouble() > 85 || c.Latitude.ToDouble() < -85)
|
if (c.Latitude.ToDouble() > 85 || c.Latitude.ToDouble() < -85) {
|
||||||
{
|
|
||||||
Debug.WriteLine("UTM conversions greater than 85 degrees or less than -85 degree latitude contain major deviations and should be used with caution.");
|
Debug.WriteLine("UTM conversions greater than 85 degrees or less than -85 degree latitude contain major deviations and should be used with caution.");
|
||||||
}
|
}
|
||||||
return c;
|
return c;
|
||||||
@ -563,11 +465,10 @@ namespace CoordinateSharp
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private static double UTMCentralMeridian(double zone)
|
private static Double UTMCentralMeridian(Double zone) {
|
||||||
{
|
Double cmeridian;
|
||||||
double cmeridian;
|
|
||||||
|
|
||||||
cmeridian = DegToRad(-183.0 + (zone * 6.0));
|
cmeridian = DegToRad(-183.0 + zone * 6.0);
|
||||||
|
|
||||||
return cmeridian;
|
return cmeridian;
|
||||||
}
|
}
|
||||||
@ -580,10 +481,8 @@ namespace CoordinateSharp
|
|||||||
/// Notify property changed
|
/// Notify property changed
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="propName">Property name</param>
|
/// <param name="propName">Property name</param>
|
||||||
public void NotifyPropertyChanged(string propName)
|
public void NotifyPropertyChanged(String propName) {
|
||||||
{
|
if (this.PropertyChanged != null) {
|
||||||
if (this.PropertyChanged != null)
|
|
||||||
{
|
|
||||||
PropertyChanged(this, new PropertyChangedEventArgs(propName));
|
PropertyChanged(this, new PropertyChangedEventArgs(propName));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -34,8 +34,7 @@ SOFTWARE.
|
|||||||
using System;
|
using System;
|
||||||
using System.ComponentModel;
|
using System.ComponentModel;
|
||||||
|
|
||||||
namespace CoordinateSharp
|
namespace CoordinateSharp {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Observable class for handling all location based information.
|
/// Observable class for handling all location based information.
|
||||||
/// This is the main class for CoordinateSharp.
|
/// This is the main class for CoordinateSharp.
|
||||||
@ -44,16 +43,14 @@ namespace CoordinateSharp
|
|||||||
/// All information should be pulled from this class to include celestial information
|
/// All information should be pulled from this class to include celestial information
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public class Coordinate : INotifyPropertyChanged
|
public class Coordinate : INotifyPropertyChanged {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Creates an empty Coordinate.
|
/// Creates an empty Coordinate.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <remarks>
|
/// <remarks>
|
||||||
/// Values will need to be provided to latitude/longitude CoordinateParts manually
|
/// Values will need to be provided to latitude/longitude CoordinateParts manually
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
public Coordinate()
|
public Coordinate() {
|
||||||
{
|
|
||||||
this.FormatOptions = new CoordinateFormatOptions();
|
this.FormatOptions = new CoordinateFormatOptions();
|
||||||
this.geoDate = new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc);
|
this.geoDate = new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc);
|
||||||
this.latitude = new CoordinatePart(CoordinateType.Lat);
|
this.latitude = new CoordinatePart(CoordinateType.Lat);
|
||||||
@ -77,8 +74,7 @@ namespace CoordinateSharp
|
|||||||
/// <remarks>
|
/// <remarks>
|
||||||
/// Values will need to be provided to latitude/longitude CoordinateParts manually
|
/// Values will need to be provided to latitude/longitude CoordinateParts manually
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
internal Coordinate(Double equatorialRadius, Double inverseFlattening, Boolean t)
|
internal Coordinate(Double equatorialRadius, Double inverseFlattening, Boolean _) {
|
||||||
{
|
|
||||||
this.FormatOptions = new CoordinateFormatOptions();
|
this.FormatOptions = new CoordinateFormatOptions();
|
||||||
this.geoDate = new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc);
|
this.geoDate = new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc);
|
||||||
this.latitude = new CoordinatePart(CoordinateType.Lat);
|
this.latitude = new CoordinatePart(CoordinateType.Lat);
|
||||||
@ -102,8 +98,7 @@ namespace CoordinateSharp
|
|||||||
/// <remarks>
|
/// <remarks>
|
||||||
/// Geodate will default to 1/1/1900 GMT until provided
|
/// Geodate will default to 1/1/1900 GMT until provided
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
public Coordinate(Double lat, Double longi)
|
public Coordinate(Double lat, Double longi) {
|
||||||
{
|
|
||||||
this.FormatOptions = new CoordinateFormatOptions();
|
this.FormatOptions = new CoordinateFormatOptions();
|
||||||
this.geoDate = new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc);
|
this.geoDate = new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc);
|
||||||
this.latitude = new CoordinatePart(lat, CoordinateType.Lat);
|
this.latitude = new CoordinatePart(lat, CoordinateType.Lat);
|
||||||
@ -126,8 +121,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="lat">latitude</param>
|
/// <param name="lat">latitude</param>
|
||||||
/// <param name="longi">longitude</param>
|
/// <param name="longi">longitude</param>
|
||||||
/// <param name="date">DateTime (UTC)</param>
|
/// <param name="date">DateTime (UTC)</param>
|
||||||
public Coordinate(Double lat, Double longi, DateTime date)
|
public Coordinate(Double lat, Double longi, DateTime date) {
|
||||||
{
|
|
||||||
this.FormatOptions = new CoordinateFormatOptions();
|
this.FormatOptions = new CoordinateFormatOptions();
|
||||||
this.latitude = new CoordinatePart(lat, CoordinateType.Lat);
|
this.latitude = new CoordinatePart(lat, CoordinateType.Lat);
|
||||||
this.longitude = new CoordinatePart(longi, CoordinateType.Long);
|
this.longitude = new CoordinatePart(longi, CoordinateType.Long);
|
||||||
@ -152,8 +146,7 @@ namespace CoordinateSharp
|
|||||||
/// Values will need to be provided to latitude/longitude manually
|
/// Values will need to be provided to latitude/longitude manually
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
/// <param name="eagerLoad">Eager loading options</param>
|
/// <param name="eagerLoad">Eager loading options</param>
|
||||||
public Coordinate(EagerLoad eagerLoad)
|
public Coordinate(EagerLoad eagerLoad) {
|
||||||
{
|
|
||||||
this.FormatOptions = new CoordinateFormatOptions();
|
this.FormatOptions = new CoordinateFormatOptions();
|
||||||
this.geoDate = new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc);
|
this.geoDate = new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc);
|
||||||
this.latitude = new CoordinatePart(CoordinateType.Lat);
|
this.latitude = new CoordinatePart(CoordinateType.Lat);
|
||||||
@ -188,8 +181,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="lat">latitude</param>
|
/// <param name="lat">latitude</param>
|
||||||
/// <param name="longi">longitude</param>
|
/// <param name="longi">longitude</param>
|
||||||
/// <param name="eagerLoad">Eager loading options</param>
|
/// <param name="eagerLoad">Eager loading options</param>
|
||||||
public Coordinate(Double lat, Double longi, EagerLoad eagerLoad)
|
public Coordinate(Double lat, Double longi, EagerLoad eagerLoad) {
|
||||||
{
|
|
||||||
this.FormatOptions = new CoordinateFormatOptions();
|
this.FormatOptions = new CoordinateFormatOptions();
|
||||||
this.geoDate = new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc);
|
this.geoDate = new DateTime(1900, 1, 1, 0, 0, 0, DateTimeKind.Utc);
|
||||||
this.latitude = new CoordinatePart(lat, CoordinateType.Lat);
|
this.latitude = new CoordinatePart(lat, CoordinateType.Lat);
|
||||||
@ -223,8 +215,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="longi">Decimal format longitude</param>
|
/// <param name="longi">Decimal format longitude</param>
|
||||||
/// <param name="date">DateTime you wish to use for celestial calculation</param>
|
/// <param name="date">DateTime you wish to use for celestial calculation</param>
|
||||||
/// <param name="eagerLoad">Eager loading options</param>
|
/// <param name="eagerLoad">Eager loading options</param>
|
||||||
public Coordinate(Double lat, Double longi, DateTime date, EagerLoad eagerLoad)
|
public Coordinate(Double lat, Double longi, DateTime date, EagerLoad eagerLoad) {
|
||||||
{
|
|
||||||
this.FormatOptions = new CoordinateFormatOptions();
|
this.FormatOptions = new CoordinateFormatOptions();
|
||||||
this.latitude = new CoordinatePart(lat, CoordinateType.Lat);
|
this.latitude = new CoordinatePart(lat, CoordinateType.Lat);
|
||||||
this.longitude = new CoordinatePart(longi, CoordinateType.Long);
|
this.longitude = new CoordinatePart(longi, CoordinateType.Long);
|
||||||
@ -261,8 +252,7 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Latitudinal Coordinate Part
|
/// Latitudinal Coordinate Part
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public CoordinatePart Latitude
|
public CoordinatePart Latitude {
|
||||||
{
|
|
||||||
get => this.latitude;
|
get => this.latitude;
|
||||||
set {
|
set {
|
||||||
if (this.latitude != value) {
|
if (this.latitude != value) {
|
||||||
@ -292,8 +282,7 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Longitudinal Coordinate Part
|
/// Longitudinal Coordinate Part
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public CoordinatePart Longitude
|
public CoordinatePart Longitude {
|
||||||
{
|
|
||||||
get => this.longitude;
|
get => this.longitude;
|
||||||
set {
|
set {
|
||||||
if (this.longitude != value) {
|
if (this.longitude != value) {
|
||||||
@ -325,8 +314,7 @@ namespace CoordinateSharp
|
|||||||
/// <remarks>
|
/// <remarks>
|
||||||
/// Assumes all times are in UTC
|
/// Assumes all times are in UTC
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
public DateTime GeoDate
|
public DateTime GeoDate {
|
||||||
{
|
|
||||||
get => this.geoDate;
|
get => this.geoDate;
|
||||||
set {
|
set {
|
||||||
if (this.geoDate != value) {
|
if (this.geoDate != value) {
|
||||||
@ -357,8 +345,7 @@ namespace CoordinateSharp
|
|||||||
/// Uses Ellipsoidal height with no geoid model included.
|
/// Uses Ellipsoidal height with no geoid model included.
|
||||||
/// 0 = Mean Sea Level based on the provided Datum.
|
/// 0 = Mean Sea Level based on the provided Datum.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public ECEF ECEF
|
public ECEF ECEF {
|
||||||
{
|
|
||||||
get => this.ecef;
|
get => this.ecef;
|
||||||
|
|
||||||
//Required due to GeoDetic Height
|
//Required due to GeoDetic Height
|
||||||
@ -376,8 +363,7 @@ namespace CoordinateSharp
|
|||||||
/// Used to determine what format the coordinate was parsed from.
|
/// Used to determine what format the coordinate was parsed from.
|
||||||
/// Will equal "None" if Coordinate was not initialzed via a TryParse() method.
|
/// Will equal "None" if Coordinate was not initialzed via a TryParse() method.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public Parse_Format_Type Parse_Format
|
public Parse_Format_Type Parse_Format {
|
||||||
{
|
|
||||||
get => this.parse_Format;
|
get => this.parse_Format;
|
||||||
internal set {
|
internal set {
|
||||||
if (this.parse_Format != value) {
|
if (this.parse_Format != value) {
|
||||||
@ -399,8 +385,7 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Initialize UTM and MGRS information (required if eager loading is turned off).
|
/// Initialize UTM and MGRS information (required if eager loading is turned off).
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public void LoadUTM_MGRS_Info()
|
public void LoadUTM_MGRS_Info() {
|
||||||
{
|
|
||||||
this.UTM = new UniversalTransverseMercator(this.latitude.ToDouble(), this.longitude.ToDouble(), this);
|
this.UTM = new UniversalTransverseMercator(this.latitude.ToDouble(), this.longitude.ToDouble(), this);
|
||||||
this.MGRS = new MilitaryGridReferenceSystem(this.UTM);
|
this.MGRS = new MilitaryGridReferenceSystem(this.UTM);
|
||||||
}
|
}
|
||||||
@ -431,8 +416,7 @@ namespace CoordinateSharp
|
|||||||
/// Overridden Coordinate ToString() method.
|
/// Overridden Coordinate ToString() method.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <returns>string (formatted).</returns>
|
/// <returns>string (formatted).</returns>
|
||||||
public override String ToString()
|
public override String ToString() {
|
||||||
{
|
|
||||||
String latString = this.latitude.ToString();
|
String latString = this.latitude.ToString();
|
||||||
String longSting = this.longitude.ToString();
|
String longSting = this.longitude.ToString();
|
||||||
return latString + " " + longSting;
|
return latString + " " + longSting;
|
||||||
@ -444,8 +428,7 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="options">CoordinateFormatOptions</param>
|
/// <param name="options">CoordinateFormatOptions</param>
|
||||||
/// <returns>Custom formatted coordinate</returns>
|
/// <returns>Custom formatted coordinate</returns>
|
||||||
public String ToString(CoordinateFormatOptions options)
|
public String ToString(CoordinateFormatOptions options) {
|
||||||
{
|
|
||||||
String latString = this.latitude.ToString(options);
|
String latString = this.latitude.ToString(options);
|
||||||
String longSting = this.longitude.ToString(options);
|
String longSting = this.longitude.ToString(options);
|
||||||
return latString + " " + longSting;
|
return latString + " " + longSting;
|
||||||
@ -458,8 +441,7 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="radius">Equatorial Radius</param>
|
/// <param name="radius">Equatorial Radius</param>
|
||||||
/// <param name="flat">Inverse Flattening</param>
|
/// <param name="flat">Inverse Flattening</param>
|
||||||
public void Set_Datum(Double radius, Double flat)
|
public void Set_Datum(Double radius, Double flat) {
|
||||||
{
|
|
||||||
//WGS84
|
//WGS84
|
||||||
//RADIUS 6378137.0;
|
//RADIUS 6378137.0;
|
||||||
//FLATTENING 298.257223563;
|
//FLATTENING 298.257223563;
|
||||||
@ -487,8 +469,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="radius">Equatorial Radius</param>
|
/// <param name="radius">Equatorial Radius</param>
|
||||||
/// <param name="flat">Inverse Flattening</param>
|
/// <param name="flat">Inverse Flattening</param>
|
||||||
/// <param name="cd">Coordinate_Datum</param>
|
/// <param name="cd">Coordinate_Datum</param>
|
||||||
public void Set_Datum(Double radius, Double flat, Coordinate_Datum cd)
|
public void Set_Datum(Double radius, Double flat, Coordinate_Datum cd) {
|
||||||
{
|
|
||||||
//WGS84
|
//WGS84
|
||||||
//RADIUS 6378137.0;
|
//RADIUS 6378137.0;
|
||||||
//FLATTENING 298.257223563;
|
//FLATTENING 298.257223563;
|
||||||
@ -554,8 +535,7 @@ namespace CoordinateSharp
|
|||||||
/// //New Coordinate - N 25º 4' 54.517" E 24º 57' 29.189"
|
/// //New Coordinate - N 25º 4' 54.517" E 24º 57' 29.189"
|
||||||
/// </code>
|
/// </code>
|
||||||
/// </example>
|
/// </example>
|
||||||
public void Move(Double distance, Double bearing, Shape shape)
|
public void Move(Double distance, Double bearing, Shape shape) {
|
||||||
{
|
|
||||||
//Convert to Radians for formula
|
//Convert to Radians for formula
|
||||||
Double lat1 = this.latitude.ToRadians();
|
Double lat1 = this.latitude.ToRadians();
|
||||||
Double lon1 = this.longitude.ToRadians();
|
Double lon1 = this.longitude.ToRadians();
|
||||||
@ -605,8 +585,7 @@ namespace CoordinateSharp
|
|||||||
/// //New Coordinate - N 24º 56' 21.526" E 25º 4' 23.944"
|
/// //New Coordinate - N 24º 56' 21.526" E 25º 4' 23.944"
|
||||||
/// </code>
|
/// </code>
|
||||||
/// </example>
|
/// </example>
|
||||||
public void Move(Coordinate target, Double distance, Shape shape)
|
public void Move(Coordinate target, Double distance, Shape shape) {
|
||||||
{
|
|
||||||
Distance d = new Distance(this, target, shape);
|
Distance d = new Distance(this, target, shape);
|
||||||
//Convert to Radians for formula
|
//Convert to Radians for formula
|
||||||
Double lat1 = this.latitude.ToRadians();
|
Double lat1 = this.latitude.ToRadians();
|
||||||
@ -656,8 +635,7 @@ namespace CoordinateSharp
|
|||||||
/// //New Coordinate - N 25º 4' 54.517" E 24º 57' 29.189"
|
/// //New Coordinate - N 25º 4' 54.517" E 24º 57' 29.189"
|
||||||
/// </code>
|
/// </code>
|
||||||
/// </example>
|
/// </example>
|
||||||
public void Move(Distance distance, Double bearing, Shape shape)
|
public void Move(Distance distance, Double bearing, Shape shape) {
|
||||||
{
|
|
||||||
//Convert to Radians for formula
|
//Convert to Radians for formula
|
||||||
Double lat1 = this.latitude.ToRadians();
|
Double lat1 = this.latitude.ToRadians();
|
||||||
Double lon1 = this.longitude.ToRadians();
|
Double lon1 = this.longitude.ToRadians();
|
||||||
@ -708,8 +686,7 @@ namespace CoordinateSharp
|
|||||||
/// //New Coordinate - N 24º 56' 21.526" E 25º 4' 23.944"
|
/// //New Coordinate - N 24º 56' 21.526" E 25º 4' 23.944"
|
||||||
/// </code>
|
/// </code>
|
||||||
/// </example>
|
/// </example>
|
||||||
public void Move(Coordinate target, Distance distance, Shape shape)
|
public void Move(Coordinate target, Distance distance, Shape shape) {
|
||||||
{
|
|
||||||
Distance d = new Distance(this, target, shape);
|
Distance d = new Distance(this, target, shape);
|
||||||
//Convert to Radians for formula
|
//Convert to Radians for formula
|
||||||
Double lat1 = this.latitude.ToRadians();
|
Double lat1 = this.latitude.ToRadians();
|
||||||
@ -752,9 +729,7 @@ namespace CoordinateSharp
|
|||||||
/// }
|
/// }
|
||||||
/// </code>
|
/// </code>
|
||||||
/// </example>
|
/// </example>
|
||||||
public static Boolean TryParse(String s, out Coordinate c)
|
public static Boolean TryParse(String s, out Coordinate c) {
|
||||||
{
|
|
||||||
c = null;
|
|
||||||
if (FormatFinder.TryParse(s, CartesianType.Cartesian, out c)) {
|
if (FormatFinder.TryParse(s, CartesianType.Cartesian, out c)) {
|
||||||
Parse_Format_Type pft = c.Parse_Format;
|
Parse_Format_Type pft = c.Parse_Format;
|
||||||
c = new Coordinate(c.Latitude.ToDouble(), c.Longitude.ToDouble()) {
|
c = new Coordinate(c.Latitude.ToDouble(), c.Longitude.ToDouble()) {
|
||||||
@ -781,9 +756,7 @@ namespace CoordinateSharp
|
|||||||
/// }
|
/// }
|
||||||
/// </code>
|
/// </code>
|
||||||
/// </example>
|
/// </example>
|
||||||
public static Boolean TryParse(String s, DateTime geoDate, out Coordinate c)
|
public static Boolean TryParse(String s, DateTime geoDate, out Coordinate c) {
|
||||||
{
|
|
||||||
c = null;
|
|
||||||
if (FormatFinder.TryParse(s, CartesianType.Cartesian, out c)) {
|
if (FormatFinder.TryParse(s, CartesianType.Cartesian, out c)) {
|
||||||
Parse_Format_Type pft = c.Parse_Format;
|
Parse_Format_Type pft = c.Parse_Format;
|
||||||
c = new Coordinate(c.Latitude.ToDouble(), c.Longitude.ToDouble(), geoDate) {
|
c = new Coordinate(c.Latitude.ToDouble(), c.Longitude.ToDouble(), geoDate) {
|
||||||
@ -810,9 +783,7 @@ namespace CoordinateSharp
|
|||||||
/// }
|
/// }
|
||||||
/// </code>
|
/// </code>
|
||||||
/// </example>
|
/// </example>
|
||||||
public static Boolean TryParse(String s, CartesianType ct, out Coordinate c)
|
public static Boolean TryParse(String s, CartesianType ct, out Coordinate c) {
|
||||||
{
|
|
||||||
c = null;
|
|
||||||
if (FormatFinder.TryParse(s, ct, out c)) {
|
if (FormatFinder.TryParse(s, ct, out c)) {
|
||||||
Parse_Format_Type pft = c.Parse_Format;
|
Parse_Format_Type pft = c.Parse_Format;
|
||||||
if (ct == CartesianType.ECEF) {
|
if (ct == CartesianType.ECEF) {
|
||||||
@ -845,9 +816,7 @@ namespace CoordinateSharp
|
|||||||
/// }
|
/// }
|
||||||
/// </code>
|
/// </code>
|
||||||
/// </example>
|
/// </example>
|
||||||
public static Boolean TryParse(String s, DateTime geoDate, CartesianType ct, out Coordinate c)
|
public static Boolean TryParse(String s, DateTime geoDate, CartesianType ct, out Coordinate c) {
|
||||||
{
|
|
||||||
c = null;
|
|
||||||
if (FormatFinder.TryParse(s, ct, out c)) {
|
if (FormatFinder.TryParse(s, ct, out c)) {
|
||||||
Parse_Format_Type pft = c.Parse_Format;
|
Parse_Format_Type pft = c.Parse_Format;
|
||||||
if (ct == CartesianType.ECEF) {
|
if (ct == CartesianType.ECEF) {
|
||||||
@ -872,8 +841,7 @@ namespace CoordinateSharp
|
|||||||
/// Notify property changed
|
/// Notify property changed
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="propName">Property name</param>
|
/// <param name="propName">Property name</param>
|
||||||
public void NotifyPropertyChanged(String propName)
|
public void NotifyPropertyChanged(String propName) {
|
||||||
{
|
|
||||||
switch (propName) {
|
switch (propName) {
|
||||||
case "CelestialInfo":
|
case "CelestialInfo":
|
||||||
if (!this.EagerLoadSettings.Celestial || this.CelestialInfo == null) { return; } //Prevent Null Exceptions and calls while eagerloading is off
|
if (!this.EagerLoadSettings.Celestial || this.CelestialInfo == null) { return; } //Prevent Null Exceptions and calls while eagerloading is off
|
||||||
@ -913,8 +881,7 @@ namespace CoordinateSharp
|
|||||||
/// Objects can be passed to Coordinate object Latitude and Longitude properties.
|
/// Objects can be passed to Coordinate object Latitude and Longitude properties.
|
||||||
/// </remarks>
|
/// </remarks>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public class CoordinatePart : INotifyPropertyChanged
|
public class CoordinatePart : INotifyPropertyChanged {
|
||||||
{
|
|
||||||
//Defaults:
|
//Defaults:
|
||||||
//Format: Degrees Minutes Seconds
|
//Format: Degrees Minutes Seconds
|
||||||
//Rounding: Dependent upon selected format
|
//Rounding: Dependent upon selected format
|
||||||
@ -941,8 +908,7 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Observable decimal format coordinate.
|
/// Observable decimal format coordinate.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public Double DecimalDegree
|
public Double DecimalDegree {
|
||||||
{
|
|
||||||
get => this.decimalDegree;
|
get => this.decimalDegree;
|
||||||
set {
|
set {
|
||||||
//If changing, notify the needed property changes
|
//If changing, notify the needed property changes
|
||||||
@ -1018,8 +984,7 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Observable decimal format minute.
|
/// Observable decimal format minute.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public Double DecimalMinute
|
public Double DecimalMinute {
|
||||||
{
|
|
||||||
get => this.decimalMinute;
|
get => this.decimalMinute;
|
||||||
set {
|
set {
|
||||||
if (this.decimalMinute != value) {
|
if (this.decimalMinute != value) {
|
||||||
@ -1048,7 +1013,7 @@ namespace CoordinateSharp
|
|||||||
|
|
||||||
Decimal newDM = decValue / 60; //divide decimalMinute by 60 to get storage value
|
Decimal newDM = decValue / 60; //divide decimalMinute by 60 to get storage value
|
||||||
Decimal newDD = this.degrees + newDM;//Add new decimal value to the floor degree value to get new decimalDegree;
|
Decimal newDD = this.degrees + newDM;//Add new decimal value to the floor degree value to get new decimalDegree;
|
||||||
if (this.decimalDegree < 0) { newDD = newDD * -1; } //Restore negative if needed
|
if (this.decimalDegree < 0) { newDD *= -1; } //Restore negative if needed
|
||||||
|
|
||||||
this.decimalDegree = Convert.ToDouble(newDD); //Convert back to double for storage
|
this.decimalDegree = Convert.ToDouble(newDD); //Convert back to double for storage
|
||||||
|
|
||||||
@ -1064,8 +1029,7 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Observable coordinate degree.
|
/// Observable coordinate degree.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public Int32 Degrees
|
public Int32 Degrees {
|
||||||
{
|
|
||||||
get => this.degrees;
|
get => this.degrees;
|
||||||
set {
|
set {
|
||||||
//Validate Value
|
//Validate Value
|
||||||
@ -1105,8 +1069,7 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Observable coordinate minute.
|
/// Observable coordinate minute.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public Int32 Minutes
|
public Int32 Minutes {
|
||||||
{
|
|
||||||
get => this.minutes;
|
get => this.minutes;
|
||||||
set {
|
set {
|
||||||
if (this.minutes != value) {
|
if (this.minutes != value) {
|
||||||
@ -1114,9 +1077,9 @@ namespace CoordinateSharp
|
|||||||
//Validate the minutes
|
//Validate the minutes
|
||||||
Decimal vMin = Convert.ToDecimal(value);
|
Decimal vMin = Convert.ToDecimal(value);
|
||||||
if (this.type == CoordinateType.Lat) {
|
if (this.type == CoordinateType.Lat) {
|
||||||
if (this.degrees + (vMin / 60) > 90) { throw new ArgumentOutOfRangeException("Degrees out of range", "Latitudinal degrees cannot be greater than 90"); }
|
if (this.degrees + vMin / 60 > 90) { throw new ArgumentOutOfRangeException("Degrees out of range", "Latitudinal degrees cannot be greater than 90"); }
|
||||||
} else {
|
} else {
|
||||||
if (this.degrees + (vMin / 60) > 180) { throw new ArgumentOutOfRangeException("Degrees out of range", "Longitudinal degrees cannot be greater than 180"); }
|
if (this.degrees + vMin / 60 > 180) { throw new ArgumentOutOfRangeException("Degrees out of range", "Longitudinal degrees cannot be greater than 180"); }
|
||||||
}
|
}
|
||||||
if (value >= 60) {
|
if (value >= 60) {
|
||||||
throw new ArgumentOutOfRangeException("Minutes out of range", "Minutes cannot be greater than or equal to 60");
|
throw new ArgumentOutOfRangeException("Minutes out of range", "Minutes cannot be greater than or equal to 60");
|
||||||
@ -1154,8 +1117,7 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Observable coordinate second.
|
/// Observable coordinate second.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public Double Seconds
|
public Double Seconds {
|
||||||
{
|
|
||||||
get => this.seconds;
|
get => this.seconds;
|
||||||
set {
|
set {
|
||||||
if (value < 0) { value *= -1; }//Adjust accidental negative input
|
if (value < 0) { value *= -1; }//Adjust accidental negative input
|
||||||
@ -1182,9 +1144,9 @@ namespace CoordinateSharp
|
|||||||
this.seconds = value;
|
this.seconds = value;
|
||||||
|
|
||||||
|
|
||||||
Double degABS = Math.Abs(this.decimalDegree); //Make decimalDegree positive
|
//Double degABS = Math.Abs(this.decimalDegree); //Make decimalDegree positive
|
||||||
Double degFloor = Math.Truncate(degABS); //Truncate the number left of the decimal
|
//Double degFloor = Math.Truncate(degABS); //Truncate the number left of the decimal
|
||||||
Decimal f = Convert.ToDecimal(degFloor); //Convert to decimal to keep precision
|
//Decimal f = Convert.ToDecimal(degFloor); //Convert to decimal to keep precision
|
||||||
|
|
||||||
Decimal secs = Convert.ToDecimal(this.seconds); //Convert seconds to decimal for calculations
|
Decimal secs = Convert.ToDecimal(this.seconds); //Convert seconds to decimal for calculations
|
||||||
secs /= 60; //Convert to storage format
|
secs /= 60; //Convert to storage format
|
||||||
@ -1207,8 +1169,7 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Observable coordinate position.
|
/// Observable coordinate position.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public CoordinatesPosition Position
|
public CoordinatesPosition Position {
|
||||||
{
|
|
||||||
get => this.position;
|
get => this.position;
|
||||||
set {
|
set {
|
||||||
if (this.position != value) {
|
if (this.position != value) {
|
||||||
@ -1231,8 +1192,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="t">CoordinateType</param>
|
/// <param name="t">CoordinateType</param>
|
||||||
/// <param name="c">Parent Coordinate object</param>
|
/// <param name="c">Parent Coordinate object</param>
|
||||||
[Obsolete("Method is deprecated. You no longer need to pass a Coordinate object through the constructor.")]
|
[Obsolete("Method is deprecated. You no longer need to pass a Coordinate object through the constructor.")]
|
||||||
public CoordinatePart(CoordinateType t, Coordinate c)
|
public CoordinatePart(CoordinateType t, Coordinate c) {
|
||||||
{
|
|
||||||
this.parent = c;
|
this.parent = c;
|
||||||
this.type = t;
|
this.type = t;
|
||||||
this.decimalDegree = 0;
|
this.decimalDegree = 0;
|
||||||
@ -1248,8 +1208,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="t">Coordinate type</param>
|
/// <param name="t">Coordinate type</param>
|
||||||
/// <param name="c">Parent Coordinate object</param>
|
/// <param name="c">Parent Coordinate object</param>
|
||||||
[Obsolete("Method is deprecated. You no longer need to pass a Coordinate object through the constructor.")]
|
[Obsolete("Method is deprecated. You no longer need to pass a Coordinate object through the constructor.")]
|
||||||
public CoordinatePart(Double value, CoordinateType t, Coordinate c)
|
public CoordinatePart(Double value, CoordinateType t, Coordinate c) {
|
||||||
{
|
|
||||||
this.parent = c;
|
this.parent = c;
|
||||||
this.type = t;
|
this.type = t;
|
||||||
|
|
||||||
@ -1287,8 +1246,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="pos">Coordinate Part Position</param>
|
/// <param name="pos">Coordinate Part Position</param>
|
||||||
/// <param name="c">Parent Coordinate</param>
|
/// <param name="c">Parent Coordinate</param>
|
||||||
[Obsolete("Method is deprecated. You no longer need to pass a Coordinate object through the constructor.")]
|
[Obsolete("Method is deprecated. You no longer need to pass a Coordinate object through the constructor.")]
|
||||||
public CoordinatePart(Int32 deg, Int32 min, Double sec, CoordinatesPosition pos, Coordinate c)
|
public CoordinatePart(Int32 deg, Int32 min, Double sec, CoordinatesPosition pos, Coordinate c) {
|
||||||
{
|
|
||||||
this.parent = c;
|
this.parent = c;
|
||||||
this.type = pos == CoordinatesPosition.N || pos == CoordinatesPosition.S ? CoordinateType.Lat : CoordinateType.Long;
|
this.type = pos == CoordinatesPosition.N || pos == CoordinatesPosition.S ? CoordinateType.Lat : CoordinateType.Long;
|
||||||
|
|
||||||
@ -1308,12 +1266,12 @@ namespace CoordinateSharp
|
|||||||
minD += secD; //Decimal Minutes
|
minD += secD; //Decimal Minutes
|
||||||
|
|
||||||
if (this.type == CoordinateType.Long) {
|
if (this.type == CoordinateType.Long) {
|
||||||
if (deg + (minD / 60) > 180) { throw new ArgumentOutOfRangeException("Degrees out of range", "Longitudinal Degrees cannot be greater than 180."); }
|
if (deg + minD / 60 > 180) { throw new ArgumentOutOfRangeException("Degrees out of range", "Longitudinal Degrees cannot be greater than 180."); }
|
||||||
} else {
|
} else {
|
||||||
if (deg + (minD / 60) > 90) { throw new ArgumentOutOfRangeException("Degrees out of range", "Latitudinal Degrees cannot be greater than 90."); }
|
if (deg + minD / 60 > 90) { throw new ArgumentOutOfRangeException("Degrees out of range", "Latitudinal Degrees cannot be greater than 90."); }
|
||||||
}
|
}
|
||||||
this.decimalMinute = Convert.ToDouble(minD);
|
this.decimalMinute = Convert.ToDouble(minD);
|
||||||
Decimal dd = Convert.ToDecimal(deg) + (minD / 60);
|
Decimal dd = Convert.ToDecimal(deg) + minD / 60;
|
||||||
|
|
||||||
|
|
||||||
if (pos == CoordinatesPosition.S || pos == CoordinatesPosition.W) {
|
if (pos == CoordinatesPosition.S || pos == CoordinatesPosition.W) {
|
||||||
@ -1329,8 +1287,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="pos">Coordinate Part Position</param>
|
/// <param name="pos">Coordinate Part Position</param>
|
||||||
/// <param name="c">Parent Coordinate object</param>
|
/// <param name="c">Parent Coordinate object</param>
|
||||||
[Obsolete("Method is deprecated. You no longer need to pass a Coordinate object through the constructor.")]
|
[Obsolete("Method is deprecated. You no longer need to pass a Coordinate object through the constructor.")]
|
||||||
public CoordinatePart(Int32 deg, Double minSec, CoordinatesPosition pos, Coordinate c)
|
public CoordinatePart(Int32 deg, Double minSec, CoordinatesPosition pos, Coordinate c) {
|
||||||
{
|
|
||||||
this.parent = c;
|
this.parent = c;
|
||||||
|
|
||||||
this.type = pos == CoordinatesPosition.N || pos == CoordinatesPosition.S ? CoordinateType.Lat : CoordinateType.Long;
|
this.type = pos == CoordinatesPosition.N || pos == CoordinatesPosition.S ? CoordinateType.Lat : CoordinateType.Long;
|
||||||
@ -1341,9 +1298,9 @@ namespace CoordinateSharp
|
|||||||
if (minSec >= 60) { throw new ArgumentOutOfRangeException("Minutes out of range", "Minutes cannot be greater than or equal to 60."); }
|
if (minSec >= 60) { throw new ArgumentOutOfRangeException("Minutes out of range", "Minutes cannot be greater than or equal to 60."); }
|
||||||
|
|
||||||
if (this.type == CoordinateType.Lat) {
|
if (this.type == CoordinateType.Lat) {
|
||||||
if (deg + (minSec / 60) > 90) { throw new ArgumentOutOfRangeException("Degree out of range", "Latitudinal degrees cannot be greater than 90."); }
|
if (deg + minSec / 60 > 90) { throw new ArgumentOutOfRangeException("Degree out of range", "Latitudinal degrees cannot be greater than 90."); }
|
||||||
} else {
|
} else {
|
||||||
if (deg + (minSec / 60) > 180) { throw new ArgumentOutOfRangeException("Degree out of range", "Longitudinal degrees cannot be greater than 180."); }
|
if (deg + minSec / 60 > 180) { throw new ArgumentOutOfRangeException("Degree out of range", "Longitudinal degrees cannot be greater than 180."); }
|
||||||
}
|
}
|
||||||
this.degrees = deg;
|
this.degrees = deg;
|
||||||
this.decimalMinute = minSec;
|
this.decimalMinute = minSec;
|
||||||
@ -1356,7 +1313,7 @@ namespace CoordinateSharp
|
|||||||
sec *= 60;
|
sec *= 60;
|
||||||
Decimal secD = Convert.ToDecimal(sec);
|
Decimal secD = Convert.ToDecimal(sec);
|
||||||
this.seconds = Convert.ToDouble(secD);
|
this.seconds = Convert.ToDouble(secD);
|
||||||
Decimal dd = deg + (minD / 60);
|
Decimal dd = deg + minD / 60;
|
||||||
|
|
||||||
if (pos == CoordinatesPosition.S || pos == CoordinatesPosition.W) {
|
if (pos == CoordinatesPosition.S || pos == CoordinatesPosition.W) {
|
||||||
dd *= -1;
|
dd *= -1;
|
||||||
@ -1368,8 +1325,7 @@ namespace CoordinateSharp
|
|||||||
/// Creates an empty CoordinatePart.
|
/// Creates an empty CoordinatePart.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="t">CoordinateType</param>
|
/// <param name="t">CoordinateType</param>
|
||||||
public CoordinatePart(CoordinateType t)
|
public CoordinatePart(CoordinateType t) {
|
||||||
{
|
|
||||||
this.type = t;
|
this.type = t;
|
||||||
this.decimalDegree = 0;
|
this.decimalDegree = 0;
|
||||||
this.degrees = 0;
|
this.degrees = 0;
|
||||||
@ -1382,8 +1338,7 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="value">Coordinate decimal value</param>
|
/// <param name="value">Coordinate decimal value</param>
|
||||||
/// <param name="t">Coordinate type</param>
|
/// <param name="t">Coordinate type</param>
|
||||||
public CoordinatePart(Double value, CoordinateType t)
|
public CoordinatePart(Double value, CoordinateType t) {
|
||||||
{
|
|
||||||
this.type = t;
|
this.type = t;
|
||||||
|
|
||||||
if (this.type == CoordinateType.Long) {
|
if (this.type == CoordinateType.Long) {
|
||||||
@ -1418,8 +1373,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="min">Minutes</param>
|
/// <param name="min">Minutes</param>
|
||||||
/// <param name="sec">Seconds</param>
|
/// <param name="sec">Seconds</param>
|
||||||
/// <param name="pos">Coordinate Part Position</param>
|
/// <param name="pos">Coordinate Part Position</param>
|
||||||
public CoordinatePart(Int32 deg, Int32 min, Double sec, CoordinatesPosition pos)
|
public CoordinatePart(Int32 deg, Int32 min, Double sec, CoordinatesPosition pos) {
|
||||||
{
|
|
||||||
this.type = pos == CoordinatesPosition.N || pos == CoordinatesPosition.S ? CoordinateType.Lat : CoordinateType.Long;
|
this.type = pos == CoordinatesPosition.N || pos == CoordinatesPosition.S ? CoordinateType.Lat : CoordinateType.Long;
|
||||||
|
|
||||||
if (deg < 0) { throw new ArgumentOutOfRangeException("Degrees out of range", "Degrees cannot be less than 0."); }
|
if (deg < 0) { throw new ArgumentOutOfRangeException("Degrees out of range", "Degrees cannot be less than 0."); }
|
||||||
@ -1438,12 +1392,12 @@ namespace CoordinateSharp
|
|||||||
minD += secD; //Decimal Minutes
|
minD += secD; //Decimal Minutes
|
||||||
|
|
||||||
if (this.type == CoordinateType.Long) {
|
if (this.type == CoordinateType.Long) {
|
||||||
if (deg + (minD / 60) > 180) { throw new ArgumentOutOfRangeException("Degrees out of range", "Longitudinal Degrees cannot be greater than 180."); }
|
if (deg + minD / 60 > 180) { throw new ArgumentOutOfRangeException("Degrees out of range", "Longitudinal Degrees cannot be greater than 180."); }
|
||||||
} else {
|
} else {
|
||||||
if (deg + (minD / 60) > 90) { throw new ArgumentOutOfRangeException("Degrees out of range", "Latitudinal Degrees cannot be greater than 90."); }
|
if (deg + minD / 60 > 90) { throw new ArgumentOutOfRangeException("Degrees out of range", "Latitudinal Degrees cannot be greater than 90."); }
|
||||||
}
|
}
|
||||||
this.decimalMinute = Convert.ToDouble(minD);
|
this.decimalMinute = Convert.ToDouble(minD);
|
||||||
Decimal dd = Convert.ToDecimal(deg) + (minD / 60);
|
Decimal dd = Convert.ToDecimal(deg) + minD / 60;
|
||||||
|
|
||||||
|
|
||||||
if (pos == CoordinatesPosition.S || pos == CoordinatesPosition.W) {
|
if (pos == CoordinatesPosition.S || pos == CoordinatesPosition.W) {
|
||||||
@ -1457,8 +1411,7 @@ namespace CoordinateSharp
|
|||||||
/// <param name="deg">Degrees</param>
|
/// <param name="deg">Degrees</param>
|
||||||
/// <param name="minSec">Decimal Minutes</param>
|
/// <param name="minSec">Decimal Minutes</param>
|
||||||
/// <param name="pos">Coordinate Part Position</param>
|
/// <param name="pos">Coordinate Part Position</param>
|
||||||
public CoordinatePart(Int32 deg, Double minSec, CoordinatesPosition pos)
|
public CoordinatePart(Int32 deg, Double minSec, CoordinatesPosition pos) {
|
||||||
{
|
|
||||||
this.type = pos == CoordinatesPosition.N || pos == CoordinatesPosition.S ? CoordinateType.Lat : CoordinateType.Long;
|
this.type = pos == CoordinatesPosition.N || pos == CoordinatesPosition.S ? CoordinateType.Lat : CoordinateType.Long;
|
||||||
|
|
||||||
if (deg < 0) { throw new ArgumentOutOfRangeException("Degree out of range", "Degree cannot be less than 0."); }
|
if (deg < 0) { throw new ArgumentOutOfRangeException("Degree out of range", "Degree cannot be less than 0."); }
|
||||||
@ -1467,9 +1420,9 @@ namespace CoordinateSharp
|
|||||||
if (minSec >= 60) { throw new ArgumentOutOfRangeException("Minutes out of range", "Minutes cannot be greater than or equal to 60."); }
|
if (minSec >= 60) { throw new ArgumentOutOfRangeException("Minutes out of range", "Minutes cannot be greater than or equal to 60."); }
|
||||||
|
|
||||||
if (this.type == CoordinateType.Lat) {
|
if (this.type == CoordinateType.Lat) {
|
||||||
if (deg + (minSec / 60) > 90) { throw new ArgumentOutOfRangeException("Degree out of range", "Latitudinal degrees cannot be greater than 90."); }
|
if (deg + minSec / 60 > 90) { throw new ArgumentOutOfRangeException("Degree out of range", "Latitudinal degrees cannot be greater than 90."); }
|
||||||
} else {
|
} else {
|
||||||
if (deg + (minSec / 60) > 180) { throw new ArgumentOutOfRangeException("Degree out of range", "Longitudinal degrees cannot be greater than 180."); }
|
if (deg + minSec / 60 > 180) { throw new ArgumentOutOfRangeException("Degree out of range", "Longitudinal degrees cannot be greater than 180."); }
|
||||||
}
|
}
|
||||||
this.degrees = deg;
|
this.degrees = deg;
|
||||||
this.decimalMinute = minSec;
|
this.decimalMinute = minSec;
|
||||||
@ -1482,7 +1435,7 @@ namespace CoordinateSharp
|
|||||||
sec *= 60;
|
sec *= 60;
|
||||||
Decimal secD = Convert.ToDecimal(sec);
|
Decimal secD = Convert.ToDecimal(sec);
|
||||||
this.seconds = Convert.ToDouble(secD);
|
this.seconds = Convert.ToDouble(secD);
|
||||||
Decimal dd = deg + (minD / 60);
|
Decimal dd = deg + minD / 60;
|
||||||
|
|
||||||
if (pos == CoordinatesPosition.S || pos == CoordinatesPosition.W) {
|
if (pos == CoordinatesPosition.S || pos == CoordinatesPosition.W) {
|
||||||
dd *= -1;
|
dd *= -1;
|
||||||
@ -1513,46 +1466,25 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="options">CoordinateFormatOptions</param>
|
/// <param name="options">CoordinateFormatOptions</param>
|
||||||
/// <returns>Formatted coordinate part string</returns>
|
/// <returns>Formatted coordinate part string</returns>
|
||||||
private String FormatString(CoordinateFormatOptions options)
|
private String FormatString(CoordinateFormatOptions options) {
|
||||||
{
|
|
||||||
ToStringType type = ToStringType.Degree_Minute_Second;
|
|
||||||
Int32? rounding = null;
|
|
||||||
Boolean lead = false;
|
|
||||||
Boolean trail = false;
|
|
||||||
Boolean hyphen = false;
|
|
||||||
Boolean symbols = true;
|
|
||||||
Boolean degreeSymbol = true;
|
|
||||||
Boolean minuteSymbol = true;
|
|
||||||
Boolean secondsSymbol = true;
|
|
||||||
Boolean positionFirst = true;
|
|
||||||
|
|
||||||
#region Assign Formatting Rules
|
#region Assign Formatting Rules
|
||||||
switch (options.Format) {
|
ToStringType type = options.Format switch
|
||||||
case CoordinateFormatType.Degree_Minutes_Seconds:
|
{
|
||||||
type = ToStringType.Degree_Minute_Second;
|
CoordinateFormatType.Degree_Minutes_Seconds => ToStringType.Degree_Minute_Second,
|
||||||
break;
|
CoordinateFormatType.Degree_Decimal_Minutes => ToStringType.Degree_Decimal_Minute,
|
||||||
case CoordinateFormatType.Degree_Decimal_Minutes:
|
CoordinateFormatType.Decimal_Degree => ToStringType.Decimal_Degree,
|
||||||
type = ToStringType.Degree_Decimal_Minute;
|
CoordinateFormatType.Decimal => ToStringType.Decimal,
|
||||||
break;
|
_ => ToStringType.Degree_Minute_Second,
|
||||||
case CoordinateFormatType.Decimal_Degree:
|
};
|
||||||
type = ToStringType.Decimal_Degree;
|
Int32? rounding = options.Round;
|
||||||
break;
|
Boolean lead = options.Display_Leading_Zeros;
|
||||||
case CoordinateFormatType.Decimal:
|
Boolean trail = options.Display_Trailing_Zeros;
|
||||||
type = ToStringType.Decimal;
|
Boolean symbols = options.Display_Symbols;
|
||||||
break;
|
Boolean degreeSymbol = options.Display_Degree_Symbol;
|
||||||
default:
|
Boolean minuteSymbol = options.Display_Minute_Symbol;
|
||||||
type = ToStringType.Degree_Minute_Second;
|
Boolean secondsSymbol = options.Display_Seconds_Symbol;
|
||||||
break;
|
Boolean hyphen = options.Display_Hyphens;
|
||||||
}
|
Boolean positionFirst = options.Position_First;
|
||||||
rounding = options.Round;
|
|
||||||
lead = options.Display_Leading_Zeros;
|
|
||||||
trail = options.Display_Trailing_Zeros;
|
|
||||||
symbols = options.Display_Symbols;
|
|
||||||
degreeSymbol = options.Display_Degree_Symbol;
|
|
||||||
minuteSymbol = options.Display_Minute_Symbol;
|
|
||||||
secondsSymbol = options.Display_Seconds_Symbol;
|
|
||||||
hyphen = options.Display_Hyphens;
|
|
||||||
positionFirst = options.Position_First;
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
switch (type) {
|
switch (type) {
|
||||||
@ -1576,8 +1508,7 @@ namespace CoordinateSharp
|
|||||||
return String.Empty;
|
return String.Empty;
|
||||||
}
|
}
|
||||||
//DMS Coordinate Format
|
//DMS Coordinate Format
|
||||||
private String ToDegreeMinuteSecondString(Int32 rounding, Boolean lead, Boolean trail, Boolean symbols, Boolean degreeSymbol, Boolean minuteSymbol, Boolean secondSymbol, Boolean hyphen, Boolean positionFirst)
|
private String ToDegreeMinuteSecondString(Int32 rounding, Boolean lead, Boolean trail, Boolean symbols, Boolean degreeSymbol, Boolean minuteSymbol, Boolean secondSymbol, Boolean hyphen, Boolean positionFirst) {
|
||||||
{
|
|
||||||
|
|
||||||
String leadString = this.Leading_Trailing_Format(lead, false, rounding, this.Position);
|
String leadString = this.Leading_Trailing_Format(lead, false, rounding, this.Position);
|
||||||
String d = String.Format(leadString, this.Degrees); // Degree String
|
String d = String.Format(leadString, this.Degrees); // Degree String
|
||||||
@ -1602,8 +1533,7 @@ namespace CoordinateSharp
|
|||||||
: d + ds + hs + minute + ms + hs + second + ss + hs + this.Position.ToString();
|
: d + ds + hs + minute + ms + hs + second + ss + hs + this.Position.ToString();
|
||||||
}
|
}
|
||||||
//DDM Coordinate Format
|
//DDM Coordinate Format
|
||||||
private String ToDegreeDecimalMinuteString(Int32 rounding, Boolean lead, Boolean trail, Boolean symbols, Boolean degreeSymbol, Boolean minuteSymbol, Boolean hyphen, Boolean positionFirst)
|
private String ToDegreeDecimalMinuteString(Int32 rounding, Boolean lead, Boolean trail, Boolean symbols, Boolean degreeSymbol, Boolean minuteSymbol, Boolean hyphen, Boolean positionFirst) {
|
||||||
{
|
|
||||||
String leadString = "{0:0";
|
String leadString = "{0:0";
|
||||||
if (lead) {
|
if (lead) {
|
||||||
if (this.Position == CoordinatesPosition.E || this.Position == CoordinatesPosition.W) {
|
if (this.Position == CoordinatesPosition.E || this.Position == CoordinatesPosition.W) {
|
||||||
@ -1646,8 +1576,7 @@ namespace CoordinateSharp
|
|||||||
|
|
||||||
}
|
}
|
||||||
////DD Coordinate Format
|
////DD Coordinate Format
|
||||||
private String ToDecimalDegreeString(Int32 rounding, Boolean lead, Boolean trail, Boolean symbols, Boolean degreeSymbol, Boolean positionFirst, Boolean hyphen)
|
private String ToDecimalDegreeString(Int32 rounding, Boolean lead, Boolean trail, Boolean symbols, Boolean degreeSymbol, Boolean positionFirst, Boolean hyphen) {
|
||||||
{
|
|
||||||
String degreeS = "";
|
String degreeS = "";
|
||||||
String hyph = " ";
|
String hyph = " ";
|
||||||
if (degreeSymbol) { degreeS = "º"; }
|
if (degreeSymbol) { degreeS = "º"; }
|
||||||
@ -1672,15 +1601,14 @@ namespace CoordinateSharp
|
|||||||
}
|
}
|
||||||
leadTrail += "}";
|
leadTrail += "}";
|
||||||
|
|
||||||
Double result = (this.Degrees) + (Convert.ToDouble(this.Minutes)) / 60 + (Convert.ToDouble(this.Seconds)) / 3600;
|
Double result = this.Degrees + Convert.ToDouble(this.Minutes) / 60 + Convert.ToDouble(this.Seconds) / 3600;
|
||||||
result = Math.Round(result, rounding);
|
result = Math.Round(result, rounding);
|
||||||
String d = String.Format(leadTrail, Math.Abs(result));
|
String d = String.Format(leadTrail, Math.Abs(result));
|
||||||
return positionFirst ? this.Position.ToString() + hyph + d + degreeS : d + degreeS + hyph + this.Position.ToString();
|
return positionFirst ? this.Position.ToString() + hyph + d + degreeS : d + degreeS + hyph + this.Position.ToString();
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private String Leading_Trailing_Format(Boolean isLead, Boolean isTrail, Int32 rounding, CoordinatesPosition? p = null)
|
private String Leading_Trailing_Format(Boolean isLead, Boolean isTrail, Int32 rounding, CoordinatesPosition? p = null) {
|
||||||
{
|
|
||||||
String leadString = "{0:0";
|
String leadString = "{0:0";
|
||||||
if (isLead) {
|
if (isLead) {
|
||||||
if (p != null) {
|
if (p != null) {
|
||||||
@ -1706,18 +1634,16 @@ namespace CoordinateSharp
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private String FormatError(String argument, String rule) => "'" + argument + "' is not a valid argument for string format rule: " + rule + ".";
|
//private String FormatError(String argument, String rule) => "'" + argument + "' is not a valid argument for string format rule: " + rule + ".";
|
||||||
|
|
||||||
private enum ToStringType
|
private enum ToStringType {
|
||||||
{
|
|
||||||
Decimal_Degree, Degree_Decimal_Minute, Degree_Minute_Second, Decimal
|
Decimal_Degree, Degree_Decimal_Minute, Degree_Minute_Second, Decimal
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Notify the correct properties and parent properties.
|
/// Notify the correct properties and parent properties.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="p">Property Type</param>
|
/// <param name="p">Property Type</param>
|
||||||
private void NotifyProperties(PropertyTypes p)
|
private void NotifyProperties(PropertyTypes p) {
|
||||||
{
|
|
||||||
switch (p) {
|
switch (p) {
|
||||||
case PropertyTypes.DecimalDegree:
|
case PropertyTypes.DecimalDegree:
|
||||||
this.NotifyPropertyChanged("DecimalDegree");
|
this.NotifyPropertyChanged("DecimalDegree");
|
||||||
@ -1786,8 +1712,7 @@ namespace CoordinateSharp
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Used for notifying the correct properties.
|
/// Used for notifying the correct properties.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
private enum PropertyTypes
|
private enum PropertyTypes {
|
||||||
{
|
|
||||||
DecimalDegree, DecimalMinute, Position, Degree, Minute, Second, FormatChange
|
DecimalDegree, DecimalMinute, Position, Degree, Minute, Second, FormatChange
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1811,12 +1736,7 @@ namespace CoordinateSharp
|
|||||||
/// }
|
/// }
|
||||||
/// </code>
|
/// </code>
|
||||||
/// </example>
|
/// </example>
|
||||||
public static Boolean TryParse(String s, out CoordinatePart cp)
|
public static Boolean TryParse(String s, out CoordinatePart cp) => FormatFinder_CoordPart.TryParse(s, out cp) ? true : false;
|
||||||
{
|
|
||||||
cp = null;
|
|
||||||
|
|
||||||
return FormatFinder_CoordPart.TryParse(s, out cp) ? true : false;
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Attempts to parse a string into a CoordinatePart.
|
/// Attempts to parse a string into a CoordinatePart.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -1833,9 +1753,7 @@ namespace CoordinateSharp
|
|||||||
/// }
|
/// }
|
||||||
/// </code>
|
/// </code>
|
||||||
/// </example>
|
/// </example>
|
||||||
public static Boolean TryParse(String s, CoordinateType t, out CoordinatePart cp)
|
public static Boolean TryParse(String s, CoordinateType t, out CoordinatePart cp) {
|
||||||
{
|
|
||||||
cp = null;
|
|
||||||
//Comma at beginning parses to long
|
//Comma at beginning parses to long
|
||||||
//Asterik forces lat
|
//Asterik forces lat
|
||||||
s = t == CoordinateType.Long ? "," + s : "*" + s;
|
s = t == CoordinateType.Long ? "," + s : "*" + s;
|
||||||
|
12
CoordinateSharp/CoordinateSharp_Core.csproj
Normal file
12
CoordinateSharp/CoordinateSharp_Core.csproj
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<TargetFramework>netcoreapp3.0</TargetFramework>
|
||||||
|
<AssemblyName>CoordinateSharp</AssemblyName>
|
||||||
|
<RootNamespace>CoordinateSharp</RootNamespace>
|
||||||
|
<Description>A simple .NET standard library that is designed to assist with geographic coordinate conversions, formatting and location based celestial calculations.</Description>
|
||||||
|
<Copyright>Copyright 2019</Copyright>
|
||||||
|
<Version>1.1.5.2</Version>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
</Project>
|
@ -1,58 +1,43 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Diagnostics;
|
using System.Diagnostics;
|
||||||
namespace CoordinateSharp
|
|
||||||
{
|
namespace CoordinateSharp {
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Contains distance values between two coordinates.
|
/// Contains distance values between two coordinates.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Serializable]
|
[Serializable]
|
||||||
public class Distance
|
public class Distance {
|
||||||
{
|
|
||||||
private double kilometers;
|
|
||||||
private double miles;
|
|
||||||
private double feet;
|
|
||||||
private double meters;
|
|
||||||
private double bearing;
|
|
||||||
private double nauticalMiles;
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Initializes a distance object using Haversine (Spherical Earth).
|
/// Initializes a distance object using Haversine (Spherical Earth).
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="c1">Coordinate 1</param>
|
/// <param name="c1">Coordinate 1</param>
|
||||||
/// <param name="c2">Coordinate 2</param>
|
/// <param name="c2">Coordinate 2</param>
|
||||||
public Distance(Coordinate c1, Coordinate c2)
|
public Distance(Coordinate c1, Coordinate c2) => this.Haversine(c1, c2);
|
||||||
{
|
|
||||||
Haversine(c1, c2);
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Initializes a distance object using Haversine (Spherical Earth) or Vincenty (Elliptical Earth).
|
/// Initializes a distance object using Haversine (Spherical Earth) or Vincenty (Elliptical Earth).
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="c1">Coordinate 1</param>
|
/// <param name="c1">Coordinate 1</param>
|
||||||
/// <param name="c2">Coordinate 2</param>
|
/// <param name="c2">Coordinate 2</param>
|
||||||
/// <param name="shape">Shape of earth</param>
|
/// <param name="shape">Shape of earth</param>
|
||||||
public Distance(Coordinate c1, Coordinate c2, Shape shape)
|
public Distance(Coordinate c1, Coordinate c2, Shape shape) {
|
||||||
{
|
if (shape == Shape.Sphere) {
|
||||||
if (shape == Shape.Sphere)
|
this.Haversine(c1, c2);
|
||||||
{
|
} else {
|
||||||
Haversine(c1, c2);
|
this.Vincenty(c1, c2);
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
Vincenty(c1, c2);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Initializes distance object based on distance in KM
|
/// Initializes distance object based on distance in KM
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="km">Kilometers</param>
|
/// <param name="km">Kilometers</param>
|
||||||
public Distance(double km)
|
public Distance(Double km) {
|
||||||
{
|
this.Kilometers = km;
|
||||||
kilometers = km;
|
this.Meters = km * 1000;
|
||||||
meters = km * 1000;
|
this.Feet = this.Meters * 3.28084;
|
||||||
feet = meters * 3.28084;
|
this.Miles = this.Meters * 0.000621371;
|
||||||
miles = meters * 0.000621371;
|
this.NauticalMiles = this.Meters * 0.0005399565;
|
||||||
nauticalMiles = meters * 0.0005399565;
|
this.Bearing = 0;//None specified
|
||||||
bearing = 0;//None specified
|
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Initializaes distance object based on specified distance and measurement type
|
/// Initializaes distance object based on specified distance and measurement type
|
||||||
@ -60,59 +45,56 @@ namespace CoordinateSharp
|
|||||||
/// <param name="distance">Distance</param>
|
/// <param name="distance">Distance</param>
|
||||||
/// <param name="type">Measurement type</param>
|
/// <param name="type">Measurement type</param>
|
||||||
|
|
||||||
public Distance(double distance, DistanceType type)
|
public Distance(Double distance, DistanceType type) {
|
||||||
{
|
this.Bearing = 0;
|
||||||
bearing = 0;
|
switch (type) {
|
||||||
switch (type)
|
|
||||||
{
|
|
||||||
case DistanceType.Feet:
|
case DistanceType.Feet:
|
||||||
feet = distance;
|
this.Feet = distance;
|
||||||
meters = feet * 0.3048;
|
this.Meters = this.Feet * 0.3048;
|
||||||
kilometers = meters / 1000;
|
this.Kilometers = this.Meters / 1000;
|
||||||
miles = meters * 0.000621371;
|
this.Miles = this.Meters * 0.000621371;
|
||||||
nauticalMiles = meters * 0.0005399565;
|
this.NauticalMiles = this.Meters * 0.0005399565;
|
||||||
break;
|
break;
|
||||||
case DistanceType.Kilometers:
|
case DistanceType.Kilometers:
|
||||||
kilometers = distance;
|
this.Kilometers = distance;
|
||||||
meters = kilometers * 1000;
|
this.Meters = this.Kilometers * 1000;
|
||||||
feet = meters * 3.28084;
|
this.Feet = this.Meters * 3.28084;
|
||||||
miles = meters * 0.000621371;
|
this.Miles = this.Meters * 0.000621371;
|
||||||
nauticalMiles = meters * 0.0005399565;
|
this.NauticalMiles = this.Meters * 0.0005399565;
|
||||||
break;
|
break;
|
||||||
case DistanceType.Meters:
|
case DistanceType.Meters:
|
||||||
meters = distance;
|
this.Meters = distance;
|
||||||
kilometers = meters / 1000;
|
this.Kilometers = this.Meters / 1000;
|
||||||
feet = meters * 3.28084;
|
this.Feet = this.Meters * 3.28084;
|
||||||
miles = meters * 0.000621371;
|
this.Miles = this.Meters * 0.000621371;
|
||||||
nauticalMiles = meters * 0.0005399565;
|
this.NauticalMiles = this.Meters * 0.0005399565;
|
||||||
break;
|
break;
|
||||||
case DistanceType.Miles:
|
case DistanceType.Miles:
|
||||||
miles = distance;
|
this.Miles = distance;
|
||||||
meters = miles * 1609.344;
|
this.Meters = this.Miles * 1609.344;
|
||||||
feet = meters * 3.28084;
|
this.Feet = this.Meters * 3.28084;
|
||||||
kilometers = meters / 1000;
|
this.Kilometers = this.Meters / 1000;
|
||||||
nauticalMiles = meters * 0.0005399565;
|
this.NauticalMiles = this.Meters * 0.0005399565;
|
||||||
break;
|
break;
|
||||||
case DistanceType.NauticalMiles:
|
case DistanceType.NauticalMiles:
|
||||||
nauticalMiles = distance;
|
this.NauticalMiles = distance;
|
||||||
meters = nauticalMiles * 1852.001;
|
this.Meters = this.NauticalMiles * 1852.001;
|
||||||
feet = meters * 3.28084;
|
this.Feet = this.Meters * 3.28084;
|
||||||
kilometers = meters / 1000;
|
this.Kilometers = this.Meters / 1000;
|
||||||
miles = meters * 0.000621371;
|
this.Miles = this.Meters * 0.000621371;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
kilometers = distance;
|
this.Kilometers = distance;
|
||||||
meters = distance * 1000;
|
this.Meters = distance * 1000;
|
||||||
feet = meters * 3.28084;
|
this.Feet = this.Meters * 3.28084;
|
||||||
miles = meters * 0.000621371;
|
this.Miles = this.Meters * 0.000621371;
|
||||||
nauticalMiles = meters * 0.0005399565;
|
this.NauticalMiles = this.Meters * 0.0005399565;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
private void Vincenty(Coordinate coord1, Coordinate coord2)
|
private void Vincenty(Coordinate coord1, Coordinate coord2) {
|
||||||
{
|
Double lat1, lat2, lon1, lon2;
|
||||||
double lat1, lat2, lon1, lon2;
|
Double d, crs12;
|
||||||
double d, crs12, crs21;
|
|
||||||
|
|
||||||
|
|
||||||
lat1 = coord1.Latitude.ToRadians();
|
lat1 = coord1.Latitude.ToRadians();
|
||||||
@ -121,111 +103,90 @@ namespace CoordinateSharp
|
|||||||
lon2 = coord2.Longitude.ToRadians() * -1; //REVERSE FOR CALC 2.1.1.1
|
lon2 = coord2.Longitude.ToRadians() * -1; //REVERSE FOR CALC 2.1.1.1
|
||||||
|
|
||||||
//Ensure datums match between coords
|
//Ensure datums match between coords
|
||||||
if ((coord1.equatorial_radius != coord2.equatorial_radius) || (coord1.inverse_flattening != coord2.inverse_flattening))
|
if (coord1.equatorial_radius != coord2.equatorial_radius || coord1.inverse_flattening != coord2.inverse_flattening) {
|
||||||
{
|
|
||||||
throw new InvalidOperationException("The datum set does not match between Coordinate objects.");
|
throw new InvalidOperationException("The datum set does not match between Coordinate objects.");
|
||||||
}
|
}
|
||||||
double[] ellipse = new double[] { coord1.equatorial_radius, coord1.inverse_flattening };
|
Double[] ellipse = new Double[] { coord1.equatorial_radius, coord1.inverse_flattening };
|
||||||
|
|
||||||
|
|
||||||
// elliptic code
|
// elliptic code
|
||||||
double[] cde = Distance_Assistant.Dist_Ell(lat1, -lon1, lat2, -lon2, ellipse); // ellipse uses East negative
|
Double[] cde = Distance_Assistant.Dist_Ell(lat1, -lon1, lat2, -lon2, ellipse); // ellipse uses East negative
|
||||||
crs12 = cde[1] * (180 / Math.PI); //Bearing
|
crs12 = cde[1] * (180 / Math.PI); //Bearing
|
||||||
crs21 = cde[2] * (180 / Math.PI); //Reverse Bearing
|
_ = cde[2] * (180 / Math.PI); //Reverse Bearing
|
||||||
d = cde[0]; //Distance
|
d = cde[0]; //Distance
|
||||||
|
|
||||||
bearing = crs12;
|
this.Bearing = crs12;
|
||||||
//reverseBearing = crs21;
|
//reverseBearing = crs21;
|
||||||
meters = d;
|
this.Meters = d;
|
||||||
kilometers = d / 1000;
|
this.Kilometers = d / 1000;
|
||||||
feet = d * 3.28084;
|
this.Feet = d * 3.28084;
|
||||||
miles = d * 0.000621371;
|
this.Miles = d * 0.000621371;
|
||||||
nauticalMiles = d * 0.0005399565;
|
this.NauticalMiles = d * 0.0005399565;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private void Haversine(Coordinate coord1, Coordinate coord2)
|
private void Haversine(Coordinate coord1, Coordinate coord2) {
|
||||||
{
|
|
||||||
////RADIANS
|
////RADIANS
|
||||||
double lat1 = coord1.Latitude.ToRadians();
|
Double lat1 = coord1.Latitude.ToRadians();
|
||||||
double long1 = coord1.Longitude.ToRadians();
|
Double long1 = coord1.Longitude.ToRadians();
|
||||||
double lat2 = coord2.Latitude.ToRadians();
|
Double lat2 = coord2.Latitude.ToRadians();
|
||||||
double long2 = coord2.Longitude.ToRadians();
|
Double long2 = coord2.Longitude.ToRadians();
|
||||||
|
|
||||||
//Distance Calcs
|
//Distance Calcs
|
||||||
double R = 6371000; //6378137.0;//6371e3; //meters
|
Double R = 6371000; //6378137.0;//6371e3; //meters
|
||||||
double latRad = coord2.Latitude.ToRadians() - coord1.Latitude.ToRadians();
|
Double latRad = coord2.Latitude.ToRadians() - coord1.Latitude.ToRadians();
|
||||||
double longRad = coord2.Longitude.ToRadians() - coord1.Longitude.ToRadians();
|
Double longRad = coord2.Longitude.ToRadians() - coord1.Longitude.ToRadians();
|
||||||
|
|
||||||
double a = Math.Sin(latRad / 2.0) * Math.Sin(latRad / 2.0) +
|
Double a = Math.Sin(latRad / 2.0) * Math.Sin(latRad / 2.0) +
|
||||||
Math.Cos(lat1) * Math.Cos(lat2) * Math.Sin(longRad / 2.0) * Math.Sin(longRad / 2.0);
|
Math.Cos(lat1) * Math.Cos(lat2) * Math.Sin(longRad / 2.0) * Math.Sin(longRad / 2.0);
|
||||||
double cl = 2 * Math.Atan2(Math.Sqrt(a), Math.Sqrt(1 - a));
|
Double cl = 2 * Math.Atan2(Math.Sqrt(a), Math.Sqrt(1 - a));
|
||||||
double dist = R * cl;
|
Double dist = R * cl;
|
||||||
|
|
||||||
//Get bearing
|
//Get bearing
|
||||||
double dLong = long2 - long1;
|
Double dLong = long2 - long1;
|
||||||
double y = Math.Sin(dLong) * Math.Cos(lat2);
|
Double y = Math.Sin(dLong) * Math.Cos(lat2);
|
||||||
double x = Math.Cos(lat1) * Math.Sin(lat2) - Math.Sin(lat1) * Math.Cos(lat2) * Math.Cos(dLong);
|
Double x = Math.Cos(lat1) * Math.Sin(lat2) - Math.Sin(lat1) * Math.Cos(lat2) * Math.Cos(dLong);
|
||||||
double brng = Math.Atan2(y, x) * (180 / Math.PI); //Convert bearing back to degrees.
|
Double brng = Math.Atan2(y, x) * (180 / Math.PI); //Convert bearing back to degrees.
|
||||||
|
|
||||||
//if (brng < 0) { brng -= 180; brng = Math.Abs(brng); }
|
//if (brng < 0) { brng -= 180; brng = Math.Abs(brng); }
|
||||||
brng = (brng + 360) % 360; //v2.1.1.1 NORMALIZE HEADING
|
brng = (brng + 360) % 360; //v2.1.1.1 NORMALIZE HEADING
|
||||||
|
|
||||||
kilometers = dist / 1000;
|
this.Kilometers = dist / 1000;
|
||||||
meters = dist;
|
this.Meters = dist;
|
||||||
feet = dist * 3.28084;
|
this.Feet = dist * 3.28084;
|
||||||
miles = dist * 0.000621371;
|
this.Miles = dist * 0.000621371;
|
||||||
nauticalMiles = dist * 0.0005399565;
|
this.NauticalMiles = dist * 0.0005399565;
|
||||||
bearing = brng;
|
this.Bearing = brng;
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Distance in Kilometers
|
/// Distance in Kilometers
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Kilometers
|
public Double Kilometers { get; private set; }
|
||||||
{
|
|
||||||
get { return kilometers; }
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Distance in Statute Miles
|
/// Distance in Statute Miles
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Miles
|
public Double Miles { get; private set; }
|
||||||
{
|
|
||||||
get { return miles; }
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Distance in Nautical Miles
|
/// Distance in Nautical Miles
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double NauticalMiles
|
public Double NauticalMiles { get; private set; }
|
||||||
{
|
|
||||||
get { return nauticalMiles; }
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Distance in Meters
|
/// Distance in Meters
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Meters
|
public Double Meters { get; private set; }
|
||||||
{
|
|
||||||
get { return meters; }
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Distance in Feet
|
/// Distance in Feet
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Feet
|
public Double Feet { get; private set; }
|
||||||
{
|
|
||||||
get { return feet; }
|
|
||||||
}
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Initial Bearing from Coordinate 1 to Coordinate 2
|
/// Initial Bearing from Coordinate 1 to Coordinate 2
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Bearing
|
public Double Bearing { get; private set; }
|
||||||
{
|
|
||||||
get { return bearing; }
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Distance measurement type
|
/// Distance measurement type
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public enum DistanceType
|
public enum DistanceType {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Distance in Meters
|
/// Distance in Meters
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -249,8 +210,7 @@ namespace CoordinateSharp
|
|||||||
}
|
}
|
||||||
|
|
||||||
[Serializable]
|
[Serializable]
|
||||||
internal class Distance_Assistant
|
internal class Distance_Assistant {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Returns new geodetic coordinate in radians
|
/// Returns new geodetic coordinate in radians
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@ -260,34 +220,25 @@ namespace CoordinateSharp
|
|||||||
/// <param name="s">Distance</param>
|
/// <param name="s">Distance</param>
|
||||||
/// <param name="ellipse">Earth Ellipse Values</param>
|
/// <param name="ellipse">Earth Ellipse Values</param>
|
||||||
/// <returns>double[]</returns>
|
/// <returns>double[]</returns>
|
||||||
public static double[] Direct_Ell(double glat1, double glon1, double faz, double s, double[] ellipse)
|
public static Double[] Direct_Ell(Double glat1, Double glon1, Double faz, Double s, Double[] ellipse) {
|
||||||
{
|
|
||||||
glon1 *= -1; //REVERSE LONG FOR CALC 2.1.1.1
|
glon1 *= -1; //REVERSE LONG FOR CALC 2.1.1.1
|
||||||
double EPS = 0.00000000005;//Used to determine if starting at pole.
|
Double EPS = 0.00000000005;//Used to determine if starting at pole.
|
||||||
double r, tu, sf, cf, b, cu, su, sa, c2a, x, c, d, y, sy = 0, cy = 0, cz = 0, e = 0;
|
Double r, tu, sf, cf, b, cu, su, sa, c2a, x, c, d, y, sy = 0, cy = 0, cz = 0, e = 0;
|
||||||
double glat2, glon2, f;
|
Double glat2, glon2, f;
|
||||||
|
|
||||||
//Determine if near pole
|
//Determine if near pole
|
||||||
if ((Math.Abs(Math.Cos(glat1)) < EPS) && !(Math.Abs(Math.Sin(faz)) < EPS))
|
if (Math.Abs(Math.Cos(glat1)) < EPS && !(Math.Abs(Math.Sin(faz)) < EPS)) {
|
||||||
{
|
|
||||||
Debug.WriteLine("Warning: Location is at earth's pole. Only N-S courses are meaningful at this location.");
|
Debug.WriteLine("Warning: Location is at earth's pole. Only N-S courses are meaningful at this location.");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
double a = ellipse[0];//Equitorial Radius
|
Double a = ellipse[0];//Equitorial Radius
|
||||||
f = 1 / ellipse[1];//Flattening
|
f = 1 / ellipse[1];//Flattening
|
||||||
r = 1 - f;
|
r = 1 - f;
|
||||||
tu = r * Math.Tan(glat1);
|
tu = r * Math.Tan(glat1);
|
||||||
sf = Math.Sin(faz);
|
sf = Math.Sin(faz);
|
||||||
cf = Math.Cos(faz);
|
cf = Math.Cos(faz);
|
||||||
if (cf == 0)
|
b = cf == 0 ? 0.0 : 2.0 * Math.Atan2(tu, cf);
|
||||||
{
|
|
||||||
b = 0.0;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
b = 2.0 * Math.Atan2(tu, cf);
|
|
||||||
}
|
|
||||||
cu = 1.0 / Math.Sqrt(1 + tu * tu);
|
cu = 1.0 / Math.Sqrt(1 + tu * tu);
|
||||||
su = tu * cu;
|
su = tu * cu;
|
||||||
sa = cu * sf;
|
sa = cu * sf;
|
||||||
@ -300,8 +251,7 @@ namespace CoordinateSharp
|
|||||||
tu = s / (r * a * c);
|
tu = s / (r * a * c);
|
||||||
y = tu;
|
y = tu;
|
||||||
c = y + 1;
|
c = y + 1;
|
||||||
while (Math.Abs(y - c) > EPS)
|
while (Math.Abs(y - c) > EPS) {
|
||||||
{
|
|
||||||
sy = Math.Sin(y);
|
sy = Math.Sin(y);
|
||||||
cy = Math.Cos(y);
|
cy = Math.Cos(y);
|
||||||
cz = Math.Cos(b + y);
|
cz = Math.Cos(b + y);
|
||||||
@ -324,7 +274,7 @@ namespace CoordinateSharp
|
|||||||
d = ((e * cy * c + cz) * sy * c + y) * sa;
|
d = ((e * cy * c + cz) * sy * c + y) * sa;
|
||||||
glon2 = ModM.ModLon(glon1 + x - (1.0 - c) * d * f); //Adjust for IDL
|
glon2 = ModM.ModLon(glon1 + x - (1.0 - c) * d * f); //Adjust for IDL
|
||||||
//baz = ModM.ModCrs(Math.Atan2(sa, b) + Math.PI);
|
//baz = ModM.ModCrs(Math.Atan2(sa, b) + Math.PI);
|
||||||
return new double[] { glat2, glon2 };
|
return new Double[] { glat2, glon2 };
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Returns new geodetic coordinate in radians
|
/// Returns new geodetic coordinate in radians
|
||||||
@ -334,57 +284,49 @@ namespace CoordinateSharp
|
|||||||
/// <param name="crs12">Bearing</param>
|
/// <param name="crs12">Bearing</param>
|
||||||
/// <param name="d12">Distance</param>
|
/// <param name="d12">Distance</param>
|
||||||
/// <returns>double[]</returns>
|
/// <returns>double[]</returns>
|
||||||
public static double[] Direct(double lat1, double lon1, double crs12, double d12)
|
public static Double[] Direct(Double lat1, Double lon1, Double crs12, Double d12) {
|
||||||
{
|
|
||||||
lon1 *= -1; //REVERSE LONG FOR CALC 2.1.1.1
|
lon1 *= -1; //REVERSE LONG FOR CALC 2.1.1.1
|
||||||
var EPS = 0.00000000005;//Used to determine if near pole.
|
Double EPS = 0.00000000005;//Used to determine if near pole.
|
||||||
double dlon, lat, lon;
|
Double dlon, lat, lon;
|
||||||
d12 = d12 * 0.0005399565; //convert meter to nm
|
d12 *= 0.0005399565; //convert meter to nm
|
||||||
d12 = d12 / (180 * 60 / Math.PI);//Convert to Radian
|
d12 /= 180 * 60 / Math.PI;//Convert to Radian
|
||||||
//Determine if near pole
|
//Determine if near pole
|
||||||
if ((Math.Abs(Math.Cos(lat1)) < EPS) && !(Math.Abs(Math.Sin(crs12)) < EPS))
|
if (Math.Abs(Math.Cos(lat1)) < EPS && !(Math.Abs(Math.Sin(crs12)) < EPS)) {
|
||||||
{
|
|
||||||
Debug.WriteLine("Warning: Location is at earth's pole. Only N-S courses are meaningful at this location.");
|
Debug.WriteLine("Warning: Location is at earth's pole. Only N-S courses are meaningful at this location.");
|
||||||
}
|
}
|
||||||
|
|
||||||
lat = Math.Asin(Math.Sin(lat1) * Math.Cos(d12) +
|
lat = Math.Asin(Math.Sin(lat1) * Math.Cos(d12) +
|
||||||
Math.Cos(lat1) * Math.Sin(d12) * Math.Cos(crs12));
|
Math.Cos(lat1) * Math.Sin(d12) * Math.Cos(crs12));
|
||||||
if (Math.Abs(Math.Cos(lat)) < EPS)
|
if (Math.Abs(Math.Cos(lat)) < EPS) {
|
||||||
{
|
|
||||||
lon = 0.0; //endpoint a pole
|
lon = 0.0; //endpoint a pole
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
dlon = Math.Atan2(Math.Sin(crs12) * Math.Sin(d12) * Math.Cos(lat1),
|
dlon = Math.Atan2(Math.Sin(crs12) * Math.Sin(d12) * Math.Cos(lat1),
|
||||||
Math.Cos(d12) - Math.Sin(lat1) * Math.Sin(lat));
|
Math.Cos(d12) - Math.Sin(lat1) * Math.Sin(lat));
|
||||||
lon = ModM.Mod(lon1 - dlon + Math.PI, 2 * Math.PI) - Math.PI;
|
lon = ModM.Mod(lon1 - dlon + Math.PI, 2 * Math.PI) - Math.PI;
|
||||||
}
|
}
|
||||||
|
|
||||||
return new double[] { lat, lon };
|
return new Double[] { lat, lon };
|
||||||
}
|
}
|
||||||
public static double[] Dist_Ell(double glat1, double glon1, double glat2, double glon2, double[] ellipse)
|
public static Double[] Dist_Ell(Double glat1, Double glon1, Double glat2, Double glon2, Double[] ellipse) {
|
||||||
{
|
Double a = ellipse[0]; //Equitorial Radius
|
||||||
double a = ellipse[0]; //Equitorial Radius
|
Double f = 1 / ellipse[1]; //Flattening
|
||||||
double f = 1 / ellipse[1]; //Flattening
|
|
||||||
|
|
||||||
double r, tu1, tu2, cu1, su1, cu2, s1, b1, f1;
|
Double r, tu1, tu2, cu1, su1, cu2, s1, b1, f1;
|
||||||
double x = 0, sx = 0, cx = 0, sy = 0, cy = 0, y = 0, sa = 0, c2a = 0, cz = 0, e = 0, c = 0, d = 0;
|
Double sx = 0, cx = 0, sy = 0, cy = 0, y = 0, c2a = 0, cz = 0, e = 0;
|
||||||
double EPS = 0.00000000005;
|
Double EPS = 0.00000000005;
|
||||||
double faz, baz, s;
|
Double faz, baz, s;
|
||||||
double iter = 1;
|
Double iter = 1;
|
||||||
double MAXITER = 100;
|
Double MAXITER = 100;
|
||||||
if ((glat1 + glat2 == 0.0) && (Math.Abs(glon1 - glon2) == Math.PI))
|
if (glat1 + glat2 == 0.0 && Math.Abs(glon1 - glon2) == Math.PI) {
|
||||||
{
|
|
||||||
Debug.WriteLine("Warning: Course and distance between antipodal points is undefined");
|
Debug.WriteLine("Warning: Course and distance between antipodal points is undefined");
|
||||||
glat1 = glat1 + 0.00001; // allow algorithm to complete
|
glat1 += 0.00001; // allow algorithm to complete
|
||||||
}
|
}
|
||||||
if (glat1 == glat2 && (glon1 == glon2 || Math.Abs(Math.Abs(glon1 - glon2) - 2 * Math.PI) < EPS))
|
if (glat1 == glat2 && (glon1 == glon2 || Math.Abs(Math.Abs(glon1 - glon2) - 2 * Math.PI) < EPS)) {
|
||||||
{
|
|
||||||
Debug.WriteLine("Warning: Points 1 and 2 are identical- course undefined");
|
Debug.WriteLine("Warning: Points 1 and 2 are identical- course undefined");
|
||||||
//D
|
//D
|
||||||
//crs12
|
//crs12
|
||||||
//crs21
|
//crs21
|
||||||
return new double[] { 0, 0, Math.PI };
|
return new Double[] { 0, 0, Math.PI };
|
||||||
}
|
}
|
||||||
r = 1 - f;
|
r = 1 - f;
|
||||||
tu1 = r * Math.Tan(glat1);
|
tu1 = r * Math.Tan(glat1);
|
||||||
@ -395,11 +337,11 @@ namespace CoordinateSharp
|
|||||||
s1 = cu1 * cu2;
|
s1 = cu1 * cu2;
|
||||||
b1 = s1 * tu2;
|
b1 = s1 * tu2;
|
||||||
f1 = b1 * tu1;
|
f1 = b1 * tu1;
|
||||||
x = glon2 - glon1;
|
Double x = glon2 - glon1;
|
||||||
d = x + 1; // force one pass
|
Double d = x + 1;
|
||||||
while ((Math.Abs(d - x) > EPS) && (iter < MAXITER))
|
Double c;
|
||||||
{
|
while (Math.Abs(d - x) > EPS && iter < MAXITER) {
|
||||||
iter = iter + 1;
|
iter += 1;
|
||||||
sx = Math.Sin(x);
|
sx = Math.Sin(x);
|
||||||
cx = Math.Cos(x);
|
cx = Math.Cos(x);
|
||||||
tu1 = cu2 * sx;
|
tu1 = cu2 * sx;
|
||||||
@ -407,11 +349,10 @@ namespace CoordinateSharp
|
|||||||
sy = Math.Sqrt(tu1 * tu1 + tu2 * tu2);
|
sy = Math.Sqrt(tu1 * tu1 + tu2 * tu2);
|
||||||
cy = s1 * cx + f1;
|
cy = s1 * cx + f1;
|
||||||
y = Math.Atan2(sy, cy);
|
y = Math.Atan2(sy, cy);
|
||||||
sa = s1 * sx / sy;
|
Double sa = s1 * sx / sy;
|
||||||
c2a = 1 - sa * sa;
|
c2a = 1 - sa * sa;
|
||||||
cz = f1 + f1;
|
cz = f1 + f1;
|
||||||
if (c2a > 0.0)
|
if (c2a > 0.0) {
|
||||||
{
|
|
||||||
cz = cy - cz / c2a;
|
cz = cy - cz / c2a;
|
||||||
}
|
}
|
||||||
e = cz * cz * 2.0 - 1.0;
|
e = cz * cz * 2.0 - 1.0;
|
||||||
@ -431,12 +372,11 @@ namespace CoordinateSharp
|
|||||||
x = e * cy;
|
x = e * cy;
|
||||||
s = ((((sy * sy * 4.0 - 3.0) * (1.0 - e - e) * cz * d / 6.0 - x) * d / 4.0 + cz) * sy * d + y) * c * a * r;
|
s = ((((sy * sy * 4.0 - 3.0) * (1.0 - e - e) * cz * d / 6.0 - x) * d / 4.0 + cz) * sy * d + y) * c * a * r;
|
||||||
|
|
||||||
if (Math.Abs(iter - MAXITER) < EPS)
|
if (Math.Abs(iter - MAXITER) < EPS) {
|
||||||
{
|
|
||||||
Debug.WriteLine("Warning: Distance algorithm did not converge");
|
Debug.WriteLine("Warning: Distance algorithm did not converge");
|
||||||
}
|
}
|
||||||
|
|
||||||
return new double[] { s, faz, baz };
|
return new Double[] { s, faz, baz };
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -2,11 +2,9 @@
|
|||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
|
||||||
namespace CoordinateSharp.Eclipse
|
namespace CoordinateSharp.Eclipse {
|
||||||
{
|
internal class LunarData {
|
||||||
internal class LunarData
|
static readonly Double[] LE1601 = new Double[] {
|
||||||
{
|
|
||||||
static double[] LE1601 = new double[] {
|
|
||||||
// 1601 1 18
|
// 1601 1 18
|
||||||
2305831.105839, 15.0, 117.3, 0.033, -0.978, 3,
|
2305831.105839, 15.0, 117.3, 0.033, -0.978, 3,
|
||||||
-1.13536, 0.98335, 0.26794,
|
-1.13536, 0.98335, 0.26794,
|
||||||
@ -1501,7 +1499,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
-3.09161, -1.92390, -0.82385, 0.02344, 0.87082, 1.97089, 3.13800,
|
-3.09161, -1.92390, -0.82385, 0.02344, 0.87082, 1.97089, 3.13800,
|
||||||
337.8589683, 0.48164, -1.510e-04,
|
337.8589683, 0.48164, -1.510e-04,
|
||||||
-9.4195702, 0.13945, 3.390e-04 };
|
-9.4195702, 0.13945, 3.390e-04 };
|
||||||
static double[] LE1701 = new double[]
|
static readonly Double[] LE1701 = new Double[]
|
||||||
{
|
{
|
||||||
// 1701 2 22
|
// 1701 2 22
|
||||||
2342390.479120, 23.0, 8.2, 1.428, 0.463, 2,
|
2342390.479120, 23.0, 8.2, 1.428, 0.463, 2,
|
||||||
@ -3040,7 +3038,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
9.1688605, 0.46956, -7.000e-05,
|
9.1688605, 0.46956, -7.000e-05,
|
||||||
3.0790301, 0.25315, -2.000e-04
|
3.0790301, 0.25315, -2.000e-04
|
||||||
};
|
};
|
||||||
static double[] LE1801 = new double[]
|
static readonly Double[] LE1801 = new Double[]
|
||||||
{
|
{
|
||||||
// 1801 3 30
|
// 1801 3 30
|
||||||
2378949.725057, 5.0, 13.0, 2.857, 1.840, 1,
|
2378949.725057, 5.0, 13.0, 2.857, 1.840, 1,
|
||||||
@ -4537,7 +4535,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
72.2570493, 0.64062, -1.660e-04,
|
72.2570493, 0.64062, -1.660e-04,
|
||||||
21.3680795, 0.01873, -1.222e-03
|
21.3680795, 0.01873, -1.222e-03
|
||||||
};
|
};
|
||||||
static double[] LE1901 = new double[]
|
static readonly Double[] LE1901 = new Double[]
|
||||||
{
|
{
|
||||||
// 1901 5 3
|
// 1901 5 3
|
||||||
2415508.271269, 19.0, -0.9, 1.043, -0.033, 3,
|
2415508.271269, 19.0, -0.9, 1.043, -0.033, 3,
|
||||||
@ -5914,7 +5912,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
296.2552752, 0.52835, -1.150e-04,
|
296.2552752, 0.52835, -1.150e-04,
|
||||||
-21.2212594, 0.04170, 8.250e-04
|
-21.2212594, 0.04170, 8.250e-04
|
||||||
};
|
};
|
||||||
static double[] LE2001 = new double[]
|
static readonly Double[] LE2001 = new Double[]
|
||||||
{
|
{
|
||||||
// 2001 1 9
|
// 2001 1 9
|
||||||
2451919.348374, 20.0, 64.1, 2.162, 1.189, 1,
|
2451919.348374, 20.0, 64.1, 2.162, 1.189, 1,
|
||||||
@ -7285,7 +7283,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
329.8184696, 0.49978, -6.760e-04,
|
329.8184696, 0.49978, -6.760e-04,
|
||||||
-13.3626205, 0.22960, 3.990e-04
|
-13.3626205, 0.22960, 3.990e-04
|
||||||
};
|
};
|
||||||
static double[] LE2101 = new double[]
|
static readonly Double[] LE2101 = new Double[]
|
||||||
{
|
{
|
||||||
// 2101 2 14
|
// 2101 2 14
|
||||||
2488478.618055, 3.0, 205.1, 2.218, 1.183, 1,
|
2488478.618055, 3.0, 205.1, 2.218, 1.183, 1,
|
||||||
@ -8716,7 +8714,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
28.0294400, 0.59158, 9.000e-05,
|
28.0294400, 0.59158, 9.000e-05,
|
||||||
10.7019400, 0.15900, -6.160e-04
|
10.7019400, 0.15900, -6.160e-04
|
||||||
};
|
};
|
||||||
static double[] LE2201 = new double[]
|
static readonly Double[] LE2201 = new Double[]
|
||||||
{
|
{
|
||||||
// 2201 3 20
|
// 2201 3 20
|
||||||
2525037.204912, 17.0, 444.3, 0.532, -0.560, 3,
|
2525037.204912, 17.0, 444.3, 0.532, -0.560, 3,
|
||||||
@ -10231,7 +10229,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
63.0500500, 0.65278, 8.590e-04,
|
63.0500500, 0.65278, 8.590e-04,
|
||||||
21.0508309, 0.17085, -1.218e-03
|
21.0508309, 0.17085, -1.218e-03
|
||||||
};
|
};
|
||||||
static double[] LE2301 = new double[]
|
static readonly Double[] LE2301 = new Double[]
|
||||||
{
|
{
|
||||||
// 2301 5 23
|
// 2301 5 23
|
||||||
2561625.186996, 16.0, 720.0, 1.809, 0.754, 2,
|
2561625.186996, 16.0, 720.0, 1.809, 0.754, 2,
|
||||||
@ -11752,7 +11750,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
101.2753539, 0.59275, -1.730e-04,
|
101.2753539, 0.59275, -1.730e-04,
|
||||||
23.7726800, -0.09243, -1.170e-03
|
23.7726800, -0.09243, -1.170e-03
|
||||||
};
|
};
|
||||||
static double[] LE2401 = new double[] {
|
static readonly Double[] LE2401 = new Double[] {
|
||||||
// 2401 6 26
|
// 2401 6 26
|
||||||
2598183.958214, 11.0, 1059.4, 2.107, 1.139, 1,
|
2598183.958214, 11.0, 1059.4, 2.107, 1.139, 1,
|
||||||
5.31800, 0.99489, 0.27108,
|
5.31800, 0.99489, 0.27108,
|
||||||
@ -13176,7 +13174,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
348.3334732, 0.58130, -3.870e-04,
|
348.3334732, 0.58130, -3.870e-04,
|
||||||
-5.5431301, 0.18349, 2.190e-04
|
-5.5431301, 0.18349, 2.190e-04
|
||||||
};
|
};
|
||||||
static double[] LE2501 = new double[] {
|
static readonly Double[] LE2501 = new Double[] {
|
||||||
// 2501 3 6
|
// 2501 3 6
|
||||||
2634595.801080, 7.0, 1461.0, 0.491, -0.599, 3,
|
2634595.801080, 7.0, 1461.0, 0.491, -0.599, 3,
|
||||||
17.93340, 0.90700, 0.24714,
|
17.93340, 0.90700, 0.24714,
|
||||||
@ -14541,66 +14539,45 @@ namespace CoordinateSharp.Eclipse
|
|||||||
8.0835801, 0.28700, -3.300e-04
|
8.0835801, 0.28700, -3.300e-04
|
||||||
};
|
};
|
||||||
|
|
||||||
public static double[] LunarDateData(DateTime d)
|
public static Double[] LunarDateData(DateTime d) {
|
||||||
{
|
|
||||||
//Return combined 100 year arrays so in order to grab Last and Next exlipLE.
|
//Return combined 100 year arrays so in order to grab Last and Next exlipLE.
|
||||||
List<double[]> data = new List<double[]>()
|
List<Double[]> data = new List<Double[]>()
|
||||||
{
|
{
|
||||||
LE1601, LE1701,LE1801, LE1901, LE2001,
|
LE1601, LE1701,LE1801, LE1901, LE2001,
|
||||||
LE2101,LE2201, LE2301, LE2401, LE2501
|
LE2101,LE2201, LE2301, LE2401, LE2501
|
||||||
};
|
};
|
||||||
double cent = Math.Floor(d.Year * .01) * 100; //Gets turn of century year.
|
Double cent = Math.Floor(d.Year * .01) * 100; //Gets turn of century year.
|
||||||
int index = GetIndex(cent); //Gets index for calling data list.
|
Int32 index = GetIndex(cent); //Gets index for calling data list.
|
||||||
|
|
||||||
if (index == -1) { return new double[] { }; } //RETURN EMPTY ARRAY IF OUTSIDE DB RANGE
|
if (index == -1) { return new Double[] { }; } //RETURN EMPTY ARRAY IF OUTSIDE DB RANGE
|
||||||
|
|
||||||
//Determine data to LEnd if year is near beginning or end of databaLE
|
//Determine data to LEnd if year is near beginning or end of databaLE
|
||||||
int halfCent = d.Year - (int)cent;
|
Int32 halfCent = d.Year - (Int32)cent;
|
||||||
if (index == 0 || index == data.Count - 1)
|
return index == 0 || index == data.Count - 1 ? index == 0 ? halfCent <= 50 ? data[0] : data[0].Concat(data[1]).ToArray() : halfCent <= 50 ? data[index - 1].Concat(data[index]).ToArray() : data[index] : halfCent <= 50 ? data[index - 1].Concat(data[index]).ToArray() : data[index].Concat(data[index + 1]).ToArray();
|
||||||
{
|
|
||||||
if (index == 0)
|
|
||||||
{
|
|
||||||
if (halfCent <= 50) { return data[0]; }
|
|
||||||
else { return data[0].Concat(data[1]).ToArray(); }
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (halfCent <= 50) { return data[index - 1].Concat(data[index]).ToArray(); }
|
|
||||||
else { return data[index]; }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (halfCent <= 50) { return data[index - 1].Concat(data[index]).ToArray(); }
|
|
||||||
else { return data[index].Concat(data[index + 1]).ToArray(); }
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
public static double[] LunarDateData_100Year(DateTime d)
|
public static Double[] LunarDateData_100Year(DateTime d) {
|
||||||
{
|
|
||||||
//Return combined 100 year arrays
|
//Return combined 100 year arrays
|
||||||
List<double[]> data = new List<double[]>()
|
List<Double[]> data = new List<Double[]>()
|
||||||
{
|
{
|
||||||
LE1601, LE1701,LE1801, LE1901, LE2001,
|
LE1601, LE1701,LE1801, LE1901, LE2001,
|
||||||
LE2101,LE2201, LE2301, LE2401, LE2501
|
LE2101,LE2201, LE2301, LE2401, LE2501
|
||||||
};
|
};
|
||||||
double cent = Math.Floor(d.Year * .01) * 100; //Gets turn of century year.
|
Double cent = Math.Floor(d.Year * .01) * 100; //Gets turn of century year.
|
||||||
int index = GetIndex(cent); //Gets index for calling data list.
|
Int32 index = GetIndex(cent); //Gets index for calling data list.
|
||||||
|
|
||||||
if (index == -1) { return new double[] { }; } //RETURN EMPTY ARRAY IF OUTSIDE DB RANGE
|
if (index == -1) { return new Double[] { }; } //RETURN EMPTY ARRAY IF OUTSIDE DB RANGE
|
||||||
//Return proper 100 year table.
|
//Return proper 100 year table.
|
||||||
return data[index];
|
return data[index];
|
||||||
|
|
||||||
}
|
}
|
||||||
private static int GetIndex(double cent)
|
private static Int32 GetIndex(Double cent) {
|
||||||
{
|
Int32 dex = 0;
|
||||||
int dex = 0;
|
Int32 c = Convert.ToInt32(cent * .01);
|
||||||
int c = Convert.ToInt32(cent * .01);
|
|
||||||
//START CENTURY 16
|
//START CENTURY 16
|
||||||
//END CENTRURY 26
|
//END CENTRURY 26
|
||||||
//AJDUST AS DATABALE GROWS
|
//AJDUST AS DATABALE GROWS
|
||||||
for (int i = 16; i < 26; i++)
|
for (Int32 i = 16; i < 26; i++) {
|
||||||
{
|
|
||||||
if (i == c) { return dex; }
|
if (i == c) { return dex; }
|
||||||
dex++;
|
dex++;
|
||||||
}
|
}
|
||||||
|
@ -2,12 +2,10 @@
|
|||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
|
||||||
namespace CoordinateSharp.Eclipse
|
namespace CoordinateSharp.Eclipse {
|
||||||
{
|
internal class SolarData {
|
||||||
internal class SolarData
|
|
||||||
{
|
|
||||||
//ECLIPSE DATA FROM 1701-2400
|
//ECLIPSE DATA FROM 1701-2400
|
||||||
static double[] SE1601 = new double[]
|
static readonly Double[] SE1601 = new Double[]
|
||||||
{
|
{
|
||||||
// 1601 1 4
|
// 1601 1 4
|
||||||
2305817.017109, 12.0, -4.0, 4.0, 117.4, 117.4,
|
2305817.017109, 12.0, -4.0, 4.0, 117.4, 117.4,
|
||||||
@ -2242,7 +2240,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
-0.0114460, 0.0000434, -1.270e-05,
|
-0.0114460, 0.0000434, -1.270e-05,
|
||||||
0.0046524, 0.0046293
|
0.0046524, 0.0046293
|
||||||
};
|
};
|
||||||
static double[] SE1701 = new double[]
|
static readonly Double[] SE1701 = new Double[]
|
||||||
{
|
{
|
||||||
// 1701 2 7
|
// 1701 2 7
|
||||||
2342375.461729, 23.0, -4.0, 4.0, 8.2, 8.2,
|
2342375.461729, 23.0, -4.0, 4.0, 8.2, 8.2,
|
||||||
@ -4504,7 +4502,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
-0.0039760, -0.0000963, -1.230e-05,
|
-0.0039760, -0.0000963, -1.230e-05,
|
||||||
0.0046973, 0.0046739
|
0.0046973, 0.0046739
|
||||||
};
|
};
|
||||||
static double[] SE1801 = new double[]
|
static readonly Double[] SE1801 = new Double[]
|
||||||
{
|
{
|
||||||
// 1801 3 14
|
// 1801 3 14
|
||||||
2378934.156652, 16.0, -4.0, 4.0, 13.0, 13.0,
|
2378934.156652, 16.0, -4.0, 4.0, 13.0, 13.0,
|
||||||
@ -6684,7 +6682,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
0.5676560, -0.0000826, -1.030e-05,
|
0.5676560, -0.0000826, -1.030e-05,
|
||||||
0.0214110, -0.0000822, -1.030e-05,
|
0.0214110, -0.0000822, -1.030e-05,
|
||||||
0.0047365, 0.0047129};
|
0.0047365, 0.0047129};
|
||||||
static double[] SE1901 = new double[]
|
static readonly Double[] SE1901 = new Double[]
|
||||||
{
|
{
|
||||||
// 1901 5 18
|
// 1901 5 18
|
||||||
2415522.731807, 6.0, -4.0, 4.0, -0.9, -0.9,
|
2415522.731807, 6.0, -4.0, 4.0, -0.9, -0.9,
|
||||||
@ -8739,7 +8737,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
0.0268200, 0.0000511, -1.000e-05,
|
0.0268200, 0.0000511, -1.000e-05,
|
||||||
0.0047553, 0.0047316
|
0.0047553, 0.0047316
|
||||||
};
|
};
|
||||||
static double[] SE2001 = new double[]
|
static readonly Double[] SE2001 = new Double[]
|
||||||
{
|
{
|
||||||
// 2001 6 21
|
// 2001 6 21
|
||||||
2452082.003314, 12.0, -4.0, 4.0, 64.2, 64.2,
|
2452082.003314, 12.0, -4.0, 4.0, 64.2, 64.2,
|
||||||
@ -10758,7 +10756,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
-0.0062330, -0.0001026, -1.200e-05,
|
-0.0062330, -0.0001026, -1.200e-05,
|
||||||
0.0046346, 0.0046116
|
0.0046346, 0.0046116
|
||||||
};
|
};
|
||||||
static double[] SE2101 = new double[]
|
static readonly Double[] SE2101 = new Double[]
|
||||||
{
|
{
|
||||||
// 2101 2 28
|
// 2101 2 28
|
||||||
2488492.594741, 2.0, -4.0, 4.0, 205.2, 205.2,
|
2488492.594741, 2.0, -4.0, 4.0, 205.2, 205.2,
|
||||||
@ -12876,7 +12874,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
0.0190180, -0.0000736, -1.010e-05,
|
0.0190180, -0.0000736, -1.010e-05,
|
||||||
0.0046769, 0.0046536
|
0.0046769, 0.0046536
|
||||||
};
|
};
|
||||||
static double[] SE2201 = new double[]
|
static readonly Double[] SE2201 = new Double[]
|
||||||
{
|
{
|
||||||
// 2201 4 4
|
// 2201 4 4
|
||||||
2525051.763849, 6.0, -4.0, 4.0, 444.4, 444.4,
|
2525051.763849, 6.0, -4.0, 4.0, 444.4, 444.4,
|
||||||
@ -15111,7 +15109,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
0.0284480, 0.0000235, -9.800e-06,
|
0.0284480, 0.0000235, -9.800e-06,
|
||||||
0.0047462, 0.0047226
|
0.0047462, 0.0047226
|
||||||
};
|
};
|
||||||
static double[] SE2301 = new double[]
|
static readonly Double[] SE2301 = new Double[]
|
||||||
{
|
{
|
||||||
// 2301 5 9
|
// 2301 5 9
|
||||||
2561611.084014, 14.0, -4.0, 4.0, 719.9, 719.9,
|
2561611.084014, 14.0, -4.0, 4.0, 719.9, 719.9,
|
||||||
@ -17346,7 +17344,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
-0.0071310, -0.0001059, -1.190e-05,
|
-0.0071310, -0.0001059, -1.190e-05,
|
||||||
0.0046006, 0.0045776
|
0.0046006, 0.0045776
|
||||||
};
|
};
|
||||||
static double[] SE2401 = new double[] {
|
static readonly Double[] SE2401 = new Double[] {
|
||||||
// 2401 1 14
|
// 2401 1 14
|
||||||
2598021.427310, 22.0, -4.0, 4.0, 1057.8, 1057.8,
|
2598021.427310, 22.0, -4.0, 4.0, 1057.8, 1057.8,
|
||||||
-0.2870830, 0.5189539, -4.590e-05, -7.000e-06,
|
-0.2870830, 0.5189539, -4.590e-05, -7.000e-06,
|
||||||
@ -19481,7 +19479,7 @@ namespace CoordinateSharp.Eclipse
|
|||||||
0.0163870, -0.0000706, -1.000e-05,
|
0.0163870, -0.0000706, -1.000e-05,
|
||||||
0.0046201, 0.0045971
|
0.0046201, 0.0045971
|
||||||
};
|
};
|
||||||
static double[] SE2501 = new double[] {
|
static readonly Double[] SE2501 = new Double[] {
|
||||||
// 2501 2 19
|
// 2501 2 19
|
||||||
2634580.691215, 5.0, -4.0, 4.0, 1460.8, 1460.8,
|
2634580.691215, 5.0, -4.0, 4.0, 1460.8, 1460.8,
|
||||||
0.1813720, 0.5619451, -3.330e-05, -9.490e-06,
|
0.1813720, 0.5619451, -3.330e-05, -9.490e-06,
|
||||||
@ -21508,67 +21506,46 @@ namespace CoordinateSharp.Eclipse
|
|||||||
0.0248230, 0.0000365, -9.800e-06,
|
0.0248230, 0.0000365, -9.800e-06,
|
||||||
0.0046944, 0.0046710 };
|
0.0046944, 0.0046710 };
|
||||||
|
|
||||||
public static double[] SolarDateData(DateTime d)
|
public static Double[] SolarDateData(DateTime d) {
|
||||||
{
|
|
||||||
//Return combined 100 year arrays so in order to grab Last and Next exlipse.
|
//Return combined 100 year arrays so in order to grab Last and Next exlipse.
|
||||||
List<double[]> data = new List<double[]>()
|
List<Double[]> data = new List<Double[]>()
|
||||||
{
|
{
|
||||||
SE1601, SE1701, SE1801, SE1901, SE2001,
|
SE1601, SE1701, SE1801, SE1901, SE2001,
|
||||||
SE2101, SE2201, SE2301, SE2401, SE2501
|
SE2101, SE2201, SE2301, SE2401, SE2501
|
||||||
};
|
};
|
||||||
double cent = Math.Floor(d.Year * .01) * 100; //Gets turn of century year.
|
Double cent = Math.Floor(d.Year * .01) * 100; //Gets turn of century year.
|
||||||
int index = GetIndex(cent); //Gets index for calling data list.
|
Int32 index = GetIndex(cent); //Gets index for calling data list.
|
||||||
|
|
||||||
if (index == -1) { return new double[] { };} //RETURN EMPTY ARRAY IF OUTSIDE DB RANGE
|
if (index == -1) { return new Double[] { }; } //RETURN EMPTY ARRAY IF OUTSIDE DB RANGE
|
||||||
|
|
||||||
//Determine data to send if year is near beginning or end of database
|
//Determine data to send if year is near beginning or end of database
|
||||||
int halfCent = d.Year - (int)cent;
|
Int32 halfCent = d.Year - (Int32)cent;
|
||||||
|
|
||||||
if (index == 0 || index == data.Count - 1)
|
return index == 0 || index == data.Count - 1 ? index == 0 ? halfCent <= 50 ? data[0] : data[0].Concat(data[1]).ToArray() : halfCent <= 50 ? data[index - 1].Concat(data[index]).ToArray() : data[index] : halfCent <= 50 ? data[index - 1].Concat(data[index]).ToArray() : data[index].Concat(data[index + 1]).ToArray();
|
||||||
{
|
|
||||||
if(index == 0)
|
|
||||||
{
|
|
||||||
if (halfCent <= 50) { return data[0]; }
|
|
||||||
else { return data[0].Concat(data[1]).ToArray(); }
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (halfCent <= 50) { return data[index - 1].Concat(data[index]).ToArray(); }
|
|
||||||
else { return data[index]; }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
if (halfCent <= 50) { return data[index - 1].Concat(data[index]).ToArray(); }
|
|
||||||
else { return data[index].Concat(data[index+1]).ToArray(); }
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
public static double[] SolarDateData_100Year(DateTime d)
|
public static Double[] SolarDateData_100Year(DateTime d) {
|
||||||
{
|
|
||||||
//Return combined 100 year arrays
|
//Return combined 100 year arrays
|
||||||
List<double[]> data = new List<double[]>()
|
List<Double[]> data = new List<Double[]>()
|
||||||
{
|
{
|
||||||
SE1601, SE1701, SE1801, SE1901, SE2001,
|
SE1601, SE1701, SE1801, SE1901, SE2001,
|
||||||
SE2101, SE2201, SE2301, SE2401, SE2501
|
SE2101, SE2201, SE2301, SE2401, SE2501
|
||||||
};
|
};
|
||||||
double cent = Math.Floor(d.Year * .01) * 100; //Gets turn of century year.
|
Double cent = Math.Floor(d.Year * .01) * 100; //Gets turn of century year.
|
||||||
int index = GetIndex(cent); //Gets index for calling data list.
|
Int32 index = GetIndex(cent); //Gets index for calling data list.
|
||||||
|
|
||||||
if (index == -1) { return new double[] { }; } //RETURN EMPTY ARRAY IF OUTSIDE DB RANGE
|
if (index == -1) { return new Double[] { }; } //RETURN EMPTY ARRAY IF OUTSIDE DB RANGE
|
||||||
//Return proper 100 year table.
|
//Return proper 100 year table.
|
||||||
return data[index];
|
return data[index];
|
||||||
|
|
||||||
}
|
}
|
||||||
private static int GetIndex(double cent)
|
private static Int32 GetIndex(Double cent) {
|
||||||
{
|
Int32 dex = 0;
|
||||||
int dex = 0;
|
Int32 c = Convert.ToInt32(cent * .01);
|
||||||
int c = Convert.ToInt32(cent * .01);
|
|
||||||
//START CENTURY 16
|
//START CENTURY 16
|
||||||
//END CENTRURY 26
|
//END CENTRURY 26
|
||||||
//AJDUST AS DATABASE GROWS
|
//AJDUST AS DATABASE GROWS
|
||||||
for(int i = 16; i<26;i++)
|
for (Int32 i = 16; i < 26; i++) {
|
||||||
{
|
|
||||||
if (i == c) { return dex; }
|
if (i == c) { return dex; }
|
||||||
dex++;
|
dex++;
|
||||||
}
|
}
|
||||||
|
@ -1,59 +1,48 @@
|
|||||||
using System.Collections.Generic;
|
using System;
|
||||||
using System.Linq;
|
using System.Collections.Generic;
|
||||||
|
|
||||||
namespace CoordinateSharp
|
namespace CoordinateSharp {
|
||||||
{
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Geo Fence class. It helps to check if points/coordinates are inside a polygon,
|
/// Geo Fence class. It helps to check if points/coordinates are inside a polygon,
|
||||||
/// Next to a polyline, and counting...
|
/// Next to a polyline, and counting...
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public class GeoFence
|
public class GeoFence {
|
||||||
{
|
|
||||||
#region Fields
|
#region Fields
|
||||||
private List<Point> _points = new List<Point>();
|
private readonly List<Point> _points = new List<Point>();
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Prepare GeoFence with a list of points
|
/// Prepare GeoFence with a list of points
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="points">List of points</param>
|
/// <param name="points">List of points</param>
|
||||||
public GeoFence(List<Point> points)
|
public GeoFence(List<Point> points) => this._points = points;
|
||||||
{
|
|
||||||
_points = points;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Prepare Geofence with a list of coordinates
|
/// Prepare Geofence with a list of coordinates
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="coordinates">List of coordinates</param>
|
/// <param name="coordinates">List of coordinates</param>
|
||||||
public GeoFence(List<Coordinate> coordinates)
|
public GeoFence(List<Coordinate> coordinates) {
|
||||||
{
|
foreach (Coordinate c in coordinates) {
|
||||||
foreach (var c in coordinates)
|
this._points.Add(new Point { Latitude = c.Latitude.ToDouble(), Longitude = c.Longitude.ToDouble() });
|
||||||
{
|
|
||||||
_points.Add(new Point { Latitude = c.Latitude.ToDouble(), Longitude = c.Longitude.ToDouble() });
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#region Utils
|
#region Utils
|
||||||
private Coordinate ClosestPointOnSegment(Point a, Point b, Coordinate p)
|
private Coordinate ClosestPointOnSegment(Point a, Point b, Coordinate p) {
|
||||||
{
|
Point d = new Point {
|
||||||
var d = new Point
|
|
||||||
{
|
|
||||||
Longitude = b.Longitude - a.Longitude,
|
Longitude = b.Longitude - a.Longitude,
|
||||||
Latitude = b.Latitude - a.Latitude,
|
Latitude = b.Latitude - a.Latitude,
|
||||||
};
|
};
|
||||||
|
|
||||||
double number = (p.Longitude.ToDouble() - a.Longitude) * d.Longitude + (p.Latitude.ToDouble() - a.Latitude) * d.Latitude;
|
Double number = (p.Longitude.ToDouble() - a.Longitude) * d.Longitude + (p.Latitude.ToDouble() - a.Latitude) * d.Latitude;
|
||||||
|
|
||||||
if (number <= 0.0)
|
if (number <= 0.0) {
|
||||||
return new Coordinate(a.Latitude, a.Longitude);
|
return new Coordinate(a.Latitude, a.Longitude);
|
||||||
|
}
|
||||||
|
|
||||||
double denom = d.Longitude * d.Longitude + d.Latitude * d.Latitude;
|
Double denom = d.Longitude * d.Longitude + d.Latitude * d.Latitude;
|
||||||
|
|
||||||
if (number >= denom)
|
return number >= denom ? new Coordinate(b.Latitude, b.Longitude) : new Coordinate(a.Latitude + number / denom * d.Latitude, a.Longitude + number / denom * d.Longitude);
|
||||||
return new Coordinate(b.Latitude, b.Longitude);
|
|
||||||
|
|
||||||
return new Coordinate(a.Latitude + (number / denom) * d.Latitude, a.Longitude + (number / denom) * d.Longitude);
|
|
||||||
}
|
}
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
@ -64,22 +53,19 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="point">The point to test</param>
|
/// <param name="point">The point to test</param>
|
||||||
/// <returns>bool</returns>
|
/// <returns>bool</returns>
|
||||||
public bool IsPointInPolygon(Coordinate point)
|
public Boolean IsPointInPolygon(Coordinate point) {
|
||||||
{
|
if (point == null) {
|
||||||
if (point == null)
|
|
||||||
return false;
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
double latitude = point.Latitude.ToDouble();
|
Double latitude = point.Latitude.ToDouble();
|
||||||
double longitude = point.Longitude.ToDouble();
|
Double longitude = point.Longitude.ToDouble();
|
||||||
int sides = _points.Count;
|
Int32 sides = this._points.Count;
|
||||||
int j = sides - 1;
|
Int32 j = sides - 1;
|
||||||
bool pointStatus = false;
|
Boolean pointStatus = false;
|
||||||
for (int i = 0; i < sides; i++)
|
for (Int32 i = 0; i < sides; i++) {
|
||||||
{
|
if (this._points[i].Latitude < latitude && this._points[j].Latitude >= latitude || this._points[j].Latitude < latitude && this._points[i].Latitude >= latitude) {
|
||||||
if (_points[i].Latitude < latitude && _points[j].Latitude >= latitude || _points[j].Latitude < latitude && _points[i].Latitude >= latitude)
|
if (this._points[i].Longitude + (latitude - this._points[i].Latitude) / (this._points[j].Latitude - this._points[i].Latitude) * (this._points[j].Longitude - this._points[i].Longitude) < longitude) {
|
||||||
{
|
|
||||||
if (_points[i].Longitude + (latitude - _points[i].Latitude) / (_points[j].Latitude - _points[i].Latitude) * (_points[j].Longitude - _points[i].Longitude) < longitude)
|
|
||||||
{
|
|
||||||
pointStatus = !pointStatus;
|
pointStatus = !pointStatus;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -95,17 +81,17 @@ namespace CoordinateSharp
|
|||||||
/// <param name="point">The point to test</param>
|
/// <param name="point">The point to test</param>
|
||||||
/// <param name="range">The range in meters</param>
|
/// <param name="range">The range in meters</param>
|
||||||
/// <returns>bool</returns>
|
/// <returns>bool</returns>
|
||||||
public bool IsPointInRangeOfLine(Coordinate point, double range)
|
public Boolean IsPointInRangeOfLine(Coordinate point, Double range) {
|
||||||
{
|
if (point == null) {
|
||||||
if (point == null)
|
|
||||||
return false;
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
for (int i = 0; i < _points.Count - 1; i++)
|
for (Int32 i = 0; i < this._points.Count - 1; i++) {
|
||||||
{
|
Coordinate c = this.ClosestPointOnSegment(this._points[i], this._points[i + 1], point);
|
||||||
Coordinate c = ClosestPointOnSegment(_points[i], _points[i + 1], point);
|
if (c.Get_Distance_From_Coordinate(point).Meters <= range) {
|
||||||
if (c.Get_Distance_From_Coordinate(point).Meters <= range)
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -117,25 +103,17 @@ namespace CoordinateSharp
|
|||||||
/// <param name="point">The point to test</param>
|
/// <param name="point">The point to test</param>
|
||||||
/// <param name="range">The range is a distance object</param>
|
/// <param name="range">The range is a distance object</param>
|
||||||
/// <returns>bool</returns>
|
/// <returns>bool</returns>
|
||||||
public bool IsPointInRangeOfLine(Coordinate point, Distance range)
|
public Boolean IsPointInRangeOfLine(Coordinate point, Distance range) => point == null || range == null ? false : this.IsPointInRangeOfLine(point, range.Meters);
|
||||||
{
|
|
||||||
if (point == null || range == null)
|
|
||||||
return false;
|
|
||||||
|
|
||||||
return IsPointInRangeOfLine(point, range.Meters);
|
|
||||||
}
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// This class is a help class to simplify GeoFence calculus
|
/// This class is a help class to simplify GeoFence calculus
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public class Point
|
public class Point {
|
||||||
{
|
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Initialize empty point
|
/// Initialize empty point
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public Point()
|
public Point() {
|
||||||
{
|
|
||||||
|
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@ -143,19 +121,18 @@ namespace CoordinateSharp
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="lat">Latitude (signed)</param>
|
/// <param name="lat">Latitude (signed)</param>
|
||||||
/// <param name="lng">Longitude (signed)</param>
|
/// <param name="lng">Longitude (signed)</param>
|
||||||
public Point(double lat, double lng)
|
public Point(Double lat, Double lng) {
|
||||||
{
|
this.Latitude = lat;
|
||||||
Latitude = lat;
|
this.Longitude = lng;
|
||||||
Longitude = lng;
|
|
||||||
}
|
}
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// The longitude in degrees
|
/// The longitude in degrees
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Longitude;
|
public Double Longitude;
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// The latitude in degrees
|
/// The latitude in degrees
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public double Latitude;
|
public Double Latitude;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -1,4 +1,5 @@
|
|||||||
using System.Reflection;
|
#if !NETCOREAPP
|
||||||
|
using System.Reflection;
|
||||||
using System.Runtime.CompilerServices;
|
using System.Runtime.CompilerServices;
|
||||||
using System.Runtime.InteropServices;
|
using System.Runtime.InteropServices;
|
||||||
|
|
||||||
@ -34,3 +35,4 @@ using System.Runtime.InteropServices;
|
|||||||
// [assembly: AssemblyVersion("1.0.*")]
|
// [assembly: AssemblyVersion("1.0.*")]
|
||||||
[assembly: AssemblyVersion("1.1.5.2")]
|
[assembly: AssemblyVersion("1.1.5.2")]
|
||||||
[assembly: AssemblyFileVersion("1.1.5.2")]
|
[assembly: AssemblyFileVersion("1.1.5.2")]
|
||||||
|
#endif
|
25
CoordinateSharp_Core.sln
Normal file
25
CoordinateSharp_Core.sln
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
|
||||||
|
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||||
|
# Visual Studio Version 16
|
||||||
|
VisualStudioVersion = 16.0.29519.87
|
||||||
|
MinimumVisualStudioVersion = 10.0.40219.1
|
||||||
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CoordinateSharp", "CoordinateSharp\CoordinateSharp_Core.csproj", "{127E1C0F-06DC-492C-B124-19A89D44B47C}"
|
||||||
|
EndProject
|
||||||
|
Global
|
||||||
|
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||||
|
Debug|Any CPU = Debug|Any CPU
|
||||||
|
Release|Any CPU = Release|Any CPU
|
||||||
|
EndGlobalSection
|
||||||
|
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||||
|
{127E1C0F-06DC-492C-B124-19A89D44B47C}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{127E1C0F-06DC-492C-B124-19A89D44B47C}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{127E1C0F-06DC-492C-B124-19A89D44B47C}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{127E1C0F-06DC-492C-B124-19A89D44B47C}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
EndGlobalSection
|
||||||
|
GlobalSection(SolutionProperties) = preSolution
|
||||||
|
HideSolutionNode = FALSE
|
||||||
|
EndGlobalSection
|
||||||
|
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||||
|
SolutionGuid = {667C979D-42C3-4EE8-9B2B-D85EFC09940A}
|
||||||
|
EndGlobalSection
|
||||||
|
EndGlobal
|
Loading…
Reference in New Issue
Block a user