############################################################################
#
# File: geodat.icn
#
# Subject: Procedures for geodetic datum conversion
#
# Authors: William S. Evans and Gregg M. Townsend
#
# Date: July 31, 2000
#
############################################################################
#
# This file is in the public domain.
#
############################################################################
#
# These procedures provide "projections" that convert among geodetic
# datums, which relate locations on the earth's surface to longitude
# and latitude coordinates. As measurement techniques improve,
# newer datums typically give slightly different values from older
# ones. The values returned here are used with the project()
# procedure of cartog.icn.
#
# geodat(s1, s2) defines a geodetic datum conversion.
# molodensky() performs an algorithmic datum conversion.
# nadcon(s1, s2) uses data files for more precise conversion.
#
# ellipsoid(s) return the parameters of the named ellipsoid.
#
############################################################################
#
# geodat(f, t) returns a projection from longitude and latitude
# in datum f to longitude and latitude in datum t.
# f and t are strings. If f and t equal "NAD83", "NAD27",
# "HARN", or "HPGN", geodat returns a nadcon projection.
# Failing that, geodat returns a molodensky projection.
#
# The input to the projection is a list of signed numeric values,
# angles measured in degrees, with each pair representing one
# location; longitude precedes latitude. The output is a list
# with the same form and length as the input list.
#
############################################################################
#
# nadcon(f, t) returns a projection from longitude and latitude
# in datum f to longitude and latitude in datum t. The strings
# f and t must each be one of "NAD83", "NAD27", "HARN", or "HPGN".
# The projection uses our implementation of the National Oceanic
# and Atmospheric Administration's (NOAA's) North American Datum
# Conversion Utility (NADCON); for more information, see
# http://www.ngs.noaa.gov/TOOLS/Nadcon/Nadcon.html
#
# nadcon() requires data grid (.loa and .laa) files, which must be
# found in the current directory or along the space-separated path
# given by the environment variable DPATH. These files can be
# downloaded from:
# http://www.cs.arizona.edu/icon/ftp/data/nadcon/
# ftp://ftp.cs.arizona.edu/icon/data/nadcon/
#
# The projection's input and output are lists of signed numbers.
# Output is properly rounded and so may not agree exactly with
# the equivalent NOAA programs.
#
############################################################################
#
# molodensky(dx, dy, dz, ain, fin, aout, fout) returns a projection
# from input longitude and latitude to output longitude and latitude.
# The projection uses the standard Molodensky transformation.
# The input datum is specified by an ellipsoid with parameters
# ain, the equatorial radius in metres, and fin, the flattening;
# and by three shift values dx, dy, and dz. The output datum is
# specified by an ellipsoid with parameters aout and fout.
#
# If dz is null, then dx and dy are interpreted as the names of
# an input and output datum. The names are the ID codes
# specified in NIMA TR 8350.2.
#
# The projection's input and output are lists of signed numbers.
#
############################################################################
#
# ellipsoid(s) return a list [a, 1/f] containing the defining
# parameters of the standard ellipsoid model named s; a is the
# equatorial radius and 1/f is the flattening factor. Names are
# listed in the code; the default is "WGS84".
#
############################################################################
#
# Ellipsoid and datum parameters are from:
#
# Department of Defense World Geodetic System 1984
# National Imagery and Mapping Agency
# Technical Report TR8350.2
# Third Edition, Amendment 1 (3 January 2000)
# ftp://ftp.nima.mil/pub/gg/tr8350.2/
#
############################################################################
#
# Links: cartog, io
#
############################################################################
link cartog
link io
# Procedures and globals named with a "gdt_" prefix are
# not intended for access outside this file.
global gdt_datum_ptab # table of gdt_datum_rec's, keyed by code
###################### Geodat Conversion #################################
procedure geodat(f, t) #: define geodetic conversion
return nadcon(f, t) | molodensky(f, t) | fail
end
###################### NADCON Conversion #################################
record gdt_nadcon( # nadcon conversion record
proj, # projection procedure
inv, # invert myself
grids # list of gdt_nadcon_grid records to search
)
record gdt_nadcon_grid( # information about a .loa and .laa file
name, # name of file
offset, # offset in file to start of grid data
termLen, # number of chars in line termination (1 or 2)
nc, nr, nz, # number of rows, columns in file (nz = ??)
xmin, xmax, dx, # dimension of coverage
ymin, ymax, dy, #
angle # ??
)
procedure nadcon(f, t) #: define NAD data conversion
local d, ft
ft := (gdt_nadcon_datum(f) || "-" || gdt_nadcon_datum(t)) | fail
d := gdt_nadcon()
d.inv := gdt_nadcon_inv
case ft of {
"NAD27-NAD83"|"NAD83-NAD27":
# more specific grids should precede less specific ones
d.grids := gdt_nadcon_initGrids(
["hawaii","prvi","stlrnc", "stgeorge","stpaul","alaska","conus"])
"NAD83-HPGN"|"HPGN-NAD83":
d.grids := gdt_nadcon_initGrids(
["alhpgn","azhpgn","cnhpgn","cohpgn","cshpgn","emhpgn","ethpgn",
"flhpgn","gahpgn","hihpgn","inhpgn","kshpgn","kyhpgn","lahpgn",
"mdhpgn","mehpgn","mihpgn","mshpgn","nbhpgn","ndhpgn","nehpgn",
"nmhpgn","nvhpgn","nyhpgn","ohhpgn","okhpgn","pvhpgn","sdhpgn",
"tnhpgn","uthpgn","vahpgn","wihpgn","wmhpgn","wohpgn","wthpgn",
"wvhpgn","wyhpgn"])
"NAD27-HPGN":
return compose(nadcon("NAD27", "NAD83"), nadcon("NAD83", "HPGN"))
"HPGN-NAD27":
return compose(nadcon("HPGN", "NAD83"), nadcon("NAD83", "NAD27"))
default: # identity conversion
d.grids := []
}
case ft of {
"NAD27-NAD83"|"NAD83-HPGN": d.proj := gdt_nadcon_fwd
"NAD83-NAD27"|"HPGN-NAD83": d.proj := gdt_nadcon_bck
default: d.proj := gdt_identity
}
return d
end
procedure gdt_nadcon_fwd(p, L)
local i, a
a := []
every i := 1 to *L by 2 do {
gdt_nadcon_fwdPoint(p, a, L[i], L[i+1]) | fail
}
return a
end
procedure gdt_nadcon_bck(p, L)
local i, a
a := []
every i := 1 to *L by 2 do {
gdt_nadcon_bckPoint(p, a, L[i], L[i+1]) | fail
}
return a
end
procedure gdt_identity(p, L)
return L
end
procedure gdt_nadcon_inv(p)
local q
q := copy(p)
case p.proj of {
gdt_nadcon_bck : q.proj := gdt_nadcon_fwd
gdt_nadcon_fwd : q.proj := gdt_nadcon_bck
gdt_identity : q.proj := gdt_identity
}
return q
end
procedure gdt_nadcon_datum(x)
case x of {
"NAD27": return "NAD27"
"NAD83": return "NAD83"
"HARN" | "HPGN": return "HPGN"
}
end
procedure gdt_nadcon_initGrids(names)
local grids, latf, lonf, a1, a2, b1, b2, g
grids := []
every name := !names do {
close(\lonf)
close(\latf)
g := gdt_nadcon_grid()
g.name := name
lonf := dopen(name || ".loa") | &null
latf := dopen(name || ".laa") | &null
if /lonf | /latf then next # filename unreadable
a1 := read(lonf) | &null
a2 := read(lonf) | &null
b1 := read(latf) | &null
b2 := read(latf) | &null
if /a1 | /a2 | /b1 | /b2 | a1 ~== b1 | a2 ~== b2 then {
write(&errout, g.name, " incompatible or corrupt files.")
next
}
g.offset := where(lonf)
if g.offset = 141 then
g.termLen := 2
else
g.termLen := 1
a2 ? {
g.nc := integer(move(4))
g.nr := integer(move(4))
g.nz := integer(move(4))
g.xmin := real(move(12))
g.dx := real(move(12))
g.xmax := g.xmin + (g.nc - 1) * g.dx
g.ymin := real(move(12))
g.dy := real(move(12))
g.ymax := g.ymin + (g.nr - 1) * g.dy
g.angle := real(move(12))
put(grids, g)
}
}
close(\lonf)
close(\latf)
if *grids = 0 then {
write(&errout, "No valid NADCON conversion files found.")
fail
}
return grids
end
procedure gdt_nadcon_findGrid(grids, xpt, ypt)
local g
every g := !grids do {
if (g.xmin < xpt < g.xmax & g.ymin < ypt < g.ymax) then return g
}
fail
end
procedure gdt_nadcon_box(f, g, xcol, yrow)
# This procedure is very sensitive to the format of the .loa & .laa
# files. In particular, it assumes:
# 1) each line contains 6 numbers (except, possibly, the
# last line of a row, which contains (nc % 6) numbers,
# 2) each number is 12 chars long,
local charsPerRow, pos, t1, t2, t3, t4
charsPerRow := (72 + g.termLen) * integer(g.nc / 6)
if (g.nc % 6) > 0 then
charsPerRow +:= g.termLen + 12 * (g.nc % 6)
pos := g.offset + charsPerRow * (yrow - 1) +
(72 + g.termLen) * integer((xcol - 1) / 6) + 12 * ((xcol - 1) % 6)
seek(f, pos)
t1 := reads(f, 12)
if (xcol % 6 = 0) then reads(f, g.termLen) # line termination
t3 := reads(f, 12)
seek(f, pos + 12 * g.nc + g.termLen * ceil(g.nc / 6.0))
t2 := reads(f, 12)
if (xcol % 6 = 0) then reads(f, g.termLen) # line termination
t4 := reads(f, 12)
return [real(t1), real(t2), real(t3), real(t4)]
end
procedure gdt_nadcon_fwdPoint(p, a, xpt, ypt)
local g, latf, lonf, xgrid, ygrid, xcol, yrow, t, dlas, dlos
if not(g := gdt_nadcon_findGrid(p.grids, xpt, ypt)) then {
runerr(205, [xpt, ypt]) # point not in available areas
fail
}
lonf := dopen(g.name || ".loa")
latf := dopen(g.name || ".laa")
xgrid := (xpt - g.xmin) / g.dx + 1.0
ygrid := (ypt - g.ymin) / g.dy + 1.0
xcol := integer(xgrid)
yrow := integer(ygrid)
t := gdt_nadcon_box(lonf, g, xcol, yrow)
dlos := t[1] + (t[3]-t[1]) * (xgrid-xcol) + (t[2]-t[1]) * (ygrid-yrow) +
(t[4]-t[3]-t[2]+t[1]) * (xgrid-xcol) * (ygrid-yrow)
t := gdt_nadcon_box(latf, g, xcol, yrow)
dlas := t[1] + (t[3]-t[1]) * (xgrid-xcol) + (t[2]-t[1]) * (ygrid-yrow) +
(t[4]-t[3]-t[2]+t[1]) * (xgrid-xcol) * (ygrid-yrow)
close(lonf)
close(latf)
# Why is the range specified in +east and the correction in +west?
put(a, xpt - dlos / 3600.0, ypt + dlas / 3600.0)
return
end
$define CTG_NADCON_SMALL 0.000000001 # close enough for NADCON inverse
procedure gdt_nadcon_bckPoint(p, a, xpt, ypt)
local xguess, yguess, b, i, dx, dy
xguess := xpt
yguess := ypt
b := []
every i:= 1 to 10 do {
gdt_nadcon_fwdPoint(p, b, xguess, yguess) | fail
dx := xpt - get(b)
dy := ypt - get(b)
if abs(dx) > CTG_NADCON_SMALL then xguess +:= dx
if abs(dy) > CTG_NADCON_SMALL then yguess +:= dy
if abs(dx) <= CTG_NADCON_SMALL & abs(dy) <= CTG_NADCON_SMALL then {
put(a, xguess, yguess)
return
}
}
write(&errout, "Maximum iterations exceeded!!")
fail
end
################# Standard Molodensky Datum Transformation ##################
# See NIMA TR 8350.2
#
# ************************ WARNING ******************************************
# NIMA TR 8350.2 contains Molodensky parameters to convert
# from an arbitrary datum to WGS84. To convert from datum A to datum B,
# I call molodensky(Ax-Bx,Ay-By,Az-Bz,Aa,Af,Ba,Bf) where Ax,Ay,Az are the
# shift to convert A to WGS84; Bx,By,Bz are the shift to convert B to WGS84;
# Aa,Af,Ba,Bf are the ellipsoid parameters.
# ************************ WARNING ******************************************
#
# TODO:
# 1) Add special conversion for North and South pole
# 2) Add Multiple Regression Equations
# 3) Add special WGS72 to WGS84 conversion
#
record gdt_molo(
proj, # projection procedure (always gdt_molo_proj)
inv, # invert myself (always gdt_molo_inv)
dx, dy, dz, # x,y,z differences (output - input)
ain, fin, # input ellipsoid specs
aout, fout # output ellipsoid specs
)
procedure molodensky(dx,dy,dz,ain,fin,aout,fout) #: define geodetic conversion
local p, a, din, ein, dout, eout
if /dx | /dy then fail
if /dz then {
din := gdt_datum_params(dx) | fail
ein := ellipsoid(din.eps) | fail
dout := gdt_datum_params(dy) | fail
eout := ellipsoid(dout.eps) | fail
a := []
put(a, din.dx - dout.dx, din.dy - dout.dy, din.dz - dout.dz)
put(a, ein[1], ein[2], eout[1], eout[2])
return molodensky ! a
}
p := gdt_molo()
p.proj := gdt_molo_proj
p.inv := gdt_molo_inv
p.dx := dx
p.dy := dy
p.dz := dz
p.ain := ain
p.fin := fin
p.aout := aout
p.fout := fout
return p
end
procedure gdt_molo_proj(p, L)
local e2, slam, clam, sphi, cphi, Rm, Rn, dlam, dphi
local i, bbya, da, df, lam, phi, lllist
da := p.aout - p.ain
df := p.fout - p.fin
e2 := p.fin * (2 - p.fin)
bbya := 1. - p.fin
lllist := []
every i := 1 to *L by 2 do {
lam := dtor(L[i])
slam := sin(lam)
clam := cos(lam)
phi := dtor(L[i+1])
sphi := sin(phi)
cphi := cos(phi)
Rm := p.ain * (1 - e2) / (1 - e2 * sphi ^ 2) ^ (1.5)
Rn := p.ain / sqrt(1 - e2 * sphi ^ 2)
dlam := (-p.dx * slam + p.dy * clam) / (Rn * cphi)
dphi := (-p.dx * sphi * clam - p.dy * sphi * slam + p.dz * cphi +
da * (Rn * e2 * sphi * cphi) / p.ain +
df * (Rm / bbya + Rn * bbya) * sphi * cphi) / Rm
put(lllist, rtod(lam + dlam), rtod(phi + dphi))
}
return lllist
end
procedure gdt_molo_inv(p)
local q
q := gdt_molo()
q.proj := gdt_molo_proj
q.inv := gdt_molo_inv
q.dx := -p.dx
q.dy := -p.dy
q.dz := -p.dz
q.ain := p.aout
q.fin := p.fout
q.aout := p.ain
q.fout := p.fin
return q
end
###################### Ellipsoid Parameters #################################
procedure ellipsoid(name) #: return [a, 1/f] for named ellipsoid
local f, line, w, i
/name := "WGS84"
return case name of {
"Airy 1830"|"Airy"|"AA": [6377563.396, 1 / 299.3249646]
"Australian National"|"AN": [6378160.0, 1 / 298.25]
"Bessel 1841"|"BR": [6377397.155, 1 / 299.1528128]
"Bessel 1841 (Namibia)"|"BN": [6377483.865, 1 / 299.1528128]
"Clarke 1866"|"Clarke66"|"NAD27"|"CC": [6378206.4, 1 / 294.9786982]
"Clarke 1880"|"CD": [6378249.145, 1 / 293.465]
"Everest 1830"|"Everest"|"EA": [6377276.345, 1 / 300.8017]
"Everest 1948"|"Modified Everest"|"EE": [6377304.063, 1 / 300.8017]
"Everest 1956"|"EC": [6377301.243, 1 / 300.8017]
"Everest 1969"|"ED": [6377295.664, 1 / 300.8017]
"Everest (Pakistan)"|"EF": [6377309.613, 1 / 300.8017]
"Everest (Sabah & Sarawak)"|"EB": [6377298.556, 1 / 300.8017]
"Fischer 1960": [6378166.0, 1 / 298.3]
"Fischer 1968": [6378150.0, 1 / 298.3]
"GRS67": [6378160.0, 1 / 298.247167427]
"GRS80"|"NAD83"|"RF": [6378137.0, 1 / 298.257222101]
"Hayford": [6378388.0, 1 / 297.0]
"Helmert 1906"|"HE": [6378200.0, 1 / 298.3]
"Hough"|"HO": [6378270.0, 1 / 297.0]
"Indonesian 1974"|"ID": [6378160.0, 1 / 298.247]
"International 1924"|"IN": [6378388.0, 1 / 297.0]
"Krassovsky 1940"|"KA": [6378245.0, 1 / 298.3]
"Modified Airy"|"AM": [6377340.189, 1 / 299.3249646]
"Modified Fischer 1960"|"FA": [6378155.0, 1 / 298.3]
"South American 1969"|"SA": [6378160.0, 1 / 298.25]
"WGS 1960"|"WGS 60"|"WGS60"|"W60"|"WA": [6378165.0, 1 / 298.3]
"WGS 1966"|"WGS 66"|"WGS66"|"W66"|"WB": [6378145.0, 1 / 298.25]
"WGS 1972"|"WGS 72"|"WGS72"|"W72"|"WD": [6378135.0, 1 / 298.26]
"WGS 1984"|"WGS 84"|"WGS84"|"W84"|"WE": [6378137.0, 1 / 298.257223563]
default: runerr(207, name)
}
end
###################### Datum Parameters #################################
record gdt_datum_rec(
region, # major region of datum (e.g. "Africa")
name, # datum code name
area, # area of datum (e.g. "Cameroon")
eps, # ellipsoid specification (e.g. "CD")
dx, dy, dz, # x,y,z differences from WGS84
ex, ey, ez # x,y,z maximum error in converted point (unused)
)
procedure gdt_datum_params(codename)
initial gdt_datum_init()
return \gdt_datum_ptab[codename] | runerr(207, codename)
end
procedure gdt_datum_add(key, fields[])
return gdt_datum_ptab[key] := gdt_datum_rec ! fields
end
procedure gdt_datum_init()
gdt_datum_ptab := table()
$define add gdt_datum_add
# ----------------- AFRICA --------------------------------
add("ADI-M", "Africa",
"Adindan","mean Ethiopia & Sudan","CD", -166,-15,204, 5,5,3
)
add("ADI-E", "Africa",
"Adindan","Burkina Faso","CD", -118,-14,218, 25,25,25
)
add("ADI-F", "Africa",
"Adindan","Cameroon","CD", -134,-2,210, 25,25,25
)
add("ADI-A", "Africa",
"Adindan","Ethiopia","CD", -165,-11,206, 3,3,3
)
add("ADI-C", "Africa",
"Adindan","Mali","CD", -123,-20,220, 25,25,25
)
add("ADI-D", "Africa",
"Adindan","Senegal","CD", -128,-18,224, 25,25,25
)
add("ADI-B", "Africa",
"Adindan","Sudan","CD", -161,-14,205, 3,5,3
)
add("AFG", "Africa",
"Afgooye","Somalia","KA", -43,-163,45, 25,25,25
)
add("ARF-M", "Africa",
"Arc 1950","mean","CD", -143,-90,-294, 20,33,20
)
add("ARF-A", "Africa",
"Arc 1950","Botswana","CD", -138,-105,-289, 3,5,3
)
add("ARF-H", "Africa",
"Arc 1950","Burundi","CD", -153,-5,-292, 20,20,20
)
add("ARF-B", "Africa",
"Arc 1950","Lesotho","CD", -125,-108,-295, 3,3,8
)
add("ARF-C", "Africa",
"Arc 1950","Malawi","CD", -161,-73,-317, 9,24,8
)
add("ARF-D", "Africa",
"Arc 1950","Swaziland","CD", -134,-105,-295, 15,15,15
)
add("ARF-E", "Africa",
"Arc 1950","Zaire","CD", -169,-19,-278, 25,25,25
)
add("ARF-F", "Africa",
"Arc 1950","Zambia","CD", -147,-74,-283, 21,21,27
)
add("ARF-G", "Africa",
"Arc 1950","Zimbabwe","CD", -142,-96,-293, 5,8,11
)
add("ARS-M", "Africa",
"Arc 1960","mean Kenya & Tanzania","CD",-160,-6,-302, 20,20,20
)
add("ARS-A", "Africa",
"Arc 1960","Kenya","CD", -157,-2,-299, 4,3,3
)
add("ARS-B", "Africa",
"Arc 1960","Tanzania","CD", -175,-23,-303, 6,9,10
)
add("PHA", "Africa",
"Ayabelle Lighthouse","Djibouti","CD", -79,-129,145, 25,25,25
)
add("BID", "Africa",
"Bissau","Guinea-Bissau","IN", -173,253,27, 25,25,25
)
add("CAP", "Africa",
"Cape","South Africa","CD", -136,-108,-292, 3,6,6
)
add("CGE", "Africa",
"Carthage","Tunisia","CD", -263,6,431, 6,9,8
)
add("DAL", "Africa",
"Dabola","Guinea","CD", -83,37,124, 15,15,15
)
add("EUR-F", "Africa",
"European 1950","Egypt","IN", -130,-117,-151, 6,8,8
)
add("EUR-T", "Africa",
"European 1950","Tunisia","IN", -112,-77,-145, 25,25,25
)
add("LEH", "Africa",
"Leigon","Ghana","CD", -130,29,364, 2,3,2
)
add("LIB", "Africa",
"Liberia 1964","Liberia","CD", -90,40,88, 15,15,15
)
add("MAS", "Africa",
"Massawa","Eritrea (Ethiopia)","BR", 639,405,60, 25,25,25
)
add("MER", "Africa",
"Merchich","Morocco","CD", 31,146,47, 5,3,3
)
add("MIN-A", "Africa",
"Minna","Cameroon","CD", -81,-84,115, 25,25,25
)
add("MIN-B", "Africa",
"Minna","Nigeria","CD", -92,-93,122, 3,6,5
)
add("MPO", "Africa",
"M'Poraloko","Gabon","CD", -74,-130,42, 25,25,25
)
add("NSD", "Africa",
"North Sahara 1959","Algeria","CD", -186,-93,310, 25,25,25
)
add("OEG", "Africa",
"Old Egyptian 1907","Egypt","HE", -130,110,-13, 3,6,8
)
add("PTB", "Africa",
"Point 58","mean Burkina Faso & Niger","CD",-106,-129,165, 25,25,25
)
add("PTN", "Africa",
"Pointe Noire 1948","Congo","CD", -148,51,-291, 25,25,25
)
add("SCK", "Africa",
"Schwarzeck","Namibia","BN", 616,97,-251, 20,20,20
)
add("SRL", "Africa",
"Sierra Leone 1960","Sierra Leone","CD", -88,4,101, 15,15,15
)
add("VOR", "Africa",
"Voirol 1960","Algeria","CD", -123,-206,219, 25,25,25
)
# ----------------- ASIA --------------------------------
add("AIN-A", "Asia",
"Ain el Abd 1970","Bahrain","IN", -150,-250,-1, 25,25,25
)
add("AIN-B", "Asia",
"Ain el Abd 1970","Saudi Arabia","IN", -143,-236,7, 10,10,10
)
add("BAT", "Asia",
"Djakarta (Batavia)","Sumatra (Indonesia)","BR",-377,681,-50, 3,3,3
)
add("EUR-H", "Asia",
"European 1950","Iran","IN", -117,-132,-164, 9,12,11
)
add("HKD", "Asia",
"Hong Kong 1963","Hong Kong","IN", -156,-271,-189, 25,25,25
)
add("HTN", "Asia",
"Hu-Tzu-Shan","Taiwan","IN", -637,-549,-203, 15,15,15
)
add("IND-B", "Asia",
"Indian","Bangladesh","EA", 282,726,254, 10,8,12
)
add("IND-I", "Asia",
"Indian","India & Nepal","EC", 295,736,257, 12,10,15
)
add("INF-A", "Asia",
"Indian 1954","Thailand","EA", 217,823,299, 15,6,12
)
add("ING-A", "Asia",
"Indian 1960","Vietnam (near 16N)","EA",198,881,317, 25,25,25
)
add("ING-B", "Asia",
"Indian 1960","Con Son Island (Vietnam)","EA",182,915,344, 25,25,25
)
add("INH-A", "Asia",
"Indian 1975","Thailand","EA", 209,818,290, 12,10,12
)
add("INH-A1", "Asia",
"Indian 1975","Thailand","EA", 210,814,289, 3,2,3
)
add("IDN", "Asia",
"Indonesian 1974","Indonesia","ID", -24,-15,5, 25,25,25
)
add("KAN", "Asia",
"Kandawala","Sri Lanka","EA", -97,787,86, 20,20,20
)
add("KEA", "Asia",
"Kertau 1948","West Malaysia & Singapore","EE",-11,851,5, 10,8,6
)
add("KGS", "Asia",
"Korean Geodetic System 1995","South Korea","WE",0,0,0, 1,1,1
)
add("NAH-A", "Asia",
"Nahrwan","Masirah Island (Oman)","CD", -247,-148,369, 25,25,25
)
add("NAH-B", "Asia",
"Nahrwan","United Arab Emirates","CD", -249,-156,381, 25,25,25
)
add("NAH-C", "Asia",
"Nahrwan","Saudi Arabia","CD", -243,-192,477, 20,20,20
)
add("FAH", "Asia",
"Oman","Oman","CD", -346,-1,224, 3,3,9
)
add("QAT", "Asia",
"Qatar National","Qatar","IN", -128,-283,22, 20,20,20
)
add("SOA", "Asia",
"South Asia","Singapore","FA", 7,-10,-26, 25,25,25
)
add("TIL", "Asia",
"Timbalai 1948","Brunei & East Malaysia (Sarawak & Sabah)","EB",
-679,669,-48, 10,10,12
)
add("TOY-M", "Asia",
"Tokyo","mean","BR", -148,507,685, 20,5,20
)
add("TOY-A", "Asia",
"Tokyo","Japan","BR", -148,507,685, 8,5,8
)
add("TOY-C", "Asia",
"Tokyo","Okinawa","BR", -158,507,676, 20,5,20
)
add("TOY-B", "Asia",
"Tokyo","South Korea","BR", -146,507,687, 8,5,8
)
add("TOY-B1", "Asia",
"Tokyo","South Korea","BR", -147,506,687, 2,2,2
)
# ----------------- AUSTRALIA --------------------------------
add("AUA", "Australia",
"Australian Geodetic 1966","Australia & Tasmania","AN",-133,-48,148, 3,3,3
)
add("AUG", "Australia",
"Australian Geodetic 1984","Australia & Tasmania","AN",-134,-48,149, 2,2,2
)
# ----------------- EUROPE --------------------------------
add("EST", "Europe",
"Co-ordinate System 1937 of Estonia","Estonia","BN",374,150,588, 2,3,3
)
add("EUR-M", "Europe",
"European 1950","mean","IN", -87,-98,-121, 3,8,5
)
add("EUR-A", "Europe",
"European 1950","mean Western Europe","IN",-87,-96,-120, 3,3,3
)
add("EUR-E", "Europe",
"European 1950","Cyprus","IN", -104,-101,-140, 15,15,15
)
add("EUR-G", "Europe",
"European 1950","England & Channel Islands & Scotland & Shetland Islands","IN",
-86,-96,-120, 3,3,3
)
add("EUR-K", "Europe",
"European 1950","England & Ireland & Scotland & Shetland Islands","IN",
-86,-96,-120, 3,3,3
)
add("EUR-B", "Europe",
"European 1950","Greece","IN", -84,-95,-130, 25,25,25
)
add("EUR-I", "Europe",
"European 1950","Sardinia (Italy)","IN",-97,-103,-120, 25,25,25
)
add("EUR-J", "Europe",
"European 1950","Sicily (Italy)","IN", -97,-88,-135, 20,20,20
)
add("EUR-L", "Europe",
"European 1950","Malta","IN", -107,-88,-149, 25,25,25
)
add("EUR-C", "Europe",
"European 1950","Norway & Finland","IN",-87,-95,-120, 3,5,3
)
add("EUR-D", "Europe",
"European 1950","Portugal & Spain","IN",-84,-107,-120, 5,6,3
)
add("EUS", "Europe",
"European 1979","mean","IN", -86,-98,-119, 3,3,3
)
add("HJO", "Europe",
"Hjorsey 1955","Iceland","IN", -73,46,-86, 3,3,6
)
add("IRL", "Europe",
"Ireland 1965","Ireland","AM", 506,-122,611, 3,3,3
)
add("OGB-M", "Europe",
"Ordnance Survey Great Britain 1936","mean","AA",375,-111,431, 10,10,15
)
add("OGB-A", "Europe",
"Ordnance Survey Great Britain 1936","England","AA",371,-112,434, 5,5,6
)
add("OGB-B", "Europe",
"Ordnance Survey Great Britain 1936","England & Isle of Man & Wales","AA",
371,-111,434, 10,10,15
)
add("OGB-C", "Europe",
"Ordnance Survey Great Britain 1936","Scotland & Shetland Islands","AA",
384,-111,425, 10,10,10
)
add("OGB-D", "Europe",
"Ordnance Survey Great Britain 1936","Wales","AA",370,-108,434, 20,20,20
)
add("MOD", "Europe",
"Rome 1940","Sardinia","IN", -225,-65,9, 25,25,25
)
add("SPK-A", "Europe",
"S-42 (Pulkovo 1942)","Hungary","KA", 28,-121,-77, 2,2,2
)
add("SPK-B", "Europe",
"S-42 (Pulkovo 1942)","Poland","KA", 23,-124,-82, 4,2,4
)
add("SPK-C", "Europe",
"S-42 (Pulkovo 1942)","Czechoslavakia","KA",26,-121,-78, 3,3,2
)
add("SPK-D", "Europe",
"S-42 (Pulkovo 1942)","Latvia","KA", 24,-124,-82, 2,2,2
)
add("SPK-E", "Europe",
"S-42 (Pulkovo 1942)","Kazakhstan","KA",15,-130,-84, 25,25,25
)
add("SPK-F", "Europe",
"S-42 (Pulkovo 1942)","Albania","KA", 24,-130,-92, 3,3,3
)
add("SPK-G", "Europe",
"S-42 (Pulkovo 1942)","Romania","KA", 28,-121,-77, 3,5,3
)
add("CCD", "Europe",
"S-JTSK","Czechoslavakia (Prior 1 Jan 1993)","BR",589,76,480, 4,2,3
)
# ----------------- NORTH AMERICA --------------------------------
add("CAC", "North America",
"Cape Canaveral","mean Bahamas & Florida","CC",-2,151,181, 3,3,3
)
gdt_datum_ptab["NAD27"] :=
add("NAS-C", "North America",
"North American 1927","mean CONUS","CC",-8,160,176, 5,5,6
)
add("NAS-B", "North America",
"North American 1927","mean West CONUS","CC",-8,159,175, 5,3,3
)
add("NAS-A", "North America",
"North American 1927","mean East CONUS","CC",-9,161,179, 5,5,8
)
add("NAS-D", "North America",
"North American 1927","Alaska (minus Aleutian Islands)","CC",
-5,135,172, 5,9,5
)
add("NAS-V", "North America",
"North American 1927","Aleutian Islands East of 180W","CC",
-2,152,149, 6,8,10
)
add("NAS-W", "North America",
"North American 1927","Aleutian Islands West of 180W","CC",
2,204,105, 10,10,10
)
add("NAS-Q", "North America",
"North American 1927","Bahamas (minus San Salvador Island)","CC",
-4,154,178, 5,3,5
)
add("NAS-R", "North America",
"North American 1927","San Salvador Island","CC",1,140,165, 25,25,25
)
add("NAS-E", "North America",
"North American 1927","mean Canada","CC",-10,158,187, 15,11,6
)
add("NAS-F", "North America",
"North American 1927","Albert & British Columbia (Canada)","CC",
-7,162,188, 8,8,6
)
add("NAS-G", "North America",
"North American 1927","Eastern Canada","CC",-22,160,190, 6,6,3
)
add("NAS-H", "North America",
"North American 1927","Manitoba & Ontario (Canada)","CC",-9,157,184, 9,5,5
)
add("NAS-I", "North America",
"North American 1927","Northwest Territories & Saskatchewan (Canada)","CC",
4,159,188, 5,5,3
)
add("NAS-J", "North America",
"North American 1927","Yukon (Canada)","CC",-7,139,181, 5,8,3
)
add("NAS-O", "North America",
"North American 1927","Canal Zone","CC",0,125,201, 20,20,20
)
add("NAS-P", "North America",
"North American 1927","mean Caribbean","CC",-3,142,183, 3,9,12
)
add("NAS-N", "North America",
"North American 1927","mean Central America","CC",0,125,194, 8,3,5
)
add("NAS-T", "North America",
"North American 1927","Cuba","CC", -9,152,178, 25,25,25
)
add("NAS-U", "North America",
"North American 1927","Greenland (Hayes Peninsula)","CC",11,114,195, 25,25,25
)
add("NAS-L", "North America",
"North American 1927","Mexico","CC", -12,130,190, 8,6,6
)
add("NAR-A", "North America",
"North American 1983","Alaska (minus Aleutian Islands)","RF",0,0,0, 2,2,2
)
add("NAR-E", "North America",
"North American 1983","Aleutian Islands","RF",-2,0,4, 5,2,5
)
add("NAR-B", "North America",
"North American 1983","Canada","RF", 0,0,0, 2,2,2
)
gdt_datum_ptab["NAD83"] :=
add("NAR-C", "North America",
"North American 1983","CONUS","RF", 0,0,0, 2,2,2
)
add("NAR-H", "North America",
"North American 1983","Hawaii","RF", 1,1,-1, 2,2,2
)
add("NAR-D", "North America",
"North American 1983","Mexico & Central America","RF",0,0,0, 2,2,2
)
# ----------------- SOUTH AMERICA --------------------------------
add("BOO", "South America",
"Bogota Observatory","Colombia","IN", 307,304,-318, 6,5,6
)
add("CAI", "South America",
"Campo Inchauspe 1969","Argentina","IN",-148,136,90, 5,5,5
)
add("CHU", "South America",
"Chua Astro","Paraguay","IN", -134,229,-29, 6,9,5
)
add("COA", "South America",
"Corrego Alegre","Brazil","IN", -206,172,-6, 5,3,5
)
add("PRP-M", "South America",
"Provisional South American 1956","mean","IN",-288,175,-376, 17,27,27
)
add("PRP-A", "South America",
"Provisional South American 1956","Bolivia","IN",-270,188,-388, 5,11,14
)
add("PRP-B", "South America",
"Provisional South American 1956","Northern Chile","IN",
-270,183,-390, 25,25,25
)
add("PRP-C", "South America",
"Provisional South American 1956","Southern Chile","IN",
-305,243,-442, 20,20,20
)
add("PRP-D", "South America",
"Provisional South American 1956","Colombia","IN",-282,169,-371, 15,15,15
)
add("PRP-E", "South America",
"Provisional South American 1956","Ecuador","IN",-278,171,-367, 3,5,3
)
add("PRP-F", "South America",
"Provisional South American 1956","Guyana","IN",-298,159,-369, 6,14,5
)
add("PRP-G", "South America",
"Provisional South American 1956","Peru","IN",-279,175,-379, 6,8,12
)
add("PRP-H", "South America",
"Provisional South American 1956","Venezuela","IN",-295,173,-371, 9,14,15
)
add("HIT", "South America",
"Provisional South Chilean 1963","Southern Chile","IN",16,196,93, 25,25,25
)
add("SAN-M", "South America",
"South American 1969","mean","SA", -57,1,-41, 15,6,9
)
add("SAN-A", "South America",
"South American 1969","Argentina","SA", -62,-1,-37, 5,5,5
)
add("SAN-B", "South America",
"South American 1969","Bolivia","SA", -61,2,-48, 15,15,15
)
add("SAN-C", "South America",
"South American 1969","Brazil","SA", -60,-2,-41, 3,5,5
)
add("SAN-D", "South America",
"South American 1969","Chile","SA", -75,-1,-44, 15,8,11
)
add("SAN-E", "South America",
"South American 1969","Colombia","SA", -44,6,-36, 6,6,5
)
add("SAN-F", "South America",
"South American 1969","Ecuador (minus Galapagos Islands)","SA",
-48,3,-44, 3,3,3
)
add("SAN-J", "South America",
"South American 1969","Baltra & Galapagos Islands (Ecuador)","SA",
-47,26,-42, 25,25,25
)
add("SAN-G", "South America",
"South American 1969","Guyana","SA", -53,3,-47, 9,5,5
)
add("SAN-H", "South America",
"South American 1969","Paraguay","SA", -61,2,-33, 15,15,15
)
add("SAN-I", "South America",
"South American 1969","Peru","SA", -58,0,-44, 5,5,5
)
add("SAN-K", "South America",
"South American 1969","Trinidad & Tobago","SA",-45,12,-33, 25,25,25
)
add("SAN-L", "South America",
"South American 1969","Venezuela","SA", -45,8,-33, 3,6,3
)
add("SIR", "South America",
"South American Geocentric Reference System (SIRGAS)","South America","RF",
0,0,0, 1,1,1
)
add("ZAN", "South America",
"Zanderij","Suriname","IN", -265,120,-358, 5,5,8
)
# ----------------- ATLANTIC OCEAN --------------------------------
add("AIA", "Atlantic Ocean",
"Antigua Island Astro 1943","Antigua & Leeward Islands","CD",
-270,13,62, 25,25,25
)
add("ASC", "Atlantic Ocean",
"Ascension Island 1958","Ascension Island","IN",-205,107,53, 25,25,25
)
add("SHB", "Atlantic Ocean",
"Astro DOS 71/4","St Helena Island","IN",-320,550,-494, 25,25,25
)
add("BER", "Atlantic Ocean",
"Bermuda 1957","Bermuda","CC", -73,213,296, 20,20,20
)
add("DID", "Atlantic Ocean",
"Deception Island","Deception Island & Antarctica","CD",260,12,-147, 20,20,20
)
add("FOT", "Atlantic Ocean",
"Fort Thomas 1955","Nevis & St. Kitts & Leeward Islands","CD",
-7,215,225, 25,25,25
)
add("GRA", "Atlantic Ocean",
"Graciosa Base SW 1948",
"Faial & Graciosa & Pico & Sao Jorge & Terceira Islands (Azores)","IN",
-104,167,-38, 3,3,3
)
add("ISG", "Atlantic Ocean",
"ISTS 061 Astro 1968","South Georgia Island","IN",-794,119,-298, 25,25,25
)
add("LCF", "Atlantic Ocean",
"L. C. 5 Astro 1961","Cayman Brac Island","CC",42,124,147, 25,25,25
)
add("ASM", "Atlantic Ocean",
"Montserrat Island Astro 1958","Montserrat & Leeward Islands","CD",
174,359,365, 25,25,25
)
add("NAP", "Atlantic Ocean",
"Naparima BWI","Trinidad & Tobago","IN",-10,375,165, 15,15,15
)
add("FLO", "Atlantic Ocean",
"Observatorio Meteorologico 1939","Corvo & Flores Islands (Azores)","IN",
-425,-169,81, 20,20,20
)
add("PLN", "Atlantic Ocean",
"Pico de las Nieves","Canary Islands","IN",-307,-92,127, 25,25,25
)
add("POS", "Atlantic Ocean",
"Porto Santo 1936","Porto Santo & Madeira Islands","IN",-499,-249,314, 25,25,25
)
add("PUR", "Atlantic Ocean",
"Puerto Rico","Puerto Rico & Virgin Islands","CC",11,72,-101, 3,3,3
)
add("QUO", "Atlantic Ocean",
"Qornoq","South Greenland","IN", 164,138,-189, 25,25,32
)
add("SAO", "Atlantic Ocean",
"Sao Braz","Sao Miguel & Santa Maria Islands","IN",-203,141,53, 25,25,25
)
add("SAP", "Atlantic Ocean",
"Sapper Hill 1943","East Falkland Island","IN",-355,21,72, 1,1,1
)
add("SGM", "Atlantic Ocean",
"Selvagem Grande 1938","Salvage Islands","IN",-289,-124,60, 25,25,25
)
add("TDC", "Atlantic Ocean",
"Tristan Astro 1968","Tristan da Cunha","IN",-632,438,-609, 25,25,25
)
# ----------------- INDIAN OCEAN --------------------------------
add("ANO", "Indian Ocean",
"Anna 1 Astro 1965","Cocos Islands","AN",-491,-22,435, 25,25,25
)
add("GAA", "Indian Ocean",
"Gan 1970","Republic of Maldives","IN", -133,-321,50, 25,25,25
)
add("IST", "Indian Ocean",
"ISTS 073 Astro 1969","Diego Garcia","IN",208,-435,-229, 25,25,25
)
add("KEG", "Indian Ocean",
"Kerguelen Island 1949","Kerguelen Island","IN",145,-187,103, 25,25,25
)
add("MIK", "Indian Ocean",
"Mahe 1971","Mahe Island","CD", 41,-220,-134, 25,25,25
)
add("REU", "Indian Ocean",
"Reunion","Mascarene Islands","IN", 94,-948,-1262, 25,25,25
)
# ----------------- PACIFIC OCEAN --------------------------------
add("AMA", "Pacific Ocean",
"American Samoa 1962","American Samoa Islands","CC",-115,118,426, 25,25,25
)
add("ATF", "Pacific Ocean",
"Astro Beacon E 1945","Iwo Jima","IN", 145,75,-272, 25,25,25
)
add("TRN", "Pacific Ocean",
"Astro Tern Island (FRIG) 1961","Tern Island","IN",114,-116,-333, 25,25,25
)
add("ASQ", "Pacific Ocean",
"Astronomical Station 1952","Marcus Island","IN",124,-234,-25, 25,25,25
)
add("IBE", "Pacific Ocean",
"Bellevue (IGN)","Efate & Erromango Islands","IN",-127,-769,472, 20,20,20
)
add("CAO", "Pacific Ocean",
"Canton Astro 1966","Phoenix Islands","IN",298,-304,-375, 15,15,15
)
add("CHI", "Pacific Ocean",
"Chatham Island Astro 1971","Chatham Island (New Zealand)","IN",
175,-38,113, 15,15,15
)
add("GIZ", "Pacific Ocean",
"DOS 1968","Gizo Island (New Georgia Islands)","IN",230,-199,-752, 25,25,25
)
add("EAS", "Pacific Ocean",
"Easter Island 1967","Easter Island","IN",211,147,111, 25,25,25
)
add("GEO", "Pacific Ocean",
"Geodetic Datum 1949","New Zealand","IN",84,-22,209, 5,3,5
)
add("GUA", "Pacific Ocean",
"Guam 1963","Guam","CC", -100,-248,259, 3,3,3
)
add("DOB", "Pacific Ocean",
"GUX 1 Astro","Guadalcanal Island","IN",252,-209,-751, 25,25,25
)
add("JOH", "Pacific Ocean",
"Johnston Island 1961","Johnston Island","IN",189,-79,-202, 25,25,25
)
add("KUS", "Pacific Ocean",
"Kusaie Astro 1951","Caroline Islands & Fed. States of Micronesia","IN",
647,1777,-1124, 25,25,25
)
add("LUZ-A", "Pacific Ocean",
"Luzon","Philippines (minus Mindanao Island)","CC",-133,-77,-51, 8,11,9
)
add("LUZ-B", "Pacific Ocean",
"Luzon","Mindanao Island (Philippines)","CC",-133,-79,-72, 25,25,25
)
add("MID", "Pacific Ocean",
"Midway Astro 1961","Midway Islands","IN",912,-58,1227, 25,25,25
)
add("OHA-M", "Pacific Ocean",
"Old Hawaiian","mean","CC", 61,-285,-181, 25,20,20
)
add("OHA-A", "Pacific Ocean",
"Old Hawaiian","Hawaii","CC", 89,-279,-183, 25,25,25
)
add("OHA-B", "Pacific Ocean",
"Old Hawaiian","Kauai","CC", 45,-290,-172, 20,20,20
)
add("OHA-C", "Pacific Ocean",
"Old Hawaiian","Maui","CC", 65,-290,-190, 25,25,25
)
add("OHA-D", "Pacific Ocean",
"Old Hawaiian","Oahu","CC", 58,-283,-182, 10,6,6
)
add("OHI-M", "Pacific Ocean",
"Old Hawaiian Int","mean","IN", 201,-228,-346, 25,20,20
)
add("OHI-A", "Pacific Ocean",
"Old Hawaiian Int","Hawaii","IN", 229,-222,-348, 25,25,25
)
add("OHI-B", "Pacific Ocean",
"Old Hawaiian Int","Kauai","IN", 185,-233,-337, 20,20,20
)
add("OHI-C", "Pacific Ocean",
"Old Hawaiian Int","Maui","IN", 205,-233,-355, 25,25,25
)
add("OHI-D", "Pacific Ocean",
"Old Hawaiian Int","Oahu","IN", 198,-226,-347, 10,6,6
)
add("PIT", "Pacific Ocean",
"Pitcairn Astro 1967","Pitcairn Island","IN",185,165,42, 25,25,25
)
add("SAE", "Pacific Ocean",
"Santo (DOS) 1965","Espirito Santo Island","IN",170,42,84, 25,25,25
)
add("MVS", "Pacific Ocean",
"Viti Levu 1916","Viti Levu Island (Fiji Islands)","CD",51,391,-36, 25,25,25
)
add("ENW", "Pacific Ocean",
"Wake-Eniwetok 1960","Marshall Islands","HO",102,52,-38, 3,3,3
)
add("WAK", "Pacific Ocean",
"Wake Island Astro 1952","Wake Atoll","IN",276,-57,149, 25,25,25
)
# ----------------- WORLD-WIDE DATUM ----------------------------
gdt_datum_ptab["WGS66"] :=
add("W66", "World-wide Datum",
"WGS 1966","Global Definition I","WB", 0,0,0, 0,0,0
)
gdt_datum_ptab["WGS72"] :=
add("W72", "World-wide Datum",
"WGS 1972","Global Definition I","WD", 0,0,0, 3,3,3
)
gdt_datum_ptab["WGS84"] :=
add("W84", "World-wide Datum",
"WGS 1984","Global Definition II","WE", 0,0,0, 0,0,0
)
# ----------------- MISC. NON-SATELLITE DERIVED ----------------------------
# Error bounds of zero mean unknown error.
add("BUR", "Misc. Non-satellite derived",
"Bukit Rimpah","Bangka & Belitung Islands (Indonesia)","BR",-384,664,-48, 0,0,0
)
add("CAZ", "Misc. Non-satellite derived",
"Camp Area Astro","Camp McMurdo Area (Antarctica)","IN",-104,-129,239, 0,0,0
)
add("EUR-S", "Misc. Non-satellite derived",
"European 1950","mean Near East","IN", -103,-106,-141, 0,0,0
)
add("GSE", "Misc. Non-satellite derived",
"Gunung Segara","Kalimantan (Indonesia)","BR",-403,684,41, 0,0,0
)
add("HEN", "Misc. Non-satellite derived",
"Herat North","Afghanistan","IN", -333,-222,114, 0,0,0
)
add("HER", "Misc. Non-satellite derived",
"Hermannskogel",
"Yugoslavia (Prior to 1990) Slovenia & Croatia & Bosnia & Herzegovina & Serbia",
"BN", 682,-203,480, 0,0,0
)
add("IND-P", "Misc. Non-satellite derived",
"Indian","Pakistan","EF", 283,682,231, 0,0,0
)
add("PUK", "Misc. Non-satellite derived",
"Pulkovo 1942","Russia","KA", 28,-130,-95, 0,0,0
)
add("TAN", "Misc. Non-satellite derived",
"Tananarive Observatory 1925","Madagascar","IN",-189,-242,-91, 0,0,0
)
add("VOI", "Misc. Non-satellite derived",
"Voirol 1874","Tunisia & Algeria","CD", -73,-247,227,0,0,0
)
add("YAC", "Misc. Non-satellite derived",
"Yacare","Uruguay","IN", -155,171,37, 0,0,0
)
return
end
This page produced by UniDoc on 2021/04/15 @ 23:59:44.