Source code for pyplanets.planets.jupiter

# -*- coding: utf-8 -*-


# PyPlanets: Object-oriented refactoring of PyMeeus, a Python library implementing astronomical algorithms.
# Copyright (C) 2020  Martin Fünffinger
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU Lesser 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 Lesser General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public License
# along with this program.  If not, see <https://www.gnu.org/licenses/>.


from math import sin, cos, log10

from pyplanets.core.angle import Angle
from pyplanets.core.epoch import Epoch
from pyplanets.parameters.jupiter_params import VSOP87_L, VSOP87_B, VSOP87_R, ORBITAL_ELEM, ORBITAL_ELEM_J2000
from pyplanets.planets.planet import Planet

"""
.. module:: Jupiter
   :synopsis: Class to model Jupiter planet
   :license: GNU Lesser General Public License v3 (LGPLv3)

.. moduleauthor:: Martin Fünffinger
"""


[docs]class Jupiter(Planet): """ Class Jupiter models that planet. """
[docs] def __init__(self, epoch): super().__init__(epoch, VSOP87_L, VSOP87_B, VSOP87_R, ORBITAL_ELEM, ORBITAL_ELEM_J2000)
[docs] def conjunction(self) -> Epoch: """This method computes the time of the conjunction closest to the given epoch. :returns: The time when the conjunction happens, as an Epoch :rtype: :py:class:`Epoch` :raises: ValueError if input epoch outside the -2000/4000 range. >>> epoch = Epoch(1993, 10, 1.0) >>> conj = Jupiter(epoch).conjunction() >>> y, m, d = conj.get_date() >>> print(y) 1993 >>> print(m) 10 >>> print(round(d, 4)) 18.3341 """ # Check that the input epoch is within valid range y = self.epoch.year() if y < -2000.0 or y > 4000.0: raise ValueError("Epoch outside the -2000/4000 range") # Set some specific constants for Jupiter's conjunction a = 2451671.186 b = 398.884046 m0 = 121.898 m1 = 33.140229 k = round((365.2425 * y + 1721060.0 - a) / b) jde0 = a + k * b m = m0 + k * m1 m = Angle(m).to_positive() m = m.rad() t = (jde0 - 2451545.0) / 36525.0 # Compute an auxiliary angle aa = 82.74 + 40.76 * t aa = Angle(aa).rad() # Convert to radians corr = (0.1027 + t * (0.0002 - t * 0.00009) + sin(m) * (-2.2637 + t * (0.0163 - t * 0.00003)) + cos(m) * (-6.154 + t * (-0.021 + t * 0.00008)) + sin(2.0 * m) * (-0.2021 + t * (-0.0017 + t * 0.00001)) + cos(2.0 * m) * (0.131 - t * 0.0008) + sin(3.0 * m) * (0.0086) + cos(3.0 * m) * (0.0087 + t * 0.0002) + sin(aa) * (0.0 + t * (0.0144 - t * 0.00008)) + cos(aa) * (0.3642 + t * (-0.0019 - t * 0.00029))) to_return = jde0 + corr return Epoch(to_return)
[docs] def opposition(self) -> Epoch: """This method computes the time of the opposition closest to the given epoch. :returns: The time when the opposition happens, as an Epoch :rtype: :py:class:`Epoch` :raises: ValueError if input epoch outside the -2000/4000 range. >>> epoch = Epoch(-6, 9, 1.0) >>> oppo = Jupiter(epoch).opposition() >>> y, m, d = oppo.get_date() >>> print(y) -6 >>> print(m) 9 >>> print(round(d, 4)) 15.2865 """ # Check that the input epoch is within valid range y = self.epoch.year() if y < -2000.0 or y > 4000.0: raise ValueError("Epoch outside the -2000/4000 range") # Set some specific constants for Jupiter's opposition a = 2451870.628 b = 398.884046 m0 = 318.4681 m1 = 33.140229 k = round((365.2425 * y + 1721060.0 - a) / b) jde0 = a + k * b m = m0 + k * m1 m = Angle(m).to_positive() m = m.rad() t = (jde0 - 2451545.0) / 36525.0 # Compute an auxiliary angle aa = 82.74 + 40.76 * t aa = Angle(aa).rad() # Convert to radians corr = (-0.1029 - t * t * 0.00009 + sin(m) * (-1.9658 + t * (-0.0056 + t * 0.00007)) + cos(m) * (6.1537 + t * (0.021 - t * 0.00006)) + sin(2.0 * m) * (-0.2081 - t * 0.0013) + cos(2.0 * m) * (-0.1116 - t * 0.001) + sin(3.0 * m) * (0.0074 + t * 0.0001) + cos(3.0 * m) * (-0.0097 - t * 0.0001) + sin(aa) * (0.0 + t * (0.0144 - t * 0.00008)) + cos(aa) * (0.3642 + t * (-0.0019 - t * 0.00029))) to_return = jde0 + corr return Epoch(to_return)
[docs] def station_longitude_1(self) -> Epoch: """This method computes the time of the 1st station in longitude (i.e. when the planet is stationary and begins to move westward - retrograde - among the starts) closest to the given epoch. :returns: Time when the 1st station in longitude happens, as an Epoch :rtype: :py:class:`Epoch` :raises: ValueError if input epoch outside the -2000/4000 range. >>> epoch = Epoch(2018, 11, 1.0) >>> sta1 = Jupiter(epoch).station_longitude_1() >>> y, m, d = sta1.get_date() >>> print(y) 2018 >>> print(m) 3 >>> print(round(d, 4)) 9.1288 """ # Check that the input epoch is within valid range y = self.epoch.year() if y < -2000.0 or y > 4000.0: raise ValueError("Epoch outside the -2000/4000 range") # Set some specific constants for Jupiter's opposition a = 2451870.628 b = 398.884046 m0 = 318.4681 m1 = 33.140229 k = round((365.2425 * y + 1721060.0 - a) / b) jde0 = a + k * b m = m0 + k * m1 m = Angle(m).to_positive() m = m.rad() t = (jde0 - 2451545.0) / 36525.0 # Compute an auxiliary angle aa = 82.74 + 40.76 * t aa = Angle(aa).rad() # Convert to radians corr = (-60.367 + t * (-0.0001 - t * 0.00009) + sin(m) * (-2.3144 + t * (-0.0124 + t * 0.00007)) + cos(m) * (6.7439 + t * (0.0166 - t * 0.00006)) + sin(2.0 * m) * (-0.2259 - t * 0.001) + cos(2.0 * m) * (-0.1497 - t * 0.0014) + sin(3.0 * m) * (0.0105 + t * 0.0001) + cos(3.0 * m) * (-0.0098) + sin(aa) * (0.0 + t * (0.0144 - t * 0.00008)) + cos(aa) * (0.3642 + t * (-0.0019 - t * 0.00029))) to_return = jde0 + corr return Epoch(to_return)
[docs] def station_longitude_2(self) -> Epoch: """This method computes the time of the 2nd station in longitude (i.e. when the planet is stationary and begins to move eastward - prograde - among the starts) closest to the given epoch. :returns: Time when the 1st station in longitude happens, as an Epoch :rtype: :py:class:`Epoch` :raises: ValueError if input epoch outside the -2000/4000 range. >>> epoch = Epoch(2018, 11, 1.0) >>> sta2 = Jupiter(epoch).station_longitude_2() >>> y, m, d = sta2.get_date() >>> print(y) 2018 >>> print(m) 7 >>> print(round(d, 4)) 10.6679 """ # Check that the input epoch is within valid range y = self.epoch.year() if y < -2000.0 or y > 4000.0: raise ValueError("Epoch outside the -2000/4000 range") # Set some specific constants for Jupiter's opposition a = 2451870.628 b = 398.884046 m0 = 318.4681 m1 = 33.140229 k = round((365.2425 * y + 1721060.0 - a) / b) jde0 = a + k * b m = m0 + k * m1 m = Angle(m).to_positive() m = m.rad() t = (jde0 - 2451545.0) / 36525.0 # Compute an auxiliary angle aa = 82.74 + 40.76 * t aa = Angle(aa).rad() # Convert to radians corr = (60.3023 + t * (0.0002 - t * 0.00009) + sin(m) * (0.3506 + t * (-0.0034 + t * 0.00004)) + cos(m) * (5.3635 + t * (0.0247 - t * 0.00007)) + sin(2.0 * m) * (-0.1872 - t * 0.0016) + cos(2.0 * m) * (-0.0037 - t * 0.0005) + sin(3.0 * m) * (0.0012 + t * 0.0001) + cos(3.0 * m) * (-0.0096 - t * 0.0001) + sin(aa) * (0.0 + t * (0.0144 - t * 0.00008)) + cos(aa) * (0.3642 + t * (-0.0019 - t * 0.00029))) to_return = jde0 + corr return Epoch(to_return)
[docs] def aphelion(self) -> Epoch: """This method computes the time of Aphelion closer to a given epoch. :returns: The epoch of the desired Aphelion :rtype: :py:class:`Epoch` >>> epoch = Epoch(1981, 6, 1.0) >>> e = Jupiter(epoch).aphelion() >>> y, m, d, h, mi, s = e.get_full_date() >>> print(y) 1981 >>> print(m) 7 >>> print(d) 28 >>> print(h) 6 """ # First approximation k = 0.0843 * (self.epoch.year() - 2011.2) k = round(k + 0.5) - 0.5 jde = 2455636.936 + k * (4332.897065 - k * 0.0001367) # Compute the epochs a month before and after # Compute the Sun-Jupiter distance for each epoch sol = self._interpolate_jde(jde, delta=30.0) return Epoch(sol)
[docs] def perihelion(self) -> Epoch: """This method computes the time of Perihelion closer to a given epoch. :returns: The epoch of the desired Perihelion (or Aphelion) :rtype: :py:class:`Epoch` >>> epoch = Epoch(2019, 2, 23.0) >>> e = Jupiter(epoch).perihelion() >>> y, m, d, h, mi, s = e.get_full_date() >>> print(y) 2023 >>> print(m) 1 >>> print(d) 20 >>> print(h) 11 """ # First approximation k = 0.0843 * (self.epoch.year() - 2011.2) k = round(k) jde = 2455636.936 + k * (4332.897065 - k * 0.0001367) # Compute the epochs a month before and after # Compute the Sun-Jupiter distance for each epoch sol = self._interpolate_jde(jde, delta=30.0) return Epoch(sol)
[docs] @staticmethod def magnitude(sun_dist, earth_dist): """This function computes the approximate magnitude of Jupiter. :param sun_dist: Distance from Jupiter to Sun, in Astronomical Units :type sun_dist: float :param earth_dist: Distance Jupiter to Earth, in Astronomical Units :type earth_dist: float :returns: Jupiter's magnitude :rtype: float :raises: TypeError if input values are of wrong type. """ if not (isinstance(sun_dist, float) and isinstance(earth_dist, float)): raise TypeError("Invalid input types") m = -8.93 + 5.0 * log10(sun_dist * earth_dist) return round(m, 1)