Kstars

skyobject.h
1 /*
2  SPDX-FileCopyrightText: 2001 Jason Harris <[email protected]>
3 
4  SPDX-License-Identifier: GPL-2.0-or-later
5 */
6 
7 #pragma once
8 
9 #include "dms.h"
10 #include "skypoint.h"
11 
12 #include <KLocalizedString>
13 
14 #include <QSharedDataPointer>
15 #include <QString>
16 #include <QStringList>
17 
18 class QPoint;
19 class GeoLocation;
20 class KSPopupMenu;
21 
22 namespace {
23  constexpr const char *emptyString = "";
24  constexpr const char *unnamedString = I18N_NOOP("unnamed");
25  constexpr const char *unnamedObjectString = I18N_NOOP("unnamed object");
26  constexpr const char *starString = I18N_NOOP("star");
27 }
28 
29 // Set the faintest sane magnitude to 36.0 (faintest visual magnitude visible with E-ELT, acc. to Wikipedia on Apparent Magnitude.)
30 constexpr const float FAINTEST_MAGNITUDE = 36.0;
31 
32 /**
33  * @class SkyObject
34  * Provides all necessary information about an object in the sky:
35  * its coordinates, name(s), type, magnitude, and QStringLists of
36  * URLs for images and webpages regarding the object.
37  * @short Information about an object in the sky.
38  * @author Jason Harris
39  * @version 1.0
40  */
41 class SkyObject : public SkyPoint
42 {
43  public:
44  /**
45  * @short Type for Unique object IDenticator.
46  *
47  * Each object has unique ID (UID). For different objects UIDs must be different.
48  */
49  typedef qint64 UID;
50 
51  /** @short Kind of UID */
52  static const UID UID_STAR;
53  static const UID UID_GALAXY;
54  static const UID UID_DEEPSKY;
55  static const UID UID_SOLARSYS;
56 
57  /** Invalid UID. Real sky object could not have such UID */
58  static const UID invalidUID;
59 
60  /**
61  * Constructor. Set SkyObject data according to arguments.
62  * @param t Type of object
63  * @param r catalog Right Ascension
64  * @param d catalog Declination
65  * @param m magnitude (brightness)
66  * @param n Primary name
67  * @param n2 Secondary name
68  * @param lname Long name (common name)
69  */
70  explicit SkyObject(int t = TYPE_UNKNOWN, dms r = dms(0.0), dms d = dms(0.0), float m = 0.0,
71  const QString &n = QString(), const QString &n2 = QString(), const QString &lname = QString());
72  /**
73  * Constructor. Set SkyObject data according to arguments. Differs from
74  * above function only in data type of RA and Dec.
75  * @param t Type of object
76  * @param r catalog Right Ascension
77  * @param d catalog Declination
78  * @param m magnitude (brightness)
79  * @param n Primary name
80  * @param n2 Secondary name
81  * @param lname Long name (common name)
82  */
83  SkyObject(int t, double r, double d, float m = 0.0, const QString &n = QString(), const QString &n2 = QString(),
84  const QString &lname = QString());
85 
86  /** Destructor (empty) */
87  virtual ~SkyObject() override = default;
88 
89  /**
90  * @short Create copy of object.
91  * This method is virtual copy constructor. It allows for safe
92  * copying of objects. In other words, KSPlanet object stored in
93  * SkyObject pointer will be copied as KSPlanet.
94  *
95  * Each subclass of SkyObject MUST implement clone method. There
96  * is no checking to ensure this, though.
97  *
98  * @return pointer to newly allocated object. Caller takes full responsibility
99  * for deallocating it.
100  */
101  virtual SkyObject *clone() const;
102 
103  /**
104  * @enum TYPE
105  * The type classification of the SkyObject.
106  * @note Keep TYPE_UNKNOWN at 255. To find out how many known
107  * types exist, keep the NUMBER_OF_KNOWN_TYPES at the highest
108  * non-Unknown value. This is a fake type that can be used in
109  * comparisons and for loops.
110  */
111  enum TYPE
112  {
113  STAR = 0,
114  CATALOG_STAR = 1,
115  PLANET = 2,
116  OPEN_CLUSTER = 3,
117  GLOBULAR_CLUSTER = 4,
118  GASEOUS_NEBULA = 5,
119  PLANETARY_NEBULA = 6,
120  SUPERNOVA_REMNANT = 7,
121  GALAXY = 8,
122  COMET = 9,
123  ASTEROID = 10,
124  CONSTELLATION = 11,
125  MOON = 12,
126  ASTERISM = 13,
127  GALAXY_CLUSTER = 14,
128  DARK_NEBULA = 15,
129  QUASAR = 16,
130  MULT_STAR = 17,
131  RADIO_SOURCE = 18,
132  SATELLITE = 19,
133  SUPERNOVA = 20,
134  NUMBER_OF_KNOWN_TYPES = 21,
135  TYPE_UNKNOWN = 255
136  };
137  /**
138  * @return A translated string indicating the type name for a given type number
139  * @param t The type number
140  * @note Note the existence of a SkyObject::typeName( void ) method that is not static and returns the type of this object.
141  */
142  static QString typeName(const int t);
143 
144  /** @return object's primary name. */
145  inline virtual QString name(void) const { return hasName() ? Name : unnamedString; }
146 
147  /** @return object's primary name, translated to local language. */
148  inline QString translatedName() const
149  {
150  return i18n(
151  name()
152  .toUtf8()); // FIXME: Hmm... that's funny. How does the string extraction work, if we are UTF8-ing the name first? Does the string extraction change to UTF8?
153  }
154 
155  /** @return object's secondary name */
156  inline QString name2(void) const { return (hasName2() ? Name2 : emptyString); }
157 
158  /** @return object's secondary name, translated to local language. */
159  inline QString translatedName2() const { return (hasName2() ? i18n(Name2.toUtf8()) : emptyString); }
160 
161  /**
162  * @return object's common (long) name
163  */
164  virtual QString longname(void) const { return hasLongName() ? LongName : unnamedObjectString; }
165 
166  /**
167  * @return object's common (long) name, translated to local language.
168  */
169  QString translatedLongName() const { return i18n(longname().toUtf8()); }
170 
171  /**
172  * Set the object's long name.
173  * @param longname the object's long name.
174  */
175  void setLongName(const QString &longname = QString());
176 
177  /**
178  * @return the string used to label the object on the map
179  * In the default implementation, this just returns translatedName()
180  * Overridden by StarObject.
181  */
182  virtual QString labelString() const;
183 
184  /**
185  * @return object's type identifier (int)
186  * @see enum TYPE
187  */
188  inline int type(void) const { return (int)Type; }
189 
190  /**
191  * Set the object's type identifier to the argument.
192  * @param t the object's type identifier (e.g., "SkyObject::PLANETARY_NEBULA")
193  * @see enum TYPE
194  */
195  inline void setType(int t) { Type = (unsigned char)t; }
196 
197  /**
198  * @return the type name for this object
199  * @note This just calls the static method by the same name, with the appropriate type number. See SkyObject::typeName( const int )
200  */
201  QString typeName() const;
202 
203  /**
204  * @return object's magnitude
205  */
206  inline float mag() const { return sortMagnitude; }
207 
208  /**
209  * @return the object's position angle. This is overridden in KSPlanetBase
210  * and DeepSkyObject; for all other SkyObjects, this returns 0.0.
211  */
212  inline virtual double pa() const { return 0.0; }
213 
214  /**
215  * @return true if the object is a solar system body.
216  */
217  inline bool isSolarSystem() const { return (type() == 2 || type() == 9 || type() == 10 || type() == 12); }
218 
219  /**
220  * Initialize the popup menut. This function should call correct
221  * initialization function in KSPopupMenu. By overloading the
222  * function, we don't have to check the object type when we need
223  * the menu.
224  */
225  virtual void initPopupMenu(KSPopupMenu *pmenu);
226 
227  /** Show Type-specific popup menu. Overloading is done in the function initPopupMenu */
228  void showPopupMenu(KSPopupMenu *pmenu, const QPoint &pos);
229 
230  /**
231  * Determine the time at which the point will rise or set. Because solar system
232  * objects move across the sky, it is necessary to iterate on the solution.
233  * We compute the rise/set time for the object's current position, then
234  * compute the object's position at that time. Finally, we recompute then
235  * rise/set time for the new coordinates. Further iteration is not necessary,
236  * even for the most swiftly-moving object (the Moon).
237  * @return the local time that the object will rise
238  * @param dt current UT date/time
239  * @param geo current geographic location
240  * @param rst If true, compute rise time. If false, compute set time.
241  * @param exact If true, use a second iteration for more accurate time
242  */
243  QTime riseSetTime(const KStarsDateTime &dt, const GeoLocation *geo, bool rst, bool exact = true) const;
244 
245  /**
246  * @return the UT time when the object will rise or set
247  * @param dt target date/time
248  * @param geo pointer to Geographic location
249  * @param rst Boolean. If true will compute rise time. If false
250  * will compute set time.
251  * @param exact If true, use a second iteration for more accurate time
252  */
253  QTime riseSetTimeUT(const KStarsDateTime &dt, const GeoLocation *geo, bool rst, bool exact = true) const;
254 
255  /**
256  * @return the Azimuth time when the object will rise or set. This function
257  * recomputes set or rise UT times.
258  * @param dt target date/time
259  * @param geo GeoLocation object
260  * @param rst Boolen. If true will compute rise time. If false
261  * will compute set time.
262  */
263  dms riseSetTimeAz(const KStarsDateTime &dt, const GeoLocation *geo, bool rst) const;
264 
265  /**
266  * The same iteration technique described in riseSetTime() is used here.
267  * @return the local time that the object will transit the meridian.
268  * @param dt target date/time
269  * @param geo pointer to the geographic location
270  */
271  QTime transitTime(const KStarsDateTime &dt, const GeoLocation *geo) const;
272 
273  /**
274  * @return the universal time that the object will transit the meridian.
275  * @param dt target date/time
276  * @param geo pointer to the geographic location
277  */
278  QTime transitTimeUT(const KStarsDateTime &dt, const GeoLocation *geo) const;
279 
280  /**
281  * @return the altitude of the object at the moment it transits the meridian.
282  * @param dt target date/time
283  * @param geo pointer to the geographic location
284  */
285  dms transitAltitude(const KStarsDateTime &dt, const GeoLocation *geo) const;
286 
287  /**
288  * The equatorial coordinates for the object on date dt are computed and returned,
289  * but the object's internal coordinates are not modified.
290  * @return the coordinates of the selected object for the time given by jd
291  * @param dt date/time for which the coords will be computed.
292  * @param geo pointer to geographic location (used for solar system only)
293  * @note Does not update the horizontal coordinates. Call EquatorialToHorizontal for that.
294  */
295  SkyPoint recomputeCoords(const KStarsDateTime &dt, const GeoLocation *geo = nullptr) const;
296 
297  /**
298  * @short Like recomputeCoords, but also calls EquatorialToHorizontal before returning
299  */
300  SkyPoint recomputeHorizontalCoords(const KStarsDateTime &dt, const GeoLocation *geo) const;
301 
302  inline bool hasName() const { return !Name.isEmpty(); }
303 
304  inline bool hasName2() const { return !Name2.isEmpty(); }
305 
306  inline bool hasLongName() const { return !LongName.isEmpty(); }
307 
308  /**
309  * @short Given the Image title from a URL file, try to convert it to an image credit string.
310  */
311  QString messageFromTitle(const QString &imageTitle) const;
312 
313  /**
314  * @return the pixel distance for offseting the object's name label
315  * @note overridden in StarObject, DeepSkyObject, KSPlanetBase
316  */
317  virtual double labelOffset() const;
318 
319  /**
320  * @short Return UID for object.
321  * This method should be reimplemented in all concrete
322  * subclasses. Implementation for SkyObject just returns
323  * invalidUID. It's required SkyObject is not an abstract class.
324  */
325  virtual UID getUID() const;
326 
327  // TODO: (Valentin) have another think about onFocus handlers :)
328 
329  /**
330  * @brief hashBeenUpdated
331  * @return whether the coordinates of the object have been updated
332  *
333  * This is used for faster filtering.
334  */
335  bool hashBeenUpdated() { return has_been_updated; }
336 
337  private:
338  /**
339  * Compute the UT time when the object will rise or set. It is an auxiliary
340  * procedure because it does not use the RA and DEC of the object but values
341  * given as parameters. You may want to use riseSetTimeUT() which is
342  * public. riseSetTimeUT() calls this function iteratively.
343  * @param dt target date/time
344  * @param geo pointer to Geographic location
345  * @param righta pointer to Right ascention of the object
346  * @param decl pointer to Declination of the object
347  * @param rst Boolean. If true will compute rise time. If false
348  * will compute set time.
349  * @return the time at which the given position will rise or set.
350  */
351  QTime auxRiseSetTimeUT(const KStarsDateTime &dt, const GeoLocation *geo, const dms *righta, const dms *decl,
352  bool riseT) const;
353 
354  /**
355  * Compute the LST time when the object will rise or set. It is an auxiliary
356  * procedure because it does not use the RA and DEC of the object but values
357  * given as parameters. You may want to use riseSetTimeLST() which is
358  * public. riseSetTimeLST() calls this function iteratively.
359  * @param gLt Geographic latitude
360  * @param rga Right ascention of the object
361  * @param decl Declination of the object
362  * @param rst Boolean. If true will compute rise time. If false
363  * will compute set time.
364  */
365  dms auxRiseSetTimeLST(const dms *gLt, const dms *rga, const dms *decl, bool rst) const;
366 
367  /**
368  * Compute the approximate hour angle that an object with declination d will have
369  * when its altitude is h (as seen from geographic latitude gLat).
370  * This function is only used by auxRiseSetTimeLST().
371  * @param h pointer to the altitude of the object
372  * @param gLat pointer to the geographic latitude
373  * @param d pointer to the declination of the object.
374  * @return the Hour Angle, in degrees.
375  */
376  double approxHourAngle(const dms *h, const dms *gLat, const dms *d) const;
377 
378  /**
379  * Correct for the geometric altitude of the center of the body at the
380  * time of rising or setting. This is due to refraction at the horizon
381  * and to the size of the body. The moon correction has also to take into
382  * account parallax. The value we use here is a rough approximation
383  * suggested by J. Meeus.
384  *
385  * Weather status (temperature and pressure basically) is not taken
386  * into account although change of conditions between summer and
387  * winter could shift the times of sunrise and sunset by 20 seconds.
388  *
389  * This function is only used by auxRiseSetTimeLST().
390  * @return dms object with the correction.
391  */
392  dms elevationCorrection(void) const;
393 
394  unsigned char Type;
395  float
396  sortMagnitude; // This magnitude is used for sorting / making decisions about the visibility of an object. Should not be NaN.
397 
398  protected:
399  /**
400  * Set the object's sorting magnitude.
401  * @param m the object's magnitude.
402  */
403  inline void setMag(float m)
404  {
405  sortMagnitude =
406  m < FAINTEST_MAGNITUDE ?
407  m :
408  NaN::
409  f;
410  }
411  // FIXME: We claim sortMagnitude should not be NaN, but we are setting it to NaN above!! ^
412 
413  /**
414  * Set the object's primary name.
415  * @param name the object's primary name
416  */
417  inline void setName(const QString &name) { Name = name; }
418 
419  /**
420  * Set the object's secondary name.
421  * @param name2 the object's secondary name.
422  */
423  inline void setName2(const QString &name2 = QString()) { Name2 = name2; }
424 
425  QString Name, Name2, LongName;
426 
427  // Whether the coordinates of the object have been updated.
428  // The default value is chose for compatibility reasons.
429  // It primarily matters for objects which are filtered.
430  // See `KSAsteroid` for an example.
431  bool has_been_updated = true;
432 };
SkyObject(int t=TYPE_UNKNOWN, dms r=dms(0.0), dms d=dms(0.0), float m=0.0, const QString &n=QString(), const QString &n2=QString(), const QString &lname=QString())
Constructor.
Definition: skyobject.cpp:30
static const UID UID_STAR
Kind of UID.
Definition: skyobject.h:52
Extension of QDateTime for KStars KStarsDateTime can represent the date/time as a Julian Day,...
QTime riseSetTimeUT(const KStarsDateTime &dt, const GeoLocation *geo, bool rst, bool exact=true) const
Definition: skyobject.cpp:127
virtual UID getUID() const
Return UID for object.
Definition: skyobject.cpp:459
SkyPoint recomputeHorizontalCoords(const KStarsDateTime &dt, const GeoLocation *geo) const
Like recomputeCoords, but also calls EquatorialToHorizontal before returning.
Definition: skyobject.cpp:329
QString translatedLongName() const
Definition: skyobject.h:169
Stores dms coordinates for a point in the sky. for converting between coordinate systems.
Definition: skypoint.h:44
virtual QString name(void) const
Definition: skyobject.h:145
QString translatedName() const
Definition: skyobject.h:148
float mag() const
Definition: skyobject.h:206
QString translatedName2() const
Definition: skyobject.h:159
qint64 UID
Type for Unique object IDenticator.
Definition: skyobject.h:49
void showPopupMenu(KSPopupMenu *pmenu, const QPoint &pos)
Show Type-specific popup menu.
Definition: skyobject.cpp:56
virtual double pa() const
Definition: skyobject.h:212
virtual SkyObject * clone() const
Create copy of object.
Definition: skyobject.cpp:50
int type(void) const
Definition: skyobject.h:188
static const UID invalidUID
Invalid UID.
Definition: skyobject.h:58
QString i18n(const char *text, const TYPE &arg...)
void setMag(float m)
Set the object's sorting magnitude.
Definition: skyobject.h:403
dms riseSetTimeAz(const KStarsDateTime &dt, const GeoLocation *geo, bool rst) const
Definition: skyobject.cpp:190
QTime riseSetTime(const KStarsDateTime &dt, const GeoLocation *geo, bool rst, bool exact=true) const
Determine the time at which the point will rise or set.
Definition: skyobject.cpp:93
bool isEmpty() const const
QByteArray toUtf8() const const
virtual double labelOffset() const
Definition: skyobject.cpp:454
QString messageFromTitle(const QString &imageTitle) const
Given the Image title from a URL file, try to convert it to an image credit string.
Definition: skyobject.cpp:394
void setName(const QString &name)
Set the object's primary name.
Definition: skyobject.h:417
SkyPoint recomputeCoords(const KStarsDateTime &dt, const GeoLocation *geo=nullptr) const
The equatorial coordinates for the object on date dt are computed and returned, but the object's inte...
Definition: skyobject.cpp:295
virtual void initPopupMenu(KSPopupMenu *pmenu)
Initialize the popup menut.
Definition: skyobject.cpp:67
QTime transitTimeUT(const KStarsDateTime &dt, const GeoLocation *geo) const
Definition: skyobject.cpp:221
virtual QString labelString() const
Definition: skyobject.cpp:449
An angle, stored as degrees, but expressible in many ways.
Definition: dms.h:37
dms transitAltitude(const KStarsDateTime &dt, const GeoLocation *geo) const
Definition: skyobject.cpp:244
virtual ~SkyObject() override=default
Destructor (empty)
bool isSolarSystem() const
Definition: skyobject.h:217
virtual QString longname(void) const
Definition: skyobject.h:164
QTime transitTime(const KStarsDateTime &dt, const GeoLocation *geo) const
The same iteration technique described in riseSetTime() is used here.
Definition: skyobject.cpp:239
#define I18N_NOOP(text)
QString name2(void) const
Definition: skyobject.h:156
bool hashBeenUpdated()
hashBeenUpdated
Definition: skyobject.h:335
void setName2(const QString &name2=QString())
Set the object's secondary name.
Definition: skyobject.h:423
Information about an object in the sky.
Definition: skyobject.h:41
void setType(int t)
Set the object's type identifier to the argument.
Definition: skyobject.h:195
QString typeName() const
Definition: skyobject.cpp:389
void setLongName(const QString &longname=QString())
Set the object's long name.
Definition: skyobject.cpp:76
Relevant data about an observing location on Earth.
Definition: geolocation.h:27
This file is part of the KDE documentation.
Documentation copyright © 1996-2022 The KDE developers.
Generated on Fri Aug 12 2022 04:00:58 by doxygen 1.8.17 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.