@hebcal/noaa 0.8.16 → 0.9.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.ts CHANGED
@@ -116,7 +116,7 @@ export declare class NOAACalculator {
116
116
  * The zenith of astronomical sunrise and sunset. The sun is 90° from the vertical 0°
117
117
  * @private
118
118
  */
119
- private static readonly GEOMETRIC_ZENITH;
119
+ protected static readonly GEOMETRIC_ZENITH: number;
120
120
  /**
121
121
  * Default value for Sun's zenith and true rise/set Zenith (used in this class and subclasses) is the angle that the
122
122
  * center of the Sun makes to a line perpendicular to the Earth's surface. If the Sun were a point and the Earth
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@hebcal/noaa",
3
- "version": "0.8.16",
3
+ "version": "0.9.1",
4
4
  "description": "sunrise and sunset via NOAA algorithm with elevation, based on KosherJava",
5
5
  "author": "Michael J. Radwin (https://github.com/mjradwin)",
6
6
  "contributors": [
@@ -8,26 +8,25 @@
8
8
  "Eliyahu Hershfeld (https://github.com/KosherJava)",
9
9
  "Benny Powers (https://github.com/bennypowers)"
10
10
  ],
11
- "license": "LGPL-3.0",
11
+ "license": "LGPL-2.1",
12
12
  "repository": {
13
13
  "type": "git",
14
14
  "url": "git+https://github.com/hebcal/noaa.git"
15
15
  },
16
- "main": "dist/index.cjs",
17
- "module": "dist/index.mjs",
16
+ "bugs": {
17
+ "url": "https://github.com/hebcal/noaa/issues"
18
+ },
19
+ "homepage": "https://hebcal.github.io/api/noaa/",
20
+ "module": "dist/index.js",
18
21
  "typings": "dist/index.d.ts",
19
22
  "type": "module",
20
23
  "exports": {
21
- "import": "./dist/index.mjs",
22
- "require": "./dist/index.cjs",
23
- "types": "./dist/index.d.ts"
24
+ ".": "./dist/index.js"
24
25
  },
25
26
  "scripts": {
26
27
  "docs": "typedoc",
27
28
  "test": "ava",
28
- "build": "npm run build:cjs && mv dist/index.js dist/index.cjs && npm run build:es6 && mv dist/index.js dist/index.mjs",
29
- "build:cjs": "tsc -p ./tsconfig-cjs.json",
30
- "build:es6": "tsc",
29
+ "build": "tsc",
31
30
  "clean": "gts clean",
32
31
  "fix": "gts fix",
33
32
  "prepare": "npm run build",
@@ -44,13 +43,13 @@
44
43
  "dist/*"
45
44
  ],
46
45
  "devDependencies": {
47
- "@types/node": "22.10.2",
46
+ "@types/node": "22.13.14",
48
47
  "ava": "^6.2.0",
49
48
  "gts": "^5.3.1",
50
- "typedoc": "^0.27.4",
51
- "typescript": "^5.7.2"
49
+ "typedoc": "^0.28.1",
50
+ "typescript": "^5.8.2"
52
51
  },
53
52
  "dependencies": {
54
- "temporal-polyfill": "^0.2.5"
53
+ "temporal-polyfill": "^0.3.0"
55
54
  }
56
55
  }
package/dist/index.cjs DELETED
@@ -1,1102 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.NOAACalculator = exports.GeoLocation = void 0;
4
- require("temporal-polyfill/global");
5
- /**
6
- * java.lang.Math.toRadians
7
- * @private
8
- * @param degrees
9
- */
10
- function degreesToRadians(degrees) {
11
- return (degrees * Math.PI) / 180;
12
- }
13
- /**
14
- * java.lang.Math.toDegrees
15
- * @private
16
- * @param radians
17
- */
18
- function radiansToDegrees(radians) {
19
- return (radians * 180) / Math.PI;
20
- }
21
- /**
22
- * A class that contains location information such as latitude and longitude required for astronomical calculations. The
23
- * elevation field may not be used by some calculation engines and would be ignored if set.
24
- *
25
- * @author © Eliyahu Hershfeld 2004 - 2016
26
- * @version 1.1
27
- */
28
- class GeoLocation {
29
- /**
30
- * GeoLocation constructor with parameters for all required fields.
31
- *
32
- * @param {string} name
33
- * The location name for display use such as "Lakewood, NJ"
34
- * @param {number} latitude
35
- * the latitude in a double format such as 40.095965 for Lakewood, NJ.
36
- * <b>Note: </b> For latitudes south of the equator, a negative value should be used.
37
- * @param {number} longitude
38
- * double the longitude in a double format such as -74.222130 for Lakewood, NJ.
39
- * <b>Note: </b> For longitudes west of the <a href="http://en.wikipedia.org/wiki/Prime_Meridian">Prime
40
- * Meridian </a> (Greenwich), a negative value should be used.
41
- * @param {number} elevation
42
- * the elevation above sea level in Meters. Elevation is not used in most algorithms used for calculating
43
- * sunrise and set.
44
- * @param {string} timeZoneId
45
- * the <code>TimeZone</code> for the location.
46
- */
47
- constructor(name, latitude, longitude, elevation, timeZoneId) {
48
- /**
49
- * @private
50
- */
51
- this.locationName = null;
52
- this.setLocationName(name);
53
- this.setLatitude(latitude);
54
- this.setLongitude(longitude);
55
- this.setElevation(elevation);
56
- this.setTimeZone(timeZoneId);
57
- }
58
- /**
59
- * Method to get the elevation in Meters.
60
- *
61
- * @return {number} Returns the elevation in Meters.
62
- */
63
- getElevation() {
64
- return this.elevation;
65
- }
66
- /**
67
- * Method to set the elevation in Meters <b>above </b> sea level.
68
- *
69
- * @param {number} elevation
70
- * The elevation to set in Meters. An Error will be thrown if the value is a negative.
71
- */
72
- setElevation(elevation) {
73
- if (typeof elevation !== 'number')
74
- throw new TypeError('Invalid elevation');
75
- if (elevation < 0) {
76
- throw new RangeError(`elevation ${elevation} must be zero or positive`);
77
- }
78
- this.elevation = elevation;
79
- }
80
- setLatitude(latitude) {
81
- if (typeof latitude !== 'number')
82
- throw new TypeError('Invalid latitude');
83
- if (latitude < -90 || latitude > 90) {
84
- throw new RangeError(`Latitude ${latitude} out of range [-90,90]`);
85
- }
86
- this.latitude = latitude;
87
- }
88
- /**
89
- * @return {number} Returns the latitude.
90
- */
91
- getLatitude() {
92
- return this.latitude;
93
- }
94
- setLongitude(longitude) {
95
- if (typeof longitude !== 'number')
96
- throw new TypeError('Invalid longitude');
97
- if (longitude < -180 || longitude > 180) {
98
- throw new RangeError(`Longitude ${longitude} out of range [-180,180]`);
99
- }
100
- this.longitude = longitude;
101
- }
102
- /**
103
- * @return {number} Returns the longitude.
104
- */
105
- getLongitude() {
106
- return this.longitude;
107
- }
108
- /**
109
- * @return {string|null} Returns the location name.
110
- */
111
- getLocationName() {
112
- return this.locationName;
113
- }
114
- /**
115
- * @param {string|null} name
116
- * The setter method for the display name.
117
- */
118
- setLocationName(name) {
119
- this.locationName = name;
120
- }
121
- /**
122
- * @return {string} Returns the timeZone.
123
- */
124
- getTimeZone() {
125
- return this.timeZoneId;
126
- }
127
- /**
128
- * Method to set the TimeZone.
129
- * @param {string} timeZoneId
130
- * The timeZone to set.
131
- */
132
- setTimeZone(timeZoneId) {
133
- this.timeZoneId = timeZoneId;
134
- }
135
- }
136
- exports.GeoLocation = GeoLocation;
137
- /**
138
- * The commonly used average solar refraction. Calendrical Calculations lists a more accurate global average of
139
- * 34.478885263888294
140
- * @private
141
- */
142
- const refraction = 34 / 60;
143
- // private double refraction = 34.478885263888294 / 60d;
144
- /**
145
- * The commonly used average solar radius in minutes of a degree.
146
- * @private
147
- */
148
- const solarRadius = 16 / 60;
149
- /**
150
- * The commonly used average earth radius in KM. At this time, this only affects elevation adjustment and not the
151
- * sunrise and sunset calculations. The value currently defaults to 6356.9 KM.
152
- * @private
153
- */
154
- const earthRadius = 6356.9; // in KM
155
- /**
156
- * Implementation of sunrise and sunset methods to calculate astronomical times based on the <a
157
- * href="http://noaa.gov">NOAA</a> algorithm. This calculator uses the Java algorithm based on the implementation by <a
158
- * href="http://noaa.gov">NOAA - National Oceanic and Atmospheric Administration</a>'s <a href =
159
- * "http://www.srrb.noaa.gov/highlights/sunrise/sunrise.html">Surface Radiation Research Branch</a>. NOAA's <a
160
- * href="http://www.srrb.noaa.gov/highlights/sunrise/solareqns.PDF">implementation</a> is based on equations from <a
161
- * href="http://www.willbell.com/math/mc1.htm">Astronomical Algorithms</a> by <a
162
- * href="http://en.wikipedia.org/wiki/Jean_Meeus">Jean Meeus</a>. Added to the algorithm is an adjustment of the zenith
163
- * to account for elevation. The algorithm can be found in the <a
164
- * href="http://en.wikipedia.org/wiki/Sunrise_equation">Wikipedia Sunrise Equation</a> article.
165
- *
166
- * @author &copy; Eliyahu Hershfeld 2011 - 2019
167
- */
168
- class NOAACalculator {
169
- /**
170
- * A constructor that takes in <a href="http://en.wikipedia.org/wiki/Geolocation">geolocation</a> information as a
171
- * parameter.
172
- *
173
- * @param {GeoLocation} geoLocation
174
- * The location information used for calculating astronomical sun times.
175
- * @param {Temporal.PlainDate} date
176
- */
177
- constructor(geoLocation, date) {
178
- this.date = date;
179
- this.geoLocation = geoLocation;
180
- }
181
- /**
182
- * The getSunrise method Returns a `Date` representing the
183
- * {@link getElevationAdjustment elevation adjusted} sunrise time. The zenith used
184
- * for the calculation uses {@link GEOMETRIC_ZENITH geometric zenith} of 90&deg; plus
185
- * {@link getElevationAdjustment}. This is adjusted
186
- * to add approximately 50/60 of a degree to account for 34 archminutes of refraction
187
- * and 16 archminutes for the sun's radius for a total of {@link adjustZenith 90.83333&deg;}.
188
- *
189
- * @return {Temporal.ZonedDateTime | null} the `Date` representing the exact sunrise time. If the calculation can't be computed such as
190
- * in the Arctic Circle where there is at least one day a year where the sun does not rise, and one where it
191
- * does not set, a null will be returned. See detailed explanation on top of the page.
192
- * @see adjustZenith
193
- * @see getSeaLevelSunrise()
194
- * @see getUTCSunrise
195
- */
196
- getSunrise() {
197
- const sunrise = this.getUTCSunrise0(NOAACalculator.GEOMETRIC_ZENITH);
198
- if (isNaN(sunrise))
199
- return null;
200
- return this.getDateFromTime(sunrise, true);
201
- }
202
- /**
203
- * A method that returns the sunrise without {@link getElevationAdjustment elevation
204
- * adjustment}. Non-sunrise and sunset calculations such as dawn and dusk, depend on the amount of visible light,
205
- * something that is not affected by elevation. This method returns sunrise calculated at sea level. This forms the
206
- * base for dawn calculations that are calculated as a dip below the horizon before sunrise.
207
- *
208
- * @return {Temporal.ZonedDateTime | null} the `Date` representing the exact sea-level sunrise time. If the calculation can't be computed
209
- * such as in the Arctic Circle where there is at least one day a year where the sun does not rise, and one
210
- * where it does not set, a null will be returned. See detailed explanation on top of the page.
211
- * @see getSunrise
212
- * @see getUTCSeaLevelSunrise
213
- * @see getSeaLevelSunset()
214
- */
215
- getSeaLevelSunrise() {
216
- const sunrise = this.getUTCSeaLevelSunrise(NOAACalculator.GEOMETRIC_ZENITH);
217
- if (isNaN(sunrise))
218
- return null;
219
- return this.getDateFromTime(sunrise, true);
220
- }
221
- /**
222
- * A method that returns the beginning of civil twilight (dawn) using a zenith of {@link CIVIL_ZENITH 96&deg;}.
223
- *
224
- * @return {Temporal.ZonedDateTime | null} The `Date` of the beginning of civil twilight using a zenith of 96&deg;. If the calculation
225
- * can't be computed, null will be returned. See detailed explanation on top of the page.
226
- * @see CIVIL_ZENITH
227
- */
228
- getBeginCivilTwilight() {
229
- return this.getSunriseOffsetByDegrees(NOAACalculator.CIVIL_ZENITH);
230
- }
231
- /**
232
- * A method that returns the beginning of nautical twilight using a zenith of {@link NAUTICAL_ZENITH 102&deg;}.
233
- *
234
- * @return {Temporal.ZonedDateTime | null} The `Date` of the beginning of nautical twilight using a zenith of 102&deg;. If the
235
- * calculation can't be computed null will be returned. See detailed explanation on top of the page.
236
- * @see NAUTICAL_ZENITH
237
- */
238
- getBeginNauticalTwilight() {
239
- return this.getSunriseOffsetByDegrees(NOAACalculator.NAUTICAL_ZENITH);
240
- }
241
- /**
242
- * A method that returns the beginning of astronomical twilight using a zenith of {@link ASTRONOMICAL_ZENITH
243
- * 108&deg;}.
244
- *
245
- * @return {Temporal.ZonedDateTime | null} The `Date` of the beginning of astronomical twilight using a zenith of 108&deg;. If the
246
- * calculation can't be computed, null will be returned. See detailed explanation on top of the page.
247
- * @see ASTRONOMICAL_ZENITH
248
- */
249
- getBeginAstronomicalTwilight() {
250
- return this.getSunriseOffsetByDegrees(NOAACalculator.ASTRONOMICAL_ZENITH);
251
- }
252
- /**
253
- * The getSunset method Returns a `Date` representing the
254
- * {@link getElevationAdjustment elevation adjusted} sunset time. The zenith used for
255
- * the calculation uses {@link GEOMETRIC_ZENITH geometric zenith} of 90&deg; plus
256
- * {@link getElevationAdjustment}. This is adjusted
257
- * to add approximately 50/60 of a degree to account for 34 archminutes of refraction
258
- * and 16 archminutes for the sun's radius for a total of {@link adjustZenith 90.83333&deg;}.
259
- * Note:
260
- * In certain cases the calculates sunset will occur before sunrise. This will typically happen when a timezone
261
- * other than the local timezone is used (calculating Los Angeles sunset using a GMT timezone for example). In this
262
- * case the sunset date will be incremented to the following date.
263
- *
264
- * @return {Temporal.ZonedDateTime | null} The `Date` representing the exact sunset time. If the calculation can't be computed such as in
265
- * the Arctic Circle where there is at least one day a year where the sun does not rise, and one where it
266
- * does not set, a null will be returned. See detailed explanation on top of the page.
267
- * @see adjustZenith
268
- * @see getSeaLevelSunset()
269
- * @see getUTCSunset
270
- */
271
- getSunset() {
272
- const sunset = this.getUTCSunset0(NOAACalculator.GEOMETRIC_ZENITH);
273
- if (isNaN(sunset))
274
- return null;
275
- return this.getDateFromTime(sunset, false);
276
- }
277
- /**
278
- * A method that returns the sunset without {@link getElevationAdjustment elevation
279
- * adjustment}. Non-sunrise and sunset calculations such as dawn and dusk, depend on the amount of visible light,
280
- * something that is not affected by elevation. This method returns sunset calculated at sea level. This forms the
281
- * base for dusk calculations that are calculated as a dip below the horizon after sunset.
282
- *
283
- * @return {Temporal.ZonedDateTime | null} The `Date` representing the exact sea-level sunset time. If the calculation can't be computed
284
- * such as in the Arctic Circle where there is at least one day a year where the sun does not rise, and one
285
- * where it does not set, a null will be returned. See detailed explanation on top of the page.
286
- * @see getSunset
287
- * @see getUTCSeaLevelSunset
288
- */
289
- getSeaLevelSunset() {
290
- const sunset = this.getUTCSeaLevelSunset(NOAACalculator.GEOMETRIC_ZENITH);
291
- if (isNaN(sunset))
292
- return null;
293
- return this.getDateFromTime(sunset, false);
294
- }
295
- /**
296
- * A method that returns the end of civil twilight using a zenith of {@link CIVIL_ZENITH 96&deg;}.
297
- *
298
- * @return {Temporal.ZonedDateTime | null} The `Date` of the end of civil twilight using a zenith of {@link CIVIL_ZENITH 96&deg;}. If
299
- * the calculation can't be computed, null will be returned. See detailed explanation on top of the page.
300
- * @see CIVIL_ZENITH
301
- */
302
- getEndCivilTwilight() {
303
- return this.getSunsetOffsetByDegrees(NOAACalculator.CIVIL_ZENITH);
304
- }
305
- /**
306
- * A method that returns the end of nautical twilight using a zenith of {@link NAUTICAL_ZENITH 102&deg;}.
307
- *
308
- * @return {Temporal.ZonedDateTime | null} The `Date` of the end of nautical twilight using a zenith of {@link NAUTICAL_ZENITH 102&deg;}
309
- * . If the calculation can't be computed, null will be returned. See detailed explanation on top of the
310
- * page.
311
- * @see NAUTICAL_ZENITH
312
- */
313
- getEndNauticalTwilight() {
314
- return this.getSunsetOffsetByDegrees(NOAACalculator.NAUTICAL_ZENITH);
315
- }
316
- /**
317
- * A method that returns the end of astronomical twilight using a zenith of {@link ASTRONOMICAL_ZENITH 108&deg;}.
318
- *
319
- * @return {Temporal.ZonedDateTime | null} The `Date` of the end of astronomical twilight using a zenith of {@link ASTRONOMICAL_ZENITH
320
- * 108&deg;}. If the calculation can't be computed, null will be returned. See detailed explanation on top
321
- * of the page.
322
- * @see ASTRONOMICAL_ZENITH
323
- */
324
- getEndAstronomicalTwilight() {
325
- return this.getSunsetOffsetByDegrees(NOAACalculator.ASTRONOMICAL_ZENITH);
326
- }
327
- /**
328
- * A utility method that returns a date offset by the offset time passed in. Please note that the level of light
329
- * during twilight is not affected by elevation, so if this is being used to calculate an offset before sunrise or
330
- * after sunset with the intent of getting a rough "level of light" calculation, the sunrise or sunset time passed
331
- * to this method should be sea level sunrise and sunset.
332
- *
333
- * @param {Temporal.ZonedDateTime | null} time
334
- * the start time
335
- * @param {number} offset
336
- * the offset in milliseconds to add to the time.
337
- * @return {Temporal.ZonedDateTime | null} the `Date` with the offset in milliseconds added to it
338
- */
339
- static getTimeOffset(time, offset) {
340
- if (time === null || isNaN(offset)) {
341
- return null;
342
- }
343
- return time.add({ milliseconds: offset });
344
- }
345
- /**
346
- * A utility method that returns the time of an offset by degrees below or above the horizon of
347
- * {@link getSunrise() sunrise}. Note that the degree offset is from the vertical, so for a calculation of 14&deg;
348
- * before sunrise, an offset of 14 + {@link GEOMETRIC_ZENITH} = 104 would have to be passed as a parameter.
349
- *
350
- * @param {number} offsetZenith
351
- * the degrees before {@link getSunrise} to use in the calculation. For time after sunrise use
352
- * negative numbers. Note that the degree offset is from the vertical, so for a calculation of 14&deg;
353
- * before sunrise, an offset of 14 + {@link GEOMETRIC_ZENITH} = 104 would have to be passed as a
354
- * parameter.
355
- * @return {Temporal.ZonedDateTime | null} The `Date` of the offset after (or before) {@link getSunrise}. If the calculation
356
- * can't be computed such as in the Arctic Circle where there is at least one day a year where the sun does
357
- * not rise, and one where it does not set, a null will be returned. See detailed explanation on top of the
358
- * page.
359
- */
360
- getSunriseOffsetByDegrees(offsetZenith) {
361
- const dawn = this.getUTCSunrise0(offsetZenith);
362
- if (isNaN(dawn))
363
- return null;
364
- return this.getDateFromTime(dawn, true);
365
- }
366
- /**
367
- * A utility method that returns the time of an offset by degrees below or above the horizon of {@link getSunset()
368
- * sunset}. Note that the degree offset is from the vertical, so for a calculation of 14&deg; after sunset, an
369
- * offset of 14 + {@link GEOMETRIC_ZENITH} = 104 would have to be passed as a parameter.
370
- *
371
- * @param {number} offsetZenith
372
- * the degrees after {@link getSunset} to use in the calculation. For time before sunset use negative
373
- * numbers. Note that the degree offset is from the vertical, so for a calculation of 14&deg; after
374
- * sunset, an offset of 14 + {@link GEOMETRIC_ZENITH} = 104 would have to be passed as a parameter.
375
- * @return {Temporal.ZonedDateTime | null} The `Date`of the offset after (or before) {@link getSunset}. If the calculation can't
376
- * be computed such as in the Arctic Circle where there is at least one day a year where the sun does not
377
- * rise, and one where it does not set, a null will be returned. See detailed explanation on top of the
378
- * page.
379
- */
380
- getSunsetOffsetByDegrees(offsetZenith) {
381
- const sunset = this.getUTCSunset0(offsetZenith);
382
- if (isNaN(sunset))
383
- return null;
384
- return this.getDateFromTime(sunset, false);
385
- }
386
- /**
387
- * A method that returns the sunrise in UTC time without correction for time zone offset from GMT and without using
388
- * daylight savings time.
389
- *
390
- * @param {number} zenith
391
- * the degrees below the horizon. For time after sunrise use negative numbers.
392
- * @return {number} The time in the format: 18.75 for 18:45:00 UTC/GMT. If the calculation can't be computed such as in the
393
- * Arctic Circle where there is at least one day a year where the sun does not rise, and one where it does
394
- * not set, `NaN` will be returned. See detailed explanation on top of the page.
395
- */
396
- getUTCSunrise0(zenith) {
397
- return this.getUTCSunrise(this.getAdjustedDate(), this.geoLocation, zenith, true);
398
- }
399
- /**
400
- * A method that returns the sunrise in UTC time without correction for time zone offset from GMT and without using
401
- * daylight savings time. Non-sunrise and sunset calculations such as dawn and dusk, depend on the amount of visible
402
- * light, something that is not affected by elevation. This method returns UTC sunrise calculated at sea level. This
403
- * forms the base for dawn calculations that are calculated as a dip below the horizon before sunrise.
404
- *
405
- * @param {number} zenith
406
- * the degrees below the horizon. For time after sunrise use negative numbers.
407
- * @return {number} The time in the format: 18.75 for 18:45:00 UTC/GMT. If the calculation can't be computed such as in the
408
- * Arctic Circle where there is at least one day a year where the sun does not rise, and one where it does
409
- * not set, `NaN` will be returned. See detailed explanation on top of the page.
410
- * @see getUTCSunrise
411
- * @see getUTCSeaLevelSunset
412
- */
413
- getUTCSeaLevelSunrise(zenith) {
414
- return this.getUTCSunrise(this.getAdjustedDate(), this.geoLocation, zenith, false);
415
- }
416
- /**
417
- * A method that returns the sunset in UTC time without correction for time zone offset from GMT and without using
418
- * daylight savings time.
419
- *
420
- * @param {number} zenith
421
- * the degrees below the horizon. For time after sunset use negative numbers.
422
- * @return {number} The time in the format: 18.75 for 18:45:00 UTC/GMT. If the calculation can't be computed such as in the
423
- * Arctic Circle where there is at least one day a year where the sun does not rise, and one where it does
424
- * not set, `NaN` will be returned. See detailed explanation on top of the page.
425
- * @see getUTCSeaLevelSunset
426
- */
427
- getUTCSunset0(zenith) {
428
- return this.getUTCSunset(this.getAdjustedDate(), this.geoLocation, zenith, true);
429
- }
430
- /**
431
- * A method that returns the sunset in UTC time without correction for elevation, time zone offset from GMT and
432
- * without using daylight savings time. Non-sunrise and sunset calculations such as dawn and dusk, depend on the
433
- * amount of visible light, something that is not affected by elevation. This method returns UTC sunset calculated
434
- * at sea level. This forms the base for dusk calculations that are calculated as a dip below the horizon after
435
- * sunset.
436
- *
437
- * @param {number} zenith
438
- * the degrees below the horizon. For time before sunset use negative numbers.
439
- * @return {number} The time in the format: 18.75 for 18:45:00 UTC/GMT. If the calculation can't be computed such as in the
440
- * Arctic Circle where there is at least one day a year where the sun does not rise, and one where it does
441
- * not set, `NaN` will be returned. See detailed explanation on top of the page.
442
- * @see getUTCSunset
443
- * @see getUTCSeaLevelSunrise
444
- */
445
- getUTCSeaLevelSunset(zenith) {
446
- return this.getUTCSunset(this.getAdjustedDate(), this.geoLocation, zenith, false);
447
- }
448
- /**
449
- * Adjusts the <code>Calendar</code> to deal with edge cases where the location crosses the antimeridian.
450
- * @private
451
- * @see GeoLocation#getAntimeridianAdjustment()
452
- * @return the adjusted Calendar
453
- */
454
- getAdjustedDate() {
455
- return this.date;
456
- }
457
- /**
458
- * Method to return the adjustment to the zenith required to account for the elevation. Since a person at a higher
459
- * elevation can see farther below the horizon, the calculation for sunrise / sunset is calculated below the horizon
460
- * used at sea level. This is only used for sunrise and sunset and not times before or after it such as
461
- * {@link getBeginNauticalTwilight() nautical twilight} since those
462
- * calculations are based on the level of available light at the given dip below the horizon, something that is not
463
- * affected by elevation, the adjustment should only made if the zenith == 90&deg; {@link adjustZenith adjusted}
464
- * for refraction and solar radius. The algorithm used is
465
- *
466
- * <pre>
467
- * elevationAdjustment = Math.toDegrees(Math.acos(earthRadiusInMeters / (earthRadiusInMeters + elevationMeters)));
468
- * </pre>
469
- *
470
- * The source of this algorithm is <a href="http://www.calendarists.com">Calendrical Calculations</a> by Edward M.
471
- * Reingold and Nachum Dershowitz. An alternate algorithm that produces an almost identical (but not accurate)
472
- * result found in Ma'aglay Tzedek by Moishe Kosower and other sources is:
473
- *
474
- * <pre>
475
- * elevationAdjustment = 0.0347 * Math.sqrt(elevationMeters);
476
- * </pre>
477
- *
478
- * @param {number} elevation
479
- * elevation in Meters.
480
- * @return {number} the adjusted zenith
481
- */
482
- getElevationAdjustment(elevation) {
483
- // double elevationAdjustment = 0.0347 * Math.sqrt(elevation);
484
- const elevationAdjustment = radiansToDegrees(Math.acos(earthRadius / (earthRadius + elevation / 1000)));
485
- return elevationAdjustment;
486
- }
487
- /**
488
- * Adjusts the zenith of astronomical sunrise and sunset to account for solar refraction, solar radius and
489
- * elevation. The value for Sun's zenith and true rise/set Zenith (used in this class and subclasses) is the angle
490
- * that the center of the Sun makes to a line perpendicular to the Earth's surface. If the Sun were a point and the
491
- * Earth were without an atmosphere, true sunset and sunrise would correspond to a 90&deg; zenith. Because the Sun
492
- * is not a point, and because the atmosphere refracts light, this 90&deg; zenith does not, in fact, correspond to
493
- * true sunset or sunrise, instead the centre of the Sun's disk must lie just below the horizon for the upper edge
494
- * to be obscured. This means that a zenith of just above 90&deg; must be used. The Sun subtends an angle of 16
495
- * minutes of arc, and atmospheric refraction
496
- * accounts for 34 minutes or so, giving a total
497
- * of 50 arcminutes. The total value for ZENITH is 90+(5/6) or 90.8333333&deg; for true sunrise/sunset. Since a
498
- * person at an elevation can see blow the horizon of a person at sea level, this will also adjust the zenith to
499
- * account for elevation if available. Note that this will only adjust the value if the zenith is exactly 90 degrees.
500
- * For values below and above this no correction is done. As an example, astronomical twilight is when the sun is
501
- * 18&deg; below the horizon or {@link ASTRONOMICAL_ZENITH 108&deg;
502
- * below the zenith}. This is traditionally calculated with none of the above mentioned adjustments. The same goes
503
- * for various <em>tzais</em> and <em>alos</em> times such as the
504
- * {@link ZmanimCalendar#ZENITH_16_POINT_1 16.1&deg;} dip used in
505
- * {@link ComplexZmanimCalendar#getAlos16Point1Degrees}.
506
- *
507
- * @param {number} zenith
508
- * the azimuth below the vertical zenith of 90&deg;. For sunset typically the {@link adjustZenith
509
- * zenith} used for the calculation uses geometric zenith of 90&deg; and {@link adjustZenith adjusts}
510
- * this slightly to account for solar refraction and the sun's radius. Another example would be
511
- * {@link getEndNauticalTwilight} that passes
512
- * {@link NAUTICAL_ZENITH} to this method.
513
- * @param {number} elevation
514
- * elevation in Meters.
515
- * @return {number} The zenith adjusted to include the sun's radius, refracton
516
- * and {@link getElevationAdjustment elevation} adjustment. This will only be adjusted for
517
- * sunrise and sunset (if the zenith == 90&deg;)
518
- * @see getElevationAdjustment
519
- */
520
- adjustZenith(zenith, elevation) {
521
- let adjustedZenith = zenith;
522
- if (zenith === NOAACalculator.GEOMETRIC_ZENITH) {
523
- // only adjust if it is exactly sunrise or sunset
524
- adjustedZenith =
525
- zenith +
526
- (solarRadius + refraction + this.getElevationAdjustment(elevation));
527
- }
528
- return adjustedZenith;
529
- }
530
- /**
531
- * A method that calculates UTC sunrise as well as any time based on an angle above or below sunrise.
532
- * @param date
533
- * Used to calculate day of year.
534
- * @param geoLocation
535
- * The location information used for astronomical calculating sun times.
536
- * @param zenith
537
- * the azimuth below the vertical zenith of 90 degrees. for sunrise typically the {@link adjustZenith
538
- * zenith} used for the calculation uses geometric zenith of 90&deg; and {@link adjustZenith adjusts}
539
- * this slightly to account for solar refraction and the sun's radius. Another example would be
540
- * {@link getBeginNauticalTwilight} that passes
541
- * {@link NAUTICAL_ZENITH} to this method.
542
- * @param adjustForElevation
543
- * Should the time be adjusted for elevation
544
- * @return The UTC time of sunrise in 24 hour format. 5:45:00 AM will return 5.75.0. If an error was encountered in
545
- * the calculation (expected behavior for some locations such as near the poles,
546
- * `NaN` will be returned.
547
- */
548
- getUTCSunrise(date, geoLocation, zenith, adjustForElevation) {
549
- const elevation = adjustForElevation
550
- ? geoLocation.getElevation()
551
- : 0;
552
- const adjustedZenith = this.adjustZenith(zenith, elevation);
553
- let sunrise = NOAACalculator.getSunriseUTC(NOAACalculator.getJulianDay(date), geoLocation.getLatitude(), -geoLocation.getLongitude(), adjustedZenith);
554
- sunrise = sunrise / 60;
555
- // ensure that the time is >= 0 and < 24
556
- while (sunrise < 0) {
557
- sunrise += 24;
558
- }
559
- while (sunrise >= 24) {
560
- sunrise -= 24;
561
- }
562
- return sunrise;
563
- }
564
- /**
565
- * A method that calculates UTC sunset as well as any time based on an angle above or below sunset.
566
- * @param date
567
- * Used to calculate day of year.
568
- * @param geoLocation
569
- * The location information used for astronomical calculating sun times.
570
- * @param zenith
571
- * the azimuth below the vertical zenith of 90&deg;. For sunset typically the {@link adjustZenith
572
- * zenith} used for the calculation uses geometric zenith of 90&deg; and {@link adjustZenith adjusts}
573
- * this slightly to account for solar refraction and the sun's radius. Another example would be
574
- * {@link getEndNauticalTwilight} that passes
575
- * {@link NAUTICAL_ZENITH} to this method.
576
- * @param adjustForElevation
577
- * Should the time be adjusted for elevation
578
- * @return The UTC time of sunset in 24 hour format. 5:45:00 AM will return 5.75.0. If an error was encountered in
579
- * the calculation (expected behavior for some locations such as near the poles,
580
- * `NaN` will be returned.
581
- */
582
- getUTCSunset(date, geoLocation, zenith, adjustForElevation) {
583
- const elevation = adjustForElevation
584
- ? geoLocation.getElevation()
585
- : 0;
586
- const adjustedZenith = this.adjustZenith(zenith, elevation);
587
- let sunset = NOAACalculator.getSunsetUTC(NOAACalculator.getJulianDay(date), geoLocation.getLatitude(), -geoLocation.getLongitude(), adjustedZenith);
588
- sunset = sunset / 60;
589
- // ensure that the time is >= 0 and < 24
590
- while (sunset < 0) {
591
- sunset += 24;
592
- }
593
- while (sunset >= 24) {
594
- sunset -= 24;
595
- }
596
- return sunset;
597
- }
598
- /**
599
- * A utility method that will allow the calculation of a temporal (solar) hour based on the sunrise and sunset
600
- * passed as parameters to this method. An example of the use of this method would be the calculation of a
601
- * non-elevation adjusted temporal hour by passing in {@link getSeaLevelSunrise() sea level sunrise} and
602
- * {@link getSeaLevelSunset() sea level sunset} as parameters.
603
- *
604
- * @param {Temporal.ZonedDateTime | null} startOfDay
605
- * The start of the day.
606
- * @param {Temporal.ZonedDateTime | null} endOfDay
607
- * The end of the day.
608
- *
609
- * @return {number} the <code>long</code> millisecond length of the temporal hour. If the calculation can't be computed a
610
- * `NaN` will be returned. See detailed explanation on top of the page.
611
- *
612
- * @see getTemporalHour()
613
- */
614
- getTemporalHour(startOfDay = this.getSeaLevelSunrise(), endOfDay = this.getSeaLevelSunset()) {
615
- if (startOfDay === null || endOfDay === null) {
616
- return NaN;
617
- }
618
- const delta = endOfDay.epochMilliseconds - startOfDay.epochMilliseconds;
619
- return Math.floor(delta / 12);
620
- }
621
- /**
622
- * A method that returns sundial or solar noon. It occurs when the Sun is <a href
623
- * ="http://en.wikipedia.org/wiki/Transit_%28astronomy%29">transiting</a> the <a
624
- * href="http://en.wikipedia.org/wiki/Meridian_%28astronomy%29">celestial meridian</a>. In this class it is
625
- * calculated as halfway between the sunrise and sunset passed to this method. This time can be slightly off the
626
- * real transit time due to changes in declination (the lengthening or shortening day).
627
- *
628
- * @param {Temporal.ZonedDateTime | null} startOfDay
629
- * the start of day for calculating the sun's transit. This can be sea level sunrise, visual sunrise (or
630
- * any arbitrary start of day) passed to this method.
631
- * @param {Temporal.ZonedDateTime | null} endOfDay
632
- * the end of day for calculating the sun's transit. This can be sea level sunset, visual sunset (or any
633
- * arbitrary end of day) passed to this method.
634
- *
635
- * @return {Temporal.ZonedDateTime | null} The `Date` representing Sun's transit. If the calculation can't be computed such as in the
636
- * Arctic Circle where there is at least one day a year where the sun does not rise, and one where it does
637
- * not set, null will be returned. See detailed explanation on top of the page.
638
- */
639
- getSunTransit(startOfDay = this.getSeaLevelSunrise(), endOfDay = this.getSeaLevelSunset()) {
640
- const temporalHour = this.getTemporalHour(startOfDay, endOfDay);
641
- return NOAACalculator.getTimeOffset(startOfDay, temporalHour * 6);
642
- }
643
- /**
644
- * A method that returns a `Date` from the time passed in as a parameter.
645
- * @protected
646
- * @param {number} time
647
- * The time to be set as the time for the `Date`. The time expected is in the format: 18.75
648
- * for 6:45:00 PM.
649
- * @param {boolean} isSunrise true if the time is sunrise, and false if it is sunset
650
- * @return {Temporal.ZonedDateTime | null} The Date.
651
- */
652
- getDateFromTime(time, isSunrise) {
653
- if (isNaN(time)) {
654
- return null;
655
- }
656
- let calculatedTime = time;
657
- let cal = this.getAdjustedDate();
658
- // let cal = new Temporal.PlainDate(adj.year, adj.month, adj.day);
659
- const hours = Math.trunc(calculatedTime); // retain only the hours
660
- calculatedTime -= hours;
661
- const minutes = Math.trunc((calculatedTime *= 60)); // retain only the minutes
662
- calculatedTime -= minutes;
663
- const seconds = Math.trunc((calculatedTime *= 60)); // retain only the seconds
664
- calculatedTime -= seconds; // remaining milliseconds
665
- // Check if a date transition has occurred, or is about to occur - this indicates the date of the event is
666
- // actually not the target date, but the day prior or after
667
- const localTimeHours = Math.trunc(this.geoLocation.getLongitude() / 15);
668
- if (isSunrise && localTimeHours + hours > 18) {
669
- cal = cal.add({ days: -1 });
670
- // cal = cal.minus({days: 1});
671
- }
672
- else if (!isSunrise && localTimeHours + hours < 6) {
673
- cal = cal.add({ days: 1 });
674
- }
675
- return cal
676
- .toZonedDateTime({
677
- timeZone: 'UTC',
678
- plainTime: new Temporal.PlainTime(hours, minutes, seconds, Math.trunc(calculatedTime * 1000)),
679
- })
680
- .withTimeZone(this.geoLocation.getTimeZone());
681
- }
682
- /**
683
- * Return the <a href="http://en.wikipedia.org/wiki/Julian_day">Julian day</a> from a Java Calendar
684
- * @private
685
- * @param {Temporal.ZonedDateTime} date
686
- * The Java Calendar
687
- * @return the Julian day corresponding to the date Note: Number is returned for start of day. Fractional days
688
- * should be added later.
689
- */
690
- static getJulianDay(date) {
691
- let { year, month } = date;
692
- const { day } = date;
693
- if (month <= 2) {
694
- year -= 1;
695
- month += 12;
696
- }
697
- const a = Math.trunc(year / 100);
698
- const b = Math.trunc(2 - a + a / 4);
699
- return (Math.floor(365.25 * (year + 4716)) +
700
- Math.floor(30.6001 * (month + 1)) +
701
- day +
702
- b -
703
- 1524.5);
704
- }
705
- /**
706
- * Convert <a href="http://en.wikipedia.org/wiki/Julian_day">Julian day</a> to centuries since J2000.0.
707
- * @private
708
- * @param julianDay
709
- * the Julian Day to convert
710
- * @return the centuries since 2000 Julian corresponding to the Julian Day
711
- */
712
- static getJulianCenturiesFromJulianDay(julianDay) {
713
- return ((julianDay - NOAACalculator.JULIAN_DAY_JAN_1_2000) /
714
- NOAACalculator.JULIAN_DAYS_PER_CENTURY);
715
- }
716
- /**
717
- * Convert centuries since J2000.0 to <a href="http://en.wikipedia.org/wiki/Julian_day">Julian day</a>.
718
- * @private
719
- * @param julianCenturies
720
- * the number of Julian centuries since J2000.0
721
- * @return the Julian Day corresponding to the Julian centuries passed in
722
- */
723
- static getJulianDayFromJulianCenturies(julianCenturies) {
724
- return (julianCenturies * NOAACalculator.JULIAN_DAYS_PER_CENTURY +
725
- NOAACalculator.JULIAN_DAY_JAN_1_2000);
726
- }
727
- /**
728
- * Returns the Geometric <a href="http://en.wikipedia.org/wiki/Mean_longitude">Mean Longitude</a> of the Sun.
729
- * @private
730
- * @param julianCenturies
731
- * the number of Julian centuries since J2000.0
732
- * @return the Geometric Mean Longitude of the Sun in degrees
733
- */
734
- static getSunGeometricMeanLongitude(julianCenturies) {
735
- let longitude = 280.46646 + julianCenturies * (36000.76983 + 0.0003032 * julianCenturies);
736
- while (longitude > 360) {
737
- longitude -= 360;
738
- }
739
- while (longitude < 0) {
740
- longitude += 360;
741
- }
742
- return longitude; // in degrees
743
- }
744
- /**
745
- * Returns the Geometric <a href="http://en.wikipedia.org/wiki/Mean_anomaly">Mean Anomaly</a> of the Sun.
746
- * @private
747
- * @param julianCenturies
748
- * the number of Julian centuries since J2000.0
749
- * @return the Geometric Mean Anomaly of the Sun in degrees
750
- */
751
- static getSunGeometricMeanAnomaly(julianCenturies) {
752
- return (357.52911 + julianCenturies * (35999.05029 - 0.0001537 * julianCenturies)); // in degrees
753
- }
754
- /**
755
- * Return the <a href="http://en.wikipedia.org/wiki/Eccentricity_%28orbit%29">eccentricity of earth's orbit</a>.
756
- * @private
757
- * @param julianCenturies
758
- * the number of Julian centuries since J2000.0
759
- * @return the unitless eccentricity
760
- */
761
- static getEarthOrbitEccentricity(julianCenturies) {
762
- return (0.016708634 -
763
- julianCenturies * (0.000042037 + 0.0000001267 * julianCenturies)); // unitless
764
- }
765
- /**
766
- * Returns the <a href="http://en.wikipedia.org/wiki/Equation_of_the_center">equation of center</a> for the sun.
767
- * @private
768
- * @param julianCenturies
769
- * the number of Julian centuries since J2000.0
770
- * @return the equation of center for the sun in degrees
771
- */
772
- static getSunEquationOfCenter(julianCenturies) {
773
- const m = NOAACalculator.getSunGeometricMeanAnomaly(julianCenturies);
774
- const mrad = degreesToRadians(m);
775
- const sinm = Math.sin(mrad);
776
- const sin2m = Math.sin(mrad + mrad);
777
- const sin3m = Math.sin(mrad + mrad + mrad);
778
- return (sinm *
779
- (1.914602 - julianCenturies * (0.004817 + 0.000014 * julianCenturies)) +
780
- sin2m * (0.019993 - 0.000101 * julianCenturies) +
781
- sin3m * 0.000289); // in degrees
782
- }
783
- /**
784
- * Return the true longitude of the sun
785
- * @private
786
- * @param julianCenturies
787
- * the number of Julian centuries since J2000.0
788
- * @return the sun's true longitude in degrees
789
- */
790
- static getSunTrueLongitude(julianCenturies) {
791
- const sunLongitude = NOAACalculator.getSunGeometricMeanLongitude(julianCenturies);
792
- const center = NOAACalculator.getSunEquationOfCenter(julianCenturies);
793
- return sunLongitude + center; // in degrees
794
- }
795
- /**
796
- * Return the apparent longitude of the sun
797
- * @private
798
- * @param julianCenturies
799
- * the number of Julian centuries since J2000.0
800
- * @return sun's apparent longitude in degrees
801
- */
802
- static getSunApparentLongitude(julianCenturies) {
803
- const sunTrueLongitude = NOAACalculator.getSunTrueLongitude(julianCenturies);
804
- const omega = 125.04 - 1934.136 * julianCenturies;
805
- const lambda = sunTrueLongitude - 0.00569 - 0.00478 * Math.sin(degreesToRadians(omega));
806
- return lambda; // in degrees
807
- }
808
- /**
809
- * Returns the mean <a href="http://en.wikipedia.org/wiki/Axial_tilt">obliquity of the ecliptic</a> (Axial tilt).
810
- * @private
811
- * @param julianCenturies
812
- * the number of Julian centuries since J2000.0
813
- * @return the mean obliquity in degrees
814
- */
815
- static getMeanObliquityOfEcliptic(julianCenturies) {
816
- const seconds = 21.448 -
817
- julianCenturies *
818
- (46.815 + julianCenturies * (0.00059 - julianCenturies * 0.001813));
819
- return 23 + (26 + seconds / 60) / 60; // in degrees
820
- }
821
- /**
822
- * Returns the corrected <a href="http://en.wikipedia.org/wiki/Axial_tilt">obliquity of the ecliptic</a> (Axial
823
- * tilt).
824
- * @private
825
- * @param julianCenturies
826
- * the number of Julian centuries since J2000.0
827
- * @return the corrected obliquity in degrees
828
- */
829
- static getObliquityCorrection(julianCenturies) {
830
- const obliquityOfEcliptic = NOAACalculator.getMeanObliquityOfEcliptic(julianCenturies);
831
- const omega = 125.04 - 1934.136 * julianCenturies;
832
- return obliquityOfEcliptic + 0.00256 * Math.cos(degreesToRadians(omega)); // in degrees
833
- }
834
- /**
835
- * Return the <a href="http://en.wikipedia.org/wiki/Declination">declination</a> of the sun.
836
- * @private
837
- * @param julianCenturies
838
- * the number of Julian centuries since J2000.0
839
- * @return
840
- * the sun's declination in degrees
841
- */
842
- static getSunDeclination(julianCenturies) {
843
- const obliquityCorrection = NOAACalculator.getObliquityCorrection(julianCenturies);
844
- const lambda = NOAACalculator.getSunApparentLongitude(julianCenturies);
845
- const sint = Math.sin(degreesToRadians(obliquityCorrection)) *
846
- Math.sin(degreesToRadians(lambda));
847
- const theta = radiansToDegrees(Math.asin(sint));
848
- return theta; // in degrees
849
- }
850
- /**
851
- * Return the <a href="http://en.wikipedia.org/wiki/Equation_of_time">Equation of Time</a> - the difference between
852
- * true solar time and mean solar time
853
- * @private
854
- * @param julianCenturies
855
- * the number of Julian centuries since J2000.0
856
- * @return equation of time in minutes of time
857
- */
858
- static getEquationOfTime(julianCenturies) {
859
- const epsilon = NOAACalculator.getObliquityCorrection(julianCenturies);
860
- const geomMeanLongSun = NOAACalculator.getSunGeometricMeanLongitude(julianCenturies);
861
- const eccentricityEarthOrbit = NOAACalculator.getEarthOrbitEccentricity(julianCenturies);
862
- const geomMeanAnomalySun = NOAACalculator.getSunGeometricMeanAnomaly(julianCenturies);
863
- let y = Math.tan(degreesToRadians(epsilon) / 2);
864
- y *= y;
865
- const sin2l0 = Math.sin(2 * degreesToRadians(geomMeanLongSun));
866
- const sinm = Math.sin(degreesToRadians(geomMeanAnomalySun));
867
- const cos2l0 = Math.cos(2 * degreesToRadians(geomMeanLongSun));
868
- const sin4l0 = Math.sin(4 * degreesToRadians(geomMeanLongSun));
869
- const sin2m = Math.sin(2 * degreesToRadians(geomMeanAnomalySun));
870
- const equationOfTime = y * sin2l0 -
871
- 2 * eccentricityEarthOrbit * sinm +
872
- 4 * eccentricityEarthOrbit * y * sinm * cos2l0 -
873
- 0.5 * y * y * sin4l0 -
874
- 1.25 * eccentricityEarthOrbit * eccentricityEarthOrbit * sin2m;
875
- return radiansToDegrees(equationOfTime) * 4; // in minutes of time
876
- }
877
- /**
878
- * Return the <a href="http://en.wikipedia.org/wiki/Hour_angle">hour angle</a> of the sun at sunrise for the
879
- * latitude.
880
- * @private
881
- * @param {number} lat
882
- * , the latitude of observer in degrees
883
- * @param solarDec
884
- * the declination angle of sun in degrees
885
- * @param {number} zenith
886
- * the zenith
887
- * @return hour angle of sunrise in radians
888
- */
889
- static getSunHourAngleAtSunrise(lat, solarDec, zenith) {
890
- const latRad = degreesToRadians(lat);
891
- const sdRad = degreesToRadians(solarDec);
892
- return Math.acos(Math.cos(degreesToRadians(zenith)) /
893
- (Math.cos(latRad) * Math.cos(sdRad)) -
894
- Math.tan(latRad) * Math.tan(sdRad)); // in radians
895
- }
896
- /**
897
- * Returns the <a href="http://en.wikipedia.org/wiki/Hour_angle">hour angle</a> of the sun at sunset for the
898
- * latitude.
899
- * @private
900
- * @param {number} lat
901
- * the latitude of observer in degrees
902
- * @param solarDec
903
- * the declination angle of sun in degrees
904
- * @param {number} zenith
905
- * the zenith
906
- * @return the hour angle of sunset in radians
907
- */
908
- static getSunHourAngleAtSunset(lat, solarDec, zenith) {
909
- const latRad = degreesToRadians(lat);
910
- const sdRad = degreesToRadians(solarDec);
911
- const hourAngle = Math.acos(Math.cos(degreesToRadians(zenith)) /
912
- (Math.cos(latRad) * Math.cos(sdRad)) -
913
- Math.tan(latRad) * Math.tan(sdRad));
914
- return -hourAngle; // in radians
915
- }
916
- /**
917
- * Return the <a href="http://en.wikipedia.org/wiki/Celestial_coordinate_system">Solar Elevation</a> for the
918
- * horizontal coordinate system at the given location at the given time. Can be negative if the sun is below the
919
- * horizon. Not corrected for altitude.
920
- *
921
- * @param {Temporal.ZonedDateTime} date
922
- * time of calculation
923
- * @param {number} lat
924
- * latitude of location for calculation
925
- * @param {number} lon
926
- * longitude of location for calculation
927
- * @return {number} solar elevation in degrees - horizon is 0 degrees, civil twilight is -6 degrees
928
- */
929
- static getSolarElevation(date, lat, lon) {
930
- const julianDay = NOAACalculator.getJulianDay(date.toPlainDate());
931
- const julianCenturies = NOAACalculator.getJulianCenturiesFromJulianDay(julianDay);
932
- const equationOfTime = NOAACalculator.getEquationOfTime(julianCenturies);
933
- let longitude = date.hour + 12 + (date.minute + equationOfTime + date.second / 60) / 60;
934
- longitude = -((longitude * 360) / 24) % 360;
935
- const hourAngleRad = degreesToRadians(lon - longitude);
936
- const declination = NOAACalculator.getSunDeclination(julianCenturies);
937
- const decRad = degreesToRadians(declination);
938
- const latRad = degreesToRadians(lat);
939
- return radiansToDegrees(Math.asin(Math.sin(latRad) * Math.sin(decRad) +
940
- Math.cos(latRad) * Math.cos(decRad) * Math.cos(hourAngleRad)));
941
- }
942
- /**
943
- * Return the <a href="http://en.wikipedia.org/wiki/Celestial_coordinate_system">Solar Azimuth</a> for the
944
- * horizontal coordinate system at the given location at the given time. Not corrected for altitude. True south is 0
945
- * degrees.
946
- *
947
- * @param {Temporal.ZonedDateTime} date
948
- * time of calculation
949
- * @param {number} latitude
950
- * latitude of location for calculation
951
- * @param {number} lon
952
- * longitude of location for calculation
953
- * @return {number}
954
- */
955
- static getSolarAzimuth(date, latitude, lon) {
956
- const julianDay = NOAACalculator.getJulianDay(date.toPlainDate());
957
- const julianCenturies = NOAACalculator.getJulianCenturiesFromJulianDay(julianDay);
958
- const equationOfTime = NOAACalculator.getEquationOfTime(julianCenturies);
959
- let longitude = date.hour + 12 + (date.minute + equationOfTime + date.second / 60) / 60;
960
- longitude = -((longitude * 360) / 24) % 360;
961
- const hourAngleRad = degreesToRadians(lon - longitude);
962
- const declination = NOAACalculator.getSunDeclination(julianCenturies);
963
- const decRad = degreesToRadians(declination);
964
- const latRad = degreesToRadians(latitude);
965
- return (radiansToDegrees(Math.atan(Math.sin(hourAngleRad) /
966
- (Math.cos(hourAngleRad) * Math.sin(latRad) -
967
- Math.tan(decRad) * Math.cos(latRad)))) + 180);
968
- }
969
- /**
970
- * Return the <a href="http://en.wikipedia.org/wiki/Universal_Coordinated_Time">Universal Coordinated Time</a> (UTC)
971
- * of sunrise for the given day at the given location on earth
972
- * @private
973
- * @param julianDay
974
- * the Julian day
975
- * @param {number} latitude
976
- * the latitude of observer in degrees
977
- * @param {number} longitude
978
- * the longitude of observer in degrees
979
- * @param {number} zenith
980
- * the zenith
981
- * @return the time in minutes from zero UTC
982
- */
983
- static getSunriseUTC(julianDay, latitude, longitude, zenith) {
984
- const julianCenturies = NOAACalculator.getJulianCenturiesFromJulianDay(julianDay);
985
- // Find the time of solar noon at the location, and use that declination. This is better than start of the
986
- // Julian day
987
- const noonmin = NOAACalculator.getSolarNoonUTC(julianCenturies, longitude);
988
- const tnoon = NOAACalculator.getJulianCenturiesFromJulianDay(julianDay + noonmin / 1440);
989
- // First pass to approximate sunrise (using solar noon)
990
- let eqTime = NOAACalculator.getEquationOfTime(tnoon);
991
- let solarDec = NOAACalculator.getSunDeclination(tnoon);
992
- let hourAngle = NOAACalculator.getSunHourAngleAtSunrise(latitude, solarDec, zenith);
993
- let delta = longitude - radiansToDegrees(hourAngle);
994
- let timeDiff = 4 * delta; // in minutes of time
995
- let timeUTC = 720 + timeDiff - eqTime; // in minutes
996
- // Second pass includes fractional Julian Day in gamma calc
997
- const newt = NOAACalculator.getJulianCenturiesFromJulianDay(NOAACalculator.getJulianDayFromJulianCenturies(julianCenturies) +
998
- timeUTC / 1440);
999
- eqTime = NOAACalculator.getEquationOfTime(newt);
1000
- solarDec = NOAACalculator.getSunDeclination(newt);
1001
- hourAngle = NOAACalculator.getSunHourAngleAtSunrise(latitude, solarDec, zenith);
1002
- delta = longitude - radiansToDegrees(hourAngle);
1003
- timeDiff = 4 * delta;
1004
- timeUTC = 720 + timeDiff - eqTime; // in minutes
1005
- return timeUTC;
1006
- }
1007
- /**
1008
- * Return the <a href="http://en.wikipedia.org/wiki/Universal_Coordinated_Time">Universal Coordinated Time</a> (UTC)
1009
- * of <a href="http://en.wikipedia.org/wiki/Noon#Solar_noon">solar noon</a> for the given day at the given location
1010
- * on earth.
1011
- * @private
1012
- * @param julianCenturies
1013
- * the number of Julian centuries since J2000.0
1014
- * @param {number} longitude
1015
- * the longitude of observer in degrees
1016
- * @return the time in minutes from zero UTC
1017
- */
1018
- static getSolarNoonUTC(julianCenturies, longitude) {
1019
- // First pass uses approximate solar noon to calculate eqtime
1020
- const tnoon = NOAACalculator.getJulianCenturiesFromJulianDay(NOAACalculator.getJulianDayFromJulianCenturies(julianCenturies) +
1021
- longitude / 360);
1022
- let eqTime = NOAACalculator.getEquationOfTime(tnoon);
1023
- const solNoonUTC = 720 + longitude * 4 - eqTime; // min
1024
- const newt = NOAACalculator.getJulianCenturiesFromJulianDay(NOAACalculator.getJulianDayFromJulianCenturies(julianCenturies) -
1025
- 0.5 +
1026
- solNoonUTC / 1440);
1027
- eqTime = NOAACalculator.getEquationOfTime(newt);
1028
- return 720 + longitude * 4 - eqTime; // min
1029
- }
1030
- /**
1031
- * Return the <a href="http://en.wikipedia.org/wiki/Universal_Coordinated_Time">Universal Coordinated Time</a> (UTC)
1032
- * of sunset for the given day at the given location on earth
1033
- * @private
1034
- * @param julianDay
1035
- * the Julian day
1036
- * @param {number} latitude
1037
- * the latitude of observer in degrees
1038
- * @param {number} longitude
1039
- * : longitude of observer in degrees
1040
- * @param {number} zenith
1041
- * the zenith
1042
- * @return the time in minutes from zero Universal Coordinated Time (UTC)
1043
- */
1044
- static getSunsetUTC(julianDay, latitude, longitude, zenith) {
1045
- const julianCenturies = NOAACalculator.getJulianCenturiesFromJulianDay(julianDay);
1046
- // Find the time of solar noon at the location, and use that declination. This is better than start of the
1047
- // Julian day
1048
- const noonmin = NOAACalculator.getSolarNoonUTC(julianCenturies, longitude);
1049
- const tnoon = NOAACalculator.getJulianCenturiesFromJulianDay(julianDay + noonmin / 1440);
1050
- // First calculates sunrise and approx length of day
1051
- let eqTime = NOAACalculator.getEquationOfTime(tnoon);
1052
- let solarDec = NOAACalculator.getSunDeclination(tnoon);
1053
- let hourAngle = NOAACalculator.getSunHourAngleAtSunset(latitude, solarDec, zenith);
1054
- let delta = longitude - radiansToDegrees(hourAngle);
1055
- let timeDiff = 4 * delta;
1056
- let timeUTC = 720 + timeDiff - eqTime;
1057
- // Second pass includes fractional Julian Day in gamma calc
1058
- const newt = NOAACalculator.getJulianCenturiesFromJulianDay(NOAACalculator.getJulianDayFromJulianCenturies(julianCenturies) +
1059
- timeUTC / 1440);
1060
- eqTime = NOAACalculator.getEquationOfTime(newt);
1061
- solarDec = NOAACalculator.getSunDeclination(newt);
1062
- hourAngle = NOAACalculator.getSunHourAngleAtSunset(latitude, solarDec, zenith);
1063
- delta = longitude - radiansToDegrees(hourAngle);
1064
- timeDiff = 4 * delta;
1065
- timeUTC = 720 + timeDiff - eqTime; // in minutes
1066
- return timeUTC;
1067
- }
1068
- }
1069
- exports.NOAACalculator = NOAACalculator;
1070
- /**
1071
- * The zenith of astronomical sunrise and sunset. The sun is 90&deg; from the vertical 0&deg;
1072
- * @private
1073
- */
1074
- NOAACalculator.GEOMETRIC_ZENITH = 90;
1075
- /**
1076
- * Default value for Sun's zenith and true rise/set Zenith (used in this class and subclasses) is the angle that the
1077
- * center of the Sun makes to a line perpendicular to the Earth's surface. If the Sun were a point and the Earth
1078
- * were without an atmosphere, true sunset and sunrise would correspond to a 90&deg; zenith. Because the Sun is not
1079
- * a point, and because the atmosphere refracts light, this 90&deg; zenith does not, in fact, correspond to true
1080
- * sunset or sunrise, instead the center of the Sun's disk must lie just below the horizon for the upper edge to be
1081
- * obscured. This means that a zenith of just above 90&deg; must be used. The Sun subtends an angle of 16 minutes of
1082
- * arc, and atmospheric refraction accounts for
1083
- * 34 minutes or so, giving a total of 50
1084
- * arcminutes. The total value for ZENITH is 90+(5/6) or 90.8333333&deg; for true sunrise/sunset.
1085
- */
1086
- // const ZENITH: number = GEOMETRIC_ZENITH + 5.0 / 6.0;
1087
- /** Sun's zenith at civil twilight (96&deg;). */
1088
- NOAACalculator.CIVIL_ZENITH = 96;
1089
- /** Sun's zenith at nautical twilight (102&deg;). */
1090
- NOAACalculator.NAUTICAL_ZENITH = 102;
1091
- /** Sun's zenith at astronomical twilight (108&deg;). */
1092
- NOAACalculator.ASTRONOMICAL_ZENITH = 108;
1093
- /**
1094
- * The <a href="http://en.wikipedia.org/wiki/Julian_day">Julian day</a> of January 1, 2000
1095
- * @private
1096
- */
1097
- NOAACalculator.JULIAN_DAY_JAN_1_2000 = 2451545;
1098
- /**
1099
- * Julian days per century
1100
- * @private
1101
- */
1102
- NOAACalculator.JULIAN_DAYS_PER_CENTURY = 36525;
File without changes