Commit Graph

143 Commits

Author SHA1 Message Date
Don Cross
c85881c25b Python: added metersAboveGround parameter to SearchRiseSet. 2023-03-13 20:42:46 -04:00
Don Cross
6c59d14bd4 Python: added Atmosphere function. 2023-03-13 16:16:53 -04:00
Don Cross
2fcaf27995 Python: verify several thousand calendar dates. 2023-02-26 13:17:21 -05:00
Don Cross
503538da12 PY: Fixed calendar/time conversion functions for extreme year values.
Applying the same recent fixes to C and C# to the Python code.

I'm also changing my philosophy of representing times.
From now on, they will be truncated to the floor millisecond,
not rounded to the nearest millisecond. This means we don't reach
another calendar date until we have had 60 full seconds after
the last minute. Otherwise there is too much nasty logic for
rounding up calendar dates. I will follow suit across all languages.
2023-02-25 22:37:58 -05:00
Don Cross
7e17705801 PY: Fixed calendar calculations for extreme year values. 2023-02-25 14:20:55 -05:00
Don Cross
f849c11258 Require type hints for all Python functions.
I added the mypy option `--disallow-untyped-defs` to fail
any function lacking complete type hints.
Then I fixed all the resulting errors.

I ended up changing the Python code generator to create
some tuple types instead of list, because it is possible
to write stricter type checks that way. This was in
the Pluto and Jupiter Moon tables.
I still should come back and do the same thing for the VSOP tables.

The type checking revealed a couple of places where I wasn't
checking for a search failure. I fixed those too.
2023-02-20 20:04:10 -05:00
Don Cross
9e98d0fb17 PY: Implemented HourAngle function. 2023-02-12 16:20:33 -05:00
Don Cross
8bf48d0681 Slight relaxation of test tolerances.
Contributor @ris-tip ran into erroneous test failures
due to tiny floating point calculation differences.
I'm adjusting the thresholds slightly so his tests will pass.
2023-02-09 08:37:39 -05:00
Don Cross
1a4f842764 Updated Ecliptic to return ECL in all languages. 2022-12-10 19:35:42 -05:00
Don Cross
f959599497 Completed EQJ/ECT, ECT/EQJ rotations. 2022-12-09 13:12:42 -05:00
Don Cross
2dd4fc1ab4 Python: rotations for ECT/EQD. 2022-12-07 13:03:38 -05:00
Don Cross
552c7a5557 EclipticGeoMoon uses true equinox of date in all languages.
Added EclipticGeoMoon as output to the temp/*_check.txt files as 'm' lines.
This ensures that all the languages calculate nearly identical values.

Optimized EclipticGeoMoon a little more by eliminating a redundant
call to mean_obliq.
2022-12-05 21:44:35 -05:00
Don Cross
d3f36b942d Verify nutation angles are consistent across languages. 2022-12-04 14:20:44 -05:00
Don Cross
8a153315cf Simplified and optimized nutation formula.
While trying to convert ecliptic coordinates from mean
equinox of date to true equinox of date, I ran into excessive
overhead from the IAU2000B nutation model. The fact that it
uses 77 trigonometric terms made the calculations a lot slower.

https://apps.dtic.mil/sti/pdfs/AD1112517.pdf
Page 4 in the above document mentions a shorter series
“NOD version 2” that has 13 terms instead of 77 as used in IAU2000B.
I had not noticed NOD2 before, because it appears only in
the FORTRAN version of NOVAS 3.x, not the C version.

After reading the FORTRAN code, I realized NOD2 is the same
as IAU2000B, only it keeps the first 13 of 77 terms.
The terms are already arranged in descending order of
significance, so it is easy to truncate the series.

Based on this discovery, I realized I could achieve all of
the required accuracy needed for Astronomy Engine by
keeping only the first 5 terms of the nutation series.
This tremendously speeds up nutation calculations while
sacrificing only a couple of arcseconds of accuracy.

It also makes the minified JavaScript code smaller:
Before: 119500 bytes.
After:  116653 bytes.

So that's what I did here. Most of the work was updating
unit tests for accepting slightly different calculation
results.

The nutation formula change did trigger detection of a
lurking bug in the inverse_terra functions, which convert
a geocentric vector into latitude, longitude, and elevation
(i.e. an Observer object). The Newton's Method loop in
this function was not always converging, resulting in
an infinite loop. I fixed that by increasing the
convergence threshold and throwing an exception
if the loop iterates more than 10 times.

I also fixed a couple of bugs in the `demotest` scripts.
2022-12-04 10:31:15 -05:00
Don Cross
7b7a306baf Python: Find rise/set/culm of user-defined stars.
Added Python support for user-defined stars.
Defined new StateVector methods: Position and Velocity.
Defined division operator: Vector / float.
Bumped version number to 2.1.12.
2022-11-22 21:42:02 -05:00
Don Cross
351e997a2f Merge branch 'riseset_poles'
Fixed issues with finding rise/set events near the
Earth's poles. Avoid assumptions that rise/set is
tied to hour angles.
2022-11-14 12:05:20 -05:00
Don Cross
1b52e91394 Python: overhauled altitude search 2022-11-13 22:17:06 -05:00
Don Cross
5eca7d7760 CodeQL tweaks and fixes.
Updated CodeQL config to ignore source templates,
because they are not syntactically valid source code.
Ignore other stuff that is irrelevant to published
code quality.

Made various fixes based on helpful CodeQL analysis.
2022-11-07 15:31:05 -05:00
Don Cross
23fd95a53f PY: Added PlanetOrbitalPeriod function. 2022-11-01 17:30:48 -04:00
Don Cross
06b62887d2 Kotlin: obscuration for solar, lunar eclipses. 2022-10-20 17:31:21 -04:00
Don Cross
393f134c49 PY: solar eclipse obscuration
Also fixed missing improvements to C# PlanetShadow().
2022-10-20 12:32:11 -04:00
Don Cross
a90edfed0d PY: lunar eclipse obscuration 2022-10-19 20:44:22 -04:00
Don Cross
99db293317 PY Elongation test: better coding pattern. 2022-10-19 19:37:04 -04:00
Don Cross
1e95f0656b C, C#, Python: Support formatting calendar years -999999 to +999999. 2022-10-06 16:28:55 -04:00
Don Cross
409e490728 Python: No longer limited to years 0000..9999.
I ported the NOVAS C 3.1 functions julian_date and cal_date to Python,
and removed the dependence on the standard datetime class for calculating UT.
Now we can create Time objects for a much wider range of year values.

Simplified the julian_date formula in C and C#.

In the Python version, I had to account for a difference
in the way integer division works for negative numbers.
In Python, integer division always rounds down, not toward
zero like it does in C/C#. So I reworked the formulas to
avoid dividing a negative integer (month-14), dividing the
positive quantity (14-month) instead and toggling addition
of the term with subtraction of the term.

I use the reworked (14-month) version in C and C# for consistency.
Also, the formatting of the formula was wacky and didn't make sense,
so now it easier to read and understand.

The Python regex for parsing dates has been expanded to allow
years before 0 and after 9999.
Allow converting Python Time to string for years before 0 and after 9999.
2022-10-06 10:56:17 -04:00
Don Cross
dc59b55d92 Added more testing of rise/set foreward/backward searches. 2022-10-02 19:58:48 -04:00
Don Cross
6e2229603c Fixed wording, variable names in unit tests. 2022-10-02 12:33:20 -04:00
Don Cross
a3337348f5 Kotlin: better forward/reverse moon phase tests.
In the unit tests for searching forward and backward
for moon phases, in addition to new moons, also test
first quarter, full moon, and third quarter.

Verify that forward and backward searches work for
100 start times between a single pair of consecutive events.
2022-10-02 10:49:36 -04:00
Don Cross
f0b7b64a4b Python: better forward/reverse moon phase tests.
In the unit tests for searching forward and backward
for moon phases, in addition to new moons, also test
first quarter, full moon, and third quarter.

Verify that forward and backward searches work for
100 start times between a single pair of consecutive events.
2022-10-02 10:13:43 -04:00
Don Cross
b91b1d905f Python: Reverse chrono search for rise/set, hour angles.
The following Python functions now support searching
in forward or reverse chronological order:

    SearchRiseSet
    SearchAltitude
    SearchHourAngle

Made some minor performance improvements to the
other implementations: return sooner if we
go past time window.
2022-10-01 21:44:04 -04:00
Don Cross
3bed4a9bdc PY SearchMoonPhase: allow searching backward in time.
Enhanced the Python function SearchMoonPhase
to allow searching forward in time when the `limitDays`
argument is positive, or backward in time when `limitDays`
is negative.

Added unit test "moon_reverse" to verify this new feature.
2022-09-26 21:08:37 -04:00
Don Cross
d28f5ecff3 PY gravsim: passes unit tests
The Python version of the GravitySimulator class
is now passing all unit tests. This completes
the initial coding. I still need to review
documentation across all the language implementations.
2022-05-22 21:16:58 -04:00
Don Cross
66eeb3e0a0 Python: Jupiter's moons returned by name
It makes more sense to report Jupiter's moons with
individually named structure fields rather than an array.
It reduces the overall code and documentation size,
and outside of unit testing, there are few cases
where iterating over an array of moons is more
lucid than using the names of the moons.

This is a breaking change, but hopefully very few
developers are using this function yet.
Fixing the breakage is very simple.

Also added operator overloads for adding and
subtracting StateVector, just like we already had
for Vector.
2022-05-05 12:39:39 -04:00
Don Cross
8696241c90 Kotlin: search for planet aphelion/perihelion.
Added functions:

    searchPlanetApsis
    nextPlanetApsis

I discovered that I had an unnecessary special relaxation
of apsis error tolerance for Pluto. It turns out that currently
0.1 degrees of orbital rotation is enough for all the planets.
2022-04-24 20:55:51 -04:00
Don Cross
a6e72a2423 Kotlin: search for lunar nodes.
Search for times when the Moon ascends or descends
through the ecliptic plane. These are called
ascending and descending nodes. Added the functions:

    searchMoonNode
    nextMoonNode

Also corrected comments in the unit tests that
incorrectly stated nodes occur when the ecliptic
longitude is zero. They should have said the
ecliptic latitude is zero.
2022-04-23 20:34:52 -04:00
Don Cross
3ce32f8819 Kotlin: lunar libration. Fixes for other languages.
The existing lunar libration functions in the
other languages (C, C#, Python, JavaScript) were
calculating the Moon's ecliptic latitude and longitude
in radians, not degrees as intended. They have been fixed.

Implemented the libration function for Kotlin.
2022-04-22 16:36:14 -04:00
Don Cross
ef6af40b0d Kotlin: added maximum elongation search.
Added searchMaxElongation function, which finds the
next time Mercury or Venus reaches is maximum angular
separation from the Sun.
2022-04-18 13:03:08 -04:00
Don Cross
16578935ad Kotlin: implemented relative longitude search.
Implemented searchRelativeLongitude, which finds
planetary conjunctions and oppositions.
Discovered I can make all languages' unit tests
more strict: 6.8 minute error tolerance instead of 15.

Fixed documentation mistake in C# function SearchRelativeLongitude:
the function cannot return null. It either finds a solution time
or throws an exception.

Simplified Kotlin unit tests: use a more compact pattern of
scanning space-delimited tokens in lines.
2022-04-17 12:22:07 -04:00
Don Cross
0d24433db3 Fixed #187 - Seasons() failed for distant years.
For years before 1582 or years after 3668, the Seasons functions
were unable to find many equinoxes and/or solstices.
The problem was that over time, the Earth's axis precesses
enough that the calendar dates of these events drifts outside
the fixed search ranges I had provided for them.

I expanded the search ranges so all season changes can be found
for a much wider range of years, as verified by unit tests:

    C/C++:      -2000..9999
    C#:             1..9999
    JavaScript: -2000..9999
    Python:         1..9999
    Kotlin:         1..9999

Note: C#, Python, and Kotlin currently do not allow
years values below +1. In fact, I discovered we were not
noticing when an invalid year was passed into the Kotlin code.
I updated that code to throw an exception when the year does
not match what was expected. It is disturbing that the
GregorianCalendar class silently ignores invalid years!

Constricted the search tolerance from 1 second to 0.01
seconds for the seasons search, to ensure more consistent
behavior.

Fixed a bug in the Kotlin search() function's
quadratic interpolation that was causing the convergence
to be slower than it should have been.
2022-04-08 16:51:09 -04:00
Don Cross
94c7884f11 Kotlin: added moon phase and search functions.
Added the following Kotlin functions:

    equatorialToEcliptic
    pairLongitude
    moonPhase
    searchMoonPhase
    searchMoonQuarter
    nextMoonQuarter

Discovered I could tighten the tolerance for the moon phase
unit tests from 120 seconds to 90 seconds and they still pass.
2022-04-05 17:33:19 -04:00
Don Cross
12ae8291a2 Merge branch 'master' into kotlin
Bringing over Python fixes:
- Better string representations of classes.
- A few documentation fixes.
2022-03-31 23:06:58 -04:00
Don Cross
608a7a8dca Fixed #184 - repr for Python classes
Defined consistent __repr__ methods for
Astronomy Engine Python classes.
Each string representation is reversible:

eval(repr(x)) -> x

The main goal is to facilitate interactive
debugging and experimentation for developers
working directly in the Python interpreter.

Fixed documentation mistakes in the following classes:
    IlluminationInfo
    LunarEclipseInfo
2022-03-31 22:47:59 -04:00
Don Cross
9b4223193b Kotlin: sidereal time
Implemented Astronomy.siderealTime() in Kotlin.

Updated all languages' unit tests for sidereal time
to verify exact conformity between them, rather than
to an externally derived value. I wanted to make
sure all languages, including Kotlin, are calculating
the exact same value.

I don't need an external authoritative test for
sidereal time, because it will be indirectly tested
through its involvement in thousands of other calculations
that depend on it. I just need a quick sanity check
before implementing those other things that depend on it.
2022-03-26 02:07:15 -04:00
Don Cross
74044b39d3 More Python/pip package cleanup : version 2.0.17.
Generate astronomy.py directly in the package directory.
I realized it doesn't make sense to generate it in the
parent directory and then copy it; just generate it where
it will end up anyway.

Updated documentation so people know they can just do

    pip install astronomy-engine

to install Astronomy Engine in their Python project.

Removed the GitHub Actions status badge because it is redundant with
the checkmark/X indicator.

Now that private symbols are no longer exported, I had to
fix a couple of places where the unit tests still accessed them.
2022-03-20 16:47:29 -04:00
Don Cross
0943f058c9 Fixed #165 - expose sidereal time function.
There was already an internal function for calculating
Greenwich Apparent Sidereal Time (GAST). By request,
I have exposed this function for outside users.

Added a minimal unit test to verify the function is
callable and returns the correct result for one case.
This function is already exhaustively tested by unit
tests that verify other functions that already called
this function when it was internal, so minimal testing
is sufficient in this case.
2022-03-15 20:48:02 -04:00
Don Cross
d843775122 Fixed #148 - calculate Lagrange points.
Added the following new functions to all 4 languages:

MassProduct: find the GM product for all Solar System bodies.

LagrangePoint: calculate L1..L5 state vectors for a pair of bodies.

LagrangePointFast: calculate L1..L5 state vectors given
state vectors and GM products of a pair of bodies.
2022-03-13 20:56:32 -04:00
Don Cross
b773834349 Implemented Python Lagrange point calculation. 2022-03-13 17:47:40 -04:00
Don Cross
13413f2754 Prep Python unit tests for Lagrange.
Reworked the Python state vector unit tests so that they will
be ready for adding Lagrange point tests, which require
additional parameters.
2022-03-13 09:45:48 -04:00
Don Cross
6f9c906061 PY EclipticGeoMoon, SearchMoonNode, NextMoonNode. 2022-02-06 19:55:24 -05:00
Don Cross
785bfc456a Python MoonNode test: loading test data 2022-02-06 17:04:41 -05:00