2929import android .content .res .ColorStateList ;
3030import android .content .res .TypedArray ;
3131import android .os .Bundle ;
32+ import androidx .core .view .ViewCompat ;
3233import androidx .fragment .app .DialogFragment ;
3334import androidx .appcompat .widget .TooltipCompat ;
3435import android .text .TextUtils ;
@@ -112,9 +113,11 @@ public final class MaterialTimePicker extends DialogFragment implements OnDouble
112113 static final String NEGATIVE_BUTTON_TEXT_EXTRA = "TIME_PICKER_NEGATIVE_BUTTON_TEXT" ;
113114 static final String OVERRIDE_THEME_RES_ID = "TIME_PICKER_OVERRIDE_THEME_RES_ID" ;
114115
116+ private ViewGroup root ;
115117 private MaterialButton modeButton ;
116118 private Button okButton ;
117119 private Button cancelButton ;
120+ private TextView headerTitle ;
118121
119122 @ InputMode private int inputMode = INPUT_MODE_CLOCK ;
120123
@@ -270,23 +273,16 @@ public final View onCreateView(
270273 @ NonNull LayoutInflater layoutInflater ,
271274 @ Nullable ViewGroup viewGroup ,
272275 @ Nullable Bundle bundle ) {
273- ViewGroup root =
274- (ViewGroup ) layoutInflater .inflate (R .layout .material_timepicker_dialog , viewGroup );
276+ root = (ViewGroup ) layoutInflater .inflate (R .layout .material_timepicker_dialog , viewGroup );
275277 timePickerView = root .findViewById (R .id .material_timepicker_view );
276278 timePickerView .setOnDoubleTapListener (this );
277279 textInputStub = root .findViewById (R .id .material_textinput_timepicker );
278280 modeButton = root .findViewById (R .id .material_timepicker_mode_button );
279281 okButton = root .findViewById (R .id .material_timepicker_ok_button );
280282 cancelButton = root .findViewById (R .id .material_timepicker_cancel_button );
281- TextView headerTitle = root .findViewById (R .id .header_title );
283+ headerTitle = root .findViewById (R .id .header_title );
282284
283- if (titleResId != 0 ) {
284- headerTitle .setText (titleResId );
285- } else if (!TextUtils .isEmpty (titleText )) {
286- headerTitle .setText (titleText );
287- }
288-
289- updateInputMode (modeButton );
285+ updateInputMode (inputMode , /* force= */ true );
290286 okButton .setOnClickListener (
291287 v -> {
292288 if (activePresenter instanceof TimePickerTextInputPresenter ) {
@@ -324,10 +320,7 @@ public final View onCreateView(
324320 updateCancelButtonVisibility ();
325321
326322 modeButton .setOnClickListener (
327- v -> {
328- inputMode = (inputMode == INPUT_MODE_CLOCK ) ? INPUT_MODE_KEYBOARD : INPUT_MODE_CLOCK ;
329- updateInputMode (modeButton );
330- });
323+ v -> updateInputMode (inputMode == INPUT_MODE_CLOCK ? INPUT_MODE_KEYBOARD : INPUT_MODE_CLOCK ));
331324
332325 return root ;
333326 }
@@ -386,13 +379,28 @@ public void setCancelable(boolean cancelable) {
386379 @ RestrictTo (LIBRARY_GROUP )
387380 @ Override
388381 public void onDoubleTap () {
389- inputMode = INPUT_MODE_KEYBOARD ;
390- updateInputMode (modeButton );
382+ updateInputMode (INPUT_MODE_KEYBOARD );
391383 timePickerTextInputPresenter .resetChecked ();
392384 }
393385
394- private void updateInputMode (MaterialButton modeButton ) {
395- if (modeButton == null || timePickerView == null || textInputStub == null ) {
386+ private void updateInputMode (@ InputMode int inputMode ) {
387+ updateInputMode (inputMode , /* force= */ false );
388+ }
389+
390+ private void updateInputMode (@ InputMode int inputMode , boolean force ) {
391+ if (!force && this .inputMode == inputMode ) {
392+ return ;
393+ }
394+
395+ this .inputMode = inputMode ;
396+
397+ updateActivePresenter (inputMode );
398+ updateModeButton (inputMode );
399+ updateHeader (inputMode );
400+ }
401+
402+ private void updateActivePresenter (@ InputMode int inputMode ) {
403+ if (timePickerView == null || textInputStub == null ) {
396404 return ;
397405 }
398406
@@ -404,16 +412,67 @@ private void updateInputMode(MaterialButton modeButton) {
404412 initializeOrRetrieveActivePresenterForMode (inputMode , timePickerView , textInputStub );
405413 activePresenter .show ();
406414 activePresenter .invalidate ();
407- ModeButtonData modeButtonData = getModeButtonData (inputMode );
408- modeButton .setIconResource (modeButtonData .iconResId );
409- modeButton .setContentDescription (
410- getResources ().getString (modeButtonData .contentDescriptionResId ));
411- TooltipCompat .setTooltipText (
412- modeButton , getResources ().getString (modeButtonData .tooltipTextResId ));
415+ }
416+
417+ private void updateModeButton (@ InputMode int inputMode ) {
418+ if (modeButton == null ) {
419+ return ;
420+ }
421+
422+ @ DrawableRes final int iconResId ;
423+ @ StringRes final int contentDescriptionResId ;
424+ @ StringRes final int tooltipTextResId ;
425+
426+ switch (inputMode ) {
427+ case INPUT_MODE_KEYBOARD :
428+ iconResId = clockIcon ;
429+ contentDescriptionResId = R .string .material_timepicker_clock_mode_description ;
430+ tooltipTextResId = R .string .material_timepicker_clock_mode_tooltip ;
431+ break ;
432+ case INPUT_MODE_CLOCK :
433+ iconResId = keyboardIcon ;
434+ contentDescriptionResId = R .string .material_timepicker_text_input_mode_description ;
435+ tooltipTextResId = R .string .material_timepicker_text_input_mode_tooltip ;
436+ break ;
437+ default :
438+ throw new IllegalArgumentException ("Unexpected input mode: " + inputMode );
439+ }
440+
441+ modeButton .setIconResource (iconResId );
442+ modeButton .setContentDescription (getString (contentDescriptionResId ));
443+ TooltipCompat .setTooltipText (modeButton , getString (tooltipTextResId ));
413444 modeButton .sendAccessibilityEvent (
414445 AccessibilityEventCompat .CONTENT_CHANGE_TYPE_CONTENT_DESCRIPTION );
415446 }
416447
448+ private void updateHeader (int inputMode ) {
449+ if (root == null || headerTitle == null ) {
450+ return ;
451+ }
452+
453+ final CharSequence title ;
454+
455+ if (titleResId != 0 ) {
456+ title = getString (titleResId );
457+ } else if (!TextUtils .isEmpty (titleText )) {
458+ title = titleText ;
459+ } else {
460+ switch (inputMode ) {
461+ case INPUT_MODE_KEYBOARD :
462+ title = getString (R .string .material_timepicker_enter_time );
463+ break ;
464+ case INPUT_MODE_CLOCK :
465+ title = getString (R .string .material_timepicker_select_time );
466+ break ;
467+ default :
468+ throw new IllegalArgumentException ("Unexpected input mode: " + inputMode );
469+ }
470+ }
471+
472+ headerTitle .setText (title );
473+ ViewCompat .setAccessibilityPaneTitle (root , title );
474+ }
475+
417476 private void updateCancelButtonVisibility () {
418477 if (cancelButton != null ) {
419478 cancelButton .setVisibility (isCancelable () ? View .VISIBLE : View .GONE );
@@ -442,23 +501,6 @@ private TimePickerPresenter initializeOrRetrieveActivePresenterForMode(
442501 return timePickerTextInputPresenter ;
443502 }
444503
445- private ModeButtonData getModeButtonData (@ InputMode int mode ) {
446- switch (mode ) {
447- case INPUT_MODE_KEYBOARD :
448- return new ModeButtonData (
449- clockIcon ,
450- R .string .material_timepicker_clock_mode_description ,
451- R .string .material_timepicker_clock_mode_tooltip );
452- case INPUT_MODE_CLOCK :
453- return new ModeButtonData (
454- keyboardIcon ,
455- R .string .material_timepicker_text_input_mode_description ,
456- R .string .material_timepicker_text_input_mode_tooltip );
457- default :
458- throw new IllegalArgumentException ("no button data for mode: " + mode );
459- }
460- }
461-
462504 @ Nullable
463505 TimePickerClockPresenter getTimePickerClockPresenter () {
464506 return timePickerClockPresenter ;
@@ -693,19 +735,4 @@ public MaterialTimePicker build() {
693735 return MaterialTimePicker .newInstance (this );
694736 }
695737 }
696-
697- private static final class ModeButtonData {
698- @ DrawableRes final int iconResId ;
699- @ StringRes final int contentDescriptionResId ;
700- @ StringRes final int tooltipTextResId ;
701-
702- ModeButtonData (
703- @ DrawableRes int iconResId ,
704- @ StringRes int contentDescriptionResId ,
705- @ StringRes int tooltipTextResId ) {
706- this .iconResId = iconResId ;
707- this .contentDescriptionResId = contentDescriptionResId ;
708- this .tooltipTextResId = tooltipTextResId ;
709- }
710- }
711738}
0 commit comments