module Data.Astro.Moon
(
moonPosition1
, moonPosition2
, moonDistance1
, moonAngularSize
, moonHorizontalParallax
, moonPhase
, moonBrightLimbPositionAngle
)
where
import qualified Data.Astro.Utils as U
import Data.Astro.Types (DecimalDegrees(..), GeographicCoordinates, toRadians, fromRadians, kmToAU)
import Data.Astro.Time.JulianDate (JulianDate(..), numberOfDays)
import Data.Astro.Coordinate (EquatorialCoordinates1(..), EclipticCoordinates(..), eclipticToEquatorial)
import Data.Astro.Planet (planetBrightLimbPositionAngle)
import Data.Astro.Sun (sunDetails, sunMeanAnomaly2, sunEclipticLongitude2)
import Data.Astro.Moon.MoonDetails (MoonDetails(..), MoonDistanceUnits(..), j2010MoonDetails, mduToKm)
import Data.Astro.Effects (parallax)
reduceDegrees :: DecimalDegrees -> DecimalDegrees
reduceDegrees :: DecimalDegrees -> DecimalDegrees
reduceDegrees = DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. RealFrac a => a -> a -> a
U.reduceToZeroRange DecimalDegrees
360
moonPosition1 :: MoonDetails -> JulianDate -> EquatorialCoordinates1
moonPosition1 :: MoonDetails -> JulianDate -> EquatorialCoordinates1
moonPosition1 MoonDetails
md JulianDate
ut =
let sd :: SunDetails
sd = JulianDate -> SunDetails
sunDetails JulianDate
ut
lambdaS :: DecimalDegrees
lambdaS = SunDetails -> DecimalDegrees
sunEclipticLongitude2 SunDetails
sd
ms :: DecimalDegrees
ms = SunDetails -> DecimalDegrees
sunMeanAnomaly2 SunDetails
sd
mmq :: MoonQuantities
mmq = MoonDetails -> JulianDate -> MoonQuantities
meanMoonQuantities MoonDetails
md JulianDate
ut
MQ DecimalDegrees
lm'' DecimalDegrees
_ DecimalDegrees
nm' = DecimalDegrees
-> DecimalDegrees -> MoonQuantities -> MoonQuantities
correctedMoonQuantities DecimalDegrees
lambdaS DecimalDegrees
ms MoonQuantities
mmq
a :: Double
a = DecimalDegrees -> Double
toRadians (DecimalDegrees -> Double) -> DecimalDegrees -> Double
forall a b. (a -> b) -> a -> b
$ DecimalDegrees
lm''DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
-DecimalDegrees
nm'
i :: Double
i = DecimalDegrees -> Double
toRadians (DecimalDegrees -> Double) -> DecimalDegrees -> Double
forall a b. (a -> b) -> a -> b
$ MoonDetails -> DecimalDegrees
mdI MoonDetails
md
y :: Double
y = (Double -> Double
forall a. Floating a => a -> a
sin Double
a) Double -> Double -> Double
forall a. Num a => a -> a -> a
* (Double -> Double
forall a. Floating a => a -> a
cos Double
i)
x :: Double
x = Double -> Double
forall a. Floating a => a -> a
cos Double
a
at :: DecimalDegrees
at = DecimalDegrees -> DecimalDegrees
reduceDegrees (DecimalDegrees -> DecimalDegrees)
-> DecimalDegrees -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ Double -> DecimalDegrees
fromRadians (Double -> DecimalDegrees) -> Double -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ Double -> Double -> Double
forall a. RealFloat a => a -> a -> a
atan2 Double
y Double
x
lambdaM :: DecimalDegrees
lambdaM = DecimalDegrees
at DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
+ DecimalDegrees
nm'
betaM :: DecimalDegrees
betaM = Double -> DecimalDegrees
fromRadians (Double -> DecimalDegrees) -> Double -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ Double -> Double
forall a. Floating a => a -> a
asin (Double -> Double) -> Double -> Double
forall a b. (a -> b) -> a -> b
$ (Double -> Double
forall a. Floating a => a -> a
sin Double
a) Double -> Double -> Double
forall a. Num a => a -> a -> a
* (Double -> Double
forall a. Floating a => a -> a
sin Double
i)
in EclipticCoordinates -> JulianDate -> EquatorialCoordinates1
eclipticToEquatorial (DecimalDegrees -> DecimalDegrees -> EclipticCoordinates
EcC DecimalDegrees
betaM DecimalDegrees
lambdaM) JulianDate
ut
moonPosition2 :: MoonDetails -> MoonDistanceUnits -> GeographicCoordinates -> Double -> JulianDate -> EquatorialCoordinates1
moonPosition2 :: MoonDetails
-> MoonDistanceUnits
-> GeographicCoordinates
-> Double
-> JulianDate
-> EquatorialCoordinates1
moonPosition2 MoonDetails
md MoonDistanceUnits
distance GeographicCoordinates
coords Double
height JulianDate
jd =
let p :: EquatorialCoordinates1
p = MoonDetails -> JulianDate -> EquatorialCoordinates1
moonPosition1 MoonDetails
md JulianDate
jd
in GeographicCoordinates
-> Double
-> AstronomicalUnits
-> JulianDate
-> EquatorialCoordinates1
-> EquatorialCoordinates1
parallax GeographicCoordinates
coords Double
height (Double -> AstronomicalUnits
kmToAU (Double -> AstronomicalUnits) -> Double -> AstronomicalUnits
forall a b. (a -> b) -> a -> b
$ MoonDistanceUnits -> Double
mduToKm MoonDistanceUnits
distance) JulianDate
jd EquatorialCoordinates1
p
moonDistance1 :: MoonDetails -> JulianDate -> MoonDistanceUnits
moonDistance1 :: MoonDetails -> JulianDate -> MoonDistanceUnits
moonDistance1 MoonDetails
md JulianDate
ut =
let sd :: SunDetails
sd = JulianDate -> SunDetails
sunDetails JulianDate
ut
lambdaS :: DecimalDegrees
lambdaS = SunDetails -> DecimalDegrees
sunEclipticLongitude2 SunDetails
sd
ms :: DecimalDegrees
ms = SunDetails -> DecimalDegrees
sunMeanAnomaly2 SunDetails
sd
mmq :: MoonQuantities
mmq = MoonDetails -> JulianDate -> MoonQuantities
meanMoonQuantities MoonDetails
md JulianDate
ut
cmq :: MoonQuantities
cmq = DecimalDegrees
-> DecimalDegrees -> MoonQuantities -> MoonQuantities
correctedMoonQuantities DecimalDegrees
lambdaS DecimalDegrees
ms MoonQuantities
mmq
mm' :: Double
mm' = DecimalDegrees -> Double
toRadians (DecimalDegrees -> Double) -> DecimalDegrees -> Double
forall a b. (a -> b) -> a -> b
$ MoonQuantities -> DecimalDegrees
mqAnomaly MoonQuantities
cmq
ec :: Double
ec = DecimalDegrees -> Double
toRadians (DecimalDegrees -> Double) -> DecimalDegrees -> Double
forall a b. (a -> b) -> a -> b
$ Double -> DecimalDegrees
centreEquation Double
mm'
e :: Double
e = MoonDetails -> Double
mdE MoonDetails
md
in Double -> MoonDistanceUnits
MDU (Double -> MoonDistanceUnits) -> Double -> MoonDistanceUnits
forall a b. (a -> b) -> a -> b
$ (Double
1 Double -> Double -> Double
forall a. Num a => a -> a -> a
- Double
eDouble -> Double -> Double
forall a. Num a => a -> a -> a
*Double
e)Double -> Double -> Double
forall a. Fractional a => a -> a -> a
/(Double
1Double -> Double -> Double
forall a. Num a => a -> a -> a
+Double
eDouble -> Double -> Double
forall a. Num a => a -> a -> a
*(Double -> Double
forall a. Floating a => a -> a
cos(Double
mm'Double -> Double -> Double
forall a. Num a => a -> a -> a
+Double
ec)))
moonAngularSize :: MoonDistanceUnits -> DecimalDegrees
moonAngularSize :: MoonDistanceUnits -> DecimalDegrees
moonAngularSize (MDU Double
p) = (MoonDetails -> DecimalDegrees
mdBigTheta MoonDetails
j2010MoonDetails) DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Fractional a => a -> a -> a
/ (Double -> DecimalDegrees
DD Double
p)
moonHorizontalParallax :: MoonDistanceUnits -> DecimalDegrees
moonHorizontalParallax :: MoonDistanceUnits -> DecimalDegrees
moonHorizontalParallax (MDU Double
p) = (MoonDetails -> DecimalDegrees
mdPi MoonDetails
j2010MoonDetails) DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Fractional a => a -> a -> a
/ (Double -> DecimalDegrees
DD Double
p)
moonPhase :: MoonDetails -> JulianDate -> Double
moonPhase :: MoonDetails -> JulianDate -> Double
moonPhase MoonDetails
md JulianDate
ut =
let sd :: SunDetails
sd = JulianDate -> SunDetails
sunDetails JulianDate
ut
lambdaS :: DecimalDegrees
lambdaS = SunDetails -> DecimalDegrees
sunEclipticLongitude2 SunDetails
sd
ms :: DecimalDegrees
ms = SunDetails -> DecimalDegrees
sunMeanAnomaly2 SunDetails
sd
mmq :: MoonQuantities
mmq = MoonDetails -> JulianDate -> MoonQuantities
meanMoonQuantities MoonDetails
md JulianDate
ut
MQ DecimalDegrees
ml DecimalDegrees
_ DecimalDegrees
_ = DecimalDegrees
-> DecimalDegrees -> MoonQuantities -> MoonQuantities
correctedMoonQuantities DecimalDegrees
lambdaS DecimalDegrees
ms MoonQuantities
mmq
d :: Double
d = DecimalDegrees -> Double
toRadians (DecimalDegrees -> Double) -> DecimalDegrees -> Double
forall a b. (a -> b) -> a -> b
$ DecimalDegrees
ml DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
- DecimalDegrees
lambdaS
f :: Double
f = Double
0.5 Double -> Double -> Double
forall a. Num a => a -> a -> a
* (Double
1 Double -> Double -> Double
forall a. Num a => a -> a -> a
- Double -> Double
forall a. Floating a => a -> a
cos Double
d)
in Double
f
moonBrightLimbPositionAngle :: EquatorialCoordinates1 -> EquatorialCoordinates1 -> DecimalDegrees
moonBrightLimbPositionAngle :: EquatorialCoordinates1 -> EquatorialCoordinates1 -> DecimalDegrees
moonBrightLimbPositionAngle = EquatorialCoordinates1 -> EquatorialCoordinates1 -> DecimalDegrees
planetBrightLimbPositionAngle
data MoonQuantities = MQ {
MoonQuantities -> DecimalDegrees
mqLongitude :: DecimalDegrees
, MoonQuantities -> DecimalDegrees
mqAnomaly :: DecimalDegrees
, MoonQuantities -> DecimalDegrees
mqAscendingNode :: DecimalDegrees
}
meanMoonQuantities :: MoonDetails -> JulianDate -> MoonQuantities
meanMoonQuantities :: MoonDetails -> JulianDate -> MoonQuantities
meanMoonQuantities MoonDetails
md JulianDate
ut =
let d :: DecimalDegrees
d = Double -> DecimalDegrees
DD (Double -> DecimalDegrees) -> Double -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ JulianDate -> JulianDate -> Double
numberOfDays (MoonDetails -> JulianDate
mdEpoch MoonDetails
md) JulianDate
ut
lm :: DecimalDegrees
lm = DecimalDegrees -> DecimalDegrees
reduceDegrees (DecimalDegrees -> DecimalDegrees)
-> DecimalDegrees -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ (MoonDetails -> DecimalDegrees
mdL MoonDetails
md) DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
+ DecimalDegrees
13.1763966DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
*DecimalDegrees
d
mm :: DecimalDegrees
mm = DecimalDegrees -> DecimalDegrees
reduceDegrees (DecimalDegrees -> DecimalDegrees)
-> DecimalDegrees -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ DecimalDegrees
lm DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
- DecimalDegrees
0.1114041DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
*DecimalDegrees
d DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
- (MoonDetails -> DecimalDegrees
mdP MoonDetails
md)
nm :: DecimalDegrees
nm = DecimalDegrees -> DecimalDegrees
reduceDegrees (DecimalDegrees -> DecimalDegrees)
-> DecimalDegrees -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ (MoonDetails -> DecimalDegrees
mdN MoonDetails
md) DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
- DecimalDegrees
0.0529539DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
*DecimalDegrees
d
in DecimalDegrees
-> DecimalDegrees -> DecimalDegrees -> MoonQuantities
MQ DecimalDegrees
lm DecimalDegrees
mm DecimalDegrees
nm
centreEquation :: Double -> DecimalDegrees
centreEquation :: Double -> DecimalDegrees
centreEquation Double
mm = Double -> DecimalDegrees
DD (Double -> DecimalDegrees) -> Double -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ Double
6.2886 Double -> Double -> Double
forall a. Num a => a -> a -> a
* (Double -> Double
forall a. Floating a => a -> a
sin Double
mm)
correctedMoonQuantities :: DecimalDegrees -> DecimalDegrees -> MoonQuantities -> MoonQuantities
correctedMoonQuantities :: DecimalDegrees
-> DecimalDegrees -> MoonQuantities -> MoonQuantities
correctedMoonQuantities DecimalDegrees
lambdaS DecimalDegrees
ms (MQ DecimalDegrees
lm DecimalDegrees
mm DecimalDegrees
nm) =
let ms' :: Double
ms' = DecimalDegrees -> Double
toRadians DecimalDegrees
ms
c :: DecimalDegrees
c = DecimalDegrees
lm DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
- DecimalDegrees
lambdaS
ev :: DecimalDegrees
ev = Double -> DecimalDegrees
DD (Double -> DecimalDegrees) -> Double -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ Double
1.2739 Double -> Double -> Double
forall a. Num a => a -> a -> a
* (Double -> Double
forall a. Floating a => a -> a
sin (Double -> Double) -> Double -> Double
forall a b. (a -> b) -> a -> b
$ DecimalDegrees -> Double
toRadians (DecimalDegrees -> Double) -> DecimalDegrees -> Double
forall a b. (a -> b) -> a -> b
$ DecimalDegrees
2DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
*DecimalDegrees
c DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
- DecimalDegrees
mm)
ae :: DecimalDegrees
ae = Double -> DecimalDegrees
DD (Double -> DecimalDegrees) -> Double -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ Double
0.1858 Double -> Double -> Double
forall a. Num a => a -> a -> a
* (Double -> Double
forall a. Floating a => a -> a
sin Double
ms')
a3 :: DecimalDegrees
a3 = Double -> DecimalDegrees
DD (Double -> DecimalDegrees) -> Double -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ Double
0.37 Double -> Double -> Double
forall a. Num a => a -> a -> a
* (Double -> Double
forall a. Floating a => a -> a
sin Double
ms')
mm' :: DecimalDegrees
mm' = DecimalDegrees
mm DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
+ (DecimalDegrees
ev DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
- DecimalDegrees
ae DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
- DecimalDegrees
a3)
mm'' :: Double
mm'' = DecimalDegrees -> Double
toRadians DecimalDegrees
mm'
ec :: DecimalDegrees
ec = Double -> DecimalDegrees
centreEquation Double
mm''
a4 :: DecimalDegrees
a4 = Double -> DecimalDegrees
DD (Double -> DecimalDegrees) -> Double -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ Double
0.214 Double -> Double -> Double
forall a. Num a => a -> a -> a
* (Double -> Double
forall a. Floating a => a -> a
sin (Double -> Double) -> Double -> Double
forall a b. (a -> b) -> a -> b
$ Double
2Double -> Double -> Double
forall a. Num a => a -> a -> a
*Double
mm'')
lm' :: DecimalDegrees
lm' = DecimalDegrees
lm DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
+ (DecimalDegrees
ev DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
+ DecimalDegrees
ec DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
-DecimalDegrees
ae DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
+ DecimalDegrees
a4)
v :: DecimalDegrees
v = Double -> DecimalDegrees
DD (Double -> DecimalDegrees) -> Double -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ Double
0.6583 Double -> Double -> Double
forall a. Num a => a -> a -> a
* (Double -> Double
forall a. Floating a => a -> a
sin (Double -> Double) -> Double -> Double
forall a b. (a -> b) -> a -> b
$ DecimalDegrees -> Double
toRadians (DecimalDegrees -> Double) -> DecimalDegrees -> Double
forall a b. (a -> b) -> a -> b
$ DecimalDegrees
2DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
*(DecimalDegrees
lm' DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
- DecimalDegrees
lambdaS))
lm'' :: DecimalDegrees
lm'' = DecimalDegrees
lm' DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
+ DecimalDegrees
v
nm' :: DecimalDegrees
nm' = DecimalDegrees
nm DecimalDegrees -> DecimalDegrees -> DecimalDegrees
forall a. Num a => a -> a -> a
- (Double -> DecimalDegrees
DD (Double -> DecimalDegrees) -> Double -> DecimalDegrees
forall a b. (a -> b) -> a -> b
$ Double
0.16 Double -> Double -> Double
forall a. Num a => a -> a -> a
* (Double -> Double
forall a. Floating a => a -> a
sin Double
ms'))
in DecimalDegrees
-> DecimalDegrees -> DecimalDegrees -> MoonQuantities
MQ DecimalDegrees
lm'' DecimalDegrees
mm' DecimalDegrees
nm'