diff --git a/pkg/astrometry/astrometry.go b/pkg/astrometry/astrometry.go index 52c5ea3..9ab5004 100644 --- a/pkg/astrometry/astrometry.go +++ b/pkg/astrometry/astrometry.go @@ -8,4 +8,46 @@ package astrometry +import ( + "math" + "time" + + "github.com/observerly/sidera/pkg/common" + "github.com/observerly/sidera/pkg/epoch" +) + +/*****************************************************************************************************************/ + +/* +the hour angle is the angular distance on the celestial sphere measured westward along the celestial equator. + +The hour angle is the angular distance on the celestial sphere measured westward along the celestial equator +from the observer's meridian to the hour circle passing through a celestial body. It is usually expressed +in degrees, but can also be measured in time units, with 24 hours corresponding to 360 degrees. + +The hour angle is an important concept in celestial navigation and astronomy, as it is used to determine +the position of celestial objects in the sky relative to an observer's location. By knowing the hour angle +of a celestial body, an observer can determine when the body will be at its highest point in the sky +(known as the meridian transit) and calculate its position in the sky at any given time. +*/ +func GetHourAngle( + datetime time.Time, + observer common.GeographicCoordinate, + target common.EquatorialCoordinate, +) float64 { + LST := epoch.GetLocalSiderealTime(datetime, observer) + + // the hour angle is the local sidereal time (adjusted for hours) minus the right ascension: + // there are 24 hours in a full 360 degree rotation, so we multiply the local sidereal time by 15 (360/24): + var ha = LST*15 - target.RightAscension + + // if the hour angle is less than zero, ensure we rotate by 2π radians (360 degrees): + if ha < 0 { + ha += 360 + } + + // return the hour angle corrected for modulo % 360. + return math.Mod(ha, 360) +} + /*****************************************************************************************************************/ diff --git a/pkg/astrometry/astrometry_test.go b/pkg/astrometry/astrometry_test.go index 52c5ea3..0672961 100644 --- a/pkg/astrometry/astrometry_test.go +++ b/pkg/astrometry/astrometry_test.go @@ -8,4 +8,49 @@ package astrometry +import ( + "testing" + "time" + + "github.com/observerly/sidera/pkg/common" + "github.com/stretchr/testify/assert" +) + +/*****************************************************************************************************************/ + +// We define a datetime as some arbitrary date and time for testing purposes: +var datetime time.Time = time.Date(2021, 5, 14, 0, 0, 0, 0, time.UTC) + +/*****************************************************************************************************************/ + +var observer common.GeographicCoordinate = common.GeographicCoordinate{ + Latitude: 19.8207, + Longitude: -155.468094, + Elevation: 4205, +} + +/*****************************************************************************************************************/ + +var betelgeuse common.EquatorialCoordinate = common.EquatorialCoordinate{ + RightAscension: 88.7929583, + Declination: 7.4070639, +} + +/*****************************************************************************************************************/ + +func TestGetHourAngle(t *testing.T) { + ha := GetHourAngle(datetime, observer, betelgeuse) + + // Test the Julian Date calculation for the J1858.0 epoch: + assert.Equal(t, ha, 347.6983663054307) + + if ha < 0 { + t.Errorf("got %f, wanted a positive hour angle value", ha) + } + + if ha > 360 { + t.Errorf("got %f, wanted a positive hour angle value that is less than 360 degrees", ha) + } +} + /*****************************************************************************************************************/