diff options
Diffstat (limited to 'core/java/android/widget/TimePickerClockDelegate.java')
| -rw-r--r-- | core/java/android/widget/TimePickerClockDelegate.java | 126 |
1 files changed, 95 insertions, 31 deletions
diff --git a/core/java/android/widget/TimePickerClockDelegate.java b/core/java/android/widget/TimePickerClockDelegate.java index 9fdd718..718d216 100644 --- a/core/java/android/widget/TimePickerClockDelegate.java +++ b/core/java/android/widget/TimePickerClockDelegate.java @@ -16,16 +16,20 @@ package android.widget; +import android.annotation.Nullable; import android.content.Context; +import android.content.res.ColorStateList; import android.content.res.Configuration; import android.content.res.Resources; import android.content.res.TypedArray; +import android.graphics.drawable.Drawable; import android.os.Parcel; import android.os.Parcelable; import android.text.format.DateFormat; import android.text.format.DateUtils; import android.util.AttributeSet; import android.util.Log; +import android.util.StateSet; import android.util.TypedValue; import android.view.HapticFeedbackConstants; import android.view.KeyCharacterMap; @@ -48,7 +52,6 @@ import java.util.Locale; */ class TimePickerClockDelegate extends TimePicker.AbstractTimePickerDelegate implements RadialTimePickerView.OnValueSelectedListener { - private static final String TAG = "TimePickerClockDelegate"; // Index used by RadialPickerLayout @@ -61,14 +64,16 @@ class TimePickerClockDelegate extends TimePicker.AbstractTimePickerDelegate impl // Also NOT a real index, just used for keyboard mode. private static final int ENABLE_PICKER_INDEX = 3; + private static final int[] ATTRS_TEXT_COLOR = new int[] { + com.android.internal.R.attr.textColor}; + private static final int[] ATTRS_DISABLED_ALPHA = new int[] { + com.android.internal.R.attr.disabledAlpha}; + // LayoutLib relies on these constants. Change TimePickerClockDelegate_Delegate if // modifying these. static final int AM = 0; static final int PM = 1; - private static final boolean DEFAULT_ENABLED_STATE = true; - private boolean mIsEnabled = DEFAULT_ENABLED_STATE; - private static final int HOURS_IN_HALF_DAY = 12; private final View mHeaderView; @@ -83,8 +88,7 @@ class TimePickerClockDelegate extends TimePicker.AbstractTimePickerDelegate impl private final String mAmText; private final String mPmText; - private final float mDisabledAlpha; - + private boolean mIsEnabled = true; private boolean mAllowAutoAdvance; private int mInitialHourOfDay; private int mInitialMinute; @@ -134,7 +138,6 @@ class TimePickerClockDelegate extends TimePicker.AbstractTimePickerDelegate impl final View mainView = inflater.inflate(layoutResourceId, delegator); mHeaderView = mainView.findViewById(R.id.time_header); - mHeaderView.setBackground(a.getDrawable(R.styleable.TimePicker_headerBackground)); // Set up hour/minute labels. mHourView = (TextView) mainView.findViewById(R.id.hours); @@ -147,14 +150,6 @@ class TimePickerClockDelegate extends TimePicker.AbstractTimePickerDelegate impl mMinuteView.setAccessibilityDelegate( new ClickActionDelegate(context, R.string.select_minutes)); - final int headerTimeTextAppearance = a.getResourceId( - R.styleable.TimePicker_headerTimeTextAppearance, 0); - if (headerTimeTextAppearance != 0) { - mHourView.setTextAppearance(context, headerTimeTextAppearance); - mSeparatorView.setTextAppearance(context, headerTimeTextAppearance); - mMinuteView.setTextAppearance(context, headerTimeTextAppearance); - } - // Now that we have text appearances out of the way, make sure the hour // and minute views are correctly sized. mHourView.setMinWidth(computeStableWidth(mHourView, 24)); @@ -169,19 +164,40 @@ class TimePickerClockDelegate extends TimePicker.AbstractTimePickerDelegate impl mPmLabel.setText(amPmStrings[1]); mPmLabel.setOnClickListener(mClickListener); - final int headerAmPmTextAppearance = a.getResourceId( - R.styleable.TimePicker_headerAmPmTextAppearance, 0); - if (headerAmPmTextAppearance != 0) { - mAmLabel.setTextAppearance(context, headerAmPmTextAppearance); - mPmLabel.setTextAppearance(context, headerAmPmTextAppearance); + // For the sake of backwards compatibility, attempt to extract the text + // color from the header time text appearance. If it's set, we'll let + // that override the "real" header text color. + ColorStateList headerTextColor = null; + + @SuppressWarnings("deprecation") + final int timeHeaderTextAppearance = a.getResourceId( + R.styleable.TimePicker_headerTimeTextAppearance, 0); + if (timeHeaderTextAppearance != 0) { + final TypedArray textAppearance = mContext.obtainStyledAttributes(null, + ATTRS_TEXT_COLOR, 0, timeHeaderTextAppearance); + final ColorStateList legacyHeaderTextColor = textAppearance.getColorStateList(0); + headerTextColor = applyLegacyColorFixes(legacyHeaderTextColor); + textAppearance.recycle(); } - a.recycle(); + if (headerTextColor == null) { + headerTextColor = a.getColorStateList(R.styleable.TimePicker_headerTextColor); + } + + if (headerTextColor != null) { + mHourView.setTextColor(headerTextColor); + mSeparatorView.setTextColor(headerTextColor); + mMinuteView.setTextColor(headerTextColor); + mAmLabel.setTextColor(headerTextColor); + mPmLabel.setTextColor(headerTextColor); + } + + // Set up header background, if available. + if (a.hasValueOrEmpty(R.styleable.TimePicker_headerBackground)) { + mHeaderView.setBackground(a.getDrawable(R.styleable.TimePicker_headerBackground)); + } - // Pull disabled alpha from theme. - final TypedValue outValue = new TypedValue(); - context.getTheme().resolveAttribute(android.R.attr.disabledAlpha, outValue, true); - mDisabledAlpha = outValue.getFloat(); + a.recycle(); mRadialTimePickerView = (RadialTimePickerView) mainView.findViewById( R.id.radial_picker); @@ -204,6 +220,54 @@ class TimePickerClockDelegate extends TimePicker.AbstractTimePickerDelegate impl initialize(currentHour, currentMinute, false /* 12h */, HOUR_INDEX); } + /** + * The legacy text color might have been poorly defined. Ensures that it + * has an appropriate activated state, using the selected state if one + * exists or modifying the default text color otherwise. + * + * @param color a legacy text color, or {@code null} + * @return a color state list with an appropriate activated state, or + * {@code null} if a valid activated state could not be generated + */ + @Nullable + private ColorStateList applyLegacyColorFixes(@Nullable ColorStateList color) { + if (color == null || color.hasState(R.attr.state_activated)) { + return color; + } + + final int activatedColor; + final int defaultColor; + if (color.hasState(R.attr.state_selected)) { + activatedColor = color.getColorForState(StateSet.get( + StateSet.VIEW_STATE_ENABLED | StateSet.VIEW_STATE_SELECTED), 0); + defaultColor = color.getColorForState(StateSet.get( + StateSet.VIEW_STATE_ENABLED), 0); + } else { + activatedColor = color.getDefaultColor(); + + // Generate a non-activated color using the disabled alpha. + final TypedArray ta = mContext.obtainStyledAttributes(ATTRS_DISABLED_ALPHA); + final float disabledAlpha = ta.getFloat(0, 0.30f); + defaultColor = multiplyAlphaComponent(activatedColor, disabledAlpha); + } + + if (activatedColor == 0 || defaultColor == 0) { + // We somehow failed to obtain the colors. + return null; + } + + final int[][] stateSet = new int[][] {{ R.attr.state_activated }, {}}; + final int[] colors = new int[] { activatedColor, defaultColor }; + return new ColorStateList(stateSet, colors); + } + + private int multiplyAlphaComponent(int color, float alphaMod) { + final int srcRgb = color & 0xFFFFFF; + final int srcAlpha = (color >> 24) & 0xFF; + final int dstAlpha = (int) (srcAlpha * alphaMod + 0.5f); + return srcRgb | (dstAlpha << 24); + } + private static class ClickActionDelegate extends AccessibilityDelegate { private final AccessibilityAction mClickAction; @@ -604,12 +668,12 @@ class TimePickerClockDelegate extends TimePicker.AbstractTimePickerDelegate impl private void updateAmPmLabelStates(int amOrPm) { final boolean isAm = amOrPm == AM; + mAmLabel.setActivated(isAm); mAmLabel.setChecked(isAm); - mAmLabel.setSelected(isAm); final boolean isPm = amOrPm == PM; + mPmLabel.setActivated(isPm); mPmLabel.setChecked(isPm); - mPmLabel.setSelected(isPm); } /** @@ -769,8 +833,8 @@ class TimePickerClockDelegate extends TimePicker.AbstractTimePickerDelegate impl } } - mHourView.setSelected(index == HOUR_INDEX); - mMinuteView.setSelected(index == MINUTE_INDEX); + mHourView.setActivated(index == HOUR_INDEX); + mMinuteView.setActivated(index == MINUTE_INDEX); } private void setAmOrPm(int amOrPm) { @@ -960,9 +1024,9 @@ class TimePickerClockDelegate extends TimePicker.AbstractTimePickerDelegate impl String minuteStr = (values[1] == -1) ? mDoublePlaceholderText : String.format(minuteFormat, values[1]).replace(' ', mPlaceholderText); mHourView.setText(hourStr); - mHourView.setSelected(false); + mHourView.setActivated(false); mMinuteView.setText(minuteStr); - mMinuteView.setSelected(false); + mMinuteView.setActivated(false); if (!mIs24HourView) { updateAmPmLabelStates(values[2]); } |
