Подтвердить что ты не робот

Обратный вызов при отключении DialogFragment

Я хочу запустить диалог с настраиваемым макетом, который я реализовал через DialogFragment. (Я в основном просто изменил onCreateView() и добавил обработчики кнопок). Диалог позволяет пользователю быстро изменить важную настройку.

Этот диалог будет запущен из нескольких разных действий. Различные действия не имеют много общего, за исключением того, что они должны обновляться после того, как пользователь внесет изменения в настройку. Им не нужно получать какую-либо информацию из диалога; они просто должны знать, когда они закрыты (уволены).

Что я пробовал

Я попытался обновить активность в onResume(), но запуск и отклонение диалога никогда не вызывает этот метод. (Так что я не уверен, почему он даже существует, но это, вероятно, тема для другого вопроса.)

Далее я попытался добавить диалоговое окно DialogInterface.OnDismissListener:

public static void showMyDialog(OnDismissListener listener, Activity activity)
{
    DialogFragment fragment = new MyDialogFragment();
    fragment.show(activity.getFragmentManager(), "date");
    activity.getFragmentManager().executePendingTransactions();//A
    fragment.getDialog().setOnDismissListener(listener);//B
}

Когда я изначально отсутствовал в строке A, я получил исключение NullPointerException в строке B, потому что в этот момент диалоговое окно null. Следуя совету этого SO-ответа, я включил вызов executePendingTransaction(). Это приводит к исключению IllegalStateException в строке B, с сообщением "OnDismissListener уже занято диалоговым окном DialogFragment и не может быть заменено". Я также попытался поставить setOnDismissListener() перед вызовом show(), но это всегда вызывало исключение NullPointerException.

Затем я читаю этот другой ответ SO, в котором говорится, что первоначальный вопросник был "вызов getDialog() слишком рано в жизненном цикле DialogFragment". Поэтому я попытался добавить конструктор в свой диалог:

public MyDialogFragment(SomeCallback illTakeAnythingICanGet)
{
    //I'll store the callback here and call it later
}

К сожалению, добавление конструктора привело к тому, что Android Lint увлекся со смертельным исходом, и когда я его просмотрел, я нашел комментарий в этом вопросе, который, кажется, говорит этот подход сделает невозможным обращение к пользователю, поворачивающему экран во время открытия диалога.

Вопрос

Как можно определить активность, когда DialogFragment закрыт (был уволен) таким образом, чтобы не нарушать мое приложение, если пользователь поворачивает экран? Должен ли я использовать что-то еще, кроме DialogFragment?

4b9b3361

Ответ 1

Это просто более длинное объяснение комментария харизма в случае, если у кого-то еще была та же проблема, что и я.

Вы можете выполнить то, что я хотел, создав такой интерфейс:

public interface MyDialogCloseListener
{
    public void handleDialogClose(DialogInterface dialog);//or whatever args you want
}

В этом интерфейсе реализуется действие, запускающее ваш диалог (DialogFragment). Затем дайте этому DialogFragment следующий метод:

public void onDismiss(DialogInterface dialog)
{
    Activity activity = getActivity();
    if(activity instanceof MyDialogCloseListener)
        ((MyDialogCloseListener)activity).handleDialogClose(dialog);
}

Ответ 2

Более подробный код для того, чтобы кто-то сделал то же самое.

Создайте interface как:

package com.example.dialoglistener;
import android.content.DialogInterface;

public interface MyDialogCloseListener {
    public void handleDialogClose(DialogInterface dialog);
}

Внедрить интерфейс в действие как:

MyDialogCloseListener closeListener = new MyDialogCloseListener() {
        @Override
        public void handleDialogClose(DialogInterface dialog) {                                     
            //do here whatever you want to do on Dialog dismiss
        }
};

Напишите DismissListener в DialogFragement как

public void DismissListener(MyDialogCloseListener closeListener) {
        this.closeListener = closeListener;
}

вызовите DismissListener из вашей активности как:

dialogFragementObject.DismissListener(closeListener);

и, наконец, напишите onDismiss метод

@Override
    public void onDismiss(DialogInterface dialog) {
        super.onDismiss(dialog);
        if(closeListener != null) {
            closeListener.handleDialogClose(null);
        }

    }

Ответ 3

Пример Tyler был единственным примером, который я мог найти, что на самом деле работал. Единственное, что нужно изменить для примера, это вызов метода DismissListner в классе DialogFragment. У него это как:

dialogFragementObject.DismissListner(closeListener);

Это просто должно быть приведение к любому имени вашего класса, которое имеет DialogFragment. Например:

((MyDialogFragment)dialogFragementObject).DismissListner(closeListener);