forked from JuliaAstro/SkyCoords.jl
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathtypes.jl
More file actions
134 lines (107 loc) · 6.13 KB
/
types.jl
File metadata and controls
134 lines (107 loc) · 6.13 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
# -----------------------------------------------------------------------------
# Types
"""
The supertype for all sky coordinate systems.
"""
abstract type AbstractSkyCoords end
"""
ICRSCoords(ra, dec)
[International Celestial Reference System](https://en.wikipedia.org/wiki/International_Celestial_Reference_System)
This is the current standard adopted by the International Astronomical Union notably due to its high level of accuracy compared to standard equatorial coordinate systems. What sets this apart from [`FK5Coords`](@ref) is that it is completely defined using extragalactic radio sources rather than a geocentric frame, which means the reference frame will not change due to Earth's motion.
# Coordinates
- `ra` - Right ascension in radians (0, 2π)
- `dec` - Declination in radians (-π/2, π/2)
"""
struct ICRSCoords{T<:Real} <: AbstractSkyCoords
ra::T
dec::T
ICRSCoords{T}(ra, dec) where {T<:Real} = new(mod2pi(ra), dec)
end
ICRSCoords(ra::T, dec::T) where {T<:Real} = ICRSCoords{float(T)}(ra, dec)
ICRSCoords(ra::Real, dec::Real) = ICRSCoords(promote(ra, dec)...)
ICRSCoords(c::T) where {T<:AbstractSkyCoords} = convert(ICRSCoords, c)
ICRSCoords{F}(c::T) where {F,T<:AbstractSkyCoords} = convert(ICRSCoords{F}, c)
"""
GalCoords(l, b)
[Galactic Coordinate System](https://en.wikipedia.org/wiki/Galactic_coordinate_system)
This coordinate system is defined based on the projection of the Milky Way galaxy onto our celestial sphere, with (0, 0) being approximately the center of our galaxy.
# Coordinates
- `l` - Galactic longitude in radians (-π, π)
- `b` - Galactic latitude in radians (-π/2, π/2)
"""
struct GalCoords{T<:Real} <: AbstractSkyCoords
l::T
b::T
GalCoords{T}(l, b) where {T<:Real} = new(mod2pi(l), b)
end
GalCoords(l::T, b::T) where {T<:Real} = GalCoords{float(T)}(l, b)
GalCoords(l::Real, b::Real) = GalCoords(promote(l, b)...)
GalCoords(c::T) where {T<:AbstractSkyCoords} = convert(GalCoords, c)
GalCoords{F}(c::T) where {F,T<:AbstractSkyCoords} = convert(GalCoords{F}, c)
"""
SuperGalCoords(l, b)
[Supergalactic Coordinate System](https://en.wikipedia.org/wiki/Supergalactic_coordinate_system)
The supergalactic plane is part of a reference frame for the supercluster of galaxies that contains the Milky Way galaxy.
The supergalactic plane as so-far observed is more or less perpendicular to the plane of the Milky Way, the angle is 84.5 degrees. Viewed from the Earth, the plane traces a great circle across the sky through the constellations
# Coordinates
- `l` - SuperGalCoords longitude in radians (-π, π)
- `b` - SuperGalCoords latitude in radians (-π/2, π/2)
"""
struct SuperGalCoords{T<:Real} <: AbstractSkyCoords
l::T
b::T
SuperGalCoords{T}(l, b) where {T<:Real} = new(mod2pi(l), b)
end
SuperGalCoords(l::T, b::T) where {T<:Real} = SuperGalCoords{float(T)}(l, b)
SuperGalCoords(l::Real, b::Real) = SuperGalCoords(promote(l, b)...)
SuperGalCoords(c::T) where {T<:AbstractSkyCoords} = convert(SuperGalCoords, c)
SuperGalCoords{F}(c::T) where {F,T<:AbstractSkyCoords} = convert(SuperGalCoords{F}, c)
"""
FK5Coords{equinox}(ra, dec)
[Equatorial Coordinate System](https://en.wikipedia.org/wiki/Equatorial_coordinate_system)
This coordinate system maps the celestial sphere based on a geocentric observer. Historically the oldest, this coordinate system has been shown to be inaccurate due to its definitions based on the Earth, which has long-scale precession causing the reference frame to change. Because of this, an equinox must be provided (typically 2000, commonly known as J2000) which defines the reference frame.
# Coordinates
- `ra` - Right ascension in radians (0, 2π)
- `dec` - Declination in radians (-π/2, π/2)
"""
struct FK5Coords{e,T<:Real} <: AbstractSkyCoords
ra::T
dec::T
FK5Coords{e,T}(ra, dec) where {T<:Real,e} = new(mod2pi(ra), dec)
end
FK5Coords{e}(ra::T, dec::T) where {e,T<:Real} = FK5Coords{e,float(T)}(ra, dec)
FK5Coords{e}(ra::Real, dec::Real) where {e} = FK5Coords{e}(promote(ra, dec)...)
FK5Coords{e}(c::T) where {e,T<:AbstractSkyCoords} = convert(FK5Coords{e}, c)
FK5Coords{e,F}(c::T) where {e,F,T<:AbstractSkyCoords} = convert(FK5Coords{e,F}, c)
constructorof(::Type{<:FK5Coords{e}}) where {e} = FK5Coords{e}
"""
EclipticCoords{equinox}(lon, lat)
[Ecliptic Coordinate System](https://en.wikipedia.org/wiki/Ecliptic_coordinate_system)
This coordinate system is geocentric with the ecliptic plane as the xy-plane with x oriented according to the equinox specified by `equinox`.
# Coordinates
- `lon` - Longitude in radians (0, 2π)
- `lat` - Latitude in radians (-π/2, π/2)
"""
struct EclipticCoords{e,T<:Real} <: AbstractSkyCoords
lon::T
lat::T
EclipticCoords{e,T}(lon, lat) where {e,T<:Real} = new(mod2pi(lon), lat)
end
EclipticCoords{e}(lon::T, lat::T) where {e,T<:Real} = EclipticCoords{e,float(T)}(lon, lat)
EclipticCoords{e}(lon::Real, lat::Real) where {e} = EclipticCoords{e}(promote(lon, lat)...)
EclipticCoords{e}(c::AbstractSkyCoords) where {e} = convert(EclipticCoords{e}, c)
EclipticCoords{e,F}(c::AbstractSkyCoords) where {e,F} = convert(EclipticCoords{e,F}, c)
constructorof(::Type{<:EclipticCoords{e}}) where {e} = EclipticCoords{e}
# Scalar coordinate conversions
Base.convert(::Type{T}, c::T) where {T<:AbstractSkyCoords} = c
function Base.convert(::Type{T}, c::S) where {T<:AbstractSkyCoords,S<:AbstractSkyCoords}
r = rotmat(T, S) * coords2cart(c)
lon, lat = cart2coords(r)
T(lon, lat)
end
Base.:(==)(a::T, b::T) where {T<:AbstractSkyCoords} = lon(a) == lon(b) && lat(a) == lat(b)
Base.isapprox(a::ICRSCoords, b::ICRSCoords; kwargs...) = isapprox(SVector(lon(a), lat(a)), SVector(lon(b), lat(b)); kwargs...)
Base.isapprox(a::GalCoords, b::GalCoords; kwargs...) = isapprox(SVector(lon(a), lat(a)), SVector(lon(b), lat(b)); kwargs...)
Base.isapprox(a::SuperGalCoords, b::SuperGalCoords; kwargs...) = isapprox(SVector(lon(a), lat(a)), SVector(lon(b), lat(b)); kwargs...)
Base.isapprox(a::FK5Coords{e}, b::FK5Coords{e}; kwargs...) where {e} = isapprox(SVector(lon(a), lat(a)), SVector(lon(b), lat(b)); kwargs...)
Base.isapprox(a::EclipticCoords{e}, b::EclipticCoords{e}; kwargs...) where {e} = isapprox(SVector(lon(a), lat(a)), SVector(lon(b), lat(b)); kwargs...)