Notes on Celestial Navigation

CNSH - Calculate the Observer's Position Using Saint-Hilaire's Method

Description: The program calculates the latitude and longitude of the observer's position from two sights, either simultaneous (\(DMG = 0\)) or as a running fix (\(DMG > 0\)), using Saint-Hilaire's method.

Inputs:

DR LatThe DR latitude of the observer
DR LonThe DR longitude of the observer
GHA sight 1GHA of the celestial object from sight 1
Dec sight 1Declination of the celestial object from sight 1
Ho sight 1Height/Altitude of the celestial object from sight 1
DMGDistance made good between sights 1 and 2 (running fix)
CMGCourse made good between sights (\(DMG > 0\))
GHA sight 2GHA of the celestial object from sight 2
Dec sight 2Declination of the celestial object from sight 2
Ho sight 2Height/Altitude of the celestial object from sight 2

Outputs:

LatThe calculated latitude of the observer
LonThe calculated longitude of the observer

Sample execution:

DR Lat? 38,30
DR Lon? -30,0
GHA sight 1? 13,22
Dec sight 1? 20,03.3
Ho sight 1? 66,49.2
DMG? 30
CMG? 25
GHA sight 2? 43,22
Dec sight 2? 20,02.3
Ho sight 2? 67,11

Lat = 39° 12.5'
Lon = -28° 59.4'

(For explanation of notation, conventions etc, see python-programs).



Copyright (C) 2024 Ian Staniforth

This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.

This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.

You should have received a copy of the GNU General Public License along with this program. If not, see https://www.gnu.org/licenses/.


# CNSH - Calculate a fix from 2 Sights using Saint-Hilaire's Method

from math import *
from CN_LIB import *

lat = stod("DR Lat? ")
lon = stod("DR Lon? ")

# First sight

gha1 = stod("GHA sight 1? ")
dec1 = stod("Dec sight 1? ")
ho1 = stod("Ho sight 1? ")

lha1 = (gha1+lon+360)%360

hc1 = aSin(Sin(lat)*Sin(dec1)+Cos(lat)*Cos(dec1)*Cos(lha1))
z1 = aCos((Sin(dec1)-Sin(hc1)*Sin(lat))/(Cos(hc1)*Cos(lat)))

zn1 = 360-z1 if lha1 <= 180 else z1

intercept1 = ho1-hc1

dlat1 = intercept1*Cos(zn1)
dlon1 = intercept1*Sin(zn1)/Cos(lat)
lat1 = lat+dlat1
lon1 = lon+dlon1

# Running fix?

dmg = float(input("DMG? "))
if (dmg > 0):
    cmg = stod("CMG? ")
    rfdlat = dmg*Cos(cmg)/60
    rfdlon = dmg*Sin(cmg)/Cos(lat)/60
    lat1 = lat1+rfdlat
    lon1 = lon1+rfdlon

# Second sight

gha2 = stod("GHA sight 2? ")
dec2 = stod("Dec sight 2? ")
ho2 = stod("Ho sight 2? ")

lha2 = (gha2+lon1+360)%360

hc2 = aSin(Sin(lat1)*Sin(dec2)+Cos(lat1)*Cos(dec2)*Cos(lha2))
z2 = aCos((Sin(dec2)-Sin(hc2)*Sin(lat1))/(Cos(hc2)*Cos(lat1)))

zn2 = 360-z2 if lha2 <= 180 else z2

intercept2 = ho2-hc2

# Calculate position P

theta = zn1-zn2
ep = intercept2/Sin(theta)
phi = zn1-90

dlat2 = ep*Cos(phi)
dlon2 = ep*Sin(phi)/Cos(lat1)
lat2 = lat1+dlat2
lon2 = lon1+dlon2

print("")
print("Lat = "+dtos(lat2))
print("Lon = "+dtos(lon2))