blob: a24d37f4b097ce020d4bed89a893e3b8c9e4a3b3 [file] [log] [blame]
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001/*
2 * Copyright (C) 2007 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package android.widget;
18
Alan Viverette646a0f82015-03-18 13:24:07 -070019import android.annotation.NonNull;
Alan Viverette518ff0d2014-08-15 14:20:35 -070020import android.annotation.Nullable;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080021import android.annotation.Widget;
22import android.content.Context;
Svetoslav Ganovf5926962011-07-12 12:26:20 -070023import android.content.res.Configuration;
Svetoslav Ganov4243dc32011-01-18 19:39:57 -080024import android.content.res.TypedArray;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080025import android.os.Parcelable;
26import android.util.AttributeSet;
Svetoslav Ganov8a2a8952011-01-27 17:40:13 -080027import android.view.accessibility.AccessibilityEvent;
Svetoslav Ganova53efe92011-09-08 18:08:36 -070028import com.android.internal.R;
29
Svetoslav Ganovf5926962011-07-12 12:26:20 -070030import java.util.Locale;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080031
Alan Viveretteb3f24632015-10-22 16:01:48 -040032import libcore.icu.LocaleData;
33
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080034/**
Alan Viverette646a0f82015-03-18 13:24:07 -070035 * A widget for selecting the time of day, in either 24-hour or AM/PM mode.
Alan Viverette51344782014-07-16 17:39:27 -070036 * <p>
Alan Viverette646a0f82015-03-18 13:24:07 -070037 * For a dialog using this view, see {@link android.app.TimePickerDialog}. See
38 * the <a href="{@docRoot}guide/topics/ui/controls/pickers.html">Pickers</a>
39 * guide for more information.
40 *
41 * @attr ref android.R.styleable#TimePicker_timePickerMode
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080042 */
43@Widget
44public class TimePicker extends FrameLayout {
Chet Haase3053b2f2014-08-06 07:51:50 -070045 private static final int MODE_SPINNER = 1;
46 private static final int MODE_CLOCK = 2;
47
Alan Viverette51344782014-07-16 17:39:27 -070048 private final TimePickerDelegate mDelegate;
Fabrice Di Meglioeeff63a2013-08-05 12:07:24 -070049
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080050 /**
51 * The callback interface used to indicate the time has been adjusted.
52 */
53 public interface OnTimeChangedListener {
54
55 /**
56 * @param view The view associated with this listener.
57 * @param hourOfDay The current hour.
58 * @param minute The current minute.
59 */
60 void onTimeChanged(TimePicker view, int hourOfDay, int minute);
61 }
62
63 public TimePicker(Context context) {
64 this(context, null);
65 }
Svetoslav Ganov4243dc32011-01-18 19:39:57 -080066
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080067 public TimePicker(Context context, AttributeSet attrs) {
Svetoslav Ganov4243dc32011-01-18 19:39:57 -080068 this(context, attrs, R.attr.timePickerStyle);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080069 }
70
Alan Viverette617feb92013-09-09 18:09:13 -070071 public TimePicker(Context context, AttributeSet attrs, int defStyleAttr) {
72 this(context, attrs, defStyleAttr, 0);
73 }
74
75 public TimePicker(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
76 super(context, attrs, defStyleAttr, defStyleRes);
Fabrice Di Meglioeeff63a2013-08-05 12:07:24 -070077
Alan Viverette51344782014-07-16 17:39:27 -070078 final TypedArray a = context.obtainStyledAttributes(
79 attrs, R.styleable.TimePicker, defStyleAttr, defStyleRes);
Alan Viverette518ff0d2014-08-15 14:20:35 -070080 final int mode = a.getInt(R.styleable.TimePicker_timePickerMode, MODE_SPINNER);
Fabrice Di Megliodfaa6c72014-07-10 19:33:33 -070081 a.recycle();
82
Chet Haase3053b2f2014-08-06 07:51:50 -070083 switch (mode) {
84 case MODE_CLOCK:
Alan Viverettedaf33ed2014-10-23 13:34:17 -070085 mDelegate = new TimePickerClockDelegate(
Chet Haase3053b2f2014-08-06 07:51:50 -070086 this, context, attrs, defStyleAttr, defStyleRes);
87 break;
88 case MODE_SPINNER:
89 default:
Alan Viverettedaf33ed2014-10-23 13:34:17 -070090 mDelegate = new TimePickerSpinnerDelegate(
Chet Haase3053b2f2014-08-06 07:51:50 -070091 this, context, attrs, defStyleAttr, defStyleRes);
92 break;
Fabrice Di Megliodfaa6c72014-07-10 19:33:33 -070093 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080094 }
Svetoslav Ganov50f34d12010-12-03 16:05:40 -080095
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -070096 /**
Alan Viverette646a0f82015-03-18 13:24:07 -070097 * Sets the currently selected hour using 24-hour time.
98 *
99 * @param hour the hour to set, in the range (0-23)
100 * @see #getHour()
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700101 */
Alan Viverette646a0f82015-03-18 13:24:07 -0700102 public void setHour(int hour) {
Alan Viverette4420ae82015-11-16 16:10:56 -0500103 mDelegate.setHour(hour);
Fabrice Di Meglio64902bd2013-08-15 17:49:49 -0700104 }
105
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700106 /**
Alan Viverette646a0f82015-03-18 13:24:07 -0700107 * Returns the currently selected hour using 24-hour time.
108 *
109 * @return the currently selected hour, in the range (0-23)
110 * @see #setHour(int)
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700111 */
Alan Viverette646a0f82015-03-18 13:24:07 -0700112 public int getHour() {
Alan Viverette4420ae82015-11-16 16:10:56 -0500113 return mDelegate.getHour();
Alan Viverette646a0f82015-03-18 13:24:07 -0700114 }
115
116 /**
117 * Sets the currently selected minute..
118 *
119 * @param minute the minute to set, in the range (0-59)
120 * @see #getMinute()
121 */
122 public void setMinute(int minute) {
Alan Viverette4420ae82015-11-16 16:10:56 -0500123 mDelegate.setMinute(minute);
Alan Viverette646a0f82015-03-18 13:24:07 -0700124 }
125
126 /**
127 * Returns the currently selected minute.
128 *
129 * @return the currently selected minute, in the range (0-59)
130 * @see #setMinute(int)
131 */
132 public int getMinute() {
Alan Viverette4420ae82015-11-16 16:10:56 -0500133 return mDelegate.getMinute();
Alan Viverette646a0f82015-03-18 13:24:07 -0700134 }
135
136 /**
137 * Sets the current hour.
138 *
139 * @deprecated Use {@link #setHour(int)}
140 */
141 @Deprecated
142 public void setCurrentHour(@NonNull Integer currentHour) {
143 setHour(currentHour);
144 }
145
146 /**
147 * @return the current hour in the range (0-23)
148 * @deprecated Use {@link #getHour()}
149 */
150 @NonNull
151 @Deprecated
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700152 public Integer getCurrentHour() {
Alan Viverette4420ae82015-11-16 16:10:56 -0500153 return mDelegate.getHour();
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700154 }
Fabrice Di Meglio64902bd2013-08-15 17:49:49 -0700155
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700156 /**
157 * Set the current minute (0-59).
Alan Viverette646a0f82015-03-18 13:24:07 -0700158 *
159 * @deprecated Use {@link #setMinute(int)}
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700160 */
Alan Viverette646a0f82015-03-18 13:24:07 -0700161 @Deprecated
162 public void setCurrentMinute(@NonNull Integer currentMinute) {
Alan Viverette4420ae82015-11-16 16:10:56 -0500163 mDelegate.setMinute(currentMinute);
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700164 }
165
166 /**
Alan Viverette646a0f82015-03-18 13:24:07 -0700167 * @return the current minute
168 * @deprecated Use {@link #getMinute()}
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700169 */
Alan Viverette646a0f82015-03-18 13:24:07 -0700170 @NonNull
171 @Deprecated
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700172 public Integer getCurrentMinute() {
Alan Viverette4420ae82015-11-16 16:10:56 -0500173 return mDelegate.getMinute();
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700174 }
175
176 /**
Alan Viverette646a0f82015-03-18 13:24:07 -0700177 * Sets whether this widget displays time in 24-hour mode or 12-hour mode
178 * with an AM/PM picker.
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700179 *
Alan Viverette646a0f82015-03-18 13:24:07 -0700180 * @param is24HourView {@code true} to display in 24-hour mode,
181 * {@code false} for 12-hour mode with AM/PM
182 * @see #is24HourView()
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700183 */
Alan Viverette646a0f82015-03-18 13:24:07 -0700184 public void setIs24HourView(@NonNull Boolean is24HourView) {
185 if (is24HourView == null) {
186 return;
187 }
188
Alan Viverette4420ae82015-11-16 16:10:56 -0500189 mDelegate.setIs24Hour(is24HourView);
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700190 }
191
192 /**
Alan Viverette646a0f82015-03-18 13:24:07 -0700193 * @return {@code true} if this widget displays time in 24-hour mode,
194 * {@code false} otherwise}
195 * @see #setIs24HourView(Boolean)
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700196 */
197 public boolean is24HourView() {
Alan Viverette4420ae82015-11-16 16:10:56 -0500198 return mDelegate.is24Hour();
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700199 }
200
201 /**
202 * Set the callback that indicates the time has been adjusted by the user.
203 *
204 * @param onTimeChangedListener the callback, should not be null.
205 */
206 public void setOnTimeChangedListener(OnTimeChangedListener onTimeChangedListener) {
207 mDelegate.setOnTimeChangedListener(onTimeChangedListener);
Fabrice Di Meglio64902bd2013-08-15 17:49:49 -0700208 }
209
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800210 @Override
211 public void setEnabled(boolean enabled) {
212 super.setEnabled(enabled);
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700213 mDelegate.setEnabled(enabled);
Svetoslav Ganov51c52ed2010-12-28 13:45:03 -0800214 }
215
216 @Override
217 public boolean isEnabled() {
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700218 return mDelegate.isEnabled();
219 }
220
221 @Override
222 public int getBaseline() {
223 return mDelegate.getBaseline();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800224 }
225
Svetoslav Ganovf5926962011-07-12 12:26:20 -0700226 @Override
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700227 protected Parcelable onSaveInstanceState() {
228 Parcelable superState = super.onSaveInstanceState();
229 return mDelegate.onSaveInstanceState(superState);
230 }
231
232 @Override
233 protected void onRestoreInstanceState(Parcelable state) {
Fabrice Di Meglioeeff63a2013-08-05 12:07:24 -0700234 BaseSavedState ss = (BaseSavedState) state;
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700235 super.onRestoreInstanceState(ss.getSuperState());
236 mDelegate.onRestoreInstanceState(ss);
237 }
238
Dianne Hackborna7bb6fb2015-02-03 18:13:40 -0800239 @Override
240 public CharSequence getAccessibilityClassName() {
241 return TimePicker.class.getName();
242 }
243
Alan Viverettea54956a2015-01-07 16:05:02 -0800244 /** @hide */
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700245 @Override
Alan Viverettea54956a2015-01-07 16:05:02 -0800246 public boolean dispatchPopulateAccessibilityEventInternal(AccessibilityEvent event) {
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700247 return mDelegate.dispatchPopulateAccessibilityEvent(event);
248 }
249
Svetoslav Ganovf5926962011-07-12 12:26:20 -0700250 /**
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700251 * A delegate interface that defined the public API of the TimePicker. Allows different
252 * TimePicker implementations. This would need to be implemented by the TimePicker delegates
253 * for the real behavior.
Svetoslav Ganovf5926962011-07-12 12:26:20 -0700254 */
Fabrice Di Meglioeeff63a2013-08-05 12:07:24 -0700255 interface TimePickerDelegate {
Alan Viverette4420ae82015-11-16 16:10:56 -0500256 void setHour(int hour);
257 int getHour();
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700258
Alan Viverette4420ae82015-11-16 16:10:56 -0500259 void setMinute(int minute);
260 int getMinute();
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700261
Alan Viverette4420ae82015-11-16 16:10:56 -0500262 void setIs24Hour(boolean is24Hour);
263 boolean is24Hour();
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700264
265 void setOnTimeChangedListener(OnTimeChangedListener onTimeChangedListener);
266
267 void setEnabled(boolean enabled);
268 boolean isEnabled();
269
270 int getBaseline();
271
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700272 Parcelable onSaveInstanceState(Parcelable superState);
273 void onRestoreInstanceState(Parcelable state);
274
275 boolean dispatchPopulateAccessibilityEvent(AccessibilityEvent event);
276 void onPopulateAccessibilityEvent(AccessibilityEvent event);
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700277 }
278
Alan Viveretteb3f24632015-10-22 16:01:48 -0400279 static String[] getAmPmStrings(Context context) {
280 final Locale locale = context.getResources().getConfiguration().locale;
281 final LocaleData d = LocaleData.get(locale);
282
283 final String[] result = new String[2];
284 result[0] = d.amPm[0].length() > 4 ? d.narrowAm : d.amPm[0];
285 result[1] = d.amPm[1].length() > 4 ? d.narrowPm : d.amPm[1];
286 return result;
287 }
288
Fabrice Di Meglioeeff63a2013-08-05 12:07:24 -0700289 /**
290 * An abstract class which can be used as a start for TimePicker implementations
291 */
292 abstract static class AbstractTimePickerDelegate implements TimePickerDelegate {
Alan Viverette4420ae82015-11-16 16:10:56 -0500293 protected final TimePicker mDelegator;
294 protected final Context mContext;
295 protected final Locale mLocale;
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700296
Alan Viverette518ff0d2014-08-15 14:20:35 -0700297 protected OnTimeChangedListener mOnTimeChangedListener;
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700298
Alan Viverette4420ae82015-11-16 16:10:56 -0500299 public AbstractTimePickerDelegate(@NonNull TimePicker delegator, @NonNull Context context) {
Fabrice Di Meglio9e4009e2013-08-19 13:16:46 -0700300 mDelegator = delegator;
Fabrice Di Meglioeeff63a2013-08-05 12:07:24 -0700301 mContext = context;
Alan Viverette4420ae82015-11-16 16:10:56 -0500302 mLocale = context.getResources().getConfiguration().locale;
Alan Viverette518ff0d2014-08-15 14:20:35 -0700303 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800304 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800305}