2 * Copyright (c) 2010-2023 Contributors to the openHAB project
4 * See the NOTICE file(s) distributed with this work for additional
7 * This program and the accompanying materials are made available under the
8 * terms of the Eclipse Public License 2.0 which is available at
9 * http://www.eclipse.org/legal/epl-2.0
11 * SPDX-License-Identifier: EPL-2.0
13 package org.openhab.binding.astro.internal.calc;
15 import java.util.ArrayList;
16 import java.util.Calendar;
17 import java.util.HashMap;
18 import java.util.List;
20 import java.util.Optional;
22 import org.eclipse.jdt.annotation.NonNullByDefault;
23 import org.openhab.binding.astro.internal.model.SunZodiac;
24 import org.openhab.binding.astro.internal.model.ZodiacSign;
25 import org.openhab.binding.astro.internal.util.DateTimeUtils;
28 * Calculates the sign and range of the current zodiac.
30 * @author Gerhard Riegler - Initial contribution
33 public class SunZodiacCalc {
34 private Map<Integer, List<SunZodiac>> zodiacsByYear = new HashMap<>();
37 * Returns the zodiac for the specified calendar.
39 public Optional<SunZodiac> getZodiac(Calendar calendar) {
40 int year = calendar.get(Calendar.YEAR);
41 List<SunZodiac> zodiacs;
43 if (zodiacsByYear.containsKey(year)) {
44 zodiacs = zodiacsByYear.get(year);
46 zodiacs = calculateZodiacs(year);
47 zodiacsByYear.clear();
48 zodiacsByYear.put(year, zodiacs);
51 return zodiacs != null ? zodiacs.stream().filter(z -> z.isValid(calendar)).findFirst() : Optional.empty();
55 * Calculates the zodiacs for the current year.
57 private List<SunZodiac> calculateZodiacs(int year) {
58 List<SunZodiac> zodiacs = new ArrayList<>();
60 zodiacs.add(new SunZodiac(ZodiacSign.ARIES,
61 DateTimeUtils.getRange(year, Calendar.MARCH, 21, year, Calendar.APRIL, 19)));
62 zodiacs.add(new SunZodiac(ZodiacSign.TAURUS,
63 DateTimeUtils.getRange(year, Calendar.APRIL, 20, year, Calendar.MAY, 20)));
64 zodiacs.add(new SunZodiac(ZodiacSign.GEMINI,
65 DateTimeUtils.getRange(year, Calendar.MAY, 21, year, Calendar.JUNE, 20)));
66 zodiacs.add(new SunZodiac(ZodiacSign.CANCER,
67 DateTimeUtils.getRange(year, Calendar.JUNE, 21, year, Calendar.JULY, 22)));
68 zodiacs.add(new SunZodiac(ZodiacSign.LEO,
69 DateTimeUtils.getRange(year, Calendar.JULY, 23, year, Calendar.AUGUST, 22)));
70 zodiacs.add(new SunZodiac(ZodiacSign.VIRGO,
71 DateTimeUtils.getRange(year, Calendar.AUGUST, 23, year, Calendar.SEPTEMBER, 22)));
72 zodiacs.add(new SunZodiac(ZodiacSign.LIBRA,
73 DateTimeUtils.getRange(year, Calendar.SEPTEMBER, 23, year, Calendar.OCTOBER, 22)));
74 zodiacs.add(new SunZodiac(ZodiacSign.SCORPIO,
75 DateTimeUtils.getRange(year, Calendar.OCTOBER, 23, year, Calendar.NOVEMBER, 21)));
76 zodiacs.add(new SunZodiac(ZodiacSign.SAGITTARIUS,
77 DateTimeUtils.getRange(year, Calendar.NOVEMBER, 22, year, Calendar.DECEMBER, 21)));
78 zodiacs.add(new SunZodiac(ZodiacSign.CAPRICORN,
79 DateTimeUtils.getRange(year, Calendar.DECEMBER, 22, year + 1, Calendar.JANUARY, 19)));
80 zodiacs.add(new SunZodiac(ZodiacSign.CAPRICORN,
81 DateTimeUtils.getRange(year - 1, Calendar.DECEMBER, 22, year, Calendar.JANUARY, 19)));
82 zodiacs.add(new SunZodiac(ZodiacSign.AQUARIUS,
83 DateTimeUtils.getRange(year, Calendar.JANUARY, 20, year, Calendar.FEBRUARY, 18)));
84 zodiacs.add(new SunZodiac(ZodiacSign.PISCES,
85 DateTimeUtils.getRange(year, Calendar.FEBRUARY, 19, year, Calendar.MARCH, 20)));