Merge lp:~i-martividal/stellarium/Observability-1.0.2 into lp:stellarium

Proposed by Ivan Marti-Vidal
Status: Merged
Approved by: Alexander Wolf
Approved revision: no longer in the source branch.
Merged at revision: 5535
Proposed branch: lp:~i-martividal/stellarium/Observability-1.0.2
Merge into: lp:stellarium
Diff against target: 1079 lines (+445/-249)
4 files modified
plugins/Observability/src/Observability.cpp (+420/-238)
plugins/Observability/src/Observability.hpp (+21/-7)
plugins/Observability/src/gui/ObservabilityDialog.cpp (+3/-3)
plugins/Observability/src/gui/ObservabilityDialog.ui (+1/-1)
To merge this branch: bzr merge lp:~i-martividal/stellarium/Observability-1.0.2
Reviewer Review Type Date Requested Status
Alexander Wolf Approve
gzotti Approve
Review via email: mp+119999@code.launchpad.net

Description of the change

Dear all,

Here you have a new revision of the Observability plugin. The FIXME issues found by Alexander are solved, and the rise/set/transit times for the planets are now more accurate. I've also solved a few bugs (one more important regarding the dates of Full Moon, since the Secant method could jump to other months, even centuries before the present dates).

The names of the months are again in their compact form, although you can of course change it to your taste (this compact nomenclature is indeed also recognized by the IAU).

I'll answer and comment on the good suggestions made in the pubdevel list in a forthcoming e-mail (as soon as the kid is finally asleep in the bed :S).

    Best Wishes,

           Ivan

To post a comment you must log in.
Revision history for this message
gzotti (georg-zotti) wrote :

The rise/rose/risen issue (indeed wrong!) is still to be corrected. (allow some days for translators!)

I just tested cosmical set for Mercury, 2012-09-05. For me Sep 4 is closer to a simultaneous set (?)

The rise/transit/set for Mercury (and I guess for the other planets as well) change during the day caused by the planet's speed. For a better estimate, you might want to precompute positions for previous day, day of observation, following day, and do a spline interpolation. (maybe only for 0.12?)

HTH, G.

review: Needs Fixing
Revision history for this message
gzotti (georg-zotti) wrote :

Oops, sorry: I updated&rebuilt your first Observability branch! Too many branches out there...
Must check new download.
G.

Revision history for this message
gzotti (georg-zotti) wrote :

OK, the two latter points are still here. But maybe only for the next version.
G.

review: Approve
Revision history for this message
Alexander Wolf (alexwolf) :
review: Approve
Revision history for this message
Alexander Wolf (alexwolf) wrote :

I'm merge this branch before publish RC2.

5535. By Alexander Wolf

update Observability plugin

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'plugins/Observability/src/Observability.cpp'
2--- plugins/Observability/src/Observability.cpp 2012-08-12 15:50:48 +0000
3+++ plugins/Observability/src/Observability.cpp 2012-08-16 18:31:20 +0000
4@@ -90,6 +90,7 @@
5 halfpi = 1.57079632675; // pi/2
6 MoonT = 29.530588; // Moon synodic period (used as first estimate of Full Moon).
7 RefFullMoon = 2451564.696; // Reference Julian date of a Full Moon.
8+ MoonPerilune = 0.0024236308; // Smallest Earth-Moon distance (in AU).
9 nextFullMoon = 0.0;
10 prevFullMoon = 0.0;
11 selName = "";
12@@ -183,7 +184,9 @@
13
14
15 // Set names of the months:
16- QString mons[12]={q_("January"), q_("February"), q_("March"), q_("April"), q_("May"), q_("June"), q_("July"), q_("August"), q_("September"), q_("October"), q_("November"), q_("December")};
17+// QString mons[12]={q_("January"), q_("February"), q_("March"), q_("April"), q_("May"), q_("June"), q_("July"), q_("August"), q_("September"), q_("October"), q_("November"), q_("December")};
18+ QString mons[12]={q_("Jan"), q_("Feb"), q_("Mar"), q_("Apr"), q_("May"), q_("Jun"), q_("Jul"), q_("Aug"), q_("Sep"), q_("Oct"), q_("Nov"), q_("Dec")};
19+
20 for (int i=0;i<12;i++) {
21 months[i]=mons[i];
22 };
23@@ -244,10 +247,10 @@
24
25 /////////////////////////////////////////////////////////////////
26 // PRELIMINARS:
27- bool souChanged, locChanged, yearChanged;
28+ bool locChanged, yearChanged;
29 StelObjectP selectedObject;
30 Planet* currPlanet;
31-
32+ PlanetP Object, parent;
33
34 // Only execute plugin if we are on Earth.
35 if (core->getCurrentLocation().planetName != "Earth") {return;};
36@@ -265,12 +268,13 @@
37 double currheight = (6371.+(core->getCurrentLocation().altitude)/1000.)/UA;
38 double currJD = core->getJDay();
39 double currJDint;
40- double currLocalT = 24.*modf(currJD + StelApp::getInstance().getLocaleMgr().getGMTShift(currJD)/24.0,&currJDint);
41+ GMTShift = StelApp::getInstance().getLocaleMgr().getGMTShift(currJD)/24.0;
42+ double currLocalT = 24.*modf(currJD + GMTShift,&currJDint);
43
44 int auxm, auxd, auxy;
45 StelUtils::getDateFromJulianDay(currJD,&auxy,&auxm,&auxd);
46 bool isSource = StelApp::getInstance().getStelObjectMgr().getWasSelected();
47- bool show_Year = show_Best_Night || show_Good_Nights || show_AcroCos; // || show_FullMoon;
48+ bool show_Year = show_Best_Night || show_Good_Nights || show_AcroCos;
49
50 //////////////////////////////////////////////////////////////////
51
52@@ -332,19 +336,51 @@
53 isMoon = ("Moon" == tempName)?true:false;
54 isSun = ("Sun" == tempName)?true:false;
55
56+// If Moon is not selected (or was unselected), force re-compute of Full Moon next time it is selected:
57+ if (!isMoon) {prevFullMoon=0.0; nextFullMoon=0.0;};
58+
59 //Update position:
60 EquPos = selectedObject->getEquinoxEquatorialPos(core);
61 EquPos.normalize();
62 LocPos = core->equinoxEquToAltAz(EquPos);
63
64 // Check if the user has changed the source (or if the source is Sun/Moon).
65- if (tempName == selName && isMoon==false && isSun == false) {
66- souChanged = false;} // Don't retouch anything regarding RA/Dec (to save a bit of resources).
67- else { // Check also if the (new) source belongs to the Solar System:
68+ if (tempName == selName)
69+ {
70+ souChanged = false;}
71+ else
72+ { // Check also if the (new) source belongs to the Solar System:
73+
74+ souChanged = true;
75+ selName = tempName;
76+
77 currPlanet = dynamic_cast<Planet*>(selectedObject.data());
78 isStar = (currPlanet)?false:true;
79- souChanged = true;
80- selName = tempName;
81+
82+ if (!isStar && !isMoon && !isSun) // Object in the Solar System, but is not Sun nor Moon.
83+ {
84+
85+ int gene = -1;
86+
87+ // If object is a planet's moon, we get its parent planet:
88+ Object = GETSTELMODULE(SolarSystem)->searchByEnglishName(selName);
89+
90+ parent = Object->getParent();
91+
92+ if (parent)
93+ {
94+ while (parent) {
95+ gene += 1;
96+ parent = parent->getParent();}
97+ };
98+ for (int g=0; g<gene;g++) {
99+ Object = Object->getParent();
100+ };
101+
102+ // Now get a pointer to the planet's instance:
103+ myPlanet = Object.data();
104+ };
105+
106 };
107 }
108 else { // There is no source selected!
109@@ -381,23 +417,27 @@
110 QString RS1, RS2, Cul; // strings with Rise/Set/Culmination times
111 double Rise, Set; // Actual Rise/Set times (in GMT).
112 int d1,m1,s1,d2,m2,s2,dc,mc,sc; // Integers for the time spans in hh:mm:ss.
113- bool solvedMoon = false;
114- bool transit; // Is the source above the horizon? Did it culminate?
115+ bool solvedMoon = false; // Check if solutions were found for Sun, Moon, or planet.
116+ bool transit = false; // Is the source above the horizon? Did it culminate?
117
118 int ephHour, ephMinute, ephSecond; // Local time for selected ephemeris
119
120 if (show_Today) { // We show ephemeris for today (i.e., rise, set, and transit times).
121
122- if (isMoon || isSun) {
123- solvedMoon = MoonSunSolve(core); // False if fails; True otherwise.
124+
125+ if (!isStar)
126+ {
127+ int Kind = (isSun)?1:0; // Set "Kind" according to the selected object.
128+ Kind += (isMoon)?2:0; Kind += (!isSun && !isMoon)?3:0;
129+
130+ solvedMoon = SolarSystemSolve(core, Kind); // False if fails; True otherwise.
131 currH = std::abs(24.*(MoonCulm-myJD)/TFrac);
132 transit = MoonCulm-myJD<0.0;
133 if (solvedMoon) { // If failed, Set and Rise will be dummy.
134 Set = std::abs(24.*(MoonSet-myJD)/TFrac);
135 Rise = std::abs(24.*(MoonRise-myJD)/TFrac);
136 };
137- }
138- else if (horizH>0.0) { // The source is not circumpolar and can be seen from this latitude.
139+ } else if (horizH>0.0) { // The source is not circumpolar and can be seen from this latitude.
140
141 if ( LocPos[1]>0.0 ) { // The source is at the eastern side...
142 if ( currH>horizH ) { // ... and below the horizon.
143@@ -422,7 +462,7 @@
144
145 };
146
147- if ((solvedMoon && MoonRise>0.0) || (isMoon==false && isSun==false && horizH>0.0))
148+ if ((solvedMoon && MoonRise>0.0) || (!isSun && !isMoon && horizH>0.0))
149 {
150 double2hms(TFrac*Set,d1,m1,s1);
151 double2hms(TFrac*Rise,d2,m2,s2);
152@@ -439,7 +479,7 @@
153 RiseTime = QString("%1:%2").arg(ephHour).arg(ephMinute,2,10,QLatin1Char('0'));
154
155 RS1 = q_("Sets at %1 (in %2)").arg(SetTime).arg(RS1);
156- RS2 = q_("Raised at %1 (%2 ago)").arg(RiseTime).arg(RS2);
157+ RS2 = q_("Rose at %1 (%2 ago)").arg(RiseTime).arg(RS2);
158 }
159 else
160 {
161@@ -449,8 +489,8 @@
162 double2hms(toUnsignedRA(currLocalT+TFrac*Rise+12.),ephHour,ephMinute,ephSecond);
163 RiseTime = QString("%1:%2").arg(ephHour).arg(ephMinute,2,10,QLatin1Char('0'));
164
165- RS1 = q_("Has set at %1 (%2 ago)").arg(SetTime).arg(RS1);
166- RS2 = q_("Raises at %1 (in %2)").arg(RiseTime).arg(RS2);
167+ RS1 = q_("Set at %1 (%2 ago)").arg(SetTime).arg(RS1);
168+ RS2 = q_("Rises at %1 (in %2)").arg(RiseTime).arg(RS2);
169 };
170 }
171 else { // The source is either circumpolar or never rises:
172@@ -460,8 +500,7 @@
173
174 // Culmination:
175
176- transit = false;
177- if (isSun==false && isMoon == false)
178+ if (isStar)
179 {
180 culmAlt = std::abs(mylat-selDec); // 90.-altitude at transit.
181 transit = LocPos[1]<0.0;
182@@ -494,10 +533,6 @@
183
184 // Compute yearly ephemeris (only if necessary, and not for Sun nor Moon):
185
186-// if (isMoon && (show_FullMoon || show_Crescent || show_SuperMoon))
187-// {
188-// computeMoonEphemeris();
189-// };
190
191 if (isSun)
192 {
193@@ -506,7 +541,7 @@
194 else if (!isMoon && show_Year) {
195
196 if (isStar==false && (souChanged || yearChanged)) { // Object moves.
197- PlanetRADec(core,selName);} // Re-compute ephemeris.
198+ PlanetRADec(core);} // Re-compute ephemeris.
199
200 else { // Object is fixed on the sky.
201 double auxH = HourAngle(mylat,0.0,selDec);
202@@ -536,13 +571,20 @@
203 if (show_Best_Night) {
204 int selday = 0;
205 double deltaPhs = -1.0; // Initial dummy value
206- double tempPhs; //, tempSep;
207-
208+ double tempPhs;
209 for (int i=0;i<nDays;i++) { // Maximize the Sun-object separation.
210 tempPhs = Lambda(ObjectRA[i],ObjectDec[i],SunRA[i],SunDec[i]);
211 if (tempPhs>deltaPhs) {selday=i;deltaPhs=tempPhs;};
212 };
213- bestNight = q_("Largest Sun separation: ");
214+
215+ if (selName=="Mercury" || selName=="Venus")
216+ {
217+ bestNight = q_("Greatest elongation: ");
218+ } else
219+ {
220+ bestNight = q_("Largest Sun separation: ");
221+ };
222+
223 bestNight = bestNight + CalenDate(selday) + q_(" (at %1 deg.)").arg(deltaPhs*Rad2Deg,0,'f',1);
224 };
225
226@@ -617,11 +659,9 @@
227 }
228 else
229 {
230- ObsRange = QString("%1 %2").arg(q_("Best observed")).arg(dateRange);
231+ ObsRange = QString("%1 %2").arg(q_("Nights above horizon: ")).arg(dateRange);
232 };
233
234-// if (selName == "Mercury") {ObsRange = "Observable in many dates of the year";}; // Special case of Mercury.
235-
236 }; // Comes from show_Good_Nights==True"
237 }; // Comes from the "else" of "culmAlt>=..."
238 };// Comes from "souChanged || ..."
239@@ -629,34 +669,37 @@
240
241 // Print all results:
242
243- int yLine = 7*fontSize+80;
244+
245+ int spacing = (int) (1.3* ( (double) fontSize)); // between lines
246+ int spacing2 = 6*fontSize; // between daily and yearly results
247+ int yLine = 8*fontSize+80;
248 int xLine = 50;
249
250 if (show_Today)
251 {
252 paintresult.drawText(xLine, yLine,q_(" TODAY:"));
253- paintresult.drawText(xLine+fontSize, yLine-fontSize, RS2);
254- paintresult.drawText(xLine+fontSize, yLine-fontSize*2, RS1);
255- paintresult.drawText(xLine+fontSize, yLine-fontSize*3, Cul);
256- yLine -= fontSize*5;
257+ paintresult.drawText(xLine+fontSize, yLine-spacing, RS2);
258+ paintresult.drawText(xLine+fontSize, yLine-spacing*2, RS1);
259+ paintresult.drawText(xLine+fontSize, yLine-spacing*3, Cul);
260+ yLine -= spacing2;
261 };
262-
263- if ((isMoon && show_FullMoon) || (isSun == false && isMoon == false && show_Year))
264+
265+ if ((isMoon && show_FullMoon) || (!isSun && !isMoon && show_Year))
266 {
267 paintresult.drawText(xLine,yLine," THIS YEAR:");
268 if (show_Best_Night || show_FullMoon)
269 {
270- yLine -= fontSize;
271+ yLine -= spacing;
272 paintresult.drawText(xLine+fontSize, yLine, bestNight);
273 };
274 if (show_Good_Nights)
275 {
276- yLine -= fontSize;
277+ yLine -= spacing;
278 paintresult.drawText(xLine+fontSize, yLine, ObsRange);
279 };
280 if (show_AcroCos)
281 {
282- yLine -= fontSize;
283+ yLine -= spacing;
284 paintresult.drawText(xLine+fontSize, yLine, AcroCos);
285 };
286
287@@ -719,7 +762,7 @@
288 double ffrac2 = std::modf(60.*ffrac,&f2);
289 //FIXME: ffrac2 is unused variable; need fix
290 ffrac2 = std::modf(3600.*(ffrac-f2/60.),&f3);
291- h1 = (int)f1 ; h2 = (int)std::abs(f2) ; h3 = (int)std::abs(f3);
292+ h1 = (int)f1 ; h2 = (int)std::abs(f2+0.0*ffrac2) ; h3 = (int)std::abs(f3);
293 }
294 ////////////////////////////////////
295
296@@ -730,7 +773,7 @@
297 {
298 double tempRA,tempmod;
299 //FIXME: tempmod is unused variable; need fix
300- if (RA<0.0) {tempmod = std::modf(-RA/24.,&tempRA); RA += 24.*(tempRA+1.0);};
301+ if (RA<0.0) {tempmod = std::modf(-RA/24.,&tempRA); RA += 24.*(tempRA+1.0)+0.0*tempmod;};
302 double auxRA = 24.*std::modf(RA/24.,&tempRA);
303 auxRA += (auxRA<0.0)?24.0:((auxRA>24.0)?-24.0:0.0);
304 return auxRA;
305@@ -752,38 +795,14 @@
306 //////////////////////////////////////////////////
307 // Returns the RA and Dec of the selected planet
308 //for each day of the current year:
309-void Observability::PlanetRADec(StelCore *core, QString Name)
310+void Observability::PlanetRADec(StelCore *core)
311 {
312- int gene = -1;
313 double TempH;
314- Vec3d TP, TP2;
315- Mat4d LocTrans;
316-
317-// If object is a Moon, we select its parent planet:
318- PlanetP Object = GETSTELMODULE(SolarSystem)->searchByEnglishName(Name);
319- PlanetP parent = Object->getParent();
320-
321- if (parent) {
322- while (parent) {
323- gene += 1;
324- parent = parent->getParent();}
325- };
326- for (int g=0; g<gene;g++) {
327- Object = Object->getParent();
328- };
329-
330-// Get a pointer to the planet's instance:
331- Planet* myPlanet = Object.data();
332
333 // Compute planet's position for each day of the current year:
334
335 for (int i=0;i<nDays;i++) {
336- myPlanet->computePosition(yearJD[i]);
337- myPlanet->computeTransMatrix(yearJD[i]);
338- TP = myPlanet->getHeliocentricEclipticPos();
339- LocTrans = (core->matVsop87ToJ2000)*(Mat4d::translation(EarthPos[i]));
340- TP2 = core->j2000ToEquinoxEqu(LocTrans*TP);
341- toRADec(TP2,ObjectRA[i],ObjectDec[i]);
342+ getPlanetCoords(core,yearJD[i],ObjectRA[i],ObjectDec[i],false);
343 TempH = HourAngle(mylat,0.0,ObjectDec[i]);
344 ObjectH0[i] = TempH;
345 ObjectSidT[0][i] = toUnsignedRA(ObjectRA[i]-TempH);
346@@ -791,8 +810,7 @@
347 }
348
349 // Return the planet to its current time:
350- myPlanet->computePosition(myJD);
351- myPlanet->computeTransMatrix(myJD);
352+ getPlanetCoords(core,myJD,ObjectRA[0],ObjectDec[0],true);
353
354
355 }
356@@ -803,7 +821,6 @@
357 void Observability::SunRADec(StelCore* core)
358 {
359 int day,month,year,year2;
360- Vec3d TP, TP2;
361
362 // Get current date:
363 StelUtils::getDateFromJulianDay(myJD,&year,&month,&day);
364@@ -820,11 +837,10 @@
365 yearJD[i] = Jan1stJD+(double)i;
366 myEarth->computePosition(yearJD[i]);
367 myEarth->computeTransMatrix(yearJD[i]);
368- TP = myEarth->getHeliocentricEclipticPos();
369- TP[0] = -TP[0]; TP[1] = -TP[1]; TP[2] = -TP[2];
370- TP2 = core->j2000ToEquinoxEqu((core->matVsop87ToJ2000)*TP);
371- EarthPos[i] = TP;
372- toRADec(TP2,SunRA[i],SunDec[i]);
373+ Pos1 = myEarth->getHeliocentricEclipticPos();
374+ Pos2 = core->j2000ToEquinoxEqu((core->matVsop87ToJ2000)*(-Pos1));
375+ EarthPos[i] = -Pos1;
376+ toRADec(Pos2,SunRA[i],SunDec[i]);
377 };
378
379 //Return the Earth to its current time:
380@@ -952,7 +968,6 @@
381 Set *= (BestDiffSet > 0.083)?-1:1; // Check that difference is lower than 5 minutes.
382 Rise2 *= (BestDiffRise2 > 0.083)?-1:1; // Check that difference is lower than 5 minutes.
383 Set2 *= (BestDiffSet2 > 0.083)?-1:1; // Check that difference is lower than 5 minutes.
384-// qDebug() << q_("%1 %2").arg(Rise).arg(Rise2);
385 int Result = (Rise>0 || Set>0)?1:0;
386 Result += (Rise2>0 || Set2>0)?2:0;
387 return (success)?Result:0;
388@@ -990,10 +1005,10 @@
389
390 if (getBack) // Return the Moon and Earth to their current position:
391 {
392- myEarth->computePosition(myJD);
393- myEarth->computeTransMatrix(myJD);
394- myMoon->computePosition(myJD);
395- myMoon->computeTransMatrix(myJD);
396+ myEarth->computePosition(JD);
397+ myEarth->computeTransMatrix(JD);
398+ myMoon->computePosition(JD);
399+ myMoon->computeTransMatrix(JD);
400 }
401 else
402 { // Compute coordinates:
403@@ -1022,9 +1037,83 @@
404
405
406
407-//////////////////////////////////////////////
408-// Solves Moon's or Sun's ephemeris by bissection. Returns JD:
409-bool Observability::MoonSunSolve(StelCore* core)
410+//////////////////////////
411+// Get the Observer-to-Moon distance JD:
412+// getBack controls whether Earth and Moon must be returned to their original positions after computation.
413+void Observability::getMoonDistance(StelCore *core, double JD, double &Distance, bool getBack)
414+{
415+
416+ if (getBack) // Return the Moon and Earth to their current position:
417+ {
418+ myEarth->computePosition(JD);
419+ myEarth->computeTransMatrix(JD);
420+ myMoon->computePosition(JD);
421+ myMoon->computeTransMatrix(JD);
422+ }
423+ else
424+ { // Compute coordinates:
425+ myEarth->computePosition(JD);
426+ myEarth->computeTransMatrix(JD);
427+ Pos0 = myEarth->getHeliocentricEclipticPos();
428+// double currSidT;
429+
430+// Sun coordinates:
431+// Pos2 = core->j2000ToEquinoxEqu((core->matVsop87ToJ2000)*(-Pos0));
432+// toRADec(Pos2,RASun,DecSun);
433+
434+// Moon coordinates:
435+// currSidT = myEarth->getSiderealTime(JD)/Rad2Deg;
436+// RotObserver = (Mat4d::zrotation(currSidT))*ObserverLoc;
437+ LocTrans = (core->matVsop87ToJ2000)*(Mat4d::translation(-Pos0));
438+ myMoon->computePosition(JD);
439+ myMoon->computeTransMatrix(JD);
440+ Pos1 = myMoon->getHeliocentricEclipticPos();
441+ Pos2 = (core->j2000ToEquinoxEqu(LocTrans*Pos1)); //-RotObserver;
442+
443+ Distance = std::sqrt(Pos2*Pos2);
444+
445+// toRADec(Pos2,RAMoon,DecMoon);
446+ };
447+}
448+//////////////////////////////////////////////
449+
450+
451+
452+
453+//////////////////////////////////////////////
454+// Get the Coords of a planet:
455+void Observability::getPlanetCoords(StelCore *core, double JD, double &RA, double &Dec, bool getBack)
456+{
457+
458+ if (getBack)
459+ {
460+ // Return the planet to its current time:
461+ myPlanet->computePosition(JD);
462+ myPlanet->computeTransMatrix(JD);
463+ myEarth->computePosition(JD);
464+ myEarth->computeTransMatrix(JD);
465+ } else
466+ {
467+ // Compute planet's position:
468+ myPlanet->computePosition(JD);
469+ myPlanet->computeTransMatrix(JD);
470+ Pos1 = myPlanet->getHeliocentricEclipticPos();
471+ myEarth->computePosition(JD);
472+ myEarth->computeTransMatrix(JD);
473+ Pos2 = myEarth->getHeliocentricEclipticPos();
474+ LocTrans = (core->matVsop87ToJ2000)*(Mat4d::translation(-Pos2));
475+ Pos2 = core->j2000ToEquinoxEqu(LocTrans*Pos1);
476+ toRADec(Pos2,RA,Dec);
477+ };
478+
479+}
480+//////////////////////////////////////////////
481+
482+
483+
484+//////////////////////////////////////////////
485+// Solves Moon's, Sun's, or Planet's ephemeris by bissection. Returns JD:
486+bool Observability::SolarSystemSolve(StelCore* core, int Kind)
487 {
488
489 int Niter = 100;
490@@ -1038,159 +1127,207 @@
491
492 // Only recompute ephemeris from second to second (at least)
493 // or if the source has changed (i.e., Sun <-> Moon). This saves resources:
494- if (std::abs(myJD-lastJDMoon)<JDsec && LastSun==isSun) return raises;
495-
496- LastSun = isSun;
497- myEarth->computePosition(myJD);
498- myEarth->computeTransMatrix(myJD);
499- Pos0 = myEarth->getHeliocentricEclipticPos();
500-
501- if (isSun)
502+ if (std::abs(myJD-lastJDMoon)>JDsec || LastObject!=Kind || souChanged)
503 {
504- Pos2 = core->j2000ToEquinoxEqu((core->matVsop87ToJ2000)*(-Pos0));}
505- else
506- {
507- currSidT = myEarth->getSiderealTime(myJD)/Rad2Deg;
508- RotObserver = (Mat4d::zrotation(currSidT))*ObserverLoc;
509- LocTrans = (core->matVsop87ToJ2000)*(Mat4d::translation(-Pos0));
510- myMoon->computePosition(myJD);
511- myMoon->computeTransMatrix(myJD);
512- Pos1 = myMoon->getHeliocentricEclipticPos();
513- Pos2 = (core->j2000ToEquinoxEqu(LocTrans*Pos1))-RotObserver;
514- };
515-
516- toRADec(Pos2,RA,Dec);
517- Vec3d MoonAltAz = core->equinoxEquToAltAz(Pos2);
518- raised = MoonAltAz[2] > 0.0;
519+
520+// qDebug() << q_("%1 %2 %3 %4").arg(Kind).arg(LastObject).arg(myJD,0,'f',5).arg(lastJDMoon,0,'f',5);
521+
522+ LastObject = Kind;
523+
524+ myEarth->computePosition(myJD);
525+ myEarth->computeTransMatrix(myJD);
526+ Pos0 = myEarth->getHeliocentricEclipticPos();
527+
528+ if (Kind==1)
529+ { // Sun position:
530+ Pos2 = core->j2000ToEquinoxEqu((core->matVsop87ToJ2000)*(-Pos0));
531+ } else if (Kind==2)
532+ { // Moon position:
533+ currSidT = myEarth->getSiderealTime(myJD)/Rad2Deg;
534+ RotObserver = (Mat4d::zrotation(currSidT))*ObserverLoc;
535+ LocTrans = (core->matVsop87ToJ2000)*(Mat4d::translation(-Pos0));
536+ myMoon->computePosition(myJD);
537+ myMoon->computeTransMatrix(myJD);
538+ Pos1 = myMoon->getHeliocentricEclipticPos();
539+ Pos2 = (core->j2000ToEquinoxEqu(LocTrans*Pos1))-RotObserver;
540+ } else
541+ { // Planet position:
542+ myPlanet->computePosition(myJD);
543+ myPlanet->computeTransMatrix(myJD);
544+ Pos1 = myPlanet->getHeliocentricEclipticPos();
545+ LocTrans = (core->matVsop87ToJ2000)*(Mat4d::translation(-Pos0));
546+ Pos2 = core->j2000ToEquinoxEqu(LocTrans*Pos1);
547+ };
548+
549+ toRADec(Pos2,RA,Dec);
550+ Vec3d MoonAltAz = core->equinoxEquToAltAz(Pos2);
551+ raised = MoonAltAz[2] > 0.0;
552
553 // Initial guesses of rise/set/transit times.
554-// They are called 'Moon', but are also used for the Sun:
555-
556- double Hcurr = -HourAngle(mylat,alti,selDec)*sign(LocPos[1]);
557- double SidT = toUnsignedRA(selRA + Hcurr);
558-
559- MoonCulm = -Hcurr;
560- MoonRise = (-Hhoriz-Hcurr);
561- MoonSet = (Hhoriz-Hcurr);
562-
563- if (raises) {
564- if (raised==false) {
565- MoonRise += (MoonRise<0.0)?24.0:0.0;
566- MoonSet -= (MoonSet>0.0)?24.0:0.0;
567- };
568+// They are called 'Moon', but are also used for the Sun or planet:
569+
570+ double Hcurr = -HourAngle(mylat,alti,selDec)*sign(LocPos[1]);
571+ double SidT = toUnsignedRA(selRA + Hcurr);
572+
573+ MoonCulm = -Hcurr;
574+ MoonRise = (-Hhoriz-Hcurr);
575+ MoonSet = (Hhoriz-Hcurr);
576+
577+ if (raises) {
578+ if (raised==false) {
579+ MoonRise += (MoonRise<0.0)?24.0:0.0;
580+ MoonSet -= (MoonSet>0.0)?24.0:0.0;
581+ };
582
583 // Rise time:
584- tempEphH = MoonRise*TFrac;
585- MoonRise = myJD + (MoonRise/24.);
586- for (i=0; i<Niter; i++)
587- {
588- // Get modified coordinates:
589- jd1 = MoonRise;
590- getSunMoonCoords(core,jd1,RAS,DecS,RA,Dec,false);
591- if (isSun) {RA = RAS; Dec = DecS;};
592-
593- // Current hour angle at mod. coordinates:
594- Hcurr = toUnsignedRA(SidT-RA);
595- Hcurr -= (raised)?0.0:24.;
596- Hcurr -= (Hcurr>12.)?24.0:0.0;
597-
598- // H at horizon for mod. coordinates:
599- Hhoriz = HourAngle(mylat,0.0,Dec);
600- // Compute eph. times for mod. coordinates:
601- TempH = (-Hhoriz-Hcurr)*TFrac;
602- if (raised==false) TempH += (TempH<0.0)?24.0:0.0;
603+ tempEphH = MoonRise*TFrac;
604+ MoonRise = myJD + (MoonRise/24.);
605+ for (i=0; i<Niter; i++)
606+ {
607+ // Get modified coordinates:
608+ jd1 = MoonRise;
609+
610+ if (Kind<3)
611+ {
612+ getSunMoonCoords(core,jd1,RAS,DecS,RA,Dec,false);
613+ } else
614+ {
615+ getPlanetCoords(core,jd1,RA,Dec,false);
616+ };
617+
618+ if (Kind==1) {RA = RAS; Dec = DecS;};
619+
620+ // Current hour angle at mod. coordinates:
621+ Hcurr = toUnsignedRA(SidT-RA);
622+ Hcurr -= (raised)?0.0:24.;
623+ Hcurr -= (Hcurr>12.)?24.0:0.0;
624+
625+ // H at horizon for mod. coordinates:
626+ Hhoriz = HourAngle(mylat,0.0,Dec);
627+ // Compute eph. times for mod. coordinates:
628+ TempH = (-Hhoriz-Hcurr)*TFrac;
629+ if (raised==false) TempH += (TempH<0.0)?24.0:0.0;
630+ // Check convergence:
631+ if (std::abs(TempH-tempEphH)<JDsec) break;
632+ // Update rise-time estimate:
633+ tempEphH = TempH;
634+ MoonRise = myJD + (tempEphH/24.);
635+ };
636+
637+// Set time:
638+ tempEphH = MoonSet;
639+ MoonSet = myJD + (MoonSet/24.);
640+ for (i=0; i<Niter; i++)
641+ {
642+ // Get modified coordinates:
643+ jd1 = MoonSet;
644+
645+ if (Kind<3)
646+ {
647+ getSunMoonCoords(core,jd1,RAS,DecS,RA,Dec,false);
648+ } else
649+ {
650+ getPlanetCoords(core,jd1,RA,Dec,false);
651+ };
652+
653+ if (Kind==1) {RA = RAS; Dec = DecS;};
654+
655+ // Current hour angle at mod. coordinates:
656+ Hcurr = toUnsignedRA(SidT-RA);
657+ Hcurr -= (raised)?24.:0.;
658+ Hcurr += (Hcurr<-12.)?24.0:0.0;
659+ // H at horizon for mod. coordinates:
660+ Hhoriz = HourAngle(mylat,0.0,Dec);
661+ // Compute eph. times for mod. coordinates:
662+ TempH = (Hhoriz-Hcurr)*TFrac;
663+ if (raised==false) TempH -= (TempH>0.0)?24.0:0.0;
664 // Check convergence:
665- if (std::abs(TempH-tempEphH)<JDsec) break;
666- // Update rise-time estimate:
667- tempEphH = TempH;
668- MoonRise = myJD + (tempEphH/24.);
669- };
670-
671-// Set time:
672- tempEphH = MoonSet;
673- MoonSet = myJD + (MoonSet/24.);
674- for (i=0; i<Niter; i++)
675+ if (std::abs(TempH-tempEphH)<JDsec) break;
676+ // Update set-time estimate:
677+ tempEphH = TempH;
678+ MoonSet = myJD + (tempEphH/24.);
679+ };
680+ }
681+ else // Comes from if(raises)
682 {
683- // Get modified coordinates:
684- jd1 = MoonSet;
685- getSunMoonCoords(core,jd1,RAS,DecS,RA,Dec,false);
686- if (isSun) {RA = RAS; Dec = DecS;};
687-
688- // Current hour angle at mod. coordinates:
689- Hcurr = toUnsignedRA(SidT-RA);
690- Hcurr -= (raised)?24.:0.;
691- Hcurr += (Hcurr<-12.)?24.0:0.0;
692- // H at horizon for mod. coordinates:
693- Hhoriz = HourAngle(mylat,0.0,Dec);
694- // Compute eph. times for mod. coordinates:
695- TempH = (Hhoriz-Hcurr)*TFrac;
696- if (raised==false) TempH -= (TempH>0.0)?24.0:0.0;
697- // Check convergence:
698- if (std::abs(TempH-tempEphH)<JDsec) break;
699- // Update set-time estimate:
700- tempEphH = TempH;
701- MoonSet = myJD + (tempEphH/24.);
702+ MoonSet = -1.0; MoonRise = -1.0;
703 };
704- }
705- else // Comes from if(raises)
706- {
707- MoonSet = -1.0; MoonRise = -1.0;
708- };
709
710 // Culmination time:
711- tempEphH = MoonCulm;
712- MoonCulm = myJD + (MoonCulm/24.);
713+ tempEphH = MoonCulm;
714+ MoonCulm = myJD + (MoonCulm/24.);
715
716- for (i=0; i<Niter; i++)
717- {
718+ for (i=0; i<Niter; i++)
719+ {
720 // Get modified coordinates:
721- jd1 = MoonCulm;
722- getSunMoonCoords(core,jd1,RAS,DecS,RA,Dec,false);
723- if (isSun) {RA = RAS; Dec = DecS;};
724+ jd1 = MoonCulm;
725+
726+ if (Kind<3)
727+ {
728+ getSunMoonCoords(core,jd1,RAS,DecS,RA,Dec,false);
729+ } else
730+ {
731+ getPlanetCoords(core,jd1,RA,Dec,false);
732+ };
733+
734+
735+ if (Kind==1) {RA = RAS; Dec = DecS;};
736
737
738 // Current hour angle at mod. coordinates:
739- Hcurr = toUnsignedRA(SidT-RA);
740- Hcurr += (LocPos[1]<0.0)?24.0:-24.0;
741- Hcurr -= (Hcurr>12.)?24.0:0.0;
742+ Hcurr = toUnsignedRA(SidT-RA);
743+ Hcurr += (LocPos[1]<0.0)?24.0:-24.0;
744+ Hcurr -= (Hcurr>12.)?24.0:0.0;
745
746 // Compute eph. times for mod. coordinates:
747- TempH = -Hcurr*TFrac;
748+ TempH = -Hcurr*TFrac;
749 // Check convergence:
750- if (std::abs(TempH-tempEphH)<JDsec) break;
751- tempEphH = TempH;
752- MoonCulm = myJD + (tempEphH/24.);
753- culmAlt = std::abs(mylat-Dec); // 90 - altitude at transit.
754- };
755-
756-
757-// Find out the days of Full Moon and Crescent at Sunset:
758- if (isMoon && show_FullMoon) // || show_SuperMoon))
759+ if (std::abs(TempH-tempEphH)<JDsec) break;
760+ tempEphH = TempH;
761+ MoonCulm = myJD + (tempEphH/24.);
762+ culmAlt = std::abs(mylat-Dec); // 90 - altitude at transit.
763+ };
764+
765+// qDebug() << q_("%1").arg(MoonCulm,0,'f',5);
766+
767+ }; // Comes from if (std::abs(myJD-lastJDMoon)>JDsec || LastObject!=Kind)
768+
769+
770+
771+
772+// Find out the days of Full Moon:
773+ if (Kind==2 && show_FullMoon) // || show_SuperMoon))
774 {
775
776- // Only extimate date of Full Moon if we have changed Lunar month:
777+ // Only estimate date of Full Moon if we have changed Lunar month:
778 if (myJD > nextFullMoon || myJD < prevFullMoon)
779 {
780
781
782- // Estimate the closest Full Moon:
783+ // Estimate the nearest (in time) Full Moon:
784 double nT;
785 double dT = std::modf((myJD-RefFullMoon)/MoonT,&nT);
786 if (dT>0.5) {nT += 1.0;};
787+ if (dT<-0.5) {nT -= 1.0;};
788+
789 double TempFullMoon = RefFullMoon + nT*MoonT;
790
791 // Improve the estimate iteratively (Secant method over Lunar-phase vs. time):
792
793- dT = 1./1440.; // Our time span for the finite-difference derivative estimate.
794- //double Phase1, Phase2; // Variables for temporal use.
795+ dT = 0.1/1440.; // 6 seconds. Our time span for the finite-difference derivative estimate.
796 double Deriv1, Deriv2; // Variables for temporal use.
797- double Sec1, Sec2, Temp1, Temp2; // Variables for temporal use.
798+ double Sec1, Sec2, SecMed, Temp1, Temp2; // Variables for temporal use.
799+ double iniEst1, iniEst2; // JD values that MUST include the solution within them.
800+ double Phase1, Phase2, PhaseMed;
801
802 for (int j=0; j<2; j++)
803 { // Two steps: one for the previos Full Moon and the other for the next one.
804
805- Sec1 = TempFullMoon - 0.01*MoonT;
806- Sec2 = TempFullMoon + 0.01*MoonT;
807+ iniEst1 = TempFullMoon - 0.25*MoonT;
808+ iniEst2 = TempFullMoon + 0.25*MoonT;
809+
810+ Sec1 = iniEst1; // TempFullMoon - 0.05*MoonT; // Initial estimates of Full-Moon dates
811+ Sec2 = iniEst2; // TempFullMoon + 0.05*MoonT;
812
813 for (int i=0; i<100; i++) // A limit of 100 iterations.
814 {
815@@ -1200,7 +1337,7 @@
816 Temp2 = Lambda(RA,Dec,RAS,DecS);
817
818 Deriv1 = (Temp1-Temp2)/dT;
819- //Phase1 = (Temp1+Temp2)/2.;
820+ Phase1 = (Temp1+Temp2)/2.;
821
822 getSunMoonCoords(core,Sec2+dT/2.,RAS,DecS,RA,Dec,false);
823 Temp1 = Lambda(RA,Dec,RAS,DecS);
824@@ -1208,12 +1345,36 @@
825 Temp2 = Lambda(RA,Dec,RAS,DecS);
826
827 Deriv2 = (Temp1-Temp2)/dT;
828- //Phase2 = (Temp1+Temp2)/2.;
829+ Phase2 = (Temp1+Temp2)/2.;
830+
831+ SecMed = (Sec2+Sec1)/2.;
832+ getSunMoonCoords(core,SecMed+dT/2.,RAS,DecS,RA,Dec,false);
833+ Temp1 = Lambda(RA,Dec,RAS,DecS);
834+ getSunMoonCoords(core,SecMed-dT/2.,RAS,DecS,RA,Dec,false);
835+ Temp2 = Lambda(RA,Dec,RAS,DecS);
836+
837+ // DerivMed = (Temp1-Temp2)/dT;
838+ PhaseMed = (Temp1+Temp2)/2.;
839
840 Temp1 = Sec2 - Deriv2*(Sec2-Sec1)/(Deriv2-Deriv1);
841- Sec1 = Sec2; Sec2 = Temp1;
842-
843- if (std::abs(Sec2-Sec1) < dT) {break;} // Convergence.
844+
845+ // Force the solution to fall within the range of good possible solutions:
846+ if (Temp1 < iniEst1 || Temp1 > iniEst2)
847+ {
848+ if (Phase1>Phase2)
849+ {
850+ Sec2 = (Phase2 > PhaseMed)?Sec2:SecMed;
851+ } else
852+ {
853+ Sec1 = Sec2;
854+ Sec2 = (Phase1>PhaseMed)?Sec1:SecMed;
855+ };
856+ } else
857+ {
858+ Sec1 = Sec2; Sec2 = Temp1;
859+ };
860+
861+ if (std::abs(Sec2-Sec1) < 10.*dT) {TempFullMoon = Temp1; break;} // 1 minute accuracy. Convergence.
862
863 };
864
865@@ -1229,51 +1390,72 @@
866
867 };
868
869- };
870
871 // Update the string shown in the screen:
872- int fullDay, fullMonth,fullYear, fullHour, fullMinute, fullSecond;
873- StelUtils::getDateFromJulianDay(prevFullMoon,&fullYear,&fullMonth,&fullDay);
874- double dT;
875- double nT = 24.*(std::modf(prevFullMoon,&dT));
876- double2hms(nT,fullHour,fullMinute,fullSecond);
877- bestNight = q_("Previous Full Moon: %1 %2 at %3:%4. ").arg(months[fullMonth-1]).arg(fullDay).arg(fullHour).arg(fullMinute,2,10,QLatin1Char('0'));
878- StelUtils::getDateFromJulianDay(nextFullMoon,&fullYear,&fullMonth,&fullDay);
879- nT = 24.*(std::modf(nextFullMoon,&dT));
880- double2hms(nT,fullHour,fullMinute,fullSecond);
881- bestNight += q_("Next Full Moon: %1 %2 at %3:%4. ").arg(months[fullMonth-1]).arg(fullDay).arg(fullHour).arg(fullMinute,2,10,QLatin1Char('0'));
882+ int fullDay, fullMonth,fullYear, fullHour, fullMinute, fullSecond;
883+ double LocalPrev = prevFullMoon+GMTShift+0.5; // Shift to the local time.
884+ double LocalNext = nextFullMoon+GMTShift+0.5;
885+ double intMoon;
886+ double LocalTMoon = 24.*modf(LocalPrev,&intMoon);
887+ StelUtils::getDateFromJulianDay(intMoon,&fullYear,&fullMonth,&fullDay);
888+ double2hms(toUnsignedRA(LocalTMoon),fullHour,fullMinute,fullSecond);
889+ bestNight = q_("Previous Full Moon: %1 "+months[fullMonth-1]+" at %2:%3. ").arg(fullDay).arg(fullHour).arg(fullMinute,2,10,QLatin1Char('0'));
890+
891+ LocalTMoon = 24.*modf(LocalNext,&intMoon);
892+ StelUtils::getDateFromJulianDay(intMoon,&fullYear,&fullMonth,&fullDay);
893+ double2hms(toUnsignedRA(LocalTMoon),fullHour,fullMinute,fullSecond);
894+ bestNight += q_(" Next Full Moon: %1 "+months[fullMonth-1]+" at %2:%3. ").arg(fullDay).arg(fullHour).arg(fullMinute,2,10,QLatin1Char('0'));
895+
896+ ObsRange = "";
897+ AcroCos = "";
898
899
900 // Now, compute the days of all the Full Moons of the current year, and get the Earth/Moon distance:
901-// double monthFrac;
902-// int PrevMonths = (int) std::modf((nextFullMoon-Jan1stJD)/MoonT,&monthFrac);
903-// double BestDistance = 1.0; // initial dummy value for Sun-Moon distance;
904-
905-// for (int i=-PrevMonths; i<13 ; i++)
906-// {
907-// jd1 = nextFullMoon + MoonT*((double) i);
908-// getSunMoonCoords(core,jd1,RAS,DecS,RA,Dec,false);
909-// COMPUTE THE DISTANCE VECTOR!
910-// if (Dist < BestDistance)
911+// double monthFrac, monthTemp, maxMoonDate;
912+// monthFrac = std::modf((nextFullMoon-Jan1stJD)/MoonT,&monthTemp);
913+// int PrevMonths = (int)(monthTemp+0.0*monthFrac);
914+// double BestDistance = 1.0; // initial dummy value for Sun-Moon distance;
915+// double Distance; // temporal variable to save Earth-Moon distance at each month.
916+
917+// qDebug() << q_("%1 ").arg(PrevMonths);
918+
919+// for (int i=-PrevMonths; i<13 ; i++)
920 // {
921-// BestDistance = Dist;
922-// nextSuperMoon = jd1;
923+// jd1 = nextFullMoon + MoonT*((double) i);
924+// getMoonDistance(core,jd1,Distance,false);
925+// if (Distance < BestDistance)
926+// { // Month with the largest Full Moon:
927+// BestDistance = Distance;
928+// maxMoonDate = jd1;
929+// };
930 // };
931-// };
932+// maxMoonDate += GMTShift+0.5;
933+// StelUtils::getDateFromJulianDay(maxMoonDate,&fullYear,&fullMonth,&fullDay);
934+// double MoonSize = MoonPerilune/BestDistance*100.;
935+// ObsRange = q_("Greatest Full Moon: %1 "+months[fullMonth-1]+" (%2% of Moon at Perilune)").arg(fullDay).arg(MoonSize,0,'f',2);
936+ };
937 }
938- else
939+ else if (Kind <3)
940 {
941 bestNight = "";
942+ ObsRange = "";
943+ AcroCos = "";
944+
945 };
946
947- ObsRange = "";
948- AcroCos = "";
949-
950
951 // Return the Moon and Earth to its current position:
952- getSunMoonCoords(core,myJD,RAS,DecS,RA,Dec,true);
953+ if (Kind<3)
954+ {
955+ getSunMoonCoords(core,myJD,RAS,DecS,RA,Dec,true);
956+ } else
957+ {
958+ getPlanetCoords(core,myJD,RA,Dec,true);
959+ };
960+
961 lastJDMoon = myJD;
962
963+
964 return raises;
965 }
966
967
968=== modified file 'plugins/Observability/src/Observability.hpp'
969--- plugins/Observability/src/Observability.hpp 2012-08-11 18:00:27 +0000
970+++ plugins/Observability/src/Observability.hpp 2012-08-16 18:31:20 +0000
971@@ -108,8 +108,9 @@
972 //! @param ST sidereal time (degrees).
973 virtual double HourAngle2(double RA, double ST);
974
975-//! Solves Moon/Sun Rise/Set/Transit times for the current Julian day. This function updates the variables MoonRise, MoonSet, MoonCulm. Returns success status.
976- virtual bool MoonSunSolve(StelCore* core);
977+//! Solves Moon/Sun/Planet Rise/Set/Transit times for the current Julian day. This function updates the variables MoonRise, MoonSet, MoonCulm. Returns success status.
978+//! @param Kind is 1 for Sun, 2 for Moon, 3 for Solar-System planet.
979+ virtual bool SolarSystemSolve(StelCore* core, int Kind);
980
981 //! Finds the heliacal rise/set dates of the year for the currently-selected object.
982 //! @param Rise day of year of the Acronycal rise.
983@@ -130,6 +131,17 @@
984 virtual void getSunMoonCoords(StelCore* core, double JD, double &RASun, double &DecSun, double &RAMoon, double &DecMoon, bool getBack);
985
986
987+//! computes the selected-planet coordinates at a given Julian date.
988+//! @param core the stellarium core.
989+//! @param JD double for the Julian date.
990+//! @param RA right ascension of the planet (in hours).
991+//! @param Dec declination of the planet (in radians).
992+//! @param getBack controls whether the planet must be returned to its original positions after computation.
993+ virtual void getPlanetCoords(StelCore* core, double JD, double &RA, double &Dec, bool getBack);
994+
995+//! Comptues the Earth-Moon distance (in AU) at a given Julian date. The parameters are similar to those of getSunMoonCoords or getPlanetCoords.
996+ virtual void getMoonDistance(StelCore* core, double JD, double &Distance, bool getBack);
997+
998 //! Returns the angular separation (in radians) between two points.
999 //! @param RA1 right ascension of point 1 (in hours)
1000 //! @param Dec1 declination of point 1 (in radians)
1001@@ -157,8 +169,7 @@
1002
1003 //! Computes the RA, Dec and Rise/Set Sid. times of the selected planet for each day of the current year.
1004 //! @param core the current Stellarium core.
1005-//! @param Name name of the currently selected planet.
1006- virtual void PlanetRADec(StelCore *core, QString Name);
1007+ virtual void PlanetRADec(StelCore *core);
1008
1009 //! Computes the Sun's RA and Dec for each day of a given year.
1010 //! @param core current Stellarium core.
1011@@ -178,7 +189,7 @@
1012 virtual bool CheckRise(int i);
1013
1014 //! Some useful constants and variables(almost self-explanatory).
1015- double Rad2Deg, Rad2Hr, AstroTwiAlti, UA, TFrac, JDsec, Jan1stJD, halfpi, MoonT, nextFullMoon, prevFullMoon, RefFullMoon;
1016+ double Rad2Deg, Rad2Hr, AstroTwiAlti, UA, TFrac, JDsec, Jan1stJD, halfpi, MoonT, nextFullMoon, prevFullMoon, RefFullMoon, GMTShift, MoonPerilune;
1017
1018 //! RA, Dec, observer latitude, object's elevation, and Hour Angle at horizon.
1019 double selRA, selDec, mylat, mylon, alti, horizH, culmAlt, myJD;
1020@@ -201,9 +212,11 @@
1021 //! Matrix to transform coordinates for Sun/Moon ephemeris:
1022 Mat4d LocTrans;
1023
1024-//! Pointer to the Earth:
1025+//! Pointer to the Earth, Moon, and planet:
1026 Planet* myEarth;
1027 Planet* myMoon;
1028+ Planet* myPlanet;
1029+
1030
1031 //! Current simulation year and number of days in the year.;
1032 int currYear, nDays, iAltitude;
1033@@ -221,7 +234,8 @@
1034 Vec3d EquPos, LocPos;
1035
1036 //! Some booleans to check the kind of source selected and the kind of output to produce.
1037- bool isStar,isMoon,isSun,isScreen, LastSun, raised, configChanged;
1038+ bool isStar,isMoon,isSun,isScreen, raised, configChanged, souChanged;
1039+ int LastObject;
1040
1041 //! Some booleans to select the kind of output.
1042 bool show_AcroCos, show_Good_Nights, show_Best_Night, show_Today, show_FullMoon; //, show_Crescent, show_SuperMoon;
1043
1044=== modified file 'plugins/Observability/src/gui/ObservabilityDialog.cpp'
1045--- plugins/Observability/src/gui/ObservabilityDialog.cpp 2012-08-12 16:35:50 +0000
1046+++ plugins/Observability/src/gui/ObservabilityDialog.cpp 2012-08-16 18:31:20 +0000
1047@@ -94,7 +94,7 @@
1048 QString html = "<html><head></head><body>";
1049
1050 html += "<h2>" + q_("Observability Plug-in") + "</h2><table width=\"90%\">";
1051- html += "<tr width=\"30%\"><td><strong>" + q_("Version") + ":</strong></td><td> 1.0.1</td></tr>";
1052+ html += "<tr width=\"30%\"><td><strong>" + q_("Version") + ":</strong></td><td> 1.0.2</td></tr>";
1053 html += "<tr><td><strong>" + q_("Author") + ":</strong></td><td>Ivan Marti-Vidal &lt;i.martividal@gmail.com&gt;</td></tr></table>";
1054
1055 html += "<p>" + q_("Plugin that analyzes the observability of the selected source (or the screen center, if no source is selected). The plugin can show rise, transit, and set times, as well as the best epoch of the year (i.e., largest angular separation from the Sun), the date range when the source is above the horizon at dark night, and the dates of Acronychal and Cosmical rise/set.<br>Ephemeris of the Solar-System objects and parallax effects are taken into account.<br><br> The author thanks Alexander Wolf and Georg Zotti for their advice.<br><br>Ivan Marti-Vidal (Onsala Space Observatory)") + "</p>";
1056@@ -104,8 +104,8 @@
1057 html += QString("<tr><td>%1</td><td>%2</td></tr>").arg(q_("Today ephemeris:")).arg(q_("Self-explanatory. The program will show the rise, set, and culmination (transit) times. The exact times for these ephemeris are given in two ways: as time spans (referred to the current time) and as clock hours (in local time)."));
1058 html += QString("<tr><td>%1</td><td>%2</td></tr>").arg(q_("Acronychal/Cosmical rise/set:")).arg(q_("The Acronychal rise (or set) of an object happens when the object rises (or sets) just when the Sun sets (or rises), respectively. The exact dates of these ephemeris depend on the Observer's location. The dates between the Acronychal set and rise are those when the altitude of the celestial object uses to be high when the Sun is well below the horizon (hence the object can be well observed). On the contrary, the Cosmical rise (or set) happens when both, the object and the Sun, rise (or set) simultaneously. It is obvious that the source is hardly observable (or not observable at all) in the dates between Cosmical set and rise."));
1059 html += QString("<tr><td>%1</td><td>%2</td></tr>").arg(q_("Largest Sun separation:")).arg(q_("Happens when the angular separation between the Sun and the celestial object are maximum. In most cases, this is equivalent to say that the Equatorial longitudes of the Sun and the object differ by 180 degrees, so the Sun is in opposition to the object. When an object is at its maximum possible angular separation from the Sun (no matter if it is a planet or a star), it culminates roughly at midnight, and on the darkest possible area of the Sky at that declination. Hence, that is the 'best' night to observe a particular object."));
1060- html += QString("<tr><td>%1</td><td>%2</td></tr>").arg(q_("Best observed from ... to ...:")).arg(q_("The program computes the range of dates when the celestial object is above the horizon at least during one moment of the night. By 'night', the program consideres the time span when the Sun altitude is below that of the twilight (which can be set by the user; see above). When the objects are fixed on the sky (or are exterior planets), the range of observable epochs for the current year can have two possible forms: either a range from one date to another (e.g., 20 Jan to 15 Sep) or in two steps (from 1 Jan to a given date and from another date to 31 Dec). In the first case, the first date (20 Jan in our example) shall be close to the so-called 'Heliacal rise of a star' and the second date (15 Sep in our example) shall be close to the 'Heliacal set'. In the second case (e.g., a range in the form 1 Jan to 20 May and 21 Sep to 31 Dec), the first date (20 May in our example) would be close to the Heliacal set and the second one (21 Sep in our example) to the Heliacal rise. More exact equations to estimate the Heliacal rise/set of stars and planets (which will not depend on the mere input of a twilight Sun elevation by the user) will be implemented in future versions of this plugin."));
1061- html += QString("<tr><td>%1</td><td>%2</td></tr>").arg(q_("Full Moon:")).arg(q_("When the Moon is selected, the program can compute the exact closest dates (up to 1 minute accuracy) of the Moon's opposition to the Sun."));
1062+ html += QString("<tr><td>%1</td><td>%2</td></tr>").arg(q_("Nights with source above horizon:")).arg(q_("The program computes the range of dates when the celestial object is above the horizon at least during one moment of the night. By 'night', the program considers the time span when the Sun altitude is below that of the twilight (which can be set by the user; see above). When the objects are fixed on the sky (or are exterior planets), the range of observable epochs for the current year can have two possible forms: either a range from one date to another (e.g., 20 Jan to 15 Sep) or in two steps (from 1 Jan to a given date and from another date to 31 Dec). In the first case, the first date (20 Jan in our example) shall be close to the so-called 'Heliacal rise of a star' and the second date (15 Sep in our example) shall be close to the 'Heliacal set'. In the second case (e.g., a range in the form 1 Jan to 20 May and 21 Sep to 31 Dec), the first date (20 May in our example) would be close to the Heliacal set and the second one (21 Sep in our example) to the Heliacal rise. More exact equations to estimate the Heliacal rise/set of stars and planets (which will not depend on the mere input of a twilight Sun elevation by the user) will be implemented in future versions of this plugin."));
1063+ html += QString("<tr><td>%1</td><td>%2</td></tr>").arg(q_("Full Moon:")).arg(q_("When the Moon is selected, the program can compute the exact closest dates of the Moon's opposition to the Sun."));
1064 html += "</table>";
1065 html += "</body></html>";
1066
1067
1068=== modified file 'plugins/Observability/src/gui/ObservabilityDialog.ui'
1069--- plugins/Observability/src/gui/ObservabilityDialog.ui 2012-08-12 12:12:04 +0000
1070+++ plugins/Observability/src/gui/ObservabilityDialog.ui 2012-08-16 18:31:20 +0000
1071@@ -177,7 +177,7 @@
1072 <item>
1073 <widget class="QCheckBox" name="Goods">
1074 <property name="text">
1075- <string>Range of observable epochs</string>
1076+ <string>Nights with the source above horizon</string>
1077 </property>
1078 </widget>
1079 </item>