1/* GENERATED SOURCE. DO NOT MODIFY. */ 2// © 2016 and later: Unicode, Inc. and others. 3// License & terms of use: http://www.unicode.org/copyright.html#License 4/* 5 ******************************************************************************* 6 * Copyright (C) 1996-2010, International Business Machines Corporation and * 7 * others. All Rights Reserved. * 8 ******************************************************************************* 9 */ 10 11package android.icu.util; 12 13import java.util.Date; 14 15/** 16 * <b>Note:</b> The Holiday framework is a technology preview. 17 * Despite its age, is still draft API, and clients should treat it as such. 18 * 19 * Simple implementation of DateRule. 20 * @hide Only a subset of ICU is exposed in Android 21 * @hide draft / provisional / internal are hidden on Android 22 */ 23public class SimpleDateRule implements DateRule 24{ 25 /** 26 * Construct a rule for a fixed date within a month 27 * 28 * @param month The month in which this rule occurs (0-based). 29 * @param dayOfMonth The date in that month (1-based). 30 * @hide draft / provisional / internal are hidden on Android 31 */ 32 public SimpleDateRule(int month, int dayOfMonth) 33 { 34 this.month = month; 35 this.dayOfMonth = dayOfMonth; 36 this.dayOfWeek = 0; 37 } 38 39 // temporary 40 /* package */SimpleDateRule(int month, int dayOfMonth, Calendar cal) 41 { 42 this.month = month; 43 this.dayOfMonth = dayOfMonth; 44 this.dayOfWeek = 0; 45 this.calendar = cal; 46 } 47 48 /** 49 * Construct a rule for a weekday within a month, e.g. the first Monday. 50 * 51 * @param month The month in which this rule occurs (0-based). 52 * @param dayOfMonth A date within that month (1-based). 53 * @param dayOfWeek The day of the week on which this rule occurs. 54 * @param after If true, this rule selects the first dayOfWeek 55 * on or after dayOfMonth. If false, the rule selects 56 * the first dayOfWeek on or before dayOfMonth. 57 * @hide draft / provisional / internal are hidden on Android 58 */ 59 public SimpleDateRule(int month, int dayOfMonth, int dayOfWeek, boolean after) 60 { 61 this.month = month; 62 this.dayOfMonth = dayOfMonth; 63 this.dayOfWeek = after ? dayOfWeek : -dayOfWeek; 64 } 65 66 /** 67 * Return the first occurrance of the event represented by this rule 68 * that is on or after the given start date. 69 * 70 * @param start Only occurrances on or after this date are returned. 71 * 72 * @return The date on which this event occurs, or null if it 73 * does not occur on or after the start date. 74 * 75 * @see #firstBetween 76 * @hide draft / provisional / internal are hidden on Android 77 */ 78 public Date firstAfter(Date start) 79 { 80 return doFirstBetween(start, null); 81 } 82 83 /** 84 * Return the first occurrance of the event represented by this rule 85 * that is on or after the given start date and before the given 86 * end date. 87 * 88 * @param start Only occurrances on or after this date are returned. 89 * @param end Only occurrances before this date are returned. 90 * 91 * @return The date on which this event occurs, or null if it 92 * does not occur between the start and end dates. 93 * 94 * @see #firstAfter 95 * @hide draft / provisional / internal are hidden on Android 96 */ 97 public Date firstBetween(Date start, Date end) 98 { 99 // Pin to the min/max dates for this rule 100 return doFirstBetween(start, end); 101 } 102 103 /** 104 * Checks whether this event occurs on the given date. This does 105 * <em>not</em> take time of day into account; instead it checks 106 * whether this event and the given date are on the same day. 107 * This is useful for applications such as determining whether a given 108 * day is a holiday. 109 * 110 * @param date The date to check. 111 * @return true if this event occurs on the given date. 112 * @hide draft / provisional / internal are hidden on Android 113 */ 114 public boolean isOn(Date date) 115 { 116 Calendar c = calendar; 117 118 synchronized(c) { 119 c.setTime(date); 120 121 int dayOfYear = c.get(Calendar.DAY_OF_YEAR); 122 123 c.setTime(computeInYear(c.get(Calendar.YEAR), c)); 124 125// System.out.println(" isOn: dayOfYear = " + dayOfYear); 126// System.out.println(" holiday = " + c.get(Calendar.DAY_OF_YEAR)); 127 128 return c.get(Calendar.DAY_OF_YEAR) == dayOfYear; 129 } 130 } 131 132 /** 133 * Check whether this event occurs at least once between the two 134 * dates given. 135 * @hide draft / provisional / internal are hidden on Android 136 */ 137 public boolean isBetween(Date start, Date end) 138 { 139 return firstBetween(start, end) != null; // TODO: optimize? 140 } 141 142 private Date doFirstBetween(Date start, Date end) 143 { 144 Calendar c = calendar; 145 146 synchronized(c) { 147 c.setTime(start); 148 149 int year = c.get(Calendar.YEAR); 150 int mon = c.get(Calendar.MONTH); 151 152 // If the rule is earlier in the year than the start date 153 // we have to go to the next year. 154 if (mon > this.month) { 155 year++; 156 } 157 158 // Figure out when the rule lands in the given year 159 Date result = computeInYear(year, c); 160 161 // If the rule is in the same month as the start date, it's possible 162 // to get a result that's before the start. If so, go to next year. 163 if (mon == this.month && result.before(start)) { 164 result = computeInYear(year+1, c); 165 } 166 167 if (end != null && result.after(end)) { 168 return null; 169 } 170 return result; 171 } 172 } 173 174 private Date computeInYear(int year, Calendar c) 175 { 176 synchronized(c) { 177 c.clear(); 178 c.set(Calendar.ERA, c.getMaximum(Calendar.ERA)); 179 c.set(Calendar.YEAR, year); 180 c.set(Calendar.MONTH, month); 181 c.set(Calendar.DATE, dayOfMonth); 182 183 //System.out.println(" computeInYear: start at " + c.getTime().toString()); 184 185 if (dayOfWeek != 0) { 186 c.setTime(c.getTime()); // JDK 1.1.2 workaround 187 int weekday = c.get(Calendar.DAY_OF_WEEK); 188 189 //System.out.println(" weekday = " + weekday); 190 //System.out.println(" dayOfYear = " + c.get(Calendar.DAY_OF_YEAR)); 191 192 int delta = 0; 193 if (dayOfWeek > 0) { 194 // We want the first occurrance of the given day of the week 195 // on or after the specified date in the month. 196 delta = (dayOfWeek - weekday + 7) % 7; 197 } 198 else { 199 // We want the first occurrance of the (-dayOfWeek) 200 // on or before the specified date in the month. 201 delta = -((dayOfWeek + weekday + 7) % 7); 202 } 203 //System.out.println(" adding " + delta + " days"); 204 c.add(Calendar.DATE, delta); 205 } 206 207 return c.getTime(); 208 } 209 } 210 211 /** 212 * @hide draft / provisional / internal are hidden on Android 213 */ 214// public void setCalendar(Calendar c) { 215// calendar = c; 216// } 217 218 private Calendar calendar = new GregorianCalendar(); 219 220 private int month; 221 private int dayOfMonth; 222 private int dayOfWeek; 223} 224