1 /*
2  *  This library is free software; you can redistribute it and/or
3  *  modify it under the terms of the GNU Lesser General Public
4  *  License as published by the Free Software Foundation; either
5  *  version 2 of the License, or (at your option) any later version.
6  *
7  *  This library is distributed in the hope that it will be useful,
8  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
9  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
10  *  Lesser General Public License for more details.
11  *
12  *  You should have received a copy of the GNU General Public License
13  *  along with this program; if not, write to the Free Software
14  *  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
15  *
16  *  Copyright (C) 2000 - 2005 Liam Girdwood
17  */
18 
19 #include <math.h>
20 #include <stdio.h>
21 #include <libnova/solar.h>
22 #include <libnova/earth.h>
23 #include <libnova/nutation.h>
24 #include <libnova/transform.h>
25 #include <libnova/rise_set.h>
26 #include <libnova/utility.h>
27 
28 /*! \fn void ln_get_solar_geom_coords (double JD, struct ln_helio_posn * position)
29 * \param JD Julian day
30 * \param position Pointer to store calculated solar position.
31 *
32 * Calculate geometric coordinates and radius vector
33 * accuracy 0.01 arc second error - uses VSOP87 solution.
34 *
35 * Latitude and Longitude returned are in degrees, whilst radius
36 * vector returned is in AU.
37 */
38 
ln_get_solar_geom_coords(double JD,struct ln_helio_posn * position)39 void ln_get_solar_geom_coords (double JD, struct ln_helio_posn * position)
40 {
41 	/* get earths heliocentric position */
42 	ln_get_earth_helio_coords (JD, position);
43 
44 	position->L += 180.0;
45 	position->L = ln_range_degrees (position->L);
46 	position->B *= -1.0;
47 }
48 
49 /*! \fn void ln_get_solar_equ_coords (double JD, struct ln_equ_posn * position)
50 * \param JD Julian day
51 * \param position Pointer to store calculated solar position.
52 *
53 * Calculate apparent equatorial solar coordinates for given julian day.
54 * This function includes the effects of aberration and nutation.
55 */
ln_get_solar_equ_coords(double JD,struct ln_equ_posn * position)56 void ln_get_solar_equ_coords (double JD, struct ln_equ_posn * position)
57 {
58 	struct ln_helio_posn sol;
59 	struct ln_lnlat_posn LB;
60 	struct ln_nutation nutation;
61 	double aberration;
62 
63 	/* get geometric coords */
64 	ln_get_solar_geom_coords (JD, &sol);
65 
66 	/* add nutation */
67 	ln_get_nutation (JD, &nutation);
68 	sol.L += nutation.longitude;
69 
70 	/* aberration */
71 	aberration = (20.4898 / (360 * 60 * 60)) / sol.R;
72 	sol.L -= aberration;
73 
74 	/* transform to equatorial */
75 	LB.lat = sol.B;
76 	LB.lng = sol.L;
77 	ln_get_equ_from_ecl (&LB, JD, position);
78 }
79 
80 /*! \fn void ln_get_solar_ecl_coords (double JD, struct ln_lnlat_posn * position)
81 * \param JD Julian day
82 * \param position Pointer to store calculated solar position.
83 *
84 * Calculate apparent ecliptical solar coordinates for given julian day.
85 * This function includes the effects of aberration and nutation.
86 */
ln_get_solar_ecl_coords(double JD,struct ln_lnlat_posn * position)87 void ln_get_solar_ecl_coords (double JD, struct ln_lnlat_posn * position)
88 {
89 	struct ln_helio_posn sol;
90 	struct ln_nutation nutation;
91 	double aberration;
92 
93 	/* get geometric coords */
94 	ln_get_solar_geom_coords (JD, &sol);
95 
96 	/* add nutation */
97 	ln_get_nutation (JD, &nutation);
98 	sol.L += nutation.longitude;
99 
100 	/* aberration */
101 	aberration = (20.4898 / (360 * 60 * 60)) / sol.R;
102 	sol.L -= aberration;
103 
104 	position->lng = sol.L;
105 	position->lat = sol.B;
106 }
107 
108 /*! \fn void ln_get_solar_geo_coords (double JD, struct ln_rect_posn * position)
109 * \param JD Julian day
110 * \param position Pointer to store calculated solar position.
111 *
112 * Calculate geocentric coordinates (rectangular) for given julian day.
113 * Accuracy 0.01 arc second error - uses VSOP87 solution.
114 * Position returned is in units of AU.
115 */
ln_get_solar_geo_coords(double JD,struct ln_rect_posn * position)116 void ln_get_solar_geo_coords (double JD, struct ln_rect_posn * position)
117 {
118 	/* get earths's heliocentric position */
119 	struct ln_helio_posn sol;
120 	ln_get_earth_helio_coords (JD, &sol);
121 
122 	/* now get rectangular coords */
123 	ln_get_rect_from_helio (&sol, position);
124 	position->X *=-1.0;
125 	position->Y *=-1.0;
126 	position->Z *=-1.0;
127 }
128 
ln_get_solar_rst_horizon(double JD,struct ln_lnlat_posn * observer,double horizon,struct ln_rst_time * rst)129 int ln_get_solar_rst_horizon (double JD, struct ln_lnlat_posn * observer, double horizon, struct ln_rst_time * rst)
130 {
131 	return ln_get_body_rst_horizon (JD, observer, ln_get_solar_equ_coords, horizon, rst);
132 }
133 
134 
135 /*! \fn double ln_get_solar_rst (double JD, struct ln_lnlat_posn * observer, struct ln_rst_time * rst);
136  * Calls get_solar_rst_horizon with horizon set to LN_SOLAR_STANDART_HORIZON.
137  */
138 
ln_get_solar_rst(double JD,struct ln_lnlat_posn * observer,struct ln_rst_time * rst)139 int ln_get_solar_rst (double JD, struct ln_lnlat_posn * observer, struct ln_rst_time * rst)
140 {
141 	return ln_get_solar_rst_horizon (JD, observer, LN_SOLAR_STANDART_HORIZON, rst);
142 }
143 
144 /*! \fn double ln_get_solar_sdiam (double JD)
145 * \param JD Julian day
146 * \return Semidiameter in arc seconds
147 *
148 * Calculate the semidiameter of the Sun in arc seconds for the
149 * given julian day.
150 */
ln_get_solar_sdiam(double JD)151 double ln_get_solar_sdiam (double JD)
152 {
153 	double So = 959.63; /* at 1 AU */
154 	double dist;
155 
156 	dist = ln_get_earth_solar_dist (JD);
157 	return So / dist;
158 }
159 
160 /*! \example sun.c
161  *
162  * Examples of how to use solar functions.
163  */
164