mirror of
https://github.com/cosinekitty/astronomy.git
synced 2026-03-29 11:53:58 -04:00
PY: Finished implementation of JupiterMoons function.
This commit is contained in:
@@ -403,6 +403,25 @@ body at a given date and time.
|
||||
|
||||
---
|
||||
|
||||
<a name="JupiterMoonsInfo"></a>
|
||||
### class JupiterMoonsInfo
|
||||
|
||||
**Holds the positions and velocities of Jupiter's major 4 moons.**
|
||||
|
||||
The [`JupiterMoons`](#JupiterMoons) function returns an object of this type
|
||||
to report position and velocity vectors for Jupiter's largest 4 moons
|
||||
Io, Europa, Ganymede, and Callisto. Each position vector is relative
|
||||
to the center of Jupiter. Both position and velocity are oriented in
|
||||
the EQJ system (that is, using Earth's equator at the J2000 epoch).
|
||||
The positions are expressed in astronomical units (AU),
|
||||
and the velocities in AU/day.
|
||||
|
||||
| Type | Attribute | Description |
|
||||
| --- | --- | --- |
|
||||
| [`StateVector[4]`](#StateVector[4]) | `moon` | An array of state vectors, one for each of the four major moons of Jupiter, in the following order: 0=Io, 1=Europa, 2=Ganymede, 3=Callisto. |
|
||||
|
||||
---
|
||||
|
||||
<a name="LocalSolarEclipseInfo"></a>
|
||||
### class LocalSolarEclipseInfo
|
||||
|
||||
@@ -543,6 +562,28 @@ Call [`Seasons`](#Seasons) to calculate this data structure for a given year.
|
||||
|
||||
---
|
||||
|
||||
<a name="StateVector"></a>
|
||||
### class StateVector
|
||||
|
||||
**A combination of a position vector, a velocity vector, and a time.**
|
||||
|
||||
The position (x, y, z) is measured in astronomical units (AU).
|
||||
The velocity (vx, vy, vz) is measured in AU/day.
|
||||
The coordinate system varies and depends on context.
|
||||
The state vector also includes a time stamp.
|
||||
|
||||
| Type | Attribute | Description |
|
||||
| --- | --- | --- |
|
||||
| `float` | `x` | The x-coordinate of the position, measured in AU. |
|
||||
| `float` | `y` | The y-coordinate of the position, measured in AU. |
|
||||
| `float` | `z` | The z-coordinate of the position, measured in AU. |
|
||||
| `float` | `vx` | The x-component of the velocity, measured in AU/day. |
|
||||
| `float` | `vy` | The y-component of the velocity, measured in AU/day. |
|
||||
| `float` | `vz` | The z-component of the velocity, measured in AU/day. |
|
||||
| [`Time`](#Time) | `t` | The date and time at which the position and velocity vectors are valid. |
|
||||
|
||||
---
|
||||
|
||||
<a name="Time"></a>
|
||||
### class Time
|
||||
|
||||
@@ -583,6 +624,17 @@ The value of the calling object is not modified. This function creates a brand n
|
||||
|
||||
### Returns: [`Time`](#Time)
|
||||
|
||||
<a name="Time.FromTerrestrialTime"></a>
|
||||
### Time.FromTerrestrialTime(tt)
|
||||
|
||||
**Creates a [`Time`](#Time) object from a Terrestrial Time day value.**
|
||||
|
||||
| Type | Parameter | Description |
|
||||
| --- | --- | --- |
|
||||
| [`The number of days after the J2000 epoch.`](#The number of days after the J2000 epoch.) | `tt` | |
|
||||
|
||||
### Returns: [`Time`](#Time)
|
||||
|
||||
<a name="Time.Make"></a>
|
||||
### Time.Make(year, month, day, hour, minute, second)
|
||||
|
||||
@@ -1330,6 +1382,31 @@ The inverse rotation matrix.
|
||||
|
||||
---
|
||||
|
||||
<a name="JupiterMoons"></a>
|
||||
### JupiterMoons(time)
|
||||
|
||||
**Calculates jovicentric positions and velocities of Jupiter's largest 4 moons.**
|
||||
|
||||
Calculates position and velocity vectors for Jupiter's moons
|
||||
Io, Europa, Ganymede, and Callisto, at the given date and time.
|
||||
The vectors are jovicentric (relative to the center of Jupiter).
|
||||
Their orientation is the Earth's equatorial system at the J2000 epoch (EQJ).
|
||||
The position components are expressed in astronomical units (AU), and the
|
||||
velocity components are in AU/day.
|
||||
To convert to heliocentric vectors, call [`HelioVector`](#HelioVector)
|
||||
with `Body.Jupiter` to get Jupiter's heliocentric position, then
|
||||
add the jovicentric vectors. Likewise, you can call [`GeoVector`](#GeoVector)
|
||||
to convert to geocentric vectors.
|
||||
|
||||
| Type | Parameter | Description |
|
||||
| --- | --- | --- |
|
||||
| [`Time`](#Time) | `time` | The date and time for which to calculate Jupiter's moons. |
|
||||
|
||||
### Returns: [`JupiterMoonsInfo`](#JupiterMoonsInfo)
|
||||
The positions and velocities of Jupiter's 4 largest moons.
|
||||
|
||||
---
|
||||
|
||||
<a name="LongitudeFromSun"></a>
|
||||
### LongitudeFromSun(body, time)
|
||||
|
||||
@@ -1590,6 +1667,25 @@ option selected by the `refraction` parameter.
|
||||
|
||||
---
|
||||
|
||||
<a name="RotateState"></a>
|
||||
### RotateState(rotation, state)
|
||||
|
||||
**Applies a rotation to a state vector, yielding a rotated state vector.**
|
||||
|
||||
This function transforms a state vector in one orientation to a
|
||||
state vector in another orientation. Both the position and velocity
|
||||
vectors are rotated the same way.
|
||||
|
||||
| Type | Parameter | Description |
|
||||
| --- | --- | --- |
|
||||
| [`RotationMatrix`](#RotationMatrix) | `rotation` | A rotation matrix that specifies how the orientation of the vector is to be changed. |
|
||||
| [`StateVector`](#StateVector) | `state` | The state vector whose orientation is to be changed. |
|
||||
|
||||
### Returns: [`StateVector`](#StateVector)
|
||||
A state vector in the orientation specified by `rotation`.
|
||||
|
||||
---
|
||||
|
||||
<a name="RotateVector"></a>
|
||||
### RotateVector(rotation, vector)
|
||||
|
||||
|
||||
@@ -155,6 +155,50 @@ class Vector:
|
||||
"""Returns the length of the vector in AU."""
|
||||
return math.sqrt(self.x**2 + self.y**2 + self.z**2)
|
||||
|
||||
class StateVector:
|
||||
"""A combination of a position vector, a velocity vector, and a time.
|
||||
|
||||
The position (x, y, z) is measured in astronomical units (AU).
|
||||
The velocity (vx, vy, vz) is measured in AU/day.
|
||||
The coordinate system varies and depends on context.
|
||||
The state vector also includes a time stamp.
|
||||
|
||||
Attributes
|
||||
----------
|
||||
x : float
|
||||
The x-coordinate of the position, measured in AU.
|
||||
y : float
|
||||
The y-coordinate of the position, measured in AU.
|
||||
z : float
|
||||
The z-coordinate of the position, measured in AU.
|
||||
vx : float
|
||||
The x-component of the velocity, measured in AU/day.
|
||||
vy : float
|
||||
The y-component of the velocity, measured in AU/day.
|
||||
vz : float
|
||||
The z-component of the velocity, measured in AU/day.
|
||||
t : Time
|
||||
The date and time at which the position and velocity vectors are valid.
|
||||
"""
|
||||
def __init__(self, x, y, z, vx, vy, vz, t):
|
||||
self.x = x
|
||||
self.y = y
|
||||
self.z = z
|
||||
self.vx = vx
|
||||
self.vy = vy
|
||||
self.vz = vz
|
||||
self.t = t
|
||||
|
||||
def __repr__(self):
|
||||
return 'StateVector[pos=({}, {}, {}), vel=({}, {}, {}), t{}]'.format(
|
||||
self.x, self.y, self.z,
|
||||
self.vx, self.vy, self.vz,
|
||||
str(self.t))
|
||||
|
||||
def __str__(self):
|
||||
return '({}, {}, {}, {}, {}, {}, {})'.format(self.x, self.y, self.z, self.vx, self.vy, self.vz, str(self.t))
|
||||
|
||||
|
||||
@enum.unique
|
||||
class Body(enum.Enum):
|
||||
"""The celestial bodies supported by Astronomy Engine calculations.
|
||||
@@ -411,6 +455,20 @@ _DeltaT = DeltaT_EspenakMeeus
|
||||
def _TerrestrialTime(ut):
|
||||
return ut + _DeltaT(ut) / 86400.0
|
||||
|
||||
def _UniversalTime(tt):
|
||||
# This is the inverse function of _TerrestrialTime.
|
||||
# This is an iterative numerical solver, but because
|
||||
# the relationship between UT and TT is almost perfectly linear,
|
||||
# it converges extremely fast (never more than 3 iterations).
|
||||
dt = _TerrestrialTime(tt) - tt # first approximation of dt = tt - ut
|
||||
while True:
|
||||
ut = tt - dt
|
||||
tt_check = _TerrestrialTime(ut)
|
||||
err = tt_check - tt
|
||||
if abs(err) < 1.0e-12:
|
||||
return ut
|
||||
dt += err
|
||||
|
||||
_TimeRegex = re.compile(r'^([0-9]{1,4})-([0-9]{2})-([0-9]{2})(T([0-9]{2}):([0-9]{2})(:([0-9]{2}(\.[0-9]+)?))?Z)?$')
|
||||
|
||||
class Time:
|
||||
@@ -457,11 +515,28 @@ class Time:
|
||||
such as the orbits of planets around the Sun, or the Moon around the Earth.
|
||||
Historically, Terrestrial Time has also been known by the term *Ephemeris Time* (ET).
|
||||
"""
|
||||
def __init__(self, ut):
|
||||
def __init__(self, ut, tt = None):
|
||||
self.ut = ut
|
||||
self.tt = _TerrestrialTime(ut)
|
||||
if tt is None:
|
||||
self.tt = _TerrestrialTime(ut)
|
||||
else:
|
||||
self.tt = tt
|
||||
self.etilt = None
|
||||
|
||||
@staticmethod
|
||||
def FromTerrestrialTime(tt):
|
||||
"""Creates a #Time object from a Terrestrial Time day value.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
tt : The number of days after the J2000 epoch.
|
||||
|
||||
Returns
|
||||
-------
|
||||
Time
|
||||
"""
|
||||
return Time(_UniversalTime(tt), tt)
|
||||
|
||||
@staticmethod
|
||||
def Parse(text):
|
||||
"""Creates a #Time object from a string of the form 'yyyy-mm-ddThh:mm:ss.sssZ'
|
||||
@@ -3396,6 +3471,273 @@ def _CalcPluto(time):
|
||||
|
||||
# END Pluto Integrator
|
||||
#----------------------------------------------------------------------------
|
||||
# BEGIN Jupiter Moons
|
||||
|
||||
_Rotation_JUP_EQJ = RotationMatrix([
|
||||
[ 9.9943276533865444e-01, -3.3677107469764142e-02, 0.0000000000000000e+00 ],
|
||||
[ 3.0395942890628476e-02, 9.0205791235280897e-01, 4.3054338854229507e-01 ],
|
||||
[ -1.4499455966335291e-02, -4.3029916940910073e-01, 9.0256988127375404e-01 ]
|
||||
])
|
||||
|
||||
_JupiterMoonModel = [
|
||||
# [0] Io
|
||||
[
|
||||
2.8248942843381399e-07, 1.4462132960212239e+00, 3.5515522861824000e+00, # mu, al0, al1
|
||||
[ # a
|
||||
[ 0.0028210960212903, 0.0000000000000000e+00, 0.0000000000000000e+00 ]
|
||||
],
|
||||
[ # l
|
||||
[ -0.0001925258348666, 4.9369589722644998e+00, 1.3584836583050000e-02 ],
|
||||
[ -0.0000970803596076, 4.3188796477322002e+00, 1.3034138432430000e-02 ],
|
||||
[ -0.0000898817416500, 1.9080016428616999e+00, 3.0506486715799999e-03 ],
|
||||
[ -0.0000553101050262, 1.4936156681568999e+00, 1.2938928911549999e-02 ]
|
||||
],
|
||||
[ # z
|
||||
[ 0.0041510849668155, 4.0899396355450000e+00, -1.2906864146660001e-02 ],
|
||||
[ 0.0006260521444113, 1.4461888986270000e+00, 3.5515522949801999e+00 ],
|
||||
[ 0.0000352747346169, 2.1256287034577999e+00, 1.2727416566999999e-04 ]
|
||||
],
|
||||
[ # zeta
|
||||
[ 0.0003142172466014, 2.7964219722923001e+00, -2.3150960980000000e-03 ],
|
||||
[ 0.0000904169207946, 1.0477061879627001e+00, -5.6920638196000003e-04 ]
|
||||
]
|
||||
],
|
||||
|
||||
# [1] Europa
|
||||
[
|
||||
2.8248327439289299e-07, -3.7352634374713622e-01, 1.7693227111234699e+00, # mu, al0, al1
|
||||
[ # a
|
||||
[ 0.0044871037804314, 0.0000000000000000e+00, 0.0000000000000000e+00 ],
|
||||
[ 0.0000004324367498, 1.8196456062910000e+00, 1.7822295777568000e+00 ]
|
||||
],
|
||||
[ # l
|
||||
[ 0.0008576433172936, 4.3188693178264002e+00, 1.3034138308049999e-02 ],
|
||||
[ 0.0004549582875086, 1.4936531751079001e+00, 1.2938928819619999e-02 ],
|
||||
[ 0.0003248939825174, 1.8196494533458001e+00, 1.7822295777568000e+00 ],
|
||||
[ -0.0003074250079334, 4.9377037005910998e+00, 1.3584832867240000e-02 ],
|
||||
[ 0.0001982386144784, 1.9079869054759999e+00, 3.0510121286900001e-03 ],
|
||||
[ 0.0001834063551804, 2.1402853388529000e+00, 1.4500978933800000e-03 ],
|
||||
[ -0.0001434383188452, 5.6222140366630002e+00, 8.9111478887838003e-01 ],
|
||||
[ -0.0000771939140944, 4.3002724372349999e+00, 2.6733443704265998e+00 ]
|
||||
],
|
||||
[ # z
|
||||
[ -0.0093589104136341, 4.0899396509038999e+00, -1.2906864146660001e-02 ],
|
||||
[ 0.0002988994545555, 5.9097265185595003e+00, 1.7693227079461999e+00 ],
|
||||
[ 0.0002139036390350, 2.1256289300016000e+00, 1.2727418406999999e-04 ],
|
||||
[ 0.0001980963564781, 2.7435168292649998e+00, 6.7797343008999997e-04 ],
|
||||
[ 0.0001210388158965, 5.5839943711203004e+00, 3.2056614899999997e-05 ],
|
||||
[ 0.0000837042048393, 1.6094538368039000e+00, -9.0402165808846002e-01 ],
|
||||
[ 0.0000823525166369, 1.4461887708689001e+00, 3.5515522949801999e+00 ]
|
||||
],
|
||||
[ # zeta
|
||||
[ 0.0040404917832303, 1.0477063169425000e+00, -5.6920640539999997e-04 ],
|
||||
[ 0.0002200421034564, 3.3368857864364001e+00, -1.2491307306999999e-04 ],
|
||||
[ 0.0001662544744719, 2.4134862374710999e+00, 0.0000000000000000e+00 ],
|
||||
[ 0.0000590282470983, 5.9719930968366004e+00, -3.0561602250000000e-05 ]
|
||||
]
|
||||
],
|
||||
|
||||
# [2] Ganymede
|
||||
[
|
||||
2.8249818418472298e-07, 2.8740893911433479e-01, 8.7820792358932798e-01, # mu, al0, al1
|
||||
[ # a
|
||||
[ 0.0071566594572575, 0.0000000000000000e+00, 0.0000000000000000e+00 ],
|
||||
[ 0.0000013930299110, 1.1586745884981000e+00, 2.6733443704265998e+00 ]
|
||||
],
|
||||
[ # l
|
||||
[ 0.0002310797886226, 2.1402987195941998e+00, 1.4500978438400001e-03 ],
|
||||
[ -0.0001828635964118, 4.3188672736968003e+00, 1.3034138282630000e-02 ],
|
||||
[ 0.0001512378778204, 4.9373102372298003e+00, 1.3584834812520000e-02 ],
|
||||
[ -0.0001163720969778, 4.3002659861490002e+00, 2.6733443704265998e+00 ],
|
||||
[ -0.0000955478069846, 1.4936612842567001e+00, 1.2938928798570001e-02 ],
|
||||
[ 0.0000815246854464, 5.6222137132535002e+00, 8.9111478887838003e-01 ],
|
||||
[ -0.0000801219679602, 1.2995922951532000e+00, 1.0034433456728999e+00 ],
|
||||
[ -0.0000607017260182, 6.4978769669238001e-01, 5.0172167043264004e-01 ]
|
||||
],
|
||||
[ # z
|
||||
[ 0.0014289811307319, 2.1256295942738999e+00, 1.2727413029000001e-04 ],
|
||||
[ 0.0007710931226760, 5.5836330003496002e+00, 3.2064341100000001e-05 ],
|
||||
[ 0.0005925911780766, 4.0899396636447998e+00, -1.2906864146660001e-02 ],
|
||||
[ 0.0002045597496146, 5.2713683670371996e+00, -1.2523544076106000e-01 ],
|
||||
[ 0.0001785118648258, 2.8743156721063001e-01, 8.7820792442520001e-01 ],
|
||||
[ 0.0001131999784893, 1.4462127277818000e+00, 3.5515522949801999e+00 ],
|
||||
[ -0.0000658778169210, 2.2702423990985001e+00, -1.7951364394536999e+00 ],
|
||||
[ 0.0000497058888328, 5.9096792204858000e+00, 1.7693227129285001e+00 ]
|
||||
],
|
||||
[ # zeta
|
||||
[ 0.0015932721570848, 3.3368862796665000e+00, -1.2491307058000000e-04 ],
|
||||
[ 0.0008533093128905, 2.4133881688166001e+00, 0.0000000000000000e+00 ],
|
||||
[ 0.0003513347911037, 5.9720789850126996e+00, -3.0561017709999999e-05 ],
|
||||
[ -0.0001441929255483, 1.0477061764435001e+00, -5.6920632124000004e-04 ]
|
||||
]
|
||||
],
|
||||
|
||||
# [3] Callisto
|
||||
[
|
||||
2.8249214488990899e-07, -3.6203412913757038e-01, 3.7648623343382798e-01, # mu, al0, al1
|
||||
[ # a
|
||||
[ 0.0125879701715314, 0.0000000000000000e+00, 0.0000000000000000e+00 ],
|
||||
[ 0.0000035952049470, 6.4965776007116005e-01, 5.0172168165034003e-01 ],
|
||||
[ 0.0000027580210652, 1.8084235781510001e+00, 3.1750660413359002e+00 ]
|
||||
],
|
||||
[ # l
|
||||
[ 0.0005586040123824, 2.1404207189814999e+00, 1.4500979323100001e-03 ],
|
||||
[ -0.0003805813868176, 2.7358844897852999e+00, 2.9729650620000000e-05 ],
|
||||
[ 0.0002205152863262, 6.4979652596399995e-01, 5.0172167243580001e-01 ],
|
||||
[ 0.0001877895151158, 1.8084787604004999e+00, 3.1750660413359002e+00 ],
|
||||
[ 0.0000766916975242, 6.2720114319754998e+00, 1.3928364636651001e+00 ],
|
||||
[ 0.0000747056855106, 1.2995916202344000e+00, 1.0034433456728999e+00 ]
|
||||
],
|
||||
[ # z
|
||||
[ 0.0073755808467977, 5.5836071576083999e+00, 3.2065099140000001e-05 ],
|
||||
[ 0.0002065924169942, 5.9209831565786004e+00, 3.7648624194703001e-01 ],
|
||||
[ 0.0001589869764021, 2.8744006242622999e-01, 8.7820792442520001e-01 ],
|
||||
[ -0.0001561131605348, 2.1257397865089001e+00, 1.2727441285000001e-04 ],
|
||||
[ 0.0001486043380971, 1.4462134301023000e+00, 3.5515522949801999e+00 ],
|
||||
[ 0.0000635073108731, 5.9096803285953996e+00, 1.7693227129285001e+00 ],
|
||||
[ 0.0000599351698525, 4.1125517584797997e+00, -2.7985797954588998e+00 ],
|
||||
[ 0.0000540660842731, 5.5390350845569003e+00, 2.8683408228299999e-03 ],
|
||||
[ -0.0000489596900866, 4.6218149483337996e+00, -6.2695712529518999e-01 ]
|
||||
],
|
||||
[ # zeta
|
||||
[ 0.0038422977898495, 2.4133922085556998e+00, 0.0000000000000000e+00 ],
|
||||
[ 0.0022453891791894, 5.9721736773277003e+00, -3.0561255249999997e-05 ],
|
||||
[ -0.0002604479450559, 3.3368746306408998e+00, -1.2491309972000001e-04 ],
|
||||
[ 0.0000332112143230, 5.5604137742336999e+00, 2.9003768850700000e-03 ]
|
||||
]
|
||||
]
|
||||
]
|
||||
|
||||
class JupiterMoonsInfo:
|
||||
"""Holds the positions and velocities of Jupiter's major 4 moons.
|
||||
|
||||
The #JupiterMoons function returns an object of this type
|
||||
to report position and velocity vectors for Jupiter's largest 4 moons
|
||||
Io, Europa, Ganymede, and Callisto. Each position vector is relative
|
||||
to the center of Jupiter. Both position and velocity are oriented in
|
||||
the EQJ system (that is, using Earth's equator at the J2000 epoch).
|
||||
The positions are expressed in astronomical units (AU),
|
||||
and the velocities in AU/day.
|
||||
|
||||
Attributes
|
||||
----------
|
||||
moon : StateVector[4]
|
||||
An array of state vectors, one for each of the four major moons
|
||||
of Jupiter, in the following order: 0=Io, 1=Europa, 2=Ganymede, 3=Callisto.
|
||||
"""
|
||||
def __init__(self, moon):
|
||||
self.moon = moon
|
||||
|
||||
|
||||
def _JupiterMoon_elem2pv(time, mu, A, AL, K, H, Q, P):
|
||||
# Translation of FORTRAN subroutine ELEM2PV from:
|
||||
# https://ftp.imcce.fr/pub/ephem/satel/galilean/L1/L1.2/
|
||||
AN = math.sqrt(mu / (A*A*A))
|
||||
EE = AL + K*math.sin(AL) - H*math.cos(AL)
|
||||
DE = 1
|
||||
while abs(DE) >= 1.0e-12:
|
||||
CE = math.cos(EE)
|
||||
SE = math.sin(EE)
|
||||
DE = (AL - EE + K*SE - H*CE) / (1.0 - K*CE - H*SE)
|
||||
EE += DE
|
||||
CE = math.cos(EE)
|
||||
SE = math.sin(EE)
|
||||
DLE = H*CE - K*SE
|
||||
RSAM1 = -K*CE - H*SE
|
||||
ASR = 1.0/(1.0 + RSAM1)
|
||||
PHI = math.sqrt(1.0 - K*K - H*H)
|
||||
PSI = 1.0/(1.0 + PHI)
|
||||
X1 = A*(CE - K - PSI*H*DLE)
|
||||
Y1 = A*(SE - H + PSI*K*DLE)
|
||||
VX1 = AN*ASR*A*(-SE - PSI*H*RSAM1)
|
||||
VY1 = AN*ASR*A*(+CE + PSI*K*RSAM1)
|
||||
F2 = 2.0*math.sqrt(1.0 - Q*Q - P*P)
|
||||
P2 = 1.0 - 2.0*P*P
|
||||
Q2 = 1.0 - 2.0*Q*Q
|
||||
PQ = 2.0*P*Q
|
||||
return StateVector(
|
||||
X1*P2 + Y1*PQ,
|
||||
X1*PQ + Y1*Q2,
|
||||
(Q*Y1 - X1*P)*F2,
|
||||
VX1*P2 + VY1*PQ,
|
||||
VX1*PQ + VY1*Q2,
|
||||
(Q*VY1 - VX1*P)*F2,
|
||||
time
|
||||
)
|
||||
|
||||
|
||||
def _CalcJupiterMoon(time, mu, al0, al1, a, l, z, zeta):
|
||||
# This is a translation of FORTRAN code by Duriez, Lainey, and Vienne:
|
||||
# https://ftp.imcce.fr/pub/ephem/satel/galilean/L1/L1.2/
|
||||
|
||||
t = time.tt + 18262.5 # number of days since 1950-01-01T00:00:00Z
|
||||
|
||||
# Calculate 6 orbital elements at the given time t.
|
||||
elem0 = 0.0
|
||||
for (amplitude, phase, frequency) in a:
|
||||
elem0 += amplitude * math.cos(phase + (t * frequency))
|
||||
|
||||
elem1 = al0 + (t * al1)
|
||||
for (amplitude, phase, frequency) in l:
|
||||
elem1 += amplitude * math.sin(phase + (t * frequency))
|
||||
|
||||
elem1 = math.fmod(elem1, _PI2)
|
||||
if elem1 < 0:
|
||||
elem1 += _PI2
|
||||
|
||||
elem2 = 0.0
|
||||
elem3 = 0.0
|
||||
for (amplitude, phase, frequency) in z:
|
||||
arg = phase + (t * frequency)
|
||||
elem2 += amplitude * math.cos(arg)
|
||||
elem3 += amplitude * math.sin(arg)
|
||||
|
||||
elem4 = 0.0
|
||||
elem5 = 0.0
|
||||
for (amplitude, phase, frequency) in zeta:
|
||||
arg = phase + (t * frequency)
|
||||
elem4 += amplitude * math.cos(arg)
|
||||
elem5 += amplitude * math.sin(arg)
|
||||
|
||||
# Convert the oribital elements into position vectors in the Jupiter equatorial system (JUP).
|
||||
state = _JupiterMoon_elem2pv(time, mu, elem0, elem1, elem2, elem3, elem4, elem5)
|
||||
|
||||
# Re-orient position and velocity vectors from Jupiter-equatorial (JUP) to Earth-equatorial in J2000 (EQJ).
|
||||
return RotateState(_Rotation_JUP_EQJ, state)
|
||||
|
||||
|
||||
def JupiterMoons(time):
|
||||
"""Calculates jovicentric positions and velocities of Jupiter's largest 4 moons.
|
||||
|
||||
Calculates position and velocity vectors for Jupiter's moons
|
||||
Io, Europa, Ganymede, and Callisto, at the given date and time.
|
||||
The vectors are jovicentric (relative to the center of Jupiter).
|
||||
Their orientation is the Earth's equatorial system at the J2000 epoch (EQJ).
|
||||
The position components are expressed in astronomical units (AU), and the
|
||||
velocity components are in AU/day.
|
||||
|
||||
To convert to heliocentric vectors, call #HelioVector
|
||||
with `Body.Jupiter` to get Jupiter's heliocentric position, then
|
||||
add the jovicentric vectors. Likewise, you can call #GeoVector
|
||||
to convert to geocentric vectors.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
time : Time
|
||||
The date and time for which to calculate Jupiter's moons.
|
||||
|
||||
Returns
|
||||
-------
|
||||
JupiterMoonsInfo
|
||||
The positions and velocities of Jupiter's 4 largest moons.
|
||||
"""
|
||||
infolist = []
|
||||
for (mu, al0, al1, a, l, z, zeta) in _JupiterMoonModel:
|
||||
infolist.append(_CalcJupiterMoon(time, mu, al0, al1, a, l, z, zeta))
|
||||
return JupiterMoonsInfo(infolist)
|
||||
|
||||
# END Jupiter Moons
|
||||
#----------------------------------------------------------------------------
|
||||
# BEGIN Search
|
||||
|
||||
def _QuadInterp(tm, dt, fa, fm, fb):
|
||||
@@ -6076,6 +6418,36 @@ def RotateVector(rotation, vector):
|
||||
)
|
||||
|
||||
|
||||
def RotateState(rotation, state):
|
||||
"""Applies a rotation to a state vector, yielding a rotated state vector.
|
||||
|
||||
This function transforms a state vector in one orientation to a
|
||||
state vector in another orientation. Both the position and velocity
|
||||
vectors are rotated the same way.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
rotation : RotationMatrix
|
||||
A rotation matrix that specifies how the orientation of the vector is to be changed.
|
||||
state : StateVector
|
||||
The state vector whose orientation is to be changed.
|
||||
|
||||
Returns
|
||||
-------
|
||||
StateVector
|
||||
A state vector in the orientation specified by `rotation`.
|
||||
"""
|
||||
return StateVector(
|
||||
rotation.rot[0][0]*state.x + rotation.rot[1][0]*state.y + rotation.rot[2][0]*state.z,
|
||||
rotation.rot[0][1]*state.x + rotation.rot[1][1]*state.y + rotation.rot[2][1]*state.z,
|
||||
rotation.rot[0][2]*state.x + rotation.rot[1][2]*state.y + rotation.rot[2][2]*state.z,
|
||||
rotation.rot[0][0]*state.vx + rotation.rot[1][0]*state.vy + rotation.rot[2][0]*state.vz,
|
||||
rotation.rot[0][1]*state.vx + rotation.rot[1][1]*state.vy + rotation.rot[2][1]*state.vz,
|
||||
rotation.rot[0][2]*state.vx + rotation.rot[1][2]*state.vy + rotation.rot[2][2]*state.vz,
|
||||
state.t
|
||||
)
|
||||
|
||||
|
||||
def Rotation_EQJ_ECL():
|
||||
"""Calculates a rotation matrix from equatorial J2000 (EQJ) to ecliptic J2000 (ECL).
|
||||
|
||||
|
||||
Reference in New Issue
Block a user