DatePickerCalendarDelegatepublic class DatePickerCalendarDelegate extends DatePicker.AbstractDatePickerDelegate implements View.OnClickListener, DatePickerControllerA delegate for picking up a date (day / month / year). |
Fields Summary |
---|
private static final int | USE_LOCALE | private static final int | UNINITIALIZED | private static final int | MONTH_AND_DAY_VIEW | private static final int | YEAR_VIEW | private static final int | DEFAULT_START_YEAR | private static final int | DEFAULT_END_YEAR | private static final int | ANIMATION_DURATION | private static final int | MONTH_INDEX | private static final int | DAY_INDEX | private static final int | YEAR_INDEX | private SimpleDateFormat | mYearFormat | private SimpleDateFormat | mDayFormat | private TextView | mDayOfWeekView | private LinearLayout | mMonthDayYearLayoutLayout that contains the current month, day, and year. | private LinearLayout | mMonthAndDayLayoutClickable layout that contains the current day and year. | private TextView | mHeaderMonthTextView | private TextView | mHeaderDayOfMonthTextView | private TextView | mHeaderYearTextView | private DayPickerView | mDayPickerView | private YearPickerView | mYearPickerView | private boolean | mIsEnabled | private String | mDayPickerDescription | private String | mSelectDay | private String | mYearPickerDescription | private String | mSelectYear | private com.android.internal.widget.AccessibleDateAnimator | mAnimator | private DatePicker.OnDateChangedListener | mDateChangedListener | private int | mCurrentView | private Calendar | mCurrentDate | private Calendar | mTempDate | private Calendar | mMinDate | private Calendar | mMaxDate | private int | mFirstDayOfWeek | private HashSet | mListeners | private final DayPickerView.OnDaySelectedListener | mOnDaySelectedListenerListener called when the user selects a day in the day picker view. |
Constructors Summary |
---|
public DatePickerCalendarDelegate(DatePicker delegator, android.content.Context context, android.util.AttributeSet attrs, int defStyleAttr, int defStyleRes)
super(delegator, context);
final Locale locale = Locale.getDefault();
mMinDate = getCalendarForLocale(mMinDate, locale);
mMaxDate = getCalendarForLocale(mMaxDate, locale);
mTempDate = getCalendarForLocale(mMaxDate, locale);
mCurrentDate = getCalendarForLocale(mCurrentDate, locale);
mMinDate.set(DEFAULT_START_YEAR, 1, 1);
mMaxDate.set(DEFAULT_END_YEAR, 12, 31);
final Resources res = mDelegator.getResources();
final TypedArray a = mContext.obtainStyledAttributes(attrs,
R.styleable.DatePicker, defStyleAttr, defStyleRes);
final LayoutInflater inflater = (LayoutInflater) mContext.getSystemService(
Context.LAYOUT_INFLATER_SERVICE);
final int layoutResourceId = a.getResourceId(
R.styleable.DatePicker_internalLayout, R.layout.date_picker_holo);
final View mainView = inflater.inflate(layoutResourceId, null);
mDelegator.addView(mainView);
mDayOfWeekView = (TextView) mainView.findViewById(R.id.date_picker_header);
// Layout that contains the current date and day name header.
final LinearLayout dateLayout = (LinearLayout) mainView.findViewById(
R.id.day_picker_selector_layout);
mMonthDayYearLayout = (LinearLayout) mainView.findViewById(
R.id.date_picker_month_day_year_layout);
mMonthAndDayLayout = (LinearLayout) mainView.findViewById(
R.id.date_picker_month_and_day_layout);
mMonthAndDayLayout.setOnClickListener(this);
mHeaderMonthTextView = (TextView) mainView.findViewById(R.id.date_picker_month);
mHeaderDayOfMonthTextView = (TextView) mainView.findViewById(R.id.date_picker_day);
mHeaderYearTextView = (TextView) mainView.findViewById(R.id.date_picker_year);
mHeaderYearTextView.setOnClickListener(this);
// Obtain default highlight color from the theme.
final int defaultHighlightColor = mHeaderYearTextView.getHighlightColor();
// Use Theme attributes if possible
final int dayOfWeekTextAppearanceResId = a.getResourceId(
R.styleable.DatePicker_dayOfWeekTextAppearance, -1);
if (dayOfWeekTextAppearanceResId != -1) {
mDayOfWeekView.setTextAppearance(context, dayOfWeekTextAppearanceResId);
}
mDayOfWeekView.setBackground(a.getDrawable(R.styleable.DatePicker_dayOfWeekBackground));
dateLayout.setBackground(a.getDrawable(R.styleable.DatePicker_headerBackground));
final int headerSelectedTextColor = a.getColor(
R.styleable.DatePicker_headerSelectedTextColor, defaultHighlightColor);
final int monthTextAppearanceResId = a.getResourceId(
R.styleable.DatePicker_headerMonthTextAppearance, -1);
if (monthTextAppearanceResId != -1) {
mHeaderMonthTextView.setTextAppearance(context, monthTextAppearanceResId);
}
mHeaderMonthTextView.setTextColor(ColorStateList.addFirstIfMissing(
mHeaderMonthTextView.getTextColors(), R.attr.state_selected,
headerSelectedTextColor));
final int dayOfMonthTextAppearanceResId = a.getResourceId(
R.styleable.DatePicker_headerDayOfMonthTextAppearance, -1);
if (dayOfMonthTextAppearanceResId != -1) {
mHeaderDayOfMonthTextView.setTextAppearance(context, dayOfMonthTextAppearanceResId);
}
mHeaderDayOfMonthTextView.setTextColor(ColorStateList.addFirstIfMissing(
mHeaderDayOfMonthTextView.getTextColors(), R.attr.state_selected,
headerSelectedTextColor));
final int yearTextAppearanceResId = a.getResourceId(
R.styleable.DatePicker_headerYearTextAppearance, -1);
if (yearTextAppearanceResId != -1) {
mHeaderYearTextView.setTextAppearance(context, yearTextAppearanceResId);
}
mHeaderYearTextView.setTextColor(ColorStateList.addFirstIfMissing(
mHeaderYearTextView.getTextColors(), R.attr.state_selected,
headerSelectedTextColor));
mDayPickerView = new DayPickerView(mContext);
mDayPickerView.setFirstDayOfWeek(mFirstDayOfWeek);
mDayPickerView.setMinDate(mMinDate.getTimeInMillis());
mDayPickerView.setMaxDate(mMaxDate.getTimeInMillis());
mDayPickerView.setDate(mCurrentDate.getTimeInMillis());
mDayPickerView.setOnDaySelectedListener(mOnDaySelectedListener);
mYearPickerView = new YearPickerView(mContext);
mYearPickerView.init(this);
mYearPickerView.setRange(mMinDate, mMaxDate);
final int yearSelectedCircleColor = a.getColor(R.styleable.DatePicker_yearListSelectorColor,
defaultHighlightColor);
mYearPickerView.setYearSelectedCircleColor(yearSelectedCircleColor);
final ColorStateList calendarTextColor = a.getColorStateList(
R.styleable.DatePicker_calendarTextColor);
final int calendarSelectedTextColor = a.getColor(
R.styleable.DatePicker_calendarSelectedTextColor, defaultHighlightColor);
mDayPickerView.setCalendarTextColor(ColorStateList.addFirstIfMissing(
calendarTextColor, R.attr.state_selected, calendarSelectedTextColor));
mDayPickerDescription = res.getString(R.string.day_picker_description);
mSelectDay = res.getString(R.string.select_day);
mYearPickerDescription = res.getString(R.string.year_picker_description);
mSelectYear = res.getString(R.string.select_year);
mAnimator = (AccessibleDateAnimator) mainView.findViewById(R.id.animator);
mAnimator.addView(mDayPickerView);
mAnimator.addView(mYearPickerView);
mAnimator.setDateMillis(mCurrentDate.getTimeInMillis());
final Animation animation = new AlphaAnimation(0.0f, 1.0f);
animation.setDuration(ANIMATION_DURATION);
mAnimator.setInAnimation(animation);
final Animation animation2 = new AlphaAnimation(1.0f, 0.0f);
animation2.setDuration(ANIMATION_DURATION);
mAnimator.setOutAnimation(animation2);
updateDisplay(false);
setCurrentView(MONTH_AND_DAY_VIEW);
|
Methods Summary |
---|
private void | adjustDayInMonthIfNeeded(int month, int year)
int day = mCurrentDate.get(Calendar.DAY_OF_MONTH);
int daysInMonth = getDaysInMonth(month, year);
if (day > daysInMonth) {
mCurrentDate.set(Calendar.DAY_OF_MONTH, daysInMonth);
}
| public boolean | dispatchPopulateAccessibilityEvent(android.view.accessibility.AccessibilityEvent event)
onPopulateAccessibilityEvent(event);
return true;
| private java.util.Calendar | getCalendarForLocale(java.util.Calendar oldCalendar, java.util.Locale locale)Gets a calendar for locale bootstrapped with the value of a given calendar.
if (oldCalendar == null) {
return Calendar.getInstance(locale);
} else {
final long currentTimeMillis = oldCalendar.getTimeInMillis();
Calendar newCalendar = Calendar.getInstance(locale);
newCalendar.setTimeInMillis(currentTimeMillis);
return newCalendar;
}
| public CalendarView | getCalendarView()
throw new UnsupportedOperationException(
"CalendarView does not exists for the new DatePicker");
| public boolean | getCalendarViewShown()
return false;
| public int | getDayOfMonth()
return mCurrentDate.get(Calendar.DAY_OF_MONTH);
| public static int | getDaysInMonth(int month, int year)
switch (month) {
case Calendar.JANUARY:
case Calendar.MARCH:
case Calendar.MAY:
case Calendar.JULY:
case Calendar.AUGUST:
case Calendar.OCTOBER:
case Calendar.DECEMBER:
return 31;
case Calendar.APRIL:
case Calendar.JUNE:
case Calendar.SEPTEMBER:
case Calendar.NOVEMBER:
return 30;
case Calendar.FEBRUARY:
return (year % 4 == 0) ? 29 : 28;
default:
throw new IllegalArgumentException("Invalid Month");
}
| public int | getFirstDayOfWeek()
if (mFirstDayOfWeek != USE_LOCALE) {
return mFirstDayOfWeek;
}
return mCurrentDate.getFirstDayOfWeek();
| public java.util.Calendar | getMaxDate()
return mMaxDate;
| public java.util.Calendar | getMinDate()
return mMinDate;
| public int | getMonth()
return mCurrentDate.get(Calendar.MONTH);
| private int[] | getMonthDayYearIndexes(java.lang.String pattern)Compute the array representing the order of Month / Day / Year views in their layout.
Will be used for I18N purpose as the order of them depends on the Locale.
int[] result = new int[3];
final String filteredPattern = pattern.replaceAll("'.*?'", "");
final int dayIndex = filteredPattern.indexOf('d");
final int monthMIndex = filteredPattern.indexOf("M");
final int monthIndex = (monthMIndex != -1) ? monthMIndex : filteredPattern.indexOf("L");
final int yearIndex = filteredPattern.indexOf("y");
if (yearIndex < monthIndex) {
result[YEAR_INDEX] = 0;
if (monthIndex < dayIndex) {
result[MONTH_INDEX] = 1;
result[DAY_INDEX] = 2;
} else {
result[MONTH_INDEX] = 2;
result[DAY_INDEX] = 1;
}
} else {
result[YEAR_INDEX] = 2;
if (monthIndex < dayIndex) {
result[MONTH_INDEX] = 0;
result[DAY_INDEX] = 1;
} else {
result[MONTH_INDEX] = 1;
result[DAY_INDEX] = 0;
}
}
return result;
| public java.util.Calendar | getSelectedDay()
return mCurrentDate;
| public boolean | getSpinnersShown()
return false;
| public int | getYear()
return mCurrentDate.get(Calendar.YEAR);
| public void | init(int year, int monthOfYear, int dayOfMonth, DatePicker.OnDateChangedListener callBack)
mCurrentDate.set(Calendar.YEAR, year);
mCurrentDate.set(Calendar.MONTH, monthOfYear);
mCurrentDate.set(Calendar.DAY_OF_MONTH, dayOfMonth);
mDateChangedListener = callBack;
onDateChanged(false, false);
| public boolean | isEnabled()
return mIsEnabled;
| public void | onClick(android.view.View v)
tryVibrate();
if (v.getId() == R.id.date_picker_year) {
setCurrentView(YEAR_VIEW);
} else if (v.getId() == R.id.date_picker_month_and_day_layout) {
setCurrentView(MONTH_AND_DAY_VIEW);
}
| public void | onConfigurationChanged(android.content.res.Configuration newConfig)
mYearFormat = new SimpleDateFormat("y", newConfig.locale);
mDayFormat = new SimpleDateFormat("d", newConfig.locale);
| private void | onDateChanged(boolean fromUser, boolean callbackToClient)
if (callbackToClient && mDateChangedListener != null) {
final int year = mCurrentDate.get(Calendar.YEAR);
final int monthOfYear = mCurrentDate.get(Calendar.MONTH);
final int dayOfMonth = mCurrentDate.get(Calendar.DAY_OF_MONTH);
mDateChangedListener.onDateChanged(mDelegator, year, monthOfYear, dayOfMonth);
}
for (OnDateChangedListener listener : mListeners) {
listener.onDateChanged();
}
mDayPickerView.setDate(getSelectedDay().getTimeInMillis());
updateDisplay(fromUser);
if (fromUser) {
tryVibrate();
}
| public void | onInitializeAccessibilityEvent(android.view.accessibility.AccessibilityEvent event)
event.setClassName(DatePicker.class.getName());
| public void | onInitializeAccessibilityNodeInfo(android.view.accessibility.AccessibilityNodeInfo info)
info.setClassName(DatePicker.class.getName());
| public void | onPopulateAccessibilityEvent(android.view.accessibility.AccessibilityEvent event)
event.getText().add(mCurrentDate.getTime().toString());
| public void | onRestoreInstanceState(android.os.Parcelable state)
SavedState ss = (SavedState) state;
mCurrentDate.set(ss.getSelectedYear(), ss.getSelectedMonth(), ss.getSelectedDay());
mCurrentView = ss.getCurrentView();
mMinDate.setTimeInMillis(ss.getMinDate());
mMaxDate.setTimeInMillis(ss.getMaxDate());
updateDisplay(false);
setCurrentView(mCurrentView);
final int listPosition = ss.getListPosition();
if (listPosition != -1) {
if (mCurrentView == MONTH_AND_DAY_VIEW) {
mDayPickerView.postSetSelection(listPosition);
} else if (mCurrentView == YEAR_VIEW) {
mYearPickerView.postSetSelectionFromTop(listPosition, ss.getListPositionOffset());
}
}
| public android.os.Parcelable | onSaveInstanceState(android.os.Parcelable superState)
final int year = mCurrentDate.get(Calendar.YEAR);
final int month = mCurrentDate.get(Calendar.MONTH);
final int day = mCurrentDate.get(Calendar.DAY_OF_MONTH);
int listPosition = -1;
int listPositionOffset = -1;
if (mCurrentView == MONTH_AND_DAY_VIEW) {
listPosition = mDayPickerView.getMostVisiblePosition();
} else if (mCurrentView == YEAR_VIEW) {
listPosition = mYearPickerView.getFirstVisiblePosition();
listPositionOffset = mYearPickerView.getFirstPositionOffset();
}
return new SavedState(superState, year, month, day, mMinDate.getTimeInMillis(),
mMaxDate.getTimeInMillis(), mCurrentView, listPosition, listPositionOffset);
| public void | onYearSelected(int year)
adjustDayInMonthIfNeeded(mCurrentDate.get(Calendar.MONTH), year);
mCurrentDate.set(Calendar.YEAR, year);
onDateChanged(true, true);
// Auto-advance to month and day view.
setCurrentView(MONTH_AND_DAY_VIEW);
| public void | registerOnDateChangedListener(OnDateChangedListener listener)
mListeners.add(listener);
| public void | setCalendarViewShown(boolean shown)
// No-op for compatibility with the old DatePicker.
| private void | setCurrentView(int viewIndex)
long millis = mCurrentDate.getTimeInMillis();
switch (viewIndex) {
case MONTH_AND_DAY_VIEW:
mDayPickerView.setDate(getSelectedDay().getTimeInMillis());
if (mCurrentView != viewIndex) {
mMonthAndDayLayout.setSelected(true);
mHeaderYearTextView.setSelected(false);
mAnimator.setDisplayedChild(MONTH_AND_DAY_VIEW);
mCurrentView = viewIndex;
}
final int flags = DateUtils.FORMAT_SHOW_DATE;
final String dayString = DateUtils.formatDateTime(mContext, millis, flags);
mAnimator.setContentDescription(mDayPickerDescription + ": " + dayString);
mAnimator.announceForAccessibility(mSelectDay);
break;
case YEAR_VIEW:
mYearPickerView.onDateChanged();
if (mCurrentView != viewIndex) {
mMonthAndDayLayout.setSelected(false);
mHeaderYearTextView.setSelected(true);
mAnimator.setDisplayedChild(YEAR_VIEW);
mCurrentView = viewIndex;
}
final CharSequence yearString = mYearFormat.format(millis);
mAnimator.setContentDescription(mYearPickerDescription + ": " + yearString);
mAnimator.announceForAccessibility(mSelectYear);
break;
}
| public void | setEnabled(boolean enabled)
mMonthAndDayLayout.setEnabled(enabled);
mHeaderYearTextView.setEnabled(enabled);
mAnimator.setEnabled(enabled);
mIsEnabled = enabled;
| public void | setFirstDayOfWeek(int firstDayOfWeek)
mFirstDayOfWeek = firstDayOfWeek;
mDayPickerView.setFirstDayOfWeek(firstDayOfWeek);
| public void | setMaxDate(long maxDate)
mTempDate.setTimeInMillis(maxDate);
if (mTempDate.get(Calendar.YEAR) == mMaxDate.get(Calendar.YEAR)
&& mTempDate.get(Calendar.DAY_OF_YEAR) != mMaxDate.get(Calendar.DAY_OF_YEAR)) {
return;
}
if (mCurrentDate.after(mTempDate)) {
mCurrentDate.setTimeInMillis(maxDate);
onDateChanged(false, true);
}
mMaxDate.setTimeInMillis(maxDate);
mDayPickerView.setMaxDate(maxDate);
mYearPickerView.setRange(mMinDate, mMaxDate);
| public void | setMinDate(long minDate)
mTempDate.setTimeInMillis(minDate);
if (mTempDate.get(Calendar.YEAR) == mMinDate.get(Calendar.YEAR)
&& mTempDate.get(Calendar.DAY_OF_YEAR) != mMinDate.get(Calendar.DAY_OF_YEAR)) {
return;
}
if (mCurrentDate.before(mTempDate)) {
mCurrentDate.setTimeInMillis(minDate);
onDateChanged(false, true);
}
mMinDate.setTimeInMillis(minDate);
mDayPickerView.setMinDate(minDate);
mYearPickerView.setRange(mMinDate, mMaxDate);
| public void | setSpinnersShown(boolean shown)
// No-op for compatibility with the old DatePicker.
| public void | tryVibrate()
mDelegator.performHapticFeedback(HapticFeedbackConstants.CALENDAR_DATE);
| public void | updateDate(int year, int month, int dayOfMonth)
mCurrentDate.set(Calendar.YEAR, year);
mCurrentDate.set(Calendar.MONTH, month);
mCurrentDate.set(Calendar.DAY_OF_MONTH, dayOfMonth);
onDateChanged(false, true);
| private void | updateDisplay(boolean announce)
if (mDayOfWeekView != null) {
mDayOfWeekView.setText(mCurrentDate.getDisplayName(Calendar.DAY_OF_WEEK, Calendar.LONG,
Locale.getDefault()));
}
// Compute indices of Month, Day and Year views
final String bestDateTimePattern =
DateFormat.getBestDateTimePattern(mCurrentLocale, "yMMMd");
final int[] viewIndices = getMonthDayYearIndexes(bestDateTimePattern);
// Position the Year and MonthAndDay views within the header.
mMonthDayYearLayout.removeAllViews();
if (viewIndices[YEAR_INDEX] == 0) {
mMonthDayYearLayout.addView(mHeaderYearTextView);
mMonthDayYearLayout.addView(mMonthAndDayLayout);
} else {
mMonthDayYearLayout.addView(mMonthAndDayLayout);
mMonthDayYearLayout.addView(mHeaderYearTextView);
}
// Position Day and Month views within the MonthAndDay view.
mMonthAndDayLayout.removeAllViews();
if (viewIndices[MONTH_INDEX] > viewIndices[DAY_INDEX]) {
mMonthAndDayLayout.addView(mHeaderDayOfMonthTextView);
mMonthAndDayLayout.addView(mHeaderMonthTextView);
} else {
mMonthAndDayLayout.addView(mHeaderMonthTextView);
mMonthAndDayLayout.addView(mHeaderDayOfMonthTextView);
}
mHeaderMonthTextView.setText(mCurrentDate.getDisplayName(Calendar.MONTH, Calendar.SHORT,
Locale.getDefault()).toUpperCase(Locale.getDefault()));
mHeaderDayOfMonthTextView.setText(mDayFormat.format(mCurrentDate.getTime()));
mHeaderYearTextView.setText(mYearFormat.format(mCurrentDate.getTime()));
// Accessibility.
long millis = mCurrentDate.getTimeInMillis();
mAnimator.setDateMillis(millis);
int flags = DateUtils.FORMAT_SHOW_DATE | DateUtils.FORMAT_NO_YEAR;
String monthAndDayText = DateUtils.formatDateTime(mContext, millis, flags);
mMonthAndDayLayout.setContentDescription(monthAndDayText);
if (announce) {
flags = DateUtils.FORMAT_SHOW_DATE | DateUtils.FORMAT_SHOW_YEAR;
String fullDateText = DateUtils.formatDateTime(mContext, millis, flags);
mAnimator.announceForAccessibility(fullDateText);
}
|
|