Android - Как отказаться от всех диалогов в onPause - PullRequest
37 голосов
/ 09 февраля 2012

У меня есть действие, которое может показывать разные диалоги во время выполнения. Я использую onCreateDialog (int id) для создания каждого диалога, и я использую методы showDialog (int id) и dismissDialog (int id) для показа и закрытия каждого диалога соответственно.

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

Ответы [ 4 ]

23 голосов
/ 20 мая 2015

Если вы используете DialogFragment и хотите удалить все, что можете использовать:

/**
 * Dismiss all DialogFragments added to given FragmentManager and child fragments
 */
public static void dismissAllDialogs(FragmentManager manager) {
    List<Fragment> fragments = manager.getFragments();

    if (fragments == null)
        return;

    for (Fragment fragment : fragments) {
        if (fragment instanceof DialogFragment) {
            DialogFragment dialogFragment = (DialogFragment) fragment;
            dialogFragment.dismissAllowingStateLoss();
        }

        FragmentManager childFragmentManager = fragment.getChildFragmentManager();
        if (childFragmentManager != null)
            dismissAllDialogs(childFragmentManager);
    }
}
14 голосов
/ 09 февраля 2012

В зависимости от того, сколько диалогов мы говорим.Короткий ответ - да, вам придется отклонить каждый диалог.

Могут быть элегантные способы сделать это, кроме простого объявления нескольких диалогов на уровне активности.Вы можете сохранить все диалоги в HashMap, как только они будут объявлены, а затем выполнить итерацию по списку и закрыть каждый onPause.

Поскольку вы не знаете, какие из них открыты, вам нужно пройти и протестировать или отследить состояния.

Однако, если у вас действительно так много диалогов на вашем экране, возможнонекоторые проблемы с вашим UI / UX дизайном, так как Android должен дать вам модель, которая облегчит его реализацию без того, что кажется плохим дизайном.

8 голосов
/ 19 октября 2012

С недавним акцентом Android на использовании DialogFragment контейнера вы не должны вызывать dismiss для каждого

Поскольку в диалогах будет контейнер Fragment, вы можете просто использовать их lifecycle . Рассмотрим этот DialogFragment:

public class FragDialog extends DialogFragment{

    public ProgressDialog _dialog;

    @Override
    public void onCreate(Bundle savedInstanceState) {

        super.onCreate(savedInstanceState);

        if (savedInstanceState != null) {
            //this.dismiss();     <-- The dialogs may be dismissed here
        }
    }

    @Override
    public Dialog onCreateDialog(final Bundle savedInstanceState) {

        _dialog = new ProgressDialog(getActivity());
        return _dialog;
    }

    @Override
    public void onPause() {
        super.onPause();
        // <--------- You may overload onPause
    }
}

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

FragmentManager fm = getSupportFragmentManager();
FragDialog fragDialog = new FragDialog();
fragDialog.show(fm, "my_tag");

Обратите внимание, что вы можете изменить действия DialogFragment в onPause. Когда ваша активность вызывает onPause, эта onPause также будет вызываться.

Закрытие диалога в onPause () с помощью this.dismiss () не будет работать, потому что после возобновления действия он также возобновит диалог. (Я думаю, это потому, что savestate сохраняется до onPause).

Но вы можете спокойно закрыть диалог (ы) в onCreate, если обнаружите saveInstanceState (резюме), как показано в коде.

0 голосов
/ 17 июня 2019

У меня есть другое решение, которое может быть хорошим. Вы только установили расширение Custom Dialog на этот SiblingDialog, который будет подписывать ваш Dialog на широковещательное событие закрытия диалогов. Таким образом, вы можете отправить событие трансляции в любое место, и все SiblingDialogs будут закрыты.

В этом примере метод диалога отмены и отклонения был переопределен, поэтому SiblingDialog сам закрывает каждого другого брата при закрытии.

public class SiblingDialog extends Dialog {

    protected LocalBroadcastManager mLocalBroadcastManager;

    protected BroadcastReceiver mBroadcastReceiver = new BroadcastReceiver() {
        @Override
        public void onReceive(Context context, Intent intent) {
            switch (intent.getAction()) {
                case "CLOSE_ALL_DIALOGS":
                    if (isShowing()) {
                        dismiss();
                    }
                    break;
                default:
                    break;
            }
        }
    };
    String[] ACTIONS_LIST = {"CLOSE_ALL_DIALOGS"};

    public SiblingDialog(Context context) {
        super(context);
    }

    public SiblingDialog(Context context, int themeResId) {
        super(context, themeResId);
    }


    public SiblingDialog(Context context, boolean cancelable, OnCancelListener cancelListener) {
        super(context, cancelable, cancelListener);
    }

    private void registerTheBroadCast() {
        mLocalBroadcastManager = LocalBroadcastManager.getInstance(getContext());
        IntentFilter mIntentFilter = new IntentFilter();
        for (String actions : ACTIONS_LIST) {
            mIntentFilter.addAction(actions);
        }
        mLocalBroadcastManager.registerReceiver(mBroadcastReceiver, mIntentFilter);
    }

    private void unregisterBroadCast() {
        mLocalBroadcastManager.unregisterReceiver(mBroadcastReceiver);
    }

    @Override
    public void show() {
        registerTheBroadCast();
        super.show();
    }

    @Override
    public void cancel() {
        unregisterBroadCast();
        mLocalBroadcastManager.sendBroadcast(newIntent("CLOSE_ALL_DIALOGS"));
        super.cancel();

    }

    @Override
    public void dismiss() {
        unregisterBroadCast();
        mLocalBroadcastManager.sendBroadcast(new Intent("CLOSE_ALL_DIALOGS"));
        super.dismiss();
    }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...