Class NOAACalculator

java.lang.Object
com.kosherjava.zmanim.util.AstronomicalCalculator
com.kosherjava.zmanim.util.NOAACalculator
All Implemented Interfaces:
Cloneable

Implementation of sunrise and sunset methods to calculate astronomical times based on the NOAA algorithm. This calculator uses the Java algorithm based on the implementation by NOAA - National Oceanic and Atmospheric Administration's Surface Radiation Research Branch. NOAA's implementation is based on equations from Astronomical Algorithms by Jean Meeus. Added to the algorithm is an adjustment of the zenith to account for elevation. The algorithm can be found in the Wikipedia Sunrise Equation article.
Author:
© Eliyahu Hershfeld 2011 - 2026
  • Field Details

  • Constructor Details

    • NOAACalculator

      public NOAACalculator()
      Default constructor of the NOAACalculator.
  • Method Details

    • getCalculatorName

      Description copied from class: AstronomicalCalculator
      Returns the name of the algorithm.
      Specified by:
      getCalculatorName in class AstronomicalCalculator
      Returns:
      the descriptive name of the algorithm.
    • getUTCSunrise

      public double getUTCSunrise(LocalDate dt, GeoLocation geoLocation, double zenith, boolean adjustForElevation)
      Description copied from class: AstronomicalCalculator
      A method that calculates UTC sunrise as well as any time based on an angle above or below sunrise. This abstract method is implemented by the classes that extend this class.
      Specified by:
      getUTCSunrise in class AstronomicalCalculator
      Parameters:
      dt - The LocalDate representing the date to calculate sunrise for.
      geoLocation - The location information used for astronomical calculation of solar times.
      zenith - the azimuth below the vertical zenith of 90°. For sunrise typically the zenith used for the calculation uses geometric zenith of 90° and adjusts this slightly to account for solar refraction and the sun's radius. Another example would be AstronomicalCalendar.getBeginNauticalTwilight() that passes AstronomicalCalendar.NAUTICAL_ZENITH to this method.
      adjustForElevation - Should the time be adjusted for elevation
      Returns:
      The UTC time of sunrise in 24-hour format. 5:45:00 AM will return 5.75. If an error was encountered in the calculation (expected behavior for some locations such as near the poles, Double.NaN will be returned.
      See Also:
    • getUTCSunset

      public double getUTCSunset(LocalDate dt, GeoLocation geoLocation, double zenith, boolean adjustForElevation)
      Description copied from class: AstronomicalCalculator
      A method that calculates UTC sunset as well as any time based on an angle above or below sunset. This abstract method is implemented by the classes that extend this class.
      Specified by:
      getUTCSunset in class AstronomicalCalculator
      Parameters:
      dt - The LocalDate> representing the date to calculate sunset for.
      geoLocation - The location information used for astronomical calculation of solar times.
      zenith - the azimuth below the vertical zenith of 90°. For sunset typically the zenith used for the calculation uses geometric zenith of 90° and adjusts this slightly to account for solar refraction and the sun's radius. Another example would be AstronomicalCalendar.getEndNauticalTwilight() that passes AstronomicalCalendar.NAUTICAL_ZENITH to this method.
      adjustForElevation - Should the time be adjusted for elevation
      Returns:
      The UTC time of sunset in 24-hour format. 5:45:00 AM will return 5.75. If an error was encountered in the calculation (expected behavior for some locations such as near the poles, Double.NaN will be returned.
      See Also:
    • getUTCSunRiseSet

      private double getUTCSunRiseSet(LocalDate localDate, GeoLocation geoLocation, double zenith, boolean adjustForElevation, NOAACalculator.SolarEvent solarEvent)
      A method that calculates UTC sunrise or sunset as well as any time based on an angle above or below sunset and returns it as a double in 24-hour format. 5:45:00 AM will return 5.75.
      Parameters:
      localDate - Used to calculate day of year.
      geoLocation - The location information used for astronomical calculation of solar times.
      zenith - the azimuth below the vertical zenith of 90°. For sunset typically the zenith used for the calculation uses geometric zenith of 90° and adjusts this slightly to account for solar refraction and the sun's radius. Another example would be AstronomicalCalendar.getEndNauticalTwilight() that passes AstronomicalCalendar.NAUTICAL_ZENITH to this method.
      adjustForElevation - Should the time be adjusted for elevation
      solarEvent - if the calculation is for NOAACalculator.SolarEvent.SUNRISE or NOAACalculator.SolarEvent.SUNSET
      Returns:
      The UTC time of sunrise or sunset in 24-hour format. 5:45:00 AM will return 5.75, while 5:45 PM will return 17.75. If an error was encountered in the calculation (expected behavior for some locations such as near the poles, Double.NaN will be returned.
      See Also:
    • getJulianDay

      private static double getJulianDay(LocalDate localDate)
      Return the Julian day from a Java LocalDate.
      Parameters:
      localDate - The LocalDate
      Returns:
      the Julian day corresponding to the date Note: Number is returned for the start of the Julian day. Fractional days / time should be added later.
    • getJulianCenturiesFromJulianDay

      private static double getJulianCenturiesFromJulianDay(double julianDay)
      Convert Julian day to centuries since J2000.0.
      Parameters:
      julianDay - the Julian Day to convert
      Returns:
      the centuries since 2000 Julian corresponding to the Julian Day
    • getSunGeometricMeanLongitude

      private static double getSunGeometricMeanLongitude(double julianCenturies)
      Returns the Geometric Mean Longitude of the Sun.
      Parameters:
      julianCenturies - the number of Julian centuries since J2000.0.
      Returns:
      the Geometric Mean Longitude of the Sun in degrees
    • getSunGeometricMeanAnomaly

      private static double getSunGeometricMeanAnomaly(double julianCenturies)
      Returns the Geometric Mean Anomaly of the Sun in degrees.
      Parameters:
      julianCenturies - the number of Julian centuries since J2000.0.
      Returns:
      the Geometric Mean Anomaly of the Sun in degrees
    • getEarthOrbitEccentricity

      private static double getEarthOrbitEccentricity(double julianCenturies)
      Return the unitless eccentricity of earth's orbit.
      Parameters:
      julianCenturies - the number of Julian centuries since J2000.0.
      Returns:
      the unitless eccentricity
    • getSunEquationOfCenter

      private static double getSunEquationOfCenter(double julianCenturies)
      Returns the equation of center for the sun in degrees.
      Parameters:
      julianCenturies - the number of Julian centuries since J2000.0.
      Returns:
      the equation of center for the sun in degrees
    • getSunTrueLongitude

      private static double getSunTrueLongitude(double julianCenturies)
      Return the true longitude of the sun.
      Parameters:
      julianCenturies - the number of Julian centuries since J2000.0.
      Returns:
      the sun's true longitude in degrees
    • getSunApparentLongitude

      private static double getSunApparentLongitude(double julianCenturies)
      Return the apparent longitude of the sun.
      Parameters:
      julianCenturies - the number of Julian centuries since J2000.0.
      Returns:
      sun's apparent longitude in degrees
    • getMeanObliquityOfEcliptic

      private static double getMeanObliquityOfEcliptic(double julianCenturies)
      Returns the mean obliquity of the ecliptic (Axial tilt).
      Parameters:
      julianCenturies - the number of Julian centuries since J2000.0.
      Returns:
      the mean obliquity in degrees
    • getObliquityCorrection

      private static double getObliquityCorrection(double julianCenturies)
      Returns the corrected obliquity of the ecliptic (Axial tilt).
      Parameters:
      julianCenturies - the number of Julian centuries since J2000.0.
      Returns:
      the corrected obliquity in degrees
    • getSunDeclination

      private static double getSunDeclination(double julianCenturies)
      Return the declination of the sun.
      Parameters:
      julianCenturies - the number of Julian centuries since J2000.0.
      Returns:
      the sun's declination in degrees
    • getEquationOfTime

      private static double getEquationOfTime(double julianCenturies)
      Return the Equation of Time - the difference between true solar time and mean solar time
      Parameters:
      julianCenturies - the number of Julian centuries since J2000.0.
      Returns:
      equation of time in minutes of time
    • getSunHourAngle

      private static double getSunHourAngle(double latitude, double solarDeclination, double zenith, NOAACalculator.SolarEvent solarEvent)
      Return the hour angle of the sun in radians at for the latitude.
      Parameters:
      latitude - the latitude of observer in degrees
      solarDeclination - the declination angle of sun in degrees
      zenith - the zenith
      solarEvent - If the hour angle is for SUNRISE or SUNSET
      Returns:
      hour angle of sunrise in radians
    • getSolarElevation

      public double getSolarElevation(Instant instant, GeoLocation geoLocation)
      Description copied from class: AstronomicalCalculator
      Return the Solar Elevation for the horizontal coordinate system at the given location at the given time. Can be negative if the sun is below the horizon. Not corrected for altitude.
      Specified by:
      getSolarElevation in class AstronomicalCalculator
      Parameters:
      instant - The instant to calculate the elevation for.
      geoLocation - The location information used for astronomical calculation of solar times.
      Returns:
      solar elevation in degrees. The horizon (calculated in a vacuum using the solar radius as the point)is 90°, civil twilight is 96° etc. This means that sunrise and sunset that do use refraction and are calculated from the upper limb of the sun will return about 0.8333°.
    • getSolarAzimuth

      public double getSolarAzimuth(Instant instant, GeoLocation geoLocation)
      Description copied from class: AstronomicalCalculator
      Return the Solar Azimuth for the horizontal coordinate system at the given location at the given time. Not corrected for altitude. True south is 180°.
      Specified by:
      getSolarAzimuth in class AstronomicalCalculator
      Parameters:
      instant - The instant to calculate the azimuth for.
      geoLocation - The location information used for astronomical calculation of solar times.
      Returns:
      the solar azimuth in degrees. Astronomical midday would be 180° in the norther hemosphere and 0° in the southern hemosphere. Depending on the location and time of year, sunrise will have an azimuth of about 90° and sunset about 270°.
    • getSolarElevationAzimuth

      private double getSolarElevationAzimuth(Instant instant, GeoLocation geoLocation, boolean isAzimuth)
      Return the Solar Elevation or Solar Azimuth at the given location and time. Can be negative if the sun is below the horizon. Elevation is based on sea-level and is not adjusted for altitude.
      Parameters:
      instant - date-time of calculation
      geoLocation - The location for calculating the elevation or azimuth.
      isAzimuth - true for azimuth, false for elevation
      Returns:
      solar elevation or azimuth in degrees.
      See Also:
    • adjustElevationForRefraction

      private double adjustElevationForRefraction(double elevation)
      Apply refraction adjustment to solar elevation.
      Parameters:
      elevation - the elevation to adjust.
      Returns:
      the adjusted elevation.
    • getUTCNoon

      public double getUTCNoon(LocalDate localDate, GeoLocation geoLocation)
      Return the Universal Coordinated Time (UTC) of solar noon (UTC) for the given day at the given location. The NOAACalculator, the default calculator implementation calculates true solar noon, something that can be calculated even in the Arctic / Antarctic where there may be no sunrise or sunset, while the SunTimesCalculator approximates it, calculating the time as halfway between sunrise and sunset, something that can't be calculated in Polar regions where there is no sunrise or sunset for part of the year. See The Definition of Chatzos for details on solar noon / midnight calculations.
      Specified by:
      getUTCNoon in class AstronomicalCalculator
      Parameters:
      localDate - The LocalDate representing the date to calculate noon for.
      geoLocation - The location information used for astronomical calculation of solar times.
      Returns:
      The UTC time of solar noon in 24-hour format. 1:45:00 PM will return 13.75. If an error was encountered in the the calculation (expected behavior for some locations such as near the poles, Double.NaN will be returned.
      See Also:
    • getUTCMidnight

      public double getUTCMidnight(LocalDate localDate, GeoLocation geoLocation)
      Return the Universal Coordinated Time (UTC) of solar midnight (UTC) for the given day at the given location. The NOAACalculator, the default calculator implementation calculates true solar midnight, something that can be calculated even in the Arctic / Antarctic where there may be no sunrise or sunset, while the SunTimesCalculator approximates it, calculating the time as 12 hours after halfway between sunrise and sunset, something that can't be calculated in Polar regions where there is no sunrise or sunset for part of the year. See The Definition of Chatzos for details on solar noon / midnight calculations.
      Specified by:
      getUTCMidnight in class AstronomicalCalculator
      Parameters:
      localDate - The LocalDate representing the date to calculate midnight for. The calculation will be for midnight at the end of the day passed in.
      geoLocation - The location information used for astronomical calculation of solar times.
      Returns:
      The UTC time of solar midnight in in a 24-hour double format. 1:45:00 AM will return 1.75. If an error was encountered in the calculation (expected behavior for the SunTimesCalculator at times of the year in Polar regions), Double.NaN will be returned.
      See Also:
    • getSolarNoonMidnightUTC

      private static double getSolarNoonMidnightUTC(double julianDay, double longitude, NOAACalculator.SolarEvent solarEvent)
      Return the Universal Coordinated Time (UTC) of the current day solar noon or the the upcoming midnight (about 12 hours after solar noon) of the given day at the given location on earth.
      Parameters:
      julianDay - The Julian day since J2000.0.
      longitude - The longitude of observer in degrees
      solarEvent - If the calculation is for NOON or MIDNIGHT
      Returns:
      The UTC time of sunset in 24-hour format. 12:45:00 AM will return 0.75 while 1:45:00 PM will return 13.75. If an error was encountered in the calculation (expected behavior for some locations such as near the poles, Double.NaN will be returned.
      See Also:
    • getSunRiseSetUTC

      private static double getSunRiseSetUTC(LocalDate localDate, double latitude, double longitude, double zenith, NOAACalculator.SolarEvent solarEvent)
      Return the Universal Coordinated Time (UTC) of sunrise or sunset in minutes for the given day at the given location on earth.
      Parameters:
      localDate - The LocalDate.
      latitude - The latitude of observer in degrees
      longitude - Longitude of observer in degrees
      zenith - Zenith
      solarEvent - If the calculation is for SUNRISE or SUNSET
      Returns:
      The UTC time of sunrise or sunset in 24-hour format. 5:45:00 AM will return 5.75, while 5:45 PM will return 17.75. If an error was encountered in the calculation (expected behavior for some locations such as near the poles, Double.NaN will be returned.
      TODO:
      Possibly increase the number of passes for improved accuracy, especially in the Arctic areas.
    • getTimeAtAzimuth

      public double getTimeAtAzimuth(LocalDate localDate, GeoLocation geoLocation, double targetAzimuth)
      Returns the time that the azimuth will occur for the date and location passed to this method. As an example, to know when the sun will be directly west, pass in an azimuth of 270°, and for directly east, pass in an azimuth of 90°. The current implementation in this class only supports azimuth values of 90° (directly east) or 270° (directly west) that are directly needed in this library for the ComprehensiveZmanimCalendar.getSunsetOrWesternmostSolarAzimuth() and ComprehensiveZmanimCalendar.getSunriseOrEasternmostSolarAzimuth().
      Specified by:
      getTimeAtAzimuth in class AstronomicalCalculator
      Parameters:
      localDate - The LocalDate representing the date to calculate the time of the azimuth for.
      geoLocation - The location information used for astronomical calculation of solar times.
      targetAzimuth - the azimuth to run the calculation for
      Returns:
      The UTC time that the azimuth will be reached in a 24-hour double format. 5:45:00 PM will return 17.75. If an error was encountered in the calculation (expected behavior for some dates at latitudes below 23.44°, a Double.NaN will be returned.
      Throws:
      IllegalArgumentException - if the azimuth is not 90° or 270°.
      TODO:
      complete the implementation for other azimuths. While not needed by this library, they may be of value to some projects. There will be edge cases where the azimuth will occur more than once a day when based on the equation of time, the day is shorter than 24 hours. In that case, the time for the first one will be returned.