summaryrefslogtreecommitdiff
path: root/Build/source/libs/icu/icu-xetex/test/intltest/astrotst.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'Build/source/libs/icu/icu-xetex/test/intltest/astrotst.cpp')
-rw-r--r--Build/source/libs/icu/icu-xetex/test/intltest/astrotst.cpp436
1 files changed, 436 insertions, 0 deletions
diff --git a/Build/source/libs/icu/icu-xetex/test/intltest/astrotst.cpp b/Build/source/libs/icu/icu-xetex/test/intltest/astrotst.cpp
new file mode 100644
index 00000000000..ba7b5711396
--- /dev/null
+++ b/Build/source/libs/icu/icu-xetex/test/intltest/astrotst.cpp
@@ -0,0 +1,436 @@
+/********************************************************************
+ * COPYRIGHT:
+ * Copyright (c) 1996-2006, International Business Machines Corporation and
+ * others. All Rights Reserved.
+ ********************************************************************/
+
+/* Test CalendarAstronomer for C++ */
+
+#include "unicode/utypes.h"
+#include "string.h"
+#include "unicode/locid.h"
+
+#if !UCONFIG_NO_FORMATTING
+
+#include "astro.h"
+#include "astrotst.h"
+#include "gregoimp.h" // for Math
+#include "unicode/simpletz.h"
+
+
+static const double DAY_MS = 24.*60.*60.*1000.;
+
+#define CASE(id,test) case id: name = #test; if (exec) { logln(#test "---"); logln((UnicodeString)""); test(); } break
+
+AstroTest::AstroTest(): astro(NULL), gc(NULL) {
+}
+
+void AstroTest::runIndexedTest( int32_t index, UBool exec, const char* &name, char* /*par*/ )
+{
+ if (exec) logln("TestSuite AstroTest");
+ switch (index) {
+ // CASE(0,FooTest);
+ CASE(0,TestSolarLongitude);
+ CASE(1,TestLunarPosition);
+ CASE(2,TestCoordinates);
+ CASE(3,TestCoverage);
+ CASE(4,TestSunriseTimes);
+ CASE(5,TestBasics);
+ default: name = ""; break;
+ }
+}
+
+#undef CASE
+
+#define ASSERT_OK(x) if(U_FAILURE(x)) { errln("%s:%d: %s\n", __FILE__, __LINE__, u_errorName(x)); return; }
+
+
+void AstroTest::initAstro(UErrorCode &status) {
+ if(U_FAILURE(status)) return;
+
+ if((astro != NULL) || (gc != NULL)) {
+ errln("Err: initAstro() called twice!");
+ closeAstro(status);
+ if(U_SUCCESS(status)) {
+ status = U_INTERNAL_PROGRAM_ERROR;
+ }
+ }
+
+ if(U_FAILURE(status)) return;
+
+ astro = new CalendarAstronomer();
+ gc = Calendar::createInstance(TimeZone::getGMT()->clone(), status);
+}
+
+void AstroTest::closeAstro(UErrorCode &/*status*/) {
+ if(astro != NULL) {
+ delete astro;
+ astro = NULL;
+ }
+ if(gc != NULL) {
+ delete gc;
+ gc = NULL;
+ }
+}
+
+void AstroTest::TestSolarLongitude(void) {
+ UErrorCode status = U_ZERO_ERROR;
+ initAstro(status);
+ ASSERT_OK(status);
+
+ struct {
+ int32_t d[5]; double f ;
+ } tests[] = {
+ { { 1980, 7, 27, 0, 00 }, 124.114347 },
+ { { 1988, 7, 27, 00, 00 }, 124.187732 }
+ };
+
+ logln("");
+ for (uint32_t i = 0; i < sizeof(tests)/sizeof(tests[0]); i++) {
+ gc->clear();
+ gc->set(tests[i].d[0], tests[i].d[1]-1, tests[i].d[2], tests[i].d[3], tests[i].d[4]);
+
+ astro->setDate(gc->getTime(status));
+
+ double longitude = astro->getSunLongitude();
+ //longitude = 0;
+ CalendarAstronomer::Equatorial result;
+ astro->getSunPosition(result);
+ logln((UnicodeString)"Sun position is " + result.toString() + (UnicodeString)"; " /* + result.toHmsString()*/ + " Sun longitude is " + longitude );
+ }
+ closeAstro(status);
+ ASSERT_OK(status);
+}
+
+
+
+void AstroTest::TestLunarPosition(void) {
+ UErrorCode status = U_ZERO_ERROR;
+ initAstro(status);
+ ASSERT_OK(status);
+
+ static const double tests[][7] = {
+ { 1979, 2, 26, 16, 00, 0, 0 }
+ };
+ logln("");
+
+ for (int32_t i = 0; i < (int32_t)(sizeof(tests)/sizeof(tests[0])); i++) {
+ gc->clear();
+ gc->set((int32_t)tests[i][0], (int32_t)tests[i][1]-1, (int32_t)tests[i][2], (int32_t)tests[i][3], (int32_t)tests[i][4]);
+ astro->setDate(gc->getTime(status));
+
+ const CalendarAstronomer::Equatorial& result = astro->getMoonPosition();
+ logln((UnicodeString)"Moon position is " + result.toString() + (UnicodeString)"; " /* + result->toHmsString()*/);
+ }
+
+ closeAstro(status);
+ ASSERT_OK(status);
+}
+
+
+
+void AstroTest::TestCoordinates(void) {
+ UErrorCode status = U_ZERO_ERROR;
+ initAstro(status);
+ ASSERT_OK(status);
+
+ CalendarAstronomer::Equatorial result;
+ astro->eclipticToEquatorial(result, 139.686111 * CalendarAstronomer::PI / 180.0, 4.875278* CalendarAstronomer::PI / 180.0);
+ logln((UnicodeString)"result is " + result.toString() + (UnicodeString)"; " /* + result.toHmsString()*/ );
+ closeAstro(status);
+ ASSERT_OK(status);
+}
+
+
+
+void AstroTest::TestCoverage(void) {
+ UErrorCode status = U_ZERO_ERROR;
+ initAstro(status);
+ ASSERT_OK(status);
+ GregorianCalendar *cal = new GregorianCalendar(1958, UCAL_AUGUST, 15,status);
+ UDate then = cal->getTime(status);
+ CalendarAstronomer *myastro = new CalendarAstronomer(then);
+ ASSERT_OK(status);
+
+ //Latitude: 34 degrees 05' North
+ //Longitude: 118 degrees 22' West
+ double laLat = 34 + 5./60, laLong = 360 - (118 + 22./60);
+ CalendarAstronomer *myastro2 = new CalendarAstronomer(laLong, laLat);
+
+ double eclLat = laLat * CalendarAstronomer::PI / 360;
+ double eclLong = laLong * CalendarAstronomer::PI / 360;
+
+ CalendarAstronomer::Ecliptic ecl(eclLat, eclLong);
+ CalendarAstronomer::Equatorial eq;
+ CalendarAstronomer::Horizon hor;
+
+ logln("ecliptic: " + ecl.toString());
+ CalendarAstronomer *myastro3 = new CalendarAstronomer();
+ myastro3->setJulianDay((4713 + 2000) * 365.25);
+
+ CalendarAstronomer *astronomers[] = {
+ myastro, myastro2, myastro3, myastro2 // check cache
+ };
+
+ for (uint32_t i = 0; i < sizeof(astronomers)/sizeof(astronomers[0]); ++i) {
+ CalendarAstronomer *anAstro = astronomers[i];
+
+ //logln("astro: " + astro);
+ logln((UnicodeString)" date: " + anAstro->getTime());
+ logln((UnicodeString)" cent: " + anAstro->getJulianCentury());
+ logln((UnicodeString)" gw sidereal: " + anAstro->getGreenwichSidereal());
+ logln((UnicodeString)" loc sidereal: " + anAstro->getLocalSidereal());
+ logln((UnicodeString)" equ ecl: " + (anAstro->eclipticToEquatorial(eq,ecl)).toString());
+ logln((UnicodeString)" equ long: " + (anAstro->eclipticToEquatorial(eq, eclLong)).toString());
+ logln((UnicodeString)" horiz: " + (anAstro->eclipticToHorizon(hor, eclLong)).toString());
+ logln((UnicodeString)" sunrise: " + (anAstro->getSunRiseSet(TRUE)));
+ logln((UnicodeString)" sunset: " + (anAstro->getSunRiseSet(FALSE)));
+ logln((UnicodeString)" moon phase: " + anAstro->getMoonPhase());
+ logln((UnicodeString)" moonrise: " + (anAstro->getMoonRiseSet(TRUE)));
+ logln((UnicodeString)" moonset: " + (anAstro->getMoonRiseSet(FALSE)));
+ logln((UnicodeString)" prev summer solstice: " + (anAstro->getSunTime(CalendarAstronomer::SUMMER_SOLSTICE(), FALSE)));
+ logln((UnicodeString)" next summer solstice: " + (anAstro->getSunTime(CalendarAstronomer::SUMMER_SOLSTICE(), TRUE)));
+ logln((UnicodeString)" prev full moon: " + (anAstro->getMoonTime(CalendarAstronomer::FULL_MOON(), FALSE)));
+ logln((UnicodeString)" next full moon: " + (anAstro->getMoonTime(CalendarAstronomer::FULL_MOON(), TRUE)));
+ }
+
+ delete myastro2;
+ delete myastro3;
+ delete myastro;
+ delete cal;
+
+ closeAstro(status);
+ ASSERT_OK(status);
+}
+
+
+
+void AstroTest::TestSunriseTimes(void) {
+ UErrorCode status = U_ZERO_ERROR;
+ initAstro(status);
+ ASSERT_OK(status);
+
+ // logln("Sunrise/Sunset times for San Jose, California, USA");
+ // CalendarAstronomer *astro2 = new CalendarAstronomer(-121.55, 37.20);
+ // TimeZone *tz = TimeZone::createTimeZone("America/Los_Angeles");
+
+ // We'll use a table generated by the UNSO website as our reference
+ // From: http://aa.usno.navy.mil/
+ //-Location: W079 25, N43 40
+ //-Rise and Set for the Sun for 2001
+ //-Zone: 4h West of Greenwich
+ int32_t USNO[] = {
+ 6,59, 19,45,
+ 6,57, 19,46,
+ 6,56, 19,47,
+ 6,54, 19,48,
+ 6,52, 19,49,
+ 6,50, 19,51,
+ 6,48, 19,52,
+ 6,47, 19,53,
+ 6,45, 19,54,
+ 6,43, 19,55,
+ 6,42, 19,57,
+ 6,40, 19,58,
+ 6,38, 19,59,
+ 6,36, 20, 0,
+ 6,35, 20, 1,
+ 6,33, 20, 3,
+ 6,31, 20, 4,
+ 6,30, 20, 5,
+ 6,28, 20, 6,
+ 6,27, 20, 7,
+ 6,25, 20, 8,
+ 6,23, 20,10,
+ 6,22, 20,11,
+ 6,20, 20,12,
+ 6,19, 20,13,
+ 6,17, 20,14,
+ 6,16, 20,16,
+ 6,14, 20,17,
+ 6,13, 20,18,
+ 6,11, 20,19,
+ };
+
+ logln("Sunrise/Sunset times for Toronto, Canada");
+ // long = 79 25", lat = 43 40"
+ CalendarAstronomer *astro3 = new CalendarAstronomer(-(79+25/60), 43+40/60);
+
+ // As of ICU4J 2.8 the ICU4J time zones implement pass-through
+ // to the underlying JDK. Because of variation in the
+ // underlying JDKs, we have to use a fixed-offset
+ // SimpleTimeZone to get consistent behavior between JDKs.
+ // The offset we want is [-18000000, 3600000] (raw, dst).
+ // [aliu 10/15/03]
+
+ // TimeZone tz = TimeZone.getTimeZone("America/Montreal");
+ TimeZone *tz = new SimpleTimeZone(-18000000 + 3600000, "Montreal(FIXED)");
+
+ GregorianCalendar *cal = new GregorianCalendar(tz->clone(), Locale::getUS(), status);
+ GregorianCalendar *cal2 = new GregorianCalendar(tz->clone(), Locale::getUS(), status);
+ cal->clear();
+ cal->set(UCAL_YEAR, 2001);
+ cal->set(UCAL_MONTH, UCAL_APRIL);
+ cal->set(UCAL_DAY_OF_MONTH, 1);
+ cal->set(UCAL_HOUR_OF_DAY, 12); // must be near local noon for getSunRiseSet to work
+
+ DateFormat *df_t = DateFormat::createTimeInstance(DateFormat::MEDIUM,Locale::getUS());
+ DateFormat *df_d = DateFormat::createDateInstance(DateFormat::MEDIUM,Locale::getUS());
+ DateFormat *df_dt = DateFormat::createDateTimeInstance(DateFormat::MEDIUM, DateFormat::MEDIUM, Locale::getUS());
+ if(!df_t || !df_d || !df_dt) {
+ errln("couldn't create dateformats.");
+ return;
+ }
+ df_t->adoptTimeZone(tz->clone());
+ df_d->adoptTimeZone(tz->clone());
+ df_dt->adoptTimeZone(tz->clone());
+
+ for (int32_t i=0; i < 30; i++) {
+ logln("setDate\n");
+ astro3->setDate(cal->getTime(status));
+ logln("getRiseSet(TRUE)\n");
+ UDate sunrise = astro3->getSunRiseSet(TRUE);
+ logln("getRiseSet(FALSE)\n");
+ UDate sunset = astro3->getSunRiseSet(FALSE);
+ logln("end of getRiseSet\n");
+
+ cal2->setTime(cal->getTime(status), status);
+ cal2->set(UCAL_SECOND, 0);
+ cal2->set(UCAL_MILLISECOND, 0);
+
+ cal2->set(UCAL_HOUR_OF_DAY, USNO[4*i+0]);
+ cal2->set(UCAL_MINUTE, USNO[4*i+1]);
+ UDate exprise = cal2->getTime(status);
+ cal2->set(UCAL_HOUR_OF_DAY, USNO[4*i+2]);
+ cal2->set(UCAL_MINUTE, USNO[4*i+3]);
+ UDate expset = cal2->getTime(status);
+ // Compute delta of what we got to the USNO data, in seconds
+ int32_t deltarise = (int32_t)uprv_fabs((sunrise - exprise) / 1000);
+ int32_t deltaset = (int32_t)uprv_fabs((sunset - expset) / 1000);
+
+ // Allow a deviation of 0..MAX_DEV seconds
+ // It would be nice to get down to 60 seconds, but at this
+ // point that appears to be impossible without a redo of the
+ // algorithm using something more advanced than Duffett-Smith.
+ int32_t MAX_DEV = 180;
+ UnicodeString s1, s2, s3, s4, s5;
+ if (deltarise > MAX_DEV || deltaset > MAX_DEV) {
+ if (deltarise > MAX_DEV) {
+ errln("FAIL: (rise) " + df_d->format(cal->getTime(status),s1) +
+ ", Sunrise: " + df_dt->format(sunrise, s2) +
+ " (USNO " + df_t->format(exprise,s3) +
+ " d=" + deltarise + "s)");
+ } else {
+ logln(df_d->format(cal->getTime(status),s1) +
+ ", Sunrise: " + df_dt->format(sunrise,s2) +
+ " (USNO " + df_t->format(exprise,s3) + ")");
+ }
+ s1.remove(); s2.remove(); s3.remove(); s4.remove(); s5.remove();
+ if (deltaset > MAX_DEV) {
+ errln("FAIL: (set) " + df_d->format(cal->getTime(status),s1) +
+ ", Sunset: " + df_dt->format(sunset,s2) +
+ " (USNO " + df_t->format(expset,s3) +
+ " d=" + deltaset + "s)");
+ } else {
+ logln(df_d->format(cal->getTime(status),s1) +
+ ", Sunset: " + df_dt->format(sunset,s2) +
+ " (USNO " + df_t->format(expset,s3) + ")");
+ }
+ } else {
+ logln(df_d->format(cal->getTime(status),s1) +
+ ", Sunrise: " + df_dt->format(sunrise,s2) +
+ " (USNO " + df_t->format(exprise,s3) + ")" +
+ ", Sunset: " + df_dt->format(sunset,s4) +
+ " (USNO " + df_t->format(expset,s5) + ")");
+ }
+ cal->add(UCAL_DATE, 1, status);
+ }
+
+ // CalendarAstronomer a = new CalendarAstronomer(-(71+5/60), 42+37/60);
+ // cal.clear();
+ // cal.set(cal.YEAR, 1986);
+ // cal.set(cal.MONTH, cal.MARCH);
+ // cal.set(cal.DATE, 10);
+ // cal.set(cal.YEAR, 1988);
+ // cal.set(cal.MONTH, cal.JULY);
+ // cal.set(cal.DATE, 27);
+ // a.setDate(cal.getTime());
+ // long r = a.getSunRiseSet2(true);
+ delete astro3;
+ delete tz;
+ delete cal;
+ delete cal2;
+ delete df_t;
+ delete df_d;
+ delete df_dt;
+ closeAstro(status);
+ ASSERT_OK(status);
+}
+
+
+
+void AstroTest::TestBasics(void) {
+ UErrorCode status = U_ZERO_ERROR;
+ initAstro(status);
+ ASSERT_OK(status);
+
+ // Check that our JD computation is the same as the book's (p. 88)
+ GregorianCalendar *cal3 = new GregorianCalendar(TimeZone::getGMT()->clone(), Locale::getUS(), status);
+ DateFormat *d3 = DateFormat::createDateTimeInstance(DateFormat::MEDIUM,DateFormat::MEDIUM,Locale::getUS());
+ d3->setTimeZone(*TimeZone::getGMT());
+ cal3->clear();
+ cal3->set(UCAL_YEAR, 1980);
+ cal3->set(UCAL_MONTH, UCAL_JULY);
+ cal3->set(UCAL_DATE, 2);
+ logln("cal3[a]=%.1lf, d=%d\n", cal3->getTime(status), cal3->get(UCAL_JULIAN_DAY,status));
+ {
+ UnicodeString s;
+ logln(UnicodeString("cal3[a] = ") + d3->format(cal3->getTime(status),s));
+ }
+ cal3->clear();
+ cal3->set(UCAL_YEAR, 1980);
+ cal3->set(UCAL_MONTH, UCAL_JULY);
+ cal3->set(UCAL_DATE, 27);
+ logln("cal3=%.1lf, d=%d\n", cal3->getTime(status), cal3->get(UCAL_JULIAN_DAY,status));
+
+ ASSERT_OK(status);
+ {
+ UnicodeString s;
+ logln(UnicodeString("cal3 = ") + d3->format(cal3->getTime(status),s));
+ }
+ astro->setTime(cal3->getTime(status));
+ double jd = astro->getJulianDay() - 2447891.5;
+ double exp = -3444.;
+ if (jd == exp) {
+ UnicodeString s;
+ logln(d3->format(cal3->getTime(status),s) + " => " + jd);
+ } else {
+ UnicodeString s;
+ errln("FAIL: " + d3->format(cal3->getTime(status), s) + " => " + jd +
+ ", expected " + exp);
+ }
+
+ // cal3.clear();
+ // cal3.set(cal3.YEAR, 1990);
+ // cal3.set(cal3.MONTH, Calendar.JANUARY);
+ // cal3.set(cal3.DATE, 1);
+ // cal3.add(cal3.DATE, -1);
+ // astro.setDate(cal3.getTime());
+ // astro.foo();
+
+ delete cal3;
+ delete d3;
+ ASSERT_OK(status);
+ closeAstro(status);
+ ASSERT_OK(status);
+
+}
+
+
+// TODO: try finding next new moon after 07/28/1984 16:00 GMT
+
+
+#endif
+
+
+