I want to migrate from DatePickerDialog to MaterialDatePicker. I ran into a problem when calling getDialog from MaterialDatePicker with the dialog result always null.
Is this a bug, or is the feature not supported for MaterialDatePicker?
DatePickerDialog
private static class BirthDateUpdater extends DialogFragment implements DatePickerDialog.OnDateSetListener {
@Override
public Dialog onCreateDialog(Bundle savedInstanceState) {
// create calendar instance
final Calendar c = Calendar.getInstance();
// set calendar to birthdate
c.setTimeInMillis(getBirthDate().getTime());
int year = c.get(Calendar.YEAR);
int month = c.get(Calendar.MONTH);
int day = c.get(Calendar.DAY_OF_MONTH);
// Create a new instance of DatePickerDialog and return it
return new DatePickerDialog(getActivity(), this, year, month, day);
}
public void onDateSet(DatePicker view, int year, int month, int day) {
// process date selected in here
}
}
MaterialDatePicker problem in here - result of picker.getDialog() always null?
public static class BirthDateUpdater extends DialogFragment implements
MaterialPickerOnPositiveButtonClickListener<Long>,
DialogInterface.OnCancelListener {
private Dialog dialog;
public BirthDateUpdater() {
}
@NonNull
@Override
public Dialog onCreateDialog(Bundle savedInstanceState) {
try {
// builder
MaterialDatePicker.Builder<Long> builder = MaterialDatePicker.Builder.datePicker();
builder.setTitleText("Select Date");
// set date to BirthDate
builder.setSelection(getBirthDate().getTime());
// picker
MaterialDatePicker<Long> picker = builder.build();
// add event
picker.addOnPositiveButtonClickListener(this);
picker.addOnCancelListener(this);
// dialog
dialog = picker.getDialog(); // error in here (dialog is null)?
} catch (Exception ex) {
ex.printStackTrace();
}
return dialog;
}
@Override
public void onPositiveButtonClick(Long selection) {
try {
Calendar dateSelected = Calendar.getInstance();
dateSelected.setTimeInMillis(selection);
// process date selected in here
} catch (Exception ex) {
ex.printStackTrace();
}
}
@Override
public void onCancel(@NonNull DialogInterface dialog) {
dialog.dismiss();
}
}
MaterialDatePicker
is already DialogFragment. In your case picker.getDialog()
returns null because under the hood the DialogFragment write value to DialogFragment.mDialog(value of this filed returns picker.getDialog()
) filed from life-cycle callback onCreateDialog() which will be called async after invoke the the dialog's show method, i.e. when you call to picker.show(fragmentManager) then in picker's onCreateDialog you will can get not null value from getDialog()
method.
In your case you should not extend DialogFragment or MaterialDatePicker (it is final ) instead that you can just create method like birthDateUpdater
:
public DialogFragment birthDateUpdater() {
MaterialDatePicker.Builder<Long> builder = MaterialDatePicker.Builder.datePicker();
builder.setTitleText("Select Date");
// set date to BirthDate
builder.setSelection(getBirthDate().getTime());
// picker
MaterialDatePicker<Long> picker = builder.build();
// add event
picker.addOnPositiveButtonClickListener(selection -> {
try {
Calendar dateSelected = Calendar.getInstance();
dateSelected.setTimeInMillis(selection);
// process date selected in here
} catch (Exception ex) {
ex.printStackTrace();
}
});
picker.addOnCancelListener(dialog -> {
dialog.dismiss();
});
return picker
}
Or create class, factory, whatever which will be encapsulate this logic.