Как изменить макет DialogFragment при повороте экрана в Android

У меня есть обычай DialogFragment, который содержит два DatePicker виджеты (от и до, используя layout/custom_date_picker).

Мне нужно изменить макет dialogFragment при повороте экрана на альбомную (используя layout-land/custom_date_picker).

Конфигурация Activity является:

<activity
        android:name=".activities.MainActivity"
        android:configChanges="orientation|keyboardHidden|screenSize"
        android:launchMode="singleTop"/>

Реализовано DialogFragment Источник:

public class DatePickerDialog extends DialogFragment
{

public static final String START_SEARCH_DATE = "startSearchDate";
public static final String END_SEARCH_DATE = "endSearchDate";
private CustomDatePicker dpStartDate;
private CustomDatePicker dpEndDate;
private AlertDialog d;

public interface DatePickerDialogListener
{
    void onFinishDatePickDialog(String fromDate, String toDate);
}

public DatePickerDialog()
{
}

// Use this instance of the interface to deliver action events
DatePickerDialogListener mListener;

// Override the Fragment.onAttach() method to instantiate the DatePickerDialogListener
@Override
public void onAttach(Activity activity)
{
    super.onAttach(activity);
    // Verify that the host activity implements the callback interface
    try
    {
        // Instantiate the NoticeDialogListener so we can send events to the host
        mListener = (DatePickerDialogListener) activity;
    } catch (ClassCastException e)
    {
        // The activity doesn't implement the interface, throw exception
        throw new ClassCastException(activity.toString() + " must implement DatePickerDialogListener");
    }
}

public static DatePickerDialog newInstance(String startSearchDate, String endSearchDate)
{
    DatePickerDialog frag = new DatePickerDialog();
    Bundle args = new Bundle();
    args.putString(START_SEARCH_DATE, startSearchDate);
    args.putString(END_SEARCH_DATE, endSearchDate);
    frag.setArguments(args);
    return frag;
}

@NonNull
@Override
public Dialog onCreateDialog(Bundle savedInstanceState)
{
    View customView = getActivity().getLayoutInflater().inflate(R.layout.custom_date_picker, null);
    // Define your date pickers
    dpStartDate = (CustomDatePicker) customView.findViewById(R.id.dpStartDate);
    dpEndDate = (CustomDatePicker) customView.findViewById(R.id.dpEndDate);

    String startSearchDate = getArguments().getString(START_SEARCH_DATE);
    String endSearchDate = getArguments().getString(END_SEARCH_DATE);

    dpStartDate.updateDate(startSearchDate);
    dpEndDate.updateDate(endSearchDate);

    d = new AlertDialog.Builder(getActivity())
            .setView(customView)
            .setTitle(getString(R.string.datepicker_hint))
            .setPositiveButton(getString(R.string.ok), new DialogInterface.OnClickListener()
            {
                @Override
                public void onClick(DialogInterface dialog, int which)
                {

                }
            }) //Set to null. We override the onclick
            .setNegativeButton(getString(R.string.cancel), null)
            .create();
    d.show();
    d.getButton(AlertDialog.BUTTON_POSITIVE).setOnClickListener(new View.OnClickListener()
    {
        @Override
        public void onClick(View v)
        {

            boolean b = DateUtils.largerThanEndDate(dpStartDate, dpEndDate);
            if (b)
            {
                ToastUtils.showShortText(getActivity(), getString(R.string.date_error));
            } else
            {
                mListener.onFinishDatePickDialog(dpStartDate.getDate(), dpEndDate.getDate());
                dismiss();
            }
        }
    });
    return d;
}
}

Кто-нибудь может подсказать, пожалуйста, как это можно сделать? Заранее спасибо.

Изменить: здесь код, с которым я призываю DialogFragment:

public void showDatePicker()
{
    startSearchDate = dateModel.getStartDate();
    endSearchDate = dateModel.getEndDate();
    datePickerDialog = (DatePickerDialog)fragmentManager.findFragmentByTag(DATE_PICKER_DIALOG);

    if (alertDialog == null)
    {
        alertDialog = DatePickerDialog.newInstance(startSearchDate, endSearchDate);
        alertDialog.show(fragmentManager, DATE_PICKER_DIALOG);
    }

}

1 ответ

Решение

Я полагаю, вы могли бы рассмотреть возможность использования if пункт в вашем onCreate() следующее:

int rotation = getWindowManager().getDefaultDisplay().getRotation();

а затем сделать

switch(rotation){
    case Surface.ROTATION_0: 
    case Surface.ROTATION_180:
        // show portrait

    case Surface.ROTATION_90: 
    case Surface.ROTATION_270:
        // show landscape
}

Для портретного режима покажите два диалоговых окна в стопке. А для ландшафтного режима покажите их рядом.

РЕДАКТИРОВАТЬ:

Ответ на вопрос:

  • Когда телефон поворачивается, Activity обязательно воссоздан. Это означает, что onCreate() будет вызван на ротацию. Следовательно, состояние вращения может быть определено в onCreate() как показано выше. В этом случае сделать rotation поле члена класса, чтобы к нему можно было обращаться по всему классу.
  • Действительно, как вы правильно заметили, диалог может быть показан с onConfigurationChanged() или в onCreate() сам. Для этого и для того, чтобы сохранить состояние экземпляра, пожалуйста, смотрите прикрепленные ссылки.

Рекомендации:

1. Как правильно сохранить DialogFragment через ротацию?,

2. Почему фрагмент не сохраняет состояние при повороте экрана?,

Другие вопросы по тегам