    001/*
    002 * Licensed to the Apache Software Foundation (ASF) under one or more
    003 * contributor license agreements.  See the NOTICE file distributed with
    004 * this work for additional information regarding copyright ownership.
    005 * The ASF licenses this file to You under the Apache License, Version 2.0
    006 * (the "License"); you may not use this file except in compliance with
    007 * the License.  You may obtain a copy of the License at
    008 *
    009 *      http://www.apache.org/licenses/LICENSE-2.0
    010 *
    011 * Unless required by applicable law or agreed to in writing, software
    012 * distributed under the License is distributed on an "AS IS" BASIS,
    013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    014 * See the License for the specific language governing permissions and
    015 * limitations under the License.
    016 */
    017
    018package org.apache.commons.lang3.time;
    019
    020import java.util.Calendar;
    021import java.util.Locale;
    022import java.util.Locale.Category;
    023import java.util.Map;
    024import java.util.Objects;
    025
    026/**
    027 * Helps use {@link Calendar}s.
    028 *
    029 * @since 3.10
    030 */
    031public class CalendarUtils {
    032
    033    /**
    034     * The singleton instance for {@link Calendar#getInstance()}. The instance is created when the class is initialized and is based on the current time in the
    035     * default time zone with the default {@link Category#FORMAT} locale.
    036     *
    037     * @see CalendarUtils#getInstance()
    038     */
    039    public static final CalendarUtils INSTANCE = getInstance();
    040
    041    /**
    042     * Creates a new instance based on the current time in the default time zone with the default {@link Category#FORMAT} locale.
    043     *
    044     * @return a new instance.
    045     * @since 3.14.0
    046     */
    047    public static CalendarUtils getInstance() {
    048        return new CalendarUtils(Calendar.getInstance());
    049    }
    050
    051    /**
    052     * Gets a CalendarUtils using the default time zone and specified locale. The {@code CalendarUtils} returned is based on the current time in the
    053     * default time zone with the given locale.
    054     *
    055     * @param locale the locale for the week data
    056     * @return a Calendar.
    057     */
    058    static CalendarUtils getInstance(final Locale locale) {
    059        return new CalendarUtils(Calendar.getInstance(locale), locale);
    060    }
    061
    062    private final Calendar calendar;
    063
    064    private final Locale locale;
    065
    066    /**
    067     * Creates an instance for the given Calendar.
    068     *
    069     * @param calendar A Calendar.
    070     */
    071    public CalendarUtils(final Calendar calendar) {
    072        this(calendar, Locale.getDefault());
    073    }
    074
    075    /**
    076     * Creates an instance for the given Calendar.
    077     *
    078     * @param calendar A Calendar.
    079     * @param locale A Locale.
    080     */
    081    CalendarUtils(final Calendar calendar, final Locale locale) {
    082        this.calendar = Objects.requireNonNull(calendar, "calendar");
    083        this.locale = Objects.requireNonNull(locale, "locale");
    084    }
    085    /**
    086     * Gets the current day of month.
    087     *
    088     * @return the current day of month.
    089     */
    090    public int getDayOfMonth() {
    091        return calendar.get(Calendar.DAY_OF_MONTH);
    092    }
    093
    094    /**
    095     * Gets the current day of year.
    096     *
    097     * @return the current day of year.
    098     * @since 3.13.0
    099     */
    100    public int getDayOfYear() {
    101        return calendar.get(Calendar.DAY_OF_YEAR);
    102    }
    103
    104    /**
    105     * Gets the current month.
    106     *
    107     * @return the current month.
    108     */
    109    public int getMonth() {
    110        return calendar.get(Calendar.MONTH);
    111    }
    112
    113    /**
    114     * Gets month names in the requested style.
    115     * @param style Must be a valid {@link Calendar#getDisplayNames(int, int, Locale)} month style.
    116     * @return Styled names of months
    117     */
    118    String[] getMonthDisplayNames(final int style) {
    119        // Unfortunately standalone month names are not available in DateFormatSymbols,
    120        // so we have to extract them.
    121        final Map<String, Integer> displayNames = calendar.getDisplayNames(Calendar.MONTH, style, locale);
    122        if (displayNames == null) {
    123            return null;
    124        }
    125        final String[] monthNames = new String[displayNames.size()];
    126        displayNames.forEach((k, v) -> monthNames[v] = k);
    127        return monthNames;
    128    }
    129
    130    /**
    131     * Gets full standalone month names as used in "LLLL" date formatting.
    132     * @return Long names of months
    133     */
    134    String[] getStandaloneLongMonthNames() {
    135        return getMonthDisplayNames(Calendar.LONG_STANDALONE);
    136    }
    137
    138    /**
    139     * Gets short standalone month names as used in "LLLL" date formatting.
    140     * @return Short names of months
    141     */
    142    String[] getStandaloneShortMonthNames() {
    143        return getMonthDisplayNames(Calendar.SHORT_STANDALONE);
    144    }
    145
    146    /**
    147     * Gets the current year.
    148     *
    149     * @return the current year.
    150     */
    151    public int getYear() {
    152        return calendar.get(Calendar.YEAR);
    153    }
    154}