• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

Stellarium / stellarium / 17068063291

19 Aug 2025 11:22AM UTC coverage: 11.766%. Remained the same
17068063291

push

github

alex-w
Reformatting

14706 of 124990 relevant lines covered (11.77%)

18303.49 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

0.0
/src/core/StelObject.cpp
1
/*
2
 * Stellarium
3
 * Copyright (C) 2006 Johannes Gajdosik
4
 *
5
 * This program is free software; you can redistribute it and/or
6
 * modify it under the terms of the GNU General Public License
7
 * as published by the Free Software Foundation; either version 2
8
 * of the License, or (at your option) any later version.
9
 *
10
 * This program is distributed in the hope that it will be useful,
11
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
 * GNU General Public License for more details.
14
 *
15
 * You should have received a copy of the GNU General Public License
16
 * along with this program; if not, write to the Free Software
17
 * Foundation, Inc., 51 Franklin Street, Suite 500, Boston, MA  02110-1335, USA.
18
 */
19

20

21
#include "StelObject.hpp"
22
#include "Constellation.hpp"
23
#include "ConstellationMgr.hpp"
24
#include "StelObjectMgr.hpp"
25
#include "StelApp.hpp"
26
#include "StelCore.hpp"
27
#include "StelUtils.hpp"
28
#include "StelTranslator.hpp"
29
#include "StelSkyDrawer.hpp"
30
#include "RefractionExtinction.hpp"
31
#include "StelLocation.hpp"
32
#include "StelObserver.hpp"
33
#include "SolarSystem.hpp"
34
#include "StelModuleMgr.hpp"
35
#include "LandscapeMgr.hpp"
36
#include "SpecificTimeMgr.hpp"
37
#include "planetsephems/sidereal_time.h"
38
#include "planetsephems/precession.h"
39

40
#include <QRegularExpression>
41
#include <QDebug>
42
#include <QSettings>
43

44
int StelObject::stelObjectPMetaTypeID = qRegisterMetaType<StelObjectP>();
45

46
Vec3d StelObject::getEquinoxEquatorialPos(const StelCore* core) const
×
47
{
48
        return core->j2000ToEquinoxEqu(getJ2000EquatorialPos(core), StelCore::RefractionOff);
×
49
}
50

51
Vec3d StelObject::getEquinoxEquatorialPosApparent(const StelCore* core) const
×
52
{
53
        return core->j2000ToEquinoxEqu(getJ2000EquatorialPos(core), StelCore::RefractionOn);
×
54
}
55

56
Vec3d StelObject::getEquinoxEquatorialPosAuto(const StelCore* core) const
×
57
{
58
        return core->j2000ToEquinoxEqu(getJ2000EquatorialPos(core), StelCore::RefractionAuto);
×
59
}
60

61

62
// Get observer local sidereal coordinate
63
Vec3d StelObject::getSiderealPosGeometric(const StelCore* core) const
×
64
{
65
        return Mat4d::zrotation(-core->getLocalSiderealTime())* getEquinoxEquatorialPos(core);
×
66
}
67

68
// Get observer local sidereal coordinates, deflected by refraction
69
Vec3d StelObject::getSiderealPosApparent(const StelCore* core) const
×
70
{
71
        Vec3d v=getAltAzPosApparent(core); // These already come with refraction!
×
72
        v = core->altAzToEquinoxEqu(v, StelCore::RefractionOff);
×
73
        return Mat4d::zrotation(-core->getLocalSiderealTime())*v;
×
74
}
75

76
Vec3d StelObject::getAltAzPosGeometric(const StelCore* core) const
×
77
{
78
        return core->j2000ToAltAz(getJ2000EquatorialPos(core), StelCore::RefractionOff);
×
79
}
80

81
// Get observer-centered alt/az position
82
Vec3d StelObject::getAltAzPosApparent(const StelCore* core) const
×
83
{
84
        return core->j2000ToAltAz(getJ2000EquatorialPos(core), StelCore::RefractionOn);
×
85
}
86

87
// Get observer-centered alt/az position
88
Vec3d StelObject::getAltAzPosAuto(const StelCore* core) const
×
89
{
90
        return core->j2000ToAltAz(getJ2000EquatorialPos(core), StelCore::RefractionAuto);
×
91
}
92

93
// Get observer-centered galactic position
94
Vec3d StelObject::getGalacticPos(const StelCore *core) const
×
95
{
96
        return core->j2000ToGalactic(getJ2000EquatorialPos(core));
×
97
}
98

99
// Get observer-centered supergalactic position
100
Vec3d StelObject::getSupergalacticPos(const StelCore *core) const
×
101
{
102
        return core->j2000ToSupergalactic(getJ2000EquatorialPos(core));
×
103
}
104

105
// Get parallactic angle, which is the deviation between zenith angle and north angle.
106
// Meeus, Astronomical Algorithms, 2nd ed. (1998), p.98.
107
float StelObject::getParallacticAngle(const StelCore* core) const
×
108
{
109
        const double phi=static_cast<double>(core->getCurrentLocation().getLatitude())*M_PI/180.0;
×
110
        const Vec3d siderealPos=getSiderealPosApparent(core);
×
111
        double delta, ha;
112
        StelUtils::rectToSphe(&ha, &delta, siderealPos);
×
113
        ha *= -1.0; // We must invert the orientation sense in case of sidereal positions!
×
114

115
        // A rare condition! Object exactly in zenith, avoid undefined result.
116
        if ((ha==0.0) && ((delta-phi)==0.0))
×
117
                return 0.0f;
×
118
        else
119
                return static_cast<float>(atan2(sin(ha), tan(phi)*cos(delta)-sin(delta)*cos(ha)));
×
120
}
121

122
// Checking position an object above mathematical horizon for current location
123
bool StelObject::isAboveHorizon(const StelCore *core) const
×
124
{
125
        float az, alt;
126
        StelUtils::rectToSphe(&az, &alt, getAltAzPosAuto(core));
×
127
        return (alt >= 0.f);
×
128
}
129

130
// Checking position an object above real horizon for current location
131
bool StelObject::isAboveRealHorizon(const StelCore *core) const
×
132
{
133
        bool r = true;
×
134
        LandscapeMgr* lmgr = GETSTELMODULE(LandscapeMgr);
×
135
        if (lmgr->getFlagLandscape())
×
136
        {
137
                if (lmgr->getLandscapeOpacity(getAltAzPosAuto(core))>0.85f) // landscape displayed
×
138
                        r = false;
×
139
        }
140
        else
141
                r = isAboveHorizon(core); // check object is below mathematical horizon
×
142

143
        return r;
×
144
}
145

146
float StelObject::getVMagnitude(const StelCore* core) const 
×
147
{
148
        Q_UNUSED(core)
149
        return 99.f;
×
150
}
151

152
Vec4d StelObject::getRTSTime(const StelCore *core, const double altitude) const
×
153
{
154
        const StelLocation loc=core->getCurrentLocation();
×
155
        if (loc.name.contains("->")) // a spaceship
×
156
                return Vec4d(0., 0., 0., -1000.);
×
157

158
        //StelObjectMgr* omgr=GETSTELMODULE(StelObjectMgr);
159
        double ho = 0.;
×
160
        if (core->getSkyDrawer()->getFlagHasAtmosphere())
×
161
        {
162
                // canonical" refraction at horizon is -34'. Replace by pressure-dependent value here!
163
                // This fixes 0-degree refraction. Not sure if we use refracted position throughout? Canonical ephemerides have -6/-12/-18 without refraction.
164
                Refraction refraction=core->getSkyDrawer()->getRefraction();
×
165
                Vec3d zeroAlt(1.0,0.0,0.0);
×
166
                refraction.backward(zeroAlt);
×
167
                ho += asin(zeroAlt[2]);
×
168
        }
×
169
        if (altitude != 0.)
×
170
                ho = altitude*M_PI_180; // Not sure if we use refraction for off-zero settings?
×
171
        const double phi = static_cast<double>(loc.getLatitude()) * M_PI_180;
×
172
        const double L = static_cast<double>(loc.getLongitude()) * M_PI_180; // OUR longitude. Meeus has it reversed
×
173
        PlanetP obsPlanet = core->getCurrentPlanet();
×
174
        const double rotDuration = obsPlanet->getSiderealDay();
×
175
        const double currentJD=core->getJD();
×
176
        const double currentJDE=core->getJDE();
×
177
        const double utcShift = core->getUTCOffset(currentJD) / 24.;
×
178
        int year, month, day, currentdate;
179
        StelUtils::getDateFromJulianDay(currentJD+utcShift, &year, &month, &currentdate);
×
180

181
        // And convert to equatorial coordinates of date. We can also use this day's current aberration, given the other uncertainties/omissions.
182
        const Vec3d eq_2=getEquinoxEquatorialPos(core);
×
183
        double ra2, de2;
184
        StelUtils::rectToSphe(&ra2, &de2, eq_2);
×
185
        // Around ra~12 there may be a jump between 12h and -12h which could crash interpolation. We better make sure to have either negative RA or RA>24 in this case.
186
        if (cos(ra2)<0.)
×
187
        {
188
                ra2=StelUtils::fmodpos(ra2, 2*M_PI);
×
189
        }
190

191
        // 3. Approximate times:
192
        // we use Sidereal Time of Place!
193
        const double Theta2=obsPlanet->getSiderealTime(currentJD, currentJDE) * (M_PI/180.) + L;  // [radians]
×
194
        double cosH0=(sin(ho)-sin(phi)*sin(de2))/(cos(phi)*cos(de2));
×
195

196
        //omgr->removeExtraInfoStrings(StelObject::DebugAid);
197
        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("&alpha;<sub>2</sub>: %1=%2 &delta;<sub>2</sub>: %3<br/>").arg(QString::number(ra2, 'f', 4)).arg(StelUtils::radToHmsStr(ra2)).arg(StelUtils::radToDmsStr(de2)));
198
        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("h<sub>0</sub>= %1<br/>").arg(StelUtils::radToDmsStr(ho)));
199
        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("JD<sub>2</sub>= %1<br/>").arg(QString::number(currentJD, 'f', 5)));
200
        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("&Theta;<sub>2</sub>= %1<br/>").arg(StelUtils::radToHmsStr(Theta2)));
201
        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("cos H<sub>0</sub>= %1<br/>").arg(QString::number(cosH0, 'f', 4)));
202

203

204
        double h2=StelUtils::fmodpos(Theta2-ra2, 2.*M_PI); if (h2>M_PI) h2-=2.*M_PI; // Hour angle at currentJD. This should be [-pi, pi]
×
205
        // Find approximation of transit time
206
        //double JDt=currentJD-h2/(M_PI*2.)*rotRate;
207
        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("h<sub>2</sub>= %1<br/>").arg(QString::number(h2, 'f', 4)));
208
        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("JD<sub>t</sub>= %1<br/>").arg(QString::number(JDt, 'f', 4)));
209

210
        // In terms of chapter 15, where m0, m1 and m2 are fractions of day within the current day, we use mr, mt, ms as fractions of day from currentJD, and they lie within [-1...+1].
211

212
        double mr, ms, flag=0.;
×
213
        double mt=-h2*(0.5*rotDuration/M_PI);
×
214
        // Transit should occur on current date
215
        StelUtils::getDateFromJulianDay(currentJD+mt+utcShift, &year, &month, &day);
×
216
        if (day != currentdate)
×
217
        {
218
                if (mt<0.)
×
219
                        mt += rotDuration;
×
220
                else
221
                        mt -= rotDuration;
×
222
        }
223

224
        // circumpolar: set rise and set times to lower culmination, i.e. 1/2 rotation from transit
225
        if (fabs(cosH0)>1.)
×
226
        {
227
                flag = (cosH0<-1.) ? 100 : -100; // circumpolar / never rises
×
228
                mr   = (cosH0<-1.) ? mt-0.5*rotDuration : mt;
×
229
                ms   = (cosH0<-1.) ? mt+0.5*rotDuration : mt;
×
230
        }
231
        else
232
        {
233
                const double H0 = acos(cosH0);
×
234
                //omgr->addToExtraInfoString(StelObject::DebugAid, QString("H<sub>0</sub>= %1<br/>").arg(QString::number(H0*M_180_PI, 'f', 6)));
235

236
                mr = mt - H0*rotDuration/(2.*M_PI);
×
237
                ms = mt + H0*rotDuration/(2.*M_PI);
×
238
        }
239

240
        // Rise should occur on current date
241
        StelUtils::getDateFromJulianDay(currentJD+mr+utcShift, &year, &month, &day);
×
242
        if (day != currentdate)
×
243
        {
244
                if (mr<0.)
×
245
                        mr += rotDuration;
×
246
                else
247
                        mr -= rotDuration;
×
248
        }
249

250
        // Set should occur on current date
251
        StelUtils::getDateFromJulianDay(currentJD+ms+utcShift, &year, &month, &day);
×
252
        if (day != currentdate)
×
253
        {
254
                if (ms<0.)
×
255
                        ms += rotDuration;
×
256
                else
257
                        ms -= rotDuration;
×
258
        }
259

260
        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("m<sub>t</sub>= %1<br/>").arg(QString::number(mt, 'f', 6)));
261
        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("m<sub>r</sub>= %1<br/>").arg(QString::number(mr, 'f', 6)));
262
        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("m<sub>s</sub>= %1<br/>").arg(QString::number(ms, 'f', 6)));
263

264
        // Not quite done! Do the final tweaks...
265
        if (fabs(cosH0)<1.)
×
266
        {
267
                // RISE
268
                int iterations=0; // add this to limit the loops, just in case.
×
269
                double Delta_mr=1.;
×
270
                while (Delta_mr > 1./8640.) // Do that until accurate to 10 seconds
×
271
                {
272
                        const double theta_mr=obsPlanet->getSiderealTime(currentJD+mr, currentJDE+mr) * (M_PI/180.) + L;  // [radians]
×
273
                        double hr=StelUtils::fmodpos(theta_mr-ra2, 2.*M_PI); if (hr>M_PI) hr-=2.*M_PI; // Hour angle of the rising RA at currentJD. This should be [-pi, pi]
×
274
                        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("h<sub>r</sub>': %1 = %2<br/>").arg(QString::number(hr, 'f', 6)).arg(StelUtils::radToHmsStr(hr, true)));
275

276
                        double ar=asin(sin(phi)*sin(de2)+cos(phi)*cos(de2)*cos(hr)); // altitude at this hour angle
×
277

278
                        Delta_mr= (ar-ho)/(cos(de2)*cos(phi)*sin(hr)) / (M_PI*2.);
×
279
                        Delta_mr=StelUtils::fmodpos(Delta_mr+0.5, 1.0)-0.5; // ensure this is a small correction
×
280
                        mr+=Delta_mr;
×
281

282
                        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("alt<sub>r</sub>': %1 = %2<br/>").arg(QString::number(ar, 'f', 6)).arg(StelUtils::radToDmsStr(ar)));
283
                        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("&Delta;<sub>mr</sub>'= %1<br/>").arg(QString::number(Delta_mr, 'f', 6)));
284
                        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("m<sub>r</sub>' = %1<br/>").arg(QString::number(mr, 'f', 6)));
285

286
                        if (++iterations >= 5)
×
287
                                break;
×
288
                }
289
                // SET
290
                iterations=0; // add this to limit the loops, just in case.
×
291
                double Delta_ms=1.;
×
292
                while (Delta_ms > 1./8640.) // Do that until accurate to 10 seconds
×
293
                {
294
                        const double theta_ms=obsPlanet->getSiderealTime(currentJD+ms, currentJDE+ms) * (M_PI/180.) + L;  // [radians]
×
295
                        double hs=StelUtils::fmodpos(theta_ms-ra2, 2.*M_PI); if (hs>M_PI) hs-=2.*M_PI; // Hour angle of the setting RA at currentJD. This should be [-pi, pi]
×
296
                        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("h<sub>s</sub>': %1 = %2<br/>").arg(QString::number(hs, 'f', 6)).arg(StelUtils::radToHmsStr(hs, true)));
297

298
                        double as=asin(sin(phi)*sin(de2)+cos(phi)*cos(de2)*cos(hs)); // altitude at this hour angle
×
299

300
                        Delta_ms= (as-ho)/(cos(de2)*cos(phi)*sin(hs)) / (M_PI*2.);
×
301
                        Delta_ms=StelUtils::fmodpos(Delta_ms+0.5, 1.0)-0.5; // ensure this is a small correction
×
302
                        ms+=Delta_ms;
×
303

304
                        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("alt<sub>s</sub>': %1 = %2<br/>").arg(QString::number(as, 'f', 6)).arg(StelUtils::radToDmsStr(as)));
305
                        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("&Delta;<sub>ms</sub>'= %1<br/>").arg(QString::number(Delta_ms, 'f', 6)));
306
                        //omgr->addToExtraInfoString(StelObject::DebugAid, QString("m<sub>s</sub>' = %1<br/>").arg(QString::number(ms, 'f', 6)));
307

308
                        if (++iterations >= 5)
×
309
                                break;
×
310
                }
311
        }
312
        return Vec4d(currentJD+mr, currentJD+mt, currentJD+ms, flag);
×
313
}
×
314

315
float StelObject::getSelectPriority(const StelCore* core) const
×
316
{
317
        return qMin(getVMagnitudeWithExtinction(core), 15.0f);
×
318
}
319

320
float StelObject::getVMagnitudeWithExtinction(const StelCore* core, const float knownVMag, const float& magoffset) const
×
321
{
322
        Vec3d altAzPos = getAltAzPosGeometric(core);
×
323
        altAzPos.normalize();
×
324
        float vMag = (knownVMag>-1000.f ? knownVMag : getVMagnitude(core) + magoffset);
×
325
        // without the test, planets flicker stupidly in fullsky atmosphere-less view.
326
        if (core->getSkyDrawer()->getFlagHasAtmosphere())
×
327
                core->getSkyDrawer()->getExtinction().forward(altAzPos, &vMag);
×
328
        return vMag;
×
329
}
330

331
float StelObject::getAirmass(const StelCore *core) const
×
332
{
333
        double az_app, alt_app;
334
        StelUtils::rectToSphe(&az_app, &alt_app, getAltAzPosApparent(core));
×
335
        Q_UNUSED(az_app)
336
        if (core->getSkyDrawer()->getFlagHasAtmosphere() && (alt_app>-2.0*M_PI_180)) // Don't compute extinction much below horizon where model is meaningless.
×
337
        {
338
                const Extinction &extinction=core->getSkyDrawer()->getExtinction();
×
339
                return extinction.airmass(static_cast<float>(std::cos(M_PI_2-alt_app)), true);
×
340
        }
341
        else
342
                return -1.f;
×
343
}
344

345
// Format the magnitude info string for the object, allow offset from changing distance
346
QString StelObject::getMagnitudeInfoString(const StelCore *core, const InfoStringGroup& flags, const int decimals, const float& magoffset) const
×
347
{
348
        if (flags&Magnitude)
×
349
        {
350
                float mag = getVMagnitude(core);
×
351
                QString str = QString("%1: <b>%2</b>").arg(q_("Magnitude"), QString::number(getVMagnitude(core) + magoffset, 'f', decimals));
×
352
                const float airmass = getAirmass(core);
×
353
                if (airmass>-1.f) // Don't show extincted magnitude much below horizon where model is meaningless.
×
354
                        str += QString(" (%1 <b>%2</b> %3 <b>%4</b> %5)").arg(q_("reduced to"), QString::number(getVMagnitudeWithExtinction(core, mag, magoffset), 'f', decimals), q_("by"), QString::number(airmass, 'f', 2), q_("Airmasses"));
×
355
                str += "<br/>" + getExtraInfoStrings(Magnitude).join("");
×
356
                return str;
×
357
        }
×
358
        else
359
                return QString();
×
360
}
361

362
// Format the positional info string contain J2000/of date/altaz/hour angle positions for the object
363
// computing positional info sometimes also compute others like proper motion too, so store them in the object
364
QString StelObject::getCommonInfoString(const StelCore *core, const InfoStringGroup& flags) const
×
365
{
366
        StelApp& app = StelApp::getInstance();
×
367
        StelObjectMgr* omgr=GETSTELMODULE(StelObjectMgr);
×
368
        const float airmass = getAirmass(core);
×
369
        const StelLocation currentLocation=core->getCurrentLocation();
×
370
        const bool onTransitionToNewLocation=core->getCurrentObserver()->isTraveling();
×
371
        const bool withAtmosphere = core->getSkyDrawer()->getFlagHasAtmosphere();
×
372
        const bool withDecimalDegree = app.getFlagShowDecimalDegrees();
×
373
        const bool useSouthAzimuth = app.getFlagSouthAzimuthUsage();
×
374
        const bool withTables = app.getFlagUseFormattingOutput();
×
375
        const bool withDesignations = app.getFlagUseCCSDesignation();
×
376
        const QString cepoch = qc_("on date", "coordinates for current epoch");
×
377
        const QString currentPlanet = core->getCurrentPlanet()->getEnglishName();
×
378
        const QString apparent = " " + (withAtmosphere && (airmass>-1.f) ? q_("(apparent)") : "");
×
379
        const QString dash = QChar(0x2014);
×
380
        const double currentJD = core->getJD();
×
381
        const double utcShift = core->getUTCOffset(currentJD) / 24.; // Fix DST shift...
×
382
        QString currentObjStr = getEnglishName();
×
383
        if (currentObjStr == "") // If objects have no name, we need something to represent it.
×
384
        {
385
                double ra_j2000, dec_j2000;
386
                StelUtils::rectToSphe(&ra_j2000,&dec_j2000,getJ2000EquatorialPos(core));
×
387
                currentObjStr = StelUtils::radToHmsStr(ra_j2000);
×
388
        }
389

390
        const Vec3d eqNow=getEquinoxEquatorialPos(core);
×
391
        QString res, firstCoordinate, secondCoordinate;
×
392
        int currentYear, currentMonth, currentDay;
393
        double currentLatitude=static_cast<double>(currentLocation.getLatitude());
×
394
        double currentLongitude=static_cast<double>(currentLocation.getLongitude());
×
395

396
        StelUtils::getDateFromJulianDay(currentJD+utcShift, &currentYear, &currentMonth, &currentDay);
×
397
        double az_app, alt_app;
398
        StelUtils::rectToSphe(&az_app,&alt_app,getAltAzPosApparent(core));
×
399
        Q_UNUSED(az_app)
400

401
        if (withTables)
×
402
                res += "<table style='margin:0em 0em 0em -0.125em;border-spacing:0px;border:0px;'>";
×
403

404
        // TRANSLATORS: Right ascension/Declination
405
        const QString RADec = withDesignations ? QString("&alpha;/&delta;") : qc_("RA/Dec", "celestial coordinate system");
×
406

407
        if (flags&RaDecJ2000)
×
408
        {
409
                double dec_j2000, ra_j2000;
410
                StelUtils::rectToSphe(&ra_j2000,&dec_j2000,getJ2000EquatorialPos(core));
×
411
                if (withDecimalDegree)
×
412
                {
413
                        firstCoordinate  = StelUtils::radToDecDegStr(ra_j2000,5,false,true);
×
414
                        secondCoordinate = StelUtils::radToDecDegStr(dec_j2000);
×
415
                }
416
                else
417
                {
418
                        firstCoordinate  = StelUtils::radToHmsStr(ra_j2000,true);
×
419
                        secondCoordinate = StelUtils::radToDmsStr(dec_j2000,true);
×
420
                }
421

422
                if (withTables)
×
423
                        res += QString("<tr><td>%1 (J2000.0):</td><td style='text-align:right;'>%2/</td><td style='text-align:right;'>%3</td><td></td></tr>").arg(RADec, firstCoordinate, secondCoordinate);
×
424
                else
425
                        res += QString("%1 (J2000.0): %2/%3<br/>").arg(RADec, firstCoordinate, secondCoordinate);
×
426
                res += getExtraInfoStrings(RaDecJ2000).join("");
×
427
                res += omgr->getExtraInfoStrings(RaDecJ2000).join("");
×
428
        }
429

430
        if (flags&RaDecOfDate)
×
431
        {
432
                double dec_equ, ra_equ;
433
                StelUtils::rectToSphe(&ra_equ,&dec_equ,eqNow);
×
434
                if (withDecimalDegree)
×
435
                {
436
                        firstCoordinate  = StelUtils::radToDecDegStr(ra_equ,5,false,true);
×
437
                        secondCoordinate = StelUtils::radToDecDegStr(dec_equ);
×
438
                }
439
                else
440
                {
441
                        firstCoordinate  = StelUtils::radToHmsStr(ra_equ,true);
×
442
                        secondCoordinate = StelUtils::radToDmsStr(dec_equ,true);
×
443
                }
444

445
                if (withTables)
×
446
                        res += QString("<tr><td>%1 (%4):</td><td style='text-align:right;'>%2/</td><td style='text-align:right;'>%3</td><td></td></tr>").arg(RADec, firstCoordinate, secondCoordinate, cepoch);
×
447
                else
448
                        res += QString("%1 (%4): %2/%3<br/>").arg(RADec, firstCoordinate, secondCoordinate, cepoch);
×
449
                res += getExtraInfoStrings(RaDecOfDate).join("");
×
450
                res += omgr->getExtraInfoStrings(RaDecOfDate).join("");
×
451
        }
452

453
        if (flags&HourAngle)
×
454
        {
455
                double dec_sidereal, ra_sidereal, ha_sidereal;
456
                StelUtils::rectToSphe(&ra_sidereal,&dec_sidereal,getSiderealPosGeometric(core));
×
457
                ra_sidereal = 2.*M_PI-ra_sidereal;
×
458
                if (withAtmosphere && (alt_app>-2.0*M_PI/180.0)) // Don't show refracted values much below horizon where model is meaningless.
×
459
                {
460
                        StelUtils::rectToSphe(&ra_sidereal,&dec_sidereal,getSiderealPosApparent(core));
×
461
                        ra_sidereal = 2.*M_PI-ra_sidereal;
×
462
                        if (withDecimalDegree)
×
463
                        {
464
                                ha_sidereal = ra_sidereal*12/M_PI;
×
465
                                if (ha_sidereal>24.)
×
466
                                        ha_sidereal -= 24.;
×
467
                                firstCoordinate  = QString("%1h").arg(ha_sidereal, 0, 'f', 5);
×
468
                                secondCoordinate = StelUtils::radToDecDegStr(dec_sidereal);
×
469
                        }
470
                        else
471
                        {
472
                                firstCoordinate  = StelUtils::radToHmsStr(ra_sidereal,true);
×
473
                                secondCoordinate = StelUtils::radToDmsStr(dec_sidereal,true);
×
474
                        }
475
                }
476
                else
477
                {
478
                        if (withDecimalDegree)
×
479
                        {
480
                                ha_sidereal = ra_sidereal*12/M_PI;
×
481
                                if (ha_sidereal>24.)
×
482
                                        ha_sidereal -= 24.;
×
483
                                firstCoordinate  = QString("%1h").arg(ha_sidereal, 0, 'f', 5);
×
484
                                secondCoordinate = StelUtils::radToDecDegStr(dec_sidereal);
×
485
                        }
486
                        else
487
                        {
488
                                firstCoordinate  = StelUtils::radToHmsStr(ra_sidereal,true);
×
489
                                secondCoordinate = StelUtils::radToDmsStr(dec_sidereal,true);
×
490
                        }
491
                }
492

493
                // TRANSLATORS: Hour angle/Declination
494
                const QString HADec = withDesignations ? QString("h/&delta;") : qc_("HA/Dec", "celestial coordinate system");
×
495

496
                if (withTables)
×
497
                        res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2/</td><td style='text-align:right;'>%3</td><td>%4</td></tr>").arg(HADec, firstCoordinate, secondCoordinate, apparent);
×
498
                else
499
                        res += QString("%1: %2/%3 %4<br/>").arg(HADec, firstCoordinate, secondCoordinate, apparent);
×
500
                res += getExtraInfoStrings(HourAngle).join("");
×
501
                res += omgr->getExtraInfoStrings(HourAngle).join("");
×
502
        }
×
503

504
        if (flags&AltAzi)
×
505
        {
506
                // calculate alt az
507
                double az,alt;
508
                StelUtils::rectToSphe(&az,&alt,getAltAzPosGeometric(core));
×
509
                double direction = 3.; // N is zero, E is 90 degrees
×
510
                if (useSouthAzimuth)
×
511
                        direction = 2.;
×
512
                az = direction*M_PI - az;
×
513
                if (az > M_PI*2)
×
514
                        az -= M_PI*2;
×
515
                if (withAtmosphere && (alt_app>-2.0*M_PI/180.0)) // Don't show refracted altitude much below horizon where model is meaningless.
×
516
                {
517
                        if (withDecimalDegree)
×
518
                        {
519
                                firstCoordinate  = StelUtils::radToDecDegStr(az);
×
520
                                secondCoordinate = StelUtils::radToDecDegStr(alt_app);
×
521
                        }
522
                        else
523
                        {
524
                                firstCoordinate  = StelUtils::radToDmsStr(az,true);
×
525
                                secondCoordinate = StelUtils::radToDmsStr(alt_app,true);
×
526
                        }
527
                }
528
                else
529
                {
530
                        if (withDecimalDegree)
×
531
                        {
532
                                firstCoordinate  = StelUtils::radToDecDegStr(az);
×
533
                                secondCoordinate = StelUtils::radToDecDegStr(alt);
×
534
                        }
535
                        else
536
                        {
537
                                firstCoordinate  = StelUtils::radToDmsStr(az,true);
×
538
                                secondCoordinate = StelUtils::radToDmsStr(alt,true);
×
539
                        }
540
                }
541

542
                // TRANSLATORS: Azimuth/Altitude
543
                const QString AzAlt = (withDesignations ? "A/a" : qc_("Az./Alt.", "celestial coordinate system"));
×
544

545
                if (withTables)
×
546
                        res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2/</td><td style='text-align:right;'>%3</td><td>%4</td></tr>").arg(AzAlt, firstCoordinate, secondCoordinate, apparent);
×
547
                else
548
                        res += QString("%1: %2/%3 %4<br/>").arg(AzAlt, firstCoordinate, secondCoordinate, apparent);
×
549
                res += getExtraInfoStrings(AltAzi).join("");
×
550
        }
×
551

552
        if (flags&GalacticCoord)
×
553
        {
554
                double glong, glat;
555
                StelUtils::rectToSphe(&glong, &glat, getGalacticPos(core));
×
556
                if (glong<0.) glong += 2.0*M_PI;
×
557
                if (withDecimalDegree)
×
558
                {
559
                        firstCoordinate  = StelUtils::radToDecDegStr(glong);
×
560
                        secondCoordinate = StelUtils::radToDecDegStr(glat);
×
561
                }
562
                else
563
                {
564
                        firstCoordinate  = StelUtils::radToDmsStr(glong, true);
×
565
                        secondCoordinate = StelUtils::radToDmsStr(glat, true);
×
566
                }
567

568
                // TRANSLATORS: Galactic longitude/latitude
569
                const QString GalLongLat = (withDesignations ? "l/b" : qc_("Gal. long./lat.", "celestial coordinate system"));
×
570
                if (withTables)
×
571
                        res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2/</td><td style='text-align:right;'>%3</td><td></td></tr>").arg(GalLongLat, firstCoordinate, secondCoordinate);
×
572
                else
573
                        res += QString("%1: %2/%3<br/>").arg(GalLongLat, firstCoordinate, secondCoordinate);
×
574
                res += getExtraInfoStrings(GalacticCoord).join("");
×
575
        }
×
576

577
        if (flags&SupergalacticCoord)
×
578
        {
579
                double sglong, sglat;
580
                StelUtils::rectToSphe(&sglong, &sglat, getSupergalacticPos(core));
×
581
                if (sglong<0.) sglong += 2.0*M_PI;
×
582
                if (withDecimalDegree)
×
583
                {
584
                        firstCoordinate  = StelUtils::radToDecDegStr(sglong);
×
585
                        secondCoordinate = StelUtils::radToDecDegStr(sglat);
×
586
                }
587
                else
588
                {
589
                        firstCoordinate  = StelUtils::radToDmsStr(sglong, true);
×
590
                        secondCoordinate = StelUtils::radToDmsStr(sglat, true);
×
591
                }
592

593
                // TRANSLATORS: Supergalactic longitude/latitude
594
                const QString SGalLongLat = (withDesignations ? "SGL/SGB" : qc_("Supergal. long./lat.", "celestial coordinate system"));
×
595

596
                if (withTables)
×
597
                        res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2/</td><td style='text-align:right;'>%3</td><td></td></tr>").arg(SGalLongLat, firstCoordinate, secondCoordinate);
×
598
                else
599
                        res += QString("%1: %2/%3<br/>").arg(SGalLongLat, firstCoordinate, secondCoordinate);
×
600
                res += getExtraInfoStrings(SupergalacticCoord).join("");
×
601
        }
×
602

603
        // N.B. Ecliptical coordinates are particularly earth-bound.
604
        // It may be OK to have terrestrial ecliptical coordinates of J2000.0 (standard epoch) because those are in practice linked with VSOP XY plane,
605
        // and because the ecliptical grid of J2000 is also shown for observers on other planets.
606
        // The formulation here has never computed the true position of any observer planet's orbital plane except for Earth,
607
        // or ever displayed the coordinates in the observer planet's equivalent to Earth's ecliptical coordinates.
608
        // As quick test you can observe if in any "Ecliptic coordinate" as seen from e.g. Mars or Jupiter the Sun was ever close to beta=0 (except if crossing the node...).
609

610
        // TRANSLATORS: Ecliptic longitude/latitude
611
        const QString EqlLongLat = (withDesignations ? QString("&lambda;/&beta;") :
×
612
                                                       qc_("Ecl. long./lat.", "celestial coordinate system") );
×
613

614
        if (flags&EclipticCoordJ2000)
×
615
        {
616
                const double eclJ2000=GETSTELMODULE(SolarSystem)->getEarth()->getRotObliquity(2451545.0);
×
617
                double ra_equ, dec_equ, lambda, beta;
618
                StelUtils::rectToSphe(&ra_equ,&dec_equ,getJ2000EquatorialPos(core));
×
619
                StelUtils::equToEcl(ra_equ, dec_equ, eclJ2000, &lambda, &beta);
×
620
                if (lambda<0) lambda+=2.0*M_PI;
×
621
                if (withDecimalDegree)
×
622
                {
623
                        firstCoordinate  = StelUtils::radToDecDegStr(lambda);
×
624
                        secondCoordinate = StelUtils::radToDecDegStr(beta);
×
625
                }
626
                else
627
                {
628
                        firstCoordinate  = StelUtils::radToDmsStr(lambda, true);
×
629
                        secondCoordinate = StelUtils::radToDmsStr(beta, true);
×
630
                }
631

632
                if (withTables)
×
633
                        res += QString("<tr><td>%1 (J2000.0):</td><td style='text-align:right;'>%2/</td><td style='text-align:right;'>%3</td><td></td></tr>").arg(EqlLongLat, firstCoordinate, secondCoordinate);
×
634
                else
635
                        res += QString("%1 (J2000.0): %2/%3<br/>").arg(EqlLongLat, firstCoordinate, secondCoordinate);
×
636
                res += getExtraInfoStrings(EclipticCoordJ2000).join("");
×
637
        }
638

639
        if ((flags&EclipticCoordOfDate) && (currentPlanet=="Earth"))
×
640
        {
641
                const double jde=core->getJDE();
×
642
                double eclJDE = GETSTELMODULE(SolarSystem)->getEarth()->getRotObliquity(jde);
×
643
                double ra_equ, dec_equ, lambdaJDE, betaJDE;
644

645
                StelUtils::rectToSphe(&ra_equ,&dec_equ,eqNow);
×
646
                StelUtils::equToEcl(ra_equ, dec_equ, eclJDE, &lambdaJDE, &betaJDE);
×
647
                if (lambdaJDE<0) lambdaJDE+=2.0*M_PI;
×
648
                if (withDecimalDegree)
×
649
                {
650
                        firstCoordinate  = StelUtils::radToDecDegStr(lambdaJDE);
×
651
                        secondCoordinate = StelUtils::radToDecDegStr(betaJDE);
×
652
                }
653
                else
654
                {
655
                        firstCoordinate  = StelUtils::radToDmsStr(lambdaJDE, true);
×
656
                        secondCoordinate = StelUtils::radToDmsStr(betaJDE, true);
×
657
                }
658

659
                if (withTables)
×
660
                        res += QString("<tr><td>%1 (%4):</td><td style='text-align:right;'>%2/</td><td style='text-align:right;'>%3</td><td></td></tr>").arg(EqlLongLat, firstCoordinate, secondCoordinate, cepoch) + "</table>";
×
661
                else
662
                        res += QString("%1 (%4): %2/%3<br/>").arg(EqlLongLat, firstCoordinate, secondCoordinate, cepoch);
×
663
                res += getExtraInfoStrings(EclipticCoordOfDate).join("");
×
664

665
                // GZ Only for now: display epsilon_A, angle between Earth's Axis and ecl. of date.
666
                if (withDecimalDegree)
×
667
                        firstCoordinate = StelUtils::radToDecDegStr(eclJDE);
×
668
                else
669
                        firstCoordinate = StelUtils::radToDmsStr(eclJDE, true);
×
670

671
                QString eqlObl = q_("Ecliptic obliquity");
×
672
                if (withTables)
×
673
                {
674
                        res += "<table style='margin:0em 0em 0em -0.125em;border-spacing:0px;border:0px;'>";
×
675
                        res += QString("<tr><td>%1 (%3):</td><td>%2</td></tr>").arg(eqlObl, firstCoordinate, cepoch);
×
676
                }
677
                else
678
                        res += QString("%1 (%3): %2<br/>").arg(eqlObl, firstCoordinate, cepoch);
×
679
        }
×
680

681
        if (withTables)
×
682
                 res += "</table>";
×
683

684
        // Specialized plugins (e.g. Astro Navigation or ethno-astronomical specialties) may want to provide additional types of coordinates here.
685
        if (flags&OtherCoord)
×
686
        {
687
                if (withTables)
×
688
                        res += "<table style='margin:0em 0em 0em -0.125em;border-spacing:0px;border:0px;'>";
×
689
                res += getExtraInfoStrings(OtherCoord).join("");
×
690
                res += omgr->getExtraInfoStrings(OtherCoord).join("");
×
691
                if (withTables)
×
692
                         res += "</table>";
×
693
        }
694

695
        if ((flags&SiderealTime) && (currentPlanet==QStringLiteral("Earth")))
×
696
        {
697
                const double longitude=static_cast<double>(core->getCurrentLocation().getLongitude());
×
698
                double sidereal=(get_mean_sidereal_time(core->getJD(), core->getJDE())  + longitude) / 15.;
×
699
                sidereal=StelUtils::fmodpos(sidereal, 24.);
×
700
                QString STc = q_("Mean Sidereal Time");
×
701
                QString STd = StelUtils::hoursToHmsStr(sidereal);
×
702

703
                if (withTables)
×
704
                {
705
                        res += "<table style='margin:0em 0em 0em -0.125em;border-spacing:0px;border:0px;'>";
×
706
                        res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2</td></tr>").arg(STc, STd);
×
707
                }
708
                else
709
                        res += QString("%1: %2<br/>").arg(STc, STd);
×
710

711
                if (core->getUseNutation())
×
712
                {
713
                        sidereal=(get_apparent_sidereal_time(core->getJD(), core->getJDE()) + longitude) / 15.;
×
714
                        sidereal=StelUtils::fmodpos(sidereal, 24.);
×
715
                        STc = q_("Apparent Sidereal Time");
×
716
                        STd = StelUtils::hoursToHmsStr(sidereal);
×
717
                        if (withTables)
×
718
                                res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2</td></tr>").arg(STc, STd);
×
719
                        else
720
                                res += QString("%1: %2<br/>").arg(STc, STd);
×
721
                }
722
                res += getExtraInfoStrings(flags&SiderealTime).join("");
×
723
                res += omgr->getExtraInfoStrings(flags&SiderealTime).join("");
×
724
                if (withTables && !(flags&RTSTime && !onTransitionToNewLocation && getType()!=QStringLiteral("Satellite") && currentLocation.role!='o'))
×
725
                        res += "</table>";
×
726
        }
×
727

728
        if (flags&RTSTime && getType()!=QStringLiteral("Satellite") && currentLocation.role!='o' && !onTransitionToNewLocation)
×
729
        {
730
                static int prevYear, prevMonth, prevDay;
731
                static QString prevObjStr, prevPlanet;
×
732
                static double prevLatitude, prevLongitude;
733

734
                const bool isSun = (getEnglishName()=="Sun");
×
735
                static Vec4d rts;
×
736
                bool dayChanged = false;
×
737
                bool locationChanged = false;
×
738
                if ((currentYear != prevYear) || (currentMonth != prevMonth) || (currentDay != prevDay))
×
739
                {
740
                        dayChanged = true;
×
741
                }
742

743
                if ((currentLatitude != prevLatitude) || (currentLongitude != prevLongitude))
×
744
                {
745
                        locationChanged = true;
×
746
                }
747

748
                // Avoid frequent RTS recalculation
749
                if ((currentObjStr != prevObjStr) || (currentPlanet != prevPlanet) || dayChanged || locationChanged)
×
750
                {
751
                        rts = getRTSTime(core);
×
752
                }
753
                QString sTransit = qc_("Transit", "celestial event; passage across a meridian");
×
754
                QString sRise = qc_("Rise", "celestial event");
×
755
                QString sSet = qc_("Set", "celestial event");
×
756
                double sunrise = 0.;
×
757
                double sunset = 24.;
×
758
                double hour(0);
×
759
                int year, month, day;
760

761
                if (withTables && !(flags&SiderealTime && currentPlanet==QStringLiteral("Earth")))
×
762
                        res += "<table style='margin:0em 0em 0em -0.125em;border-spacing:0px;border:0px;'>";
×
763

764
                // Rise
765
                StelUtils::getDateFromJulianDay(rts[0]+utcShift, &year, &month, &day);
×
766
                if (rts[3]==30 || rts[3]<0 || rts[3]>50 || day != currentDay) // no rise
×
767
                {
768
                        if (withTables)
×
769
                                res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2</td></tr>").arg(sRise, dash);
×
770
                        else
771
                                res += QString("%1: %2<br/>").arg(sRise, dash);
×
772
                }
773
                else
774
                {
775
                        hour = StelUtils::getHoursFromJulianDay(rts[0]+utcShift);
×
776
                        if (withTables)
×
777
                                res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2</td></tr>").arg(sRise, StelUtils::hoursToHmsStr(hour, true));
×
778
                        else
779
                                res += QString("%1: %2<br/>").arg(sRise, StelUtils::hoursToHmsStr(hour, true));
×
780

781
                        sunrise = hour;
×
782
                }
783

784
                // Transit
785
                StelUtils::getDateFromJulianDay(rts[1]+utcShift, &year, &month, &day);
×
786
                if (rts[3]==20 || day != currentDay) // no transit
×
787
                {
788
                        if (withTables)
×
789
                                res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2</td></tr>").arg(sTransit, dash);
×
790
                        else
791
                                res += QString("%1: %2<br/>").arg(sTransit, dash);
×
792
                }
793
                else {
794
                        hour = StelUtils::getHoursFromJulianDay(rts[1]+utcShift);
×
795

796
                        if (withTables)
×
797
                                res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2</td></tr>").arg(sTransit, StelUtils::hoursToHmsStr(hour, true));
×
798
                        else
799
                                res += QString("%1: %2<br/>").arg(sTransit, StelUtils::hoursToHmsStr(hour, true));
×
800
                }
801

802
                // Set
803
                StelUtils::getDateFromJulianDay(rts[2]+utcShift, &year, &month, &day);
×
804
                if (rts[3]==40 || rts[3]<0 || rts[3]>50 || day != currentDay) // no set
×
805
                {
806
                        if (withTables)
×
807
                                res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2</td></tr>").arg(sSet, dash);
×
808
                        else
809
                                res += QString("%1: %2<br/>").arg(sSet, dash);
×
810
                }
811
                else {
812
                        hour = StelUtils::getHoursFromJulianDay(rts[2]+utcShift);
×
813
                        if (withTables)
×
814
                                res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2</td></tr>").arg(sSet, StelUtils::hoursToHmsStr(hour, true));
×
815
                        else
816
                                res += QString("%1: %2<br/>").arg(sSet, StelUtils::hoursToHmsStr(hour, true));
×
817

818
                        sunset = hour;
×
819
                }
820

821
                if (isSun)
×
822
                {
823
                        QString sMTwilight = qc_("Morning twilight", "celestial event");
×
824
                        QString sETwilight = qc_("Evening twilight", "celestial event");
×
825
                        const double twilightAltitude = GETSTELMODULE(SpecificTimeMgr)->getTwilightAltitude();
×
826
                        QString alt = QString::number(twilightAltitude, 'f', 1);
×
827
                        Vec4d twilight = getRTSTime(core, twilightAltitude);
×
828
                        if (twilight[3]==0.)
×
829
                        {
830
                                hour = StelUtils::getHoursFromJulianDay(twilight[0]+utcShift);
×
831
                                if (withTables)
×
832
                                        res += QString("<tr><td>%1 (h=%2°):</td><td style='text-align:right;'>%3</td></tr>").arg(sMTwilight, alt, StelUtils::hoursToHmsStr(hour, true));
×
833
                                else
834
                                        res += QString("%1 (h=%2°): %3<br/>").arg(sMTwilight, alt, StelUtils::hoursToHmsStr(hour, true));
×
835

836
                                hour = StelUtils::getHoursFromJulianDay(twilight[2]+utcShift);
×
837
                                if (withTables)
×
838
                                        res += QString("<tr><td>%1 (h=%2°):</td><td style='text-align:right;'>%3</td></tr>").arg(sETwilight, alt, StelUtils::hoursToHmsStr(hour, true));
×
839
                                else
840
                                        res += QString("%1 (h=%2°): %3<br/>").arg(sETwilight, alt, StelUtils::hoursToHmsStr(hour, true));
×
841
                        }
842
                        double lengthOfDay = StelUtils::fmodpos(sunset - sunrise, 24.); // prevent negative value
×
843
                        if (lengthOfDay<24. && rts[3]==0.) // avoid showing Daytime: 0h 00m
×
844
                        {
845
                                QString sDay = q_("Daytime");
×
846
                                if (withTables)
×
847
                                        res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2</td></tr>").arg(sDay, StelUtils::hoursToHmsStr(lengthOfDay, true));
×
848
                                else
849
                                        res += QString("%1: %2<br/>").arg(sDay, StelUtils::hoursToHmsStr(lengthOfDay, true));
×
850
                        }
×
851
                }
×
852

853
                if (withTables)
×
854
                        res += "</table>";
×
855

856
                if (rts[3]<0.)
×
857
                {
858
                        if (isSun)
×
859
                                res += q_("Polar night") + "<br />";
×
860
                        else
861
                                res += q_("This object never rises") + "<br />";
×
862
                }
863
                else if (rts[3]>50.)
×
864
                {
865
                        if (isSun)
×
866
                                res += q_("Polar day") + "<br />";
×
867
                        else
868
                                res += q_("Circumpolar (never sets)") + "<br />";
×
869
                }
870
                // These never could have been seen before (??)
871
                //else if (rts[0]>99. && rts[2]<99.)
872
                //        res += q_("Polar dawn") + "<br />";
873
                //else if (rts[0]<99. && rts[2]>99.)
874
                //        res += q_("Polar dusk") + "<br />";
875

876

877
                // Greatest Digression: limiting azimuth and hour angles for stars with upper culmination between pole and zenith
878
                double dec_equ, ra_equ;
879
                StelUtils::rectToSphe(&ra_equ,&dec_equ,eqNow);
×
880
                const double latitude=static_cast<double>(core->getCurrentLocation().getLatitude())*M_PI_180;
×
881
                if (((latitude>0.) && (dec_equ>=latitude)) || ((latitude<0.) && (dec_equ<=latitude)))
×
882
                {
883
                        const double theta=acos(tan(latitude)/tan(dec_equ)); // hour angle
×
884
                        double az=asin(cos(dec_equ)/cos(latitude)); // azimuth (eastern)
×
885
                        // TRANSLATORS: Greatest Eastern Digression is the maximum azimuth for stars with upper culmination between pole and zenith
886
                        QString event(q_("Max. E. Digression"));
×
887
                        // TRANSLATORS: azimuth (abbrev.)
888
                        QString azStr=(withDesignations? qc_("A", "celestial coordinate system") : qc_("Az.", "celestial coordinate system"));
×
889
                        // Translators: hour angle  (abbrev.)
890
                        QString haStr=(withDesignations? qc_("h", "celestial coordinate system") : qc_("HA", "celestial coordinate system"));
×
891
                        if (latitude<0.)
×
892
                                az=M_PI-az;
×
893
                        if (StelApp::getInstance().getFlagSouthAzimuthUsage())
×
894
                                az+=M_PI;
×
895

896
                        if (withDecimalDegree)
×
897
                        {
898
                                firstCoordinate  = StelUtils::radToDecDegStr(az,5,false,true);
×
899
                                secondCoordinate = StelUtils::radToDecDegStr(-theta);
×
900
                        }
901
                        else
902
                        {
903
                                firstCoordinate  = StelUtils::radToDmsStr(az,true);
×
904
                                secondCoordinate = StelUtils::radToHmsStr(-theta,true);
×
905
                        }
906

907
                        if (withTables)
×
908
                        {
909
                                res += "<table style='margin:0em 0em 0em -0.125em;border-spacing:0px;border:0px;'>";
×
910
                                res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2:</td><td style='text-align:right;'>%3</td><td style='text-align:right;'>/%4:</td><td style='text-align:right;'>%5</td></tr>").arg(event,  azStr,  firstCoordinate, haStr, secondCoordinate);
×
911
                        }
912
                        else
913
                                res += QString("%1: %2=%3, %4=%5<br/>").arg(event,  azStr,  firstCoordinate, haStr, secondCoordinate);
×
914

915
                        // TRANSLATORS: Greatest Western Digression is the maximum western azimuth for stars with upper culmination between pole and zenith
916
                        event=q_("Max. W. Digression");
×
917
                        if (withDecimalDegree)
×
918
                        {
919
                                firstCoordinate  = StelUtils::radToDecDegStr(StelUtils::fmodpos(-az, 2.*M_PI),5,false,true);
×
920
                                secondCoordinate = StelUtils::radToDecDegStr(theta);
×
921
                        }
922
                        else
923
                        {
924
                                firstCoordinate  = StelUtils::radToDmsStr(StelUtils::fmodpos(-az, 2.*M_PI),true);
×
925
                                secondCoordinate = StelUtils::radToHmsStr(theta,true);
×
926
                        }
927

928
                        if (withTables)
×
929
                        {
930
                                res += QString("<tr><td>%1:</td><td style='text-align:right;'>%2:</td><td style='text-align:right;'>%3</td><td style='text-align:right;'>/%4:</td><td style='text-align:right;'>%5</td></tr>").arg(event,  azStr,  firstCoordinate, haStr, secondCoordinate);
×
931
                                res += QString("</table>");
×
932
                        }
933
                        else
934
                                res += QString("%1: %2=%3, %4=%5<br/>").arg(event, azStr,  firstCoordinate, haStr, secondCoordinate);
×
935
                }
×
936
                res += getExtraInfoStrings(flags&RTSTime).join(' ');
×
937
                res += omgr->getExtraInfoStrings(flags&RTSTime).join(' ');
×
938

939
                prevObjStr = currentObjStr;
×
940
                prevYear = currentYear;
×
941
                prevMonth = currentMonth;
×
942
                prevDay = currentDay;
×
943
                prevLatitude = currentLatitude;
×
944
                prevLongitude = currentLongitude;
×
945
                prevPlanet = currentPlanet;
×
946
        }
×
947

948
        if (flags&Extra)
×
949
        {
950
                if (getType()!=QStringLiteral("Star"))
×
951
                {
952
                        QString pa;
×
953
                        const double par = static_cast<double>(getParallacticAngle(core));
×
954
                        if (withDecimalDegree)
×
955
                                pa = StelUtils::radToDecDegStr(par);
×
956
                        else
957
                                pa = StelUtils::radToDmsStr(par, true);
×
958

959
                        res += QString("%1: %2<br/>").arg(q_("Parallactic Angle"), pa);
×
960
                }
×
961
                res += getExtraInfoStrings(Extra).join("");
×
962
                res += omgr->getExtraInfoStrings(Extra).join("");
×
963
        }
964

965
        if (flags&IAUConstellation)
×
966
        {
967
                static ConstellationMgr *cMgr=GETSTELMODULE(ConstellationMgr);
×
968
                QString constel = (fuzzyEquals(eqNow.normSquared(),0.) ? "---" : core->getIAUConstellation(eqNow));
×
969
                res += QString("%1: %2<br/>").arg(q_("IAU Constellation"), constel);
×
970
                res += getExtraInfoStrings(flags&IAUConstellation).join("");
×
971
                res += omgr->getExtraInfoStrings(flags&IAUConstellation).join("");
×
972

973
                // Add constellation from convex hull, if that is enabled in the first place.
974
                static QSettings *conf=StelApp::getInstance().getSettings();
×
975
                static const bool hullsEnabled = conf->value("gui/skyculture_enable_hulls", false).toBool();
×
976
                if (hullsEnabled)
×
977
                {
978
                        QList<Constellation*> constels=cMgr->isObjectIn(this, true);
×
979
                        QString constelStr = dash;
×
980
                        if (!constels.isEmpty())
×
981
                        {
982
                                QStringList cNames;
×
983
                                for(const auto &cst: std::as_const(constels))
×
984
                                {
985
                                        cNames.append(cst->getInfoLabel());
×
986
                                }
987
                                constelStr = cNames.join(", ");
×
988
                        }
×
989
                        res += QString("%1: %2<br/>").arg(q_("Constellations"), constelStr);
×
990
                }
×
991

992
                if (cMgr->hasZodiac() && (currentPlanet=="Earth"))
×
993
                {
994
                        QString zodiacSystemLabel = cMgr->getZodiacSystemName();
×
995
                        QString zodiacalPos = (fuzzyEquals(eqNow.normSquared(),0.) ? "---" : cMgr->getZodiacCoordinate(eqNow));
×
996
                        res += QString("%1: %2<br/>").arg(zodiacSystemLabel, zodiacalPos);
×
997
                }
×
998
                if (cMgr->hasLunarSystem() && (currentPlanet=="Earth"))
×
999
                {
1000
                        QString lunarSystemLabel = cMgr->getLunarSystemName();
×
1001
                        QString lunarSystemPos = (fuzzyEquals(eqNow.normSquared(),0.) ? "---" : cMgr->getLunarSystemCoordinate(eqNow));
×
1002
                        res += QString("%1: %2<br/>").arg(lunarSystemLabel, lunarSystemPos);
×
1003
                }
×
1004
        }
×
1005

1006
        return res;
×
1007
}
×
1008

1009
// Apply post processing on the info string
1010
void StelObject::postProcessInfoString(QString& str, const InfoStringGroup& flags) const
×
1011
{
1012
        StelObjectMgr* omgr;
1013
        omgr=GETSTELMODULE(StelObjectMgr);
×
1014
        str.append(getExtraInfoStrings(Script).join(' '));
×
1015
        str.append(omgr->getExtraInfoStrings(Script).join(' '));
×
1016
        str.append(getExtraInfoStrings(DebugAid).join(' ')); // TBD: Remove for Release builds?
×
1017
        str.append(omgr->getExtraInfoStrings(DebugAid).join(' ')); // TBD: Remove for Release builds?
×
1018

1019
        // hack for avoiding an empty line before table
1020
        static const QRegularExpression tableRe("<br(\\s*/)?><table");
×
1021
        static const QRegularExpression  brRe("<br(\\s*/)?>\\s*$");
×
1022
        str.replace(tableRe, "<table");
×
1023
        // chomp trailing line break (TBD: Why?)
1024
        str.replace(brRe, "");
×
1025
        // avoid two breaks (Comet Core diameter w/o table mode?)
1026
        static const QRegularExpression brbrRe("<br(\\s*/)?><br(\\s*/)?>");
×
1027
        str.replace(brbrRe, "<br/>");
×
1028

1029

1030
        if (flags&PlainText)
×
1031
        {
1032
                static const QRegularExpression brRe2("<br(\\s*/)?>\\s*");
×
1033
                static const QRegularExpression tdRe1("<td\\s*>");
×
1034
                static const QRegularExpression tdRe2("<td \\w+='[^']*'>"); // Seen: style, align, colspan, rowspan. Always only one expression.
×
1035
                static const QRegularExpression tdRe3("<td \\w+=\"[^\"]*\">");
×
1036
                static const QRegularExpression tableRe2("<table\\s*>");
×
1037
                static const QRegularExpression tableRe3("<table style='[^']*'>");
×
1038
                static const QRegularExpression tableRe4("<table style=\"[^\"]*\">");
×
1039
                str.replace("<b>", "");
×
1040
                str.replace("</b>", "");
×
1041
                str.replace("<h2>", "");
×
1042
                str.replace("</h2>", "\n");
×
1043
                str.replace(brRe2, "\n");
×
1044
                str.replace("<tr>", "");
×
1045
                str.replace(tdRe1, "");
×
1046
                str.replace(tdRe2, "");
×
1047
                str.replace(tdRe3, "");
×
1048
                str.replace("</td>", "");
×
1049
                str.replace("</tr>", "\n");
×
1050
                str.replace(tableRe2, "");
×
1051
                str.replace(tableRe3, "");
×
1052
                str.replace(tableRe4, "");
×
1053
                str.replace("</table>", "");
×
1054
        }
1055
        else if(!(flags&NoFont))
×
1056
        {
1057
                Vec3f color = getInfoColor();
×
1058
                StelCore* core = StelApp::getInstance().getCore();
×
1059
                if (StelApp::getInstance().getFlagOverwriteInfoColor())
×
1060
                {
1061
                        // make info text more readable...
1062
                        color = StelApp::getInstance().getOverwriteInfoColor();
×
1063
                }
1064
                if (core->isBrightDaylight() && !StelApp::getInstance().getVisionModeNight())
×
1065
                {
1066
                        // make info text more readable when atmosphere enabled at daylight.
1067
                        color = StelApp::getInstance().getDaylightInfoColor();
×
1068
                }
1069
                str.prepend(QString("<font color=%1>").arg(color.toHtmlColor()));
×
1070
                str.append(QString("</font>"));
×
1071
        }
1072
}
×
1073

1074
QVariantMap StelObject::getInfoMap(const StelCore *core) const
×
1075
{
1076
        const bool useSouthAzimuth = StelApp::getInstance().getFlagSouthAzimuthUsage();
×
1077
        QVariantMap map;
×
1078

1079
        Vec3d pos;
×
1080
        double ra, dec, alt, az, glong, glat;
1081
        // ra/dec
1082
        pos = getEquinoxEquatorialPos(core);
×
1083
        StelUtils::rectToSphe(&ra, &dec, pos);
×
1084
        map.insert("ra", ra*M_180_PI);
×
1085
        map.insert("dec", dec*M_180_PI);
×
1086
        map.insert("iauConstellation", core->getIAUConstellation(pos));
×
1087

1088
        QString currentObjStr = getEnglishName();
×
1089
        if (currentObjStr == "") // If objects have no name, we need something to represent it.
×
1090
        {
1091
                currentObjStr = StelUtils::radToHmsStr(ra);
×
1092
        }
1093

1094
        map.insert("type", getType());
×
1095
        map.insert("object-type", getObjectType());
×
1096

1097
        if (getType()!=QStringLiteral("Star"))
×
1098
                map.insert("parallacticAngle", static_cast<double>(getParallacticAngle(core))*M_180_PI);
×
1099

1100
        // Sidereal Time and hour angle
1101
        if (core->getCurrentLocation().planetName=="Earth")
×
1102
        {
1103
                const double longitude=static_cast<double>(core->getCurrentLocation().getLongitude());
×
1104
                double sidereal=(get_mean_sidereal_time(core->getJD(), core->getJDE())  + longitude) / 15.;
×
1105
                sidereal=fmod(sidereal, 24.);
×
1106
                if (sidereal < 0.) sidereal+=24.;
×
1107
                map.insert("meanSidTm", StelUtils::hoursToHmsStr(sidereal));
×
1108
                map.insert("meanSidTm-dd", sidereal * 15.);
×
1109

1110
                sidereal=(get_apparent_sidereal_time(core->getJD(), core->getJDE()) + longitude) / 15.;
×
1111
                sidereal=fmod(sidereal, 24.);
×
1112
                if (sidereal < 0.) sidereal+=24.;
×
1113
                map.insert("appSidTm", StelUtils::hoursToHmsStr(sidereal));
×
1114
                map.insert("appSidTm-dd", sidereal * 15.);
×
1115

1116
                double ha = sidereal * 15.0 - ra * M_180_PI;
×
1117
                ha=fmod(ha, 360.0);
×
1118
                if (ha < 0.) ha+=360.0;
×
1119
                map.insert("hourAngle-dd", ha);
×
1120
                map.insert("hourAngle-hms", StelUtils::hoursToHmsStr(ha/15.0));
×
1121
        }
1122

1123
        // ra/dec in J2000
1124
        pos = getJ2000EquatorialPos(core);
×
1125
        StelUtils::rectToSphe(&ra, &dec, pos);
×
1126
        map.insert("raJ2000", ra*M_180_PI);
×
1127
        map.insert("decJ2000", dec*M_180_PI);
×
1128

1129
        // apparent altitude/azimuth
1130
        pos = getAltAzPosApparent(core);
×
1131
        StelUtils::rectToSphe(&az, &alt, pos);
×
1132
        const double direction = (useSouthAzimuth ? 2. : 3.); // 2: S is zero, W is 90 degrees. 3: N is zero, E is 90 degrees
×
1133
        az = direction*M_PI - az;
×
1134
        if (az > M_PI*2)
×
1135
                az -= M_PI*2;
×
1136

1137
        map.insert("altitude", alt*M_180_PI);
×
1138
        map.insert("azimuth", az*M_180_PI);
×
1139
        map.insert("airmass", getAirmass(core));
×
1140

1141
        // geometric altitude/azimuth
1142
        pos = getAltAzPosGeometric(core);
×
1143
        StelUtils::rectToSphe(&az, &alt, pos);
×
1144
        az = direction*M_PI - az;
×
1145
        if (az > M_PI*2)
×
1146
                az -= M_PI*2;
×
1147

1148
        map.insert("altitude-geometric", alt*M_180_PI);
×
1149
        map.insert("azimuth-geometric", az*M_180_PI);
×
1150

1151
        // galactic long/lat
1152
        pos = getGalacticPos(core);
×
1153
        StelUtils::rectToSphe(&glong, &glat, pos);
×
1154
        if (glong<0.) glong += 2.0*M_PI;
×
1155
        map.insert("glong", glong*M_180_PI);
×
1156
        map.insert("glat", glat*M_180_PI);
×
1157

1158
        // supergalactic long/lat
1159
        pos = getSupergalacticPos(core);
×
1160
        StelUtils::rectToSphe(&glong, &glat, pos);
×
1161
        if (glong<0.) glong += 2.0*M_PI;
×
1162
        map.insert("sglong", glong*M_180_PI);
×
1163
        map.insert("sglat", glat*M_180_PI);
×
1164

1165
        SolarSystem* ssmgr = GETSTELMODULE(SolarSystem);
×
1166
        double ra_equ, dec_equ, lambda, beta;
1167
        // J2000
1168
        double eclJ2000 = ssmgr->getEarth()->getRotObliquity(2451545.0);
×
1169
        double ecl = ssmgr->getEarth()->getRotObliquity(core->getJDE());
×
1170
        map.insert("ecliptic-obliquity", ecl*M_180_PI);
×
1171

1172
        // ecliptic longitude/latitude (J2000 frame)
1173
        StelUtils::rectToSphe(&ra_equ,&dec_equ, getJ2000EquatorialPos(core));
×
1174
        StelUtils::equToEcl(ra_equ, dec_equ, eclJ2000, &lambda, &beta);
×
1175
        if (lambda<0) lambda+=2.0*M_PI;
×
1176
        map.insert("elongJ2000", lambda*M_180_PI);
×
1177
        map.insert("elatJ2000", beta*M_180_PI);
×
1178

1179
        if (QString("Earth Sun").contains(core->getCurrentLocation().planetName))
×
1180
        {
1181
                // ecliptic longitude/latitude
1182
                StelUtils::rectToSphe(&ra_equ,&dec_equ, getEquinoxEquatorialPos(core));
×
1183
                StelUtils::equToEcl(ra_equ, dec_equ, ecl, &lambda, &beta);
×
1184
                if (lambda<0) lambda+=2.0*M_PI;
×
1185
                map.insert("elong", lambda*M_180_PI);
×
1186
                map.insert("elat", beta*M_180_PI);
×
1187
        }
1188

1189
        // magnitude
1190
        map.insert("vmag", getVMagnitude(core));
×
1191
        map.insert("vmage", getVMagnitudeWithExtinction(core));
×
1192

1193
        // angular size
1194
        double angularSize = getAngularRadius(core)*(2.*M_PI_180);
×
1195
        Q_ASSERT(angularSize>=0.);
×
1196
        map.insert("size", angularSize);
×
1197
        map.insert("size-dd", angularSize*M_180_PI);
×
1198
        map.insert("size-deg", StelUtils::radToDecDegStr(angularSize, 5));
×
1199
        map.insert("size-dms", StelUtils::radToDmsPStr(angularSize, 2));
×
1200

1201
        // english name or designation & localized name
1202
        map.insert("name", getEnglishName());
×
1203
        map.insert("localized-name", getNameI18n());
×
1204

1205
        // 'above horizon' flag
1206
        map.insert("above-horizon", isAboveRealHorizon(core));
×
1207

1208
        const double currentJD = core->getJD();
×
1209
        const double utcShift = core->getUTCOffset(currentJD) / 24.; // Fix DST shift...
×
1210
        int currentYear, currentMonth, currentDay;
1211
        const StelLocation currentLocation=core->getCurrentLocation();
×
1212
        double currentLatitude=static_cast<double>(currentLocation.getLatitude());
×
1213
        double currentLongitude=static_cast<double>(currentLocation.getLongitude());
×
1214
        const QString currentPlanet = core->getCurrentPlanet()->getEnglishName();
×
1215
        StelUtils::getDateFromJulianDay(currentJD+utcShift, &currentYear, &currentMonth, &currentDay);
×
1216

1217
        static int prevYear, prevMonth, prevDay;
1218
        static Vec4d rts;
×
1219
        static QString prevObjStr, prevPlanet;
×
1220
        static double prevLatitude, prevLongitude;
1221
        bool dayChanged = false;
×
1222
        bool locationChanged = false;
×
1223
        if ((currentYear != prevYear) || (currentMonth != prevMonth) || (currentDay != prevDay))
×
1224
        {
1225
                dayChanged = true;
×
1226
        }
1227

1228
        if ((currentLatitude != prevLatitude) || (currentLongitude != prevLongitude))
×
1229
        {
1230
                locationChanged = true;
×
1231
        }
1232

1233
        // Avoid frequent RTS recalculation
1234
        if ((currentObjStr != prevObjStr) || (currentPlanet != prevPlanet) || dayChanged || locationChanged)
×
1235
        {
1236
                rts = getRTSTime(core);
×
1237
        }
1238
        if (rts[3]>-1000.)
×
1239
        {
1240
                const double utcShift = core->getUTCOffset(core->getJD()) / 24.; // Fix DST shift...
×
1241
                int hr, min, sec;
1242
                StelUtils::getTimeFromJulianDay(rts[1]+utcShift, &hr, &min, &sec);
×
1243
                double hours=hr+static_cast<double>(min)/60. + static_cast<double>(sec)/3600.;
×
1244

1245
                int year, month, day;
1246
                StelUtils::getDateFromJulianDay(core->getJD()+utcShift, &year, &month, &currentDay);
×
1247
                StelUtils::getDateFromJulianDay(rts[1]+utcShift, &year, &month, &day);
×
1248
                if (rts[3]==20 || day != currentDay) // no transit
×
1249
                {
1250
                        map.insert("transit", "---");
×
1251
                }
1252
                else {
1253
                        map.insert("transit", StelUtils::hoursToHmsStr(hours, true));
×
1254
                        map.insert("transit-dhr", hours);
×
1255
                }
1256

1257
                StelUtils::getDateFromJulianDay(rts[0]+utcShift, &year, &month, &day);
×
1258
                if (rts[3]==30 || rts[3]<0 || rts[3]>50 || day != currentDay) // no rise
×
1259
                {
1260
                        map.insert("rise", "---");
×
1261
                }
1262
                else {
1263
                        StelUtils::getTimeFromJulianDay(rts[0]+utcShift, &hr, &min, &sec);
×
1264
                        hours=hr+static_cast<double>(min)/60. + static_cast<double>(sec)/3600.;
×
1265
                        map.insert("rise", StelUtils::hoursToHmsStr(hours, true));
×
1266
                        map.insert("rise-dhr", hours);
×
1267
                }
1268

1269
                StelUtils::getDateFromJulianDay(rts[2]+utcShift, &year, &month, &day);
×
1270
                if (rts[3]==40 || rts[3]<0 || rts[3]>50 || day != currentDay) // no set
×
1271
                {
1272
                        map.insert("set", "---");
×
1273
                }
1274
                else {
1275
                        StelUtils::getTimeFromJulianDay(rts[2]+utcShift, &hr, &min, &sec);
×
1276
                        hours=hr+static_cast<double>(min)/60. + static_cast<double>(sec)/3600.;
×
1277
                        map.insert("set", StelUtils::hoursToHmsStr(hours, true));
×
1278
                        map.insert("set-dhr", hours);
×
1279
                }
1280
        }
1281

1282
        prevObjStr = currentObjStr;
×
1283
        prevYear = currentYear;
×
1284
        prevMonth = currentMonth;
×
1285
        prevDay = currentDay;
×
1286
        prevLatitude = currentLatitude;
×
1287
        prevLongitude = currentLongitude;
×
1288
        prevPlanet = currentPlanet;
×
1289

1290
        return map;
×
1291
}
×
1292

1293
void StelObject::setExtraInfoString(const InfoStringGroup& flags, const QString &str)
×
1294
{
1295
        extraInfoStrings.remove(flags); // delete all entries with these flags
×
1296
        if (!str.isEmpty())
×
1297
                extraInfoStrings.insert(flags, str);
×
1298
}
×
1299
void StelObject::addToExtraInfoString(const StelObject::InfoStringGroup &flags, const QString &str)
×
1300
{
1301
        // Avoid insertion of full duplicates!
1302
        if (!extraInfoStrings.contains(flags, str))
×
1303
                extraInfoStrings.insert(flags, str);
×
1304
}
×
1305

1306
QStringList StelObject::getExtraInfoStrings(const InfoStringGroup& flags) const
×
1307
{
1308
        QStringList list;
×
1309
        QMultiMap<InfoStringGroup, QString>::const_iterator i = extraInfoStrings.constBegin();
×
1310
        while (i != extraInfoStrings.constEnd())
×
1311
        {
1312
                if (i.key() & flags)
×
1313
                {
1314
                        QString val=i.value();
×
1315
                        if (flags&DebugAid)
×
1316
                                val.prepend("DEBUG: ");
×
1317
                        // For unclear reasons the sequence of entries can be preserved by *pre*pending in the returned list.
1318
                        list.prepend(val);
×
1319
                }
×
1320
                ++i;
×
1321
        }
1322
        return list;
×
1323
}
×
1324

1325
void StelObject::removeExtraInfoStrings(const InfoStringGroup& flags)
×
1326
{
1327
#if (QT_VERSION>=QT_VERSION_CHECK(6,0,0))
1328
        QMutableMultiMapIterator<InfoStringGroup, QString> i(extraInfoStrings);
×
1329
#else
1330
        QMutableMapIterator<InfoStringGroup, QString> i(extraInfoStrings);
1331
#endif
1332
        while (i.hasNext())
×
1333
        {
1334
                i.next();
×
1335
                if (i.key() & flags)
×
1336
                        i.remove();
×
1337
        }
1338
}
×
1339

1340
// Add horizontal coordinates of Sun and Moon where useful
1341
QString StelObject::getSolarLunarInfoString(const StelCore *core, const InfoStringGroup& flags) const
×
1342
{
1343
        QString str;
×
1344
        QTextStream oss(&str);
×
1345
        static SolarSystem *ssystem=GETSTELMODULE(SolarSystem);
×
1346
        PlanetP earth = ssystem->getEarth();
×
1347
        if ((core->getCurrentPlanet()==earth) && (flags&SolarLunarPosition))
×
1348
        {
1349
                const bool withTables = StelApp::getInstance().getFlagUseFormattingOutput();
×
1350
                const bool withDecimalDegree = StelApp::getInstance().getFlagShowDecimalDegrees();
×
1351

1352
                if (withTables)
×
1353
                        oss << "<table style='margin:0em 0em 0em -0.125em;border-spacing:0px;border:0px;'>";
×
1354
                const bool useSouthAzimuth = StelApp::getInstance().getFlagSouthAzimuthUsage();
×
1355
                const bool withDesignations = StelApp::getInstance().getFlagUseCCSDesignation();
×
1356
                double az, alt;
1357
                QString azStr, altStr;
×
1358

1359
                if (getEnglishName()!="Sun")
×
1360
                {
1361
                        StelUtils::rectToSphe(&az,&alt,ssystem->getSun()->getAltAzPosAuto(core));
×
1362
                        az = (useSouthAzimuth? 2. : 3.)*M_PI - az;
×
1363
                        if (az > M_PI*2)
×
1364
                                az -= M_PI*2;
×
1365
                        azStr  = (withDecimalDegree ? StelUtils::radToDecDegStr(az, 2)  : StelUtils::radToDmsStr(az,false));
×
1366
                        altStr = (withDecimalDegree ? StelUtils::radToDecDegStr(alt, 2) : StelUtils::radToDmsStr(alt,false));
×
1367

1368
                        // TRANSLATORS: Azimuth/Altitude
1369
                        const QString SolarAzAlt = (withDesignations ? qc_("Solar A/a", "celestial coordinate system") : qc_("Solar Az./Alt.", "celestial coordinate system"));
×
1370
                        if (withTables)
×
1371
                        {
1372
                                oss << QString("<tr><td>%1:</td><td style='text-align:right;'>%2/</td><td style='text-align:right;'>%3</td></tr>").arg(SolarAzAlt, azStr, altStr);
×
1373
                        }
1374
                        else
1375
                                oss << QString("%1: %2/%3<br/>").arg(SolarAzAlt, azStr, altStr);
×
1376
                }
×
1377
                if (getEnglishName()!="Moon")
×
1378
                {
1379
                        StelUtils::rectToSphe(&az,&alt,ssystem->getMoon()->getAltAzPosAuto(core));
×
1380
                        az = (useSouthAzimuth? 2. : 3.)*M_PI - az;
×
1381
                        if (az > M_PI*2)
×
1382
                                az -= M_PI*2;
×
1383
                        azStr  = (withDecimalDegree ? StelUtils::radToDecDegStr(az, 2)  : StelUtils::radToDmsStr(az,false));
×
1384
                        altStr = (withDecimalDegree ? StelUtils::radToDecDegStr(alt, 2) : StelUtils::radToDmsStr(alt,false));
×
1385

1386
                        // TRANSLATORS: Azimuth/Altitude
1387
                        const QString LunarAzAlt = (withDesignations ? qc_("Lunar A/a", "celestial coordinate system") : qc_("Lunar Az./Alt.", "celestial coordinate system"));
×
1388
                        if (withTables)
×
1389
                        {
1390
                                oss << QString("<tr><td>%1:</td><td style='text-align:right;'>%2/</td><td style='text-align:right;'>%3</td></tr>").arg(LunarAzAlt, azStr, altStr);
×
1391
                        }
1392
                        else
1393
                                oss << QString("%1: %2/%3<br/>").arg(LunarAzAlt, azStr, altStr);
×
1394
                }
×
1395
                if (withTables)
×
1396
                        oss << "</table>";
×
1397
        }
×
1398
        return str;
×
1399
}
×
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc