KDELibs4Support

kcalendarsystemjulian.cpp
1 /*
2  Copyright 2009, 2010 John Layt <[email protected]>
3 
4  This library is free software; you can redistribute it and/or
5  modify it under the terms of the GNU Library General Public
6  License as published by the Free Software Foundation; either
7  version 2 of the License, or (at your option) any later version.
8 
9  This library is distributed in the hope that it will be useful,
10  but WITHOUT ANY WARRANTY; without even the implied warranty of
11  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12  Library General Public License for more details.
13 
14  You should have received a copy of the GNU Library General Public License
15  along with this library; see the file COPYING.LIB. If not, write to
16  the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
17  Boston, MA 02110-1301, USA.
18 */
19 
20 #include "kcalendarsystemjulian_p.h"
21 #include "kcalendarsystemprivate_p.h"
22 
23 #include "klocale.h"
24 #include "klocalizedstring.h"
25 #include "kconfiggroup.h"
26 
27 #include <QDate>
28 #include <QCharRef>
29 
30 class KCalendarSystemJulianPrivate : public KCalendarSystemPrivate
31 {
32 public:
33  KDELIBS4SUPPORT_DEPRECATED explicit KCalendarSystemJulianPrivate(KCalendarSystemJulian *q);
34 
35  virtual ~KCalendarSystemJulianPrivate();
36 
37  // Virtual methods each calendar system must re-implement
38  void loadDefaultEraList() override;
39  int monthsInYear(int year) const override;
40  int daysInMonth(int year, int month) const override;
41  int daysInYear(int year) const override;
42  bool isLeapYear(int year) const override;
43  bool hasLeapMonths() const override;
44  bool hasYearZero() const override;
45  int maxMonthsInYear() const override;
46  int earliestValidYear() const override;
47  int latestValidYear() const override;
48  QString monthName(int month, int year, KLocale::DateTimeComponentFormat format, bool possessive) const override;
49  QString weekDayName(int weekDay, KLocale::DateTimeComponentFormat format) const override;
50 
51  bool m_useCommonEra;
52 };
53 
54 // Shared d pointer base class definitions
55 
56 KCalendarSystemJulianPrivate::KCalendarSystemJulianPrivate(KCalendarSystemJulian *q)
57  : KCalendarSystemPrivate(q)
58 {
59 }
60 
61 KCalendarSystemJulianPrivate::~KCalendarSystemJulianPrivate()
62 {
63 }
64 
65 void KCalendarSystemJulianPrivate::loadDefaultEraList()
66 {
67  QString name, shortName, format;
68 
69  KConfigGroup cg(config(), QString::fromLatin1("KCalendarSystem %1").arg(q->calendarType()));
70  m_useCommonEra = cg.readEntry("UseCommonEra", false);
71 
72  if (m_useCommonEra) {
73  name = i18nc("Calendar Era: Julian Common Era, years < 0, LongFormat", "Before Common Era");
74  shortName = i18nc("Calendar Era: Julian Common Era, years < 0, ShortFormat", "BCE");
75  } else {
76  name = i18nc("Calendar Era: Julian Christian Era, years < 0, LongFormat", "Before Christ");
77  shortName = i18nc("Calendar Era: Julian Christian Era, years < 0, ShortFormat", "BC");
78  }
79  format = i18nc("(kdedt-format) Julian, BC, full era year format used for %EY, e.g. 2000 BC", "%Ey %EC");
80  addEra('-', 1, q->epoch().addDays(-1), -1, q->earliestValidDate(), name, shortName, format);
81 
82  if (m_useCommonEra) {
83  name = i18nc("Calendar Era: Julian Common Era, years > 0, LongFormat", "Common Era");
84  shortName = i18nc("Calendar Era: Julian Common Era, years > 0, ShortFormat", "CE");
85  } else {
86  name = i18nc("Calendar Era: Julian Christian Era, years > 0, LongFormat", "Anno Domini");
87  shortName = i18nc("Calendar Era: Julian Christian Era, years > 0, ShortFormat", "AD");
88  }
89  format = i18nc("(kdedt-format) Julian, AD, full era year format used for %EY, e.g. 2000 AD", "%Ey %EC");
90  addEra('+', 1, q->epoch(), 1, q->latestValidDate(), name, shortName, format);
91 }
92 
93 int KCalendarSystemJulianPrivate::monthsInYear(int year) const
94 {
95  Q_UNUSED(year)
96  return 12;
97 }
98 
99 int KCalendarSystemJulianPrivate::daysInMonth(int year, int month) const
100 {
101  if (month == 2) {
102  if (isLeapYear(year)) {
103  return 29;
104  } else {
105  return 28;
106  }
107  }
108 
109  if (month == 4 || month == 6 || month == 9 || month == 11) {
110  return 30;
111  }
112 
113  return 31;
114 }
115 
116 int KCalendarSystemJulianPrivate::daysInYear(int year) const
117 {
118  if (isLeapYear(year)) {
119  return 366;
120  } else {
121  return 365;
122  }
123 }
124 
125 bool KCalendarSystemJulianPrivate::isLeapYear(int year) const
126 {
127  if (year < 1) {
128  year = year + 1;
129  }
130 
131  if (year % 4 == 0) {
132  return true;
133  }
134 
135  return false;
136 }
137 
138 bool KCalendarSystemJulianPrivate::hasLeapMonths() const
139 {
140  return false;
141 }
142 
143 bool KCalendarSystemJulianPrivate::hasYearZero() const
144 {
145  return false;
146 }
147 
148 int KCalendarSystemJulianPrivate::maxMonthsInYear() const
149 {
150  return 12;
151 }
152 
153 int KCalendarSystemJulianPrivate::earliestValidYear() const
154 {
155  return -4712;
156 }
157 
158 int KCalendarSystemJulianPrivate::latestValidYear() const
159 {
160  return 9999;
161 }
162 
163 QString KCalendarSystemJulianPrivate::monthName(int month, int year, KLocale::DateTimeComponentFormat format, bool possessive) const
164 {
165  Q_UNUSED(year);
166 
167  QStringList languages = locale()->languageList();
168 
169  if (format == KLocale::NarrowName) {
170  switch (month) {
171  case 1:
172  return ki18nc("Julian month 1 - KLocale::NarrowName", "J").toString(languages);
173  case 2:
174  return ki18nc("Julian month 2 - KLocale::NarrowName", "F").toString(languages);
175  case 3:
176  return ki18nc("Julian month 3 - KLocale::NarrowName", "M").toString(languages);
177  case 4:
178  return ki18nc("Julian month 4 - KLocale::NarrowName", "A").toString(languages);
179  case 5:
180  return ki18nc("Julian month 5 - KLocale::NarrowName", "M").toString(languages);
181  case 6:
182  return ki18nc("Julian month 6 - KLocale::NarrowName", "J").toString(languages);
183  case 7:
184  return ki18nc("Julian month 7 - KLocale::NarrowName", "J").toString(languages);
185  case 8:
186  return ki18nc("Julian month 8 - KLocale::NarrowName", "A").toString(languages);
187  case 9:
188  return ki18nc("Julian month 9 - KLocale::NarrowName", "S").toString(languages);
189  case 10:
190  return ki18nc("Julian month 10 - KLocale::NarrowName", "O").toString(languages);
191  case 11:
192  return ki18nc("Julian month 11 - KLocale::NarrowName", "N").toString(languages);
193  case 12:
194  return ki18nc("Julian month 12 - KLocale::NarrowName", "D").toString(languages);
195  default:
196  return QString();
197  }
198  }
199 
200  if (format == KLocale::ShortName && possessive) {
201  switch (month) {
202  case 1:
203  return ki18nc("Julian month 1 - KLocale::ShortName Possessive", "of Jan").toString(languages);
204  case 2:
205  return ki18nc("Julian month 2 - KLocale::ShortName Possessive", "of Feb").toString(languages);
206  case 3:
207  return ki18nc("Julian month 3 - KLocale::ShortName Possessive", "of Mar").toString(languages);
208  case 4:
209  return ki18nc("Julian month 4 - KLocale::ShortName Possessive", "of Apr").toString(languages);
210  case 5:
211  return ki18nc("Julian month 5 - KLocale::ShortName Possessive", "of May").toString(languages);
212  case 6:
213  return ki18nc("Julian month 6 - KLocale::ShortName Possessive", "of Jun").toString(languages);
214  case 7:
215  return ki18nc("Julian month 7 - KLocale::ShortName Possessive", "of Jul").toString(languages);
216  case 8:
217  return ki18nc("Julian month 8 - KLocale::ShortName Possessive", "of Aug").toString(languages);
218  case 9:
219  return ki18nc("Julian month 9 - KLocale::ShortName Possessive", "of Sep").toString(languages);
220  case 10:
221  return ki18nc("Julian month 10 - KLocale::ShortName Possessive", "of Oct").toString(languages);
222  case 11:
223  return ki18nc("Julian month 11 - KLocale::ShortName Possessive", "of Nov").toString(languages);
224  case 12:
225  return ki18nc("Julian month 12 - KLocale::ShortName Possessive", "of Dec").toString(languages);
226  default:
227  return QString();
228  }
229  }
230 
231  if (format == KLocale::ShortName && !possessive) {
232  switch (month) {
233  case 1:
234  return ki18nc("Julian month 1 - KLocale::ShortName", "Jan").toString(languages);
235  case 2:
236  return ki18nc("Julian month 2 - KLocale::ShortName", "Feb").toString(languages);
237  case 3:
238  return ki18nc("Julian month 3 - KLocale::ShortName", "Mar").toString(languages);
239  case 4:
240  return ki18nc("Julian month 4 - KLocale::ShortName", "Apr").toString(languages);
241  case 5:
242  return ki18nc("Julian month 5 - KLocale::ShortName", "May").toString(languages);
243  case 6:
244  return ki18nc("Julian month 6 - KLocale::ShortName", "Jun").toString(languages);
245  case 7:
246  return ki18nc("Julian month 7 - KLocale::ShortName", "Jul").toString(languages);
247  case 8:
248  return ki18nc("Julian month 8 - KLocale::ShortName", "Aug").toString(languages);
249  case 9:
250  return ki18nc("Julian month 9 - KLocale::ShortName", "Sep").toString(languages);
251  case 10:
252  return ki18nc("Julian month 10 - KLocale::ShortName", "Oct").toString(languages);
253  case 11:
254  return ki18nc("Julian month 11 - KLocale::ShortName", "Nov").toString(languages);
255  case 12:
256  return ki18nc("Julian month 12 - KLocale::ShortName", "Dec").toString(languages);
257  default:
258  return QString();
259  }
260  }
261 
262  if (format == KLocale::LongName && possessive) {
263  switch (month) {
264  case 1:
265  return ki18nc("Julian month 1 - KLocale::LongName Possessive", "of January").toString(languages);
266  case 2:
267  return ki18nc("Julian month 2 - KLocale::LongName Possessive", "of February").toString(languages);
268  case 3:
269  return ki18nc("Julian month 3 - KLocale::LongName Possessive", "of March").toString(languages);
270  case 4:
271  return ki18nc("Julian month 4 - KLocale::LongName Possessive", "of April").toString(languages);
272  case 5:
273  return ki18nc("Julian month 5 - KLocale::LongName Possessive", "of May").toString(languages);
274  case 6:
275  return ki18nc("Julian month 6 - KLocale::LongName Possessive", "of June").toString(languages);
276  case 7:
277  return ki18nc("Julian month 7 - KLocale::LongName Possessive", "of July").toString(languages);
278  case 8:
279  return ki18nc("Julian month 8 - KLocale::LongName Possessive", "of August").toString(languages);
280  case 9:
281  return ki18nc("Julian month 9 - KLocale::LongName Possessive", "of September").toString(languages);
282  case 10:
283  return ki18nc("Julian month 10 - KLocale::LongName Possessive", "of October").toString(languages);
284  case 11:
285  return ki18nc("Julian month 11 - KLocale::LongName Possessive", "of November").toString(languages);
286  case 12:
287  return ki18nc("Julian month 12 - KLocale::LongName Possessive", "of December").toString(languages);
288  default:
289  return QString();
290  }
291  }
292 
293  // Default to LongName
294  switch (month) {
295  case 1:
296  return ki18nc("Julian month 1 - KLocale::LongName", "January").toString(languages);
297  case 2:
298  return ki18nc("Julian month 2 - KLocale::LongName", "February").toString(languages);
299  case 3:
300  return ki18nc("Julian month 3 - KLocale::LongName", "March").toString(languages);
301  case 4:
302  return ki18nc("Julian month 4 - KLocale::LongName", "April").toString(languages);
303  case 5:
304  return ki18nc("Julian month 5 - KLocale::LongName", "May").toString(languages);
305  case 6:
306  return ki18nc("Julian month 6 - KLocale::LongName", "June").toString(languages);
307  case 7:
308  return ki18nc("Julian month 7 - KLocale::LongName", "July").toString(languages);
309  case 8:
310  return ki18nc("Julian month 8 - KLocale::LongName", "August").toString(languages);
311  case 9:
312  return ki18nc("Julian month 9 - KLocale::LongName", "September").toString(languages);
313  case 10:
314  return ki18nc("Julian month 10 - KLocale::LongName", "October").toString(languages);
315  case 11:
316  return ki18nc("Julian month 11 - KLocale::LongName", "November").toString(languages);
317  case 12:
318  return ki18nc("Julian month 12 - KLocale::LongName", "December").toString(languages);
319  default:
320  return QString();
321  }
322 }
323 
324 QString KCalendarSystemJulianPrivate::weekDayName(int weekDay, KLocale::DateTimeComponentFormat format) const
325 {
326  QStringList languages = locale()->languageList();
327 
328  if (format == KLocale::NarrowName) {
329  switch (weekDay) {
330  case 1:
331  return ki18nc("Julian weekday 1 - KLocale::NarrowName ", "M").toString(languages);
332  case 2:
333  return ki18nc("Julian weekday 2 - KLocale::NarrowName ", "T").toString(languages);
334  case 3:
335  return ki18nc("Julian weekday 3 - KLocale::NarrowName ", "W").toString(languages);
336  case 4:
337  return ki18nc("Julian weekday 4 - KLocale::NarrowName ", "T").toString(languages);
338  case 5:
339  return ki18nc("Julian weekday 5 - KLocale::NarrowName ", "F").toString(languages);
340  case 6:
341  return ki18nc("Julian weekday 6 - KLocale::NarrowName ", "S").toString(languages);
342  case 7:
343  return ki18nc("Julian weekday 7 - KLocale::NarrowName ", "S").toString(languages);
344  default:
345  return QString();
346  }
347  }
348 
349  if (format == KLocale::ShortName || format == KLocale:: ShortNumber) {
350  switch (weekDay) {
351  case 1:
352  return ki18nc("Julian weekday 1 - KLocale::ShortName", "Mon").toString(languages);
353  case 2:
354  return ki18nc("Julian weekday 2 - KLocale::ShortName", "Tue").toString(languages);
355  case 3:
356  return ki18nc("Julian weekday 3 - KLocale::ShortName", "Wed").toString(languages);
357  case 4:
358  return ki18nc("Julian weekday 4 - KLocale::ShortName", "Thu").toString(languages);
359  case 5:
360  return ki18nc("Julian weekday 5 - KLocale::ShortName", "Fri").toString(languages);
361  case 6:
362  return ki18nc("Julian weekday 6 - KLocale::ShortName", "Sat").toString(languages);
363  case 7:
364  return ki18nc("Julian weekday 7 - KLocale::ShortName", "Sun").toString(languages);
365  default: return QString();
366  }
367  }
368 
369  switch (weekDay) {
370  case 1:
371  return ki18nc("Julian weekday 1 - KLocale::LongName", "Monday").toString(languages);
372  case 2:
373  return ki18nc("Julian weekday 2 - KLocale::LongName", "Tuesday").toString(languages);
374  case 3:
375  return ki18nc("Julian weekday 3 - KLocale::LongName", "Wednesday").toString(languages);
376  case 4:
377  return ki18nc("Julian weekday 4 - KLocale::LongName", "Thursday").toString(languages);
378  case 5:
379  return ki18nc("Julian weekday 5 - KLocale::LongName", "Friday").toString(languages);
380  case 6:
381  return ki18nc("Julian weekday 6 - KLocale::LongName", "Saturday").toString(languages);
382  case 7:
383  return ki18nc("Julian weekday 7 - KLocale::LongName", "Sunday").toString(languages);
384  default:
385  return QString();
386  }
387 }
388 
389 KCalendarSystemJulian::KCalendarSystemJulian(const KSharedConfig::Ptr config, const KLocale *locale)
390  : KCalendarSystem(*new KCalendarSystemJulianPrivate(this), config, locale)
391 {
392  d_ptr->loadConfig(calendarType());
393 }
394 
395 KCalendarSystemJulian::KCalendarSystemJulian(KCalendarSystemJulianPrivate &dd,
396  const KSharedConfig::Ptr config, const KLocale *locale)
397  : KCalendarSystem(dd, config, locale)
398 {
399  d_ptr->loadConfig(calendarType());
400 }
401 
402 KCalendarSystemJulian::~KCalendarSystemJulian()
403 {
404 }
405 
406 QString KCalendarSystemJulian::calendarType() const
407 {
408  return QLatin1String("julian");
409 }
410 
411 KLocale::CalendarSystem KCalendarSystemJulian::calendarSystem() const
412 {
414 }
415 
416 QDate KCalendarSystemJulian::epoch() const
417 {
418  return QDate::fromJulianDay(1721426);
419 }
420 
421 QDate KCalendarSystemJulian::earliestValidDate() const
422 {
423  // 1 Jan 4712 BC, no year zero, cant be 4713BC due to error in QDate that day 0 is not valid
424  // and we really need the first in each year to be valid for the date maths
425  return QDate::fromJulianDay(366);
426 }
427 
428 QDate KCalendarSystemJulian::latestValidDate() const
429 {
430  // Set to last day of year 9999 until confirm date formats & widgets support > 9999
431  // 31 Dec 9999 AD, no year zero
432  return QDate::fromJulianDay(5373557);
433 }
434 
435 QString KCalendarSystemJulian::monthName(int month, int year, MonthNameFormat format) const
436 {
437  return KCalendarSystem::monthName(month, year, format);
438 }
439 
440 QString KCalendarSystemJulian::monthName(const QDate &date, MonthNameFormat format) const
441 {
442  return KCalendarSystem::monthName(date, format);
443 }
444 
445 QString KCalendarSystemJulian::weekDayName(int weekDay, WeekDayNameFormat format) const
446 {
447  return KCalendarSystem::weekDayName(weekDay, format);
448 }
449 
450 QString KCalendarSystemJulian::weekDayName(const QDate &date, WeekDayNameFormat format) const
451 {
452  return KCalendarSystem::weekDayName(date, format);
453 }
454 
455 bool KCalendarSystemJulian::isLunar() const
456 {
457  return false;
458 }
459 
460 bool KCalendarSystemJulian::isLunisolar() const
461 {
462  return false;
463 }
464 
465 bool KCalendarSystemJulian::isSolar() const
466 {
467  return true;
468 }
469 
470 bool KCalendarSystemJulian::isProleptic() const
471 {
472  return true;
473 }
474 
475 bool KCalendarSystemJulian::julianDayToDate(qint64 jd, int &year, int &month, int &day) const
476 {
477  // Formula from The Calendar FAQ by Claus Tondering
478  // http://www.tondering.dk/claus/cal/node3.html#SECTION003161000000000000000
479  // NOTE: Coded from scratch from mathematical formulas, not copied from
480  // the Boost licensed source code
481 
482  int b = 0;
483  int c = jd + 32082;
484  int d = ((4 * c) + 3) / 1461;
485  int e = c - ((1461 * d) / 4);
486  int m = ((5 * e) + 2) / 153;
487  day = e - (((153 * m) + 2) / 5) + 1;
488  month = m + 3 - (12 * (m / 10));
489  year = (100 * b) + d - 4800 + (m / 10);
490 
491  // If year is -ve then is BC. In Julian there is no year 0, but the maths
492  // is easier if we pretend there is, so internally year of 0 = 1BC = -1 outside
493  if (year < 1) {
494  year = year - 1;
495  }
496 
497  return true;
498 }
499 
500 bool KCalendarSystemJulian::dateToJulianDay(int year, int month, int day, qint64 &jd) const
501 {
502  // Formula from The Calendar FAQ by Claus Tondering
503  // http://www.tondering.dk/claus/cal/node3.html#SECTION003161000000000000000
504  // NOTE: Coded from scratch from mathematical formulas, not copied from
505  // the Boost licensed source code
506 
507  // If year is -ve then is BC. In Julian there is no year 0, but the maths
508  // is easier if we pretend there is, so internally year of -1 = 1BC = 0 internally
509  int y;
510  if (year < 1) {
511  y = year + 1;
512  } else {
513  y = year;
514  }
515 
516  int a = (14 - month) / 12;
517  y = y + 4800 - a;
518  int m = month + (12 * a) - 3;
519 
520  jd = day
521  + (((153 * m) + 2) / 5)
522  + (365 * y)
523  + (y / 4)
524  - 32083;
525 
526  return true;
527 }
Narrow text format, may not be unique, e.g.
Definition: klocale.h:775
QString toString() const
QString name(const QVariant &location)
virtual int day(const QDate &date) const
Returns the day portion of a given date in the current calendar system.
virtual QString weekDayName(int weekDay, WeekDayNameFormat format=LongDayName) const =0
Gets specific calendar type week day name.
MonthNameFormat
Format for returned month / day name.
Number at its natural width, e.g.
Definition: klocale.h:772
KCalendarSystem abstract base class, provides support for local Calendar Systems in KDE...
DateTimeComponentFormat
Definition: klocale.h:770
KSharedConfigPtr config()
Returns the general config object.
Definition: kglobal.cpp:104
CalendarSystem
Definition: klocale.h:646
bool isLeapYear(int year) const
Returns whether a given year is a leap year.
QString i18nc(const char *context, const char *text, const TYPE &arg...)
Long text format, e.g.
Definition: klocale.h:777
virtual int month(const QDate &date) const
Returns the month portion of a given date in the current calendar system.
const KLocale * locale() const
Returns the locale used for translations and formats for this calendar system instance.
WeekDayNameFormat
Format for returned month / day name.
Short text format, e.g.
Definition: klocale.h:776
virtual int year(const QDate &date) const
Returns the year portion of a given date in the current calendar system.
KLocalizedString KI18N_EXPORT ki18nc(const char *context, const char *text)
QStringList languageList() const
Returns the language codes selected by user, ordered by decreasing priority.
Definition: klocale.cpp:376
virtual QString monthName(int month, int year, MonthNameFormat format=LongName) const =0
Gets specific calendar type month name for a given month number If an invalid month is specified...
KLocale provides support for language and country specific stuff.
Definition: klocale.h:75
QString fromLatin1(const char *str, int size)
QDate fromJulianDay(qint64 jd)
virtual QString calendarType() const =0
Julian Calendar, as used in Orthodox Churches.
Definition: klocale.h:666
int daysInMonth(const QDate &date) const
Returns the number of days in the given month.
This file is part of the KDE documentation.
Documentation copyright © 1996-2020 The KDE developers.
Generated on Sun Jul 5 2020 22:58:44 by doxygen 1.8.11 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.