从库中添加 Material 对话框

Add Material Dialog from library

我想使用 material-dialog 库中的 this,而不使用我的 build.gradle 文件中的库。

有办法吗?

感谢 Abderrahim Soubai Elidrissi 删除了我使用 LovelyDialog 并在我的项目中实现了以下 类 的答案:

AbsLovelyDialog.java

@SuppressWarnings({"unchecked", "WeakerAccess"})
public abstract class AbsLovelyDialog<T extends AbsLovelyDialog> {

    private static final String KEY_SAVED_STATE_TOKEN = "key_saved_state_token";

    private Dialog dialog;
    private View dialogView;

    private ImageView iconView;
    private TextView topTitleView;
    private TextView titleView;
    private TextView messageView;

    public AbsLovelyDialog(Context context) {
        init(new AlertDialog.Builder(context));
    }

    public AbsLovelyDialog(Context context, int theme) {
        init(new AlertDialog.Builder(context, theme));
    }

    private void init(AlertDialog.Builder dialogBuilder) {
        dialogView = LayoutInflater.from(dialogBuilder.getContext()).inflate(getLayout(), null);
        dialog = dialogBuilder.setView(dialogView).create();

        iconView = findView(R.id.ld_icon);
        titleView = findView(R.id.ld_title);
        messageView = findView(R.id.ld_message);
        topTitleView = findView(R.id.ld_top_title);
    }

    @LayoutRes
    protected abstract int getLayout();

    public T setMessage(@StringRes int message) {
        return setMessage(string(message));
    }

    public T setMessage(CharSequence message) {
        messageView.setVisibility(View.VISIBLE);
        messageView.setText(message);
        return (T) this;
    }

    public T setTitle(@StringRes int title) {
        return setTitle(string(title));
    }

    public T setTopTitle(@StringRes int title) {
        return setTopTitle(string(title));
    }

    public T setTitle(CharSequence title) {
        titleView.setVisibility(View.VISIBLE);
        titleView.setText(title);
        return (T) this;
    }

    public T setTopTitle(CharSequence title) {
        topTitleView.setVisibility(View.VISIBLE);
        topTitleView.setText(title);
        return (T) this;
    }

    public T setTopTitleColor(int color) {
        topTitleView.setTextColor(color);
        return (T) this;
    }

    public T setIcon(Bitmap bitmap) {
        iconView.setVisibility(View.VISIBLE);
        iconView.setImageBitmap(bitmap);
        return (T) this;
    }

    public T setIcon(Drawable drawable) {
        iconView.setVisibility(View.VISIBLE);
        iconView.setImageDrawable(drawable);
        return (T) this;
    }

    public T setIcon(@DrawableRes int iconRes) {
        iconView.setVisibility(View.VISIBLE);
        iconView.setImageResource(iconRes);
        return (T) this;
    }

    public T setIconTintColor(int iconTintColor) {
        iconView.setColorFilter(iconTintColor);
        return (T) this;
    }

    public T setTitleGravity(int gravity) {
        titleView.setGravity(gravity);
        return (T) this;
    }

    public T setMessageGravity(int gravity) {
        messageView.setGravity(gravity);
        return (T) this;
    }

    public T setTopColor(@ColorInt int topColor) {
        findView(R.id.ld_color_area).setBackgroundColor(topColor);
        return (T) this;
    }

    public T setTopColorRes(@ColorRes int topColoRes) {
        return setTopColor(color(topColoRes));
    }

    /*
     * You should call method saveInstanceState on handler object and then use saved info to restore
     * your dialog in onRestoreInstanceState. Static methods wasDialogOnScreen and getDialogId will
     * help you in this.
     */
    public T setInstanceStateHandler(int id, LovelySaveStateHandler handler) {
        handler.handleDialogStateSave(id, this);
        return (T) this;
    }

    public T setCancelable(boolean cancelable) {
        dialog.setCancelable(cancelable);
        return (T) this;
    }

    public T setSavedInstanceState(Bundle savedInstanceState) {
        if (savedInstanceState != null) {
            boolean hasSavedStateHere =
                    savedInstanceState.keySet().contains(KEY_SAVED_STATE_TOKEN) &&
                            savedInstanceState.getSerializable(KEY_SAVED_STATE_TOKEN) == getClass();
            if (hasSavedStateHere) {
                restoreState(savedInstanceState);
            }
        }
        return (T) this;
    }

    public Dialog show() {
        dialog.show();
        return dialog;
    }

    public Dialog create() {
        return dialog;
    }

    public void dismiss() {
        dialog.dismiss();
    }

    void onSaveInstanceState(Bundle outState) {
        outState.putSerializable(KEY_SAVED_STATE_TOKEN, getClass());
    }

    void restoreState(Bundle savedState) {
    }

    boolean isShowing() {
        return dialog != null && dialog.isShowing();
    }

    protected String string(@StringRes int res) {
        return dialogView.getContext().getString(res);
    }

    protected int color(@ColorRes int colorRes) {
        return ContextCompat.getColor(getContext(), colorRes);
    }

    protected Context getContext() {
        return dialogView.getContext();
    }

    protected <ViewClass extends View> ViewClass findView(int id) {
        return (ViewClass) dialogView.findViewById(id);
    }

    protected class ClickListenerDecorator implements View.OnClickListener {

        private View.OnClickListener clickListener;
        private boolean closeOnClick;

        protected ClickListenerDecorator(View.OnClickListener clickListener, boolean closeOnClick) {
            this.clickListener = clickListener;
            this.closeOnClick = closeOnClick;
        }

        @Override
        public void onClick(View v) {
            if (clickListener != null) {
                if (clickListener instanceof LovelyDialogCompat.DialogOnClickListenerAdapter) {
                    LovelyDialogCompat.DialogOnClickListenerAdapter listener =
                            (LovelyDialogCompat.DialogOnClickListenerAdapter) clickListener;
                    listener.onClick(dialog, v.getId());
                } else {
                    clickListener.onClick(v);
                }
            }
            if (closeOnClick) {
                dismiss();
            }
        }
    }
}

LovelyChoiceDialog.java

public class LovelyChoiceDialog extends AbsLovelyDialog<LovelyChoiceDialog> {

    private static final String KEY_ITEM_CHECKED_STATES = "key_item_checked_states";

    private ListView choicesList;
    private TextView confirmButton;

    {
        choicesList = findView(R.id.ld_choices);
    }

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

    public LovelyChoiceDialog(Context context, int theme) {
        super(context, theme);
    }

    public <T> LovelyChoiceDialog setItems(T[] items, OnItemSelectedListener<T> itemSelectedListener) {
        return setItems(Arrays.asList(items), itemSelectedListener);
    }

    public <T> LovelyChoiceDialog setItems(List<T> items, OnItemSelectedListener<T> itemSelectedListener) {
        ArrayAdapter<T> adapter = new ArrayAdapter<>(getContext(),
                R.layout.dialog_item_simple_text, android.R.id.text1,
                items);
        return setItems(adapter, itemSelectedListener);
    }

    public <T> LovelyChoiceDialog setItems(ArrayAdapter<T> adapter, OnItemSelectedListener<T> itemSelectedListener) {
        choicesList.setOnItemClickListener(new ItemSelectedAdapter<>(itemSelectedListener));
        choicesList.setAdapter(adapter);
        return this;
    }

    public <T> LovelyChoiceDialog setItemsMultiChoice(T[] items, OnItemsSelectedListener<T> itemsSelectedListener) {
        return setItemsMultiChoice(items, null, itemsSelectedListener);
    }

    public <T> LovelyChoiceDialog setItemsMultiChoice(T[] items, boolean[] selectionState, OnItemsSelectedListener<T> itemsSelectedListener) {
        return setItemsMultiChoice(Arrays.asList(items), selectionState, itemsSelectedListener);
    }

    public <T> LovelyChoiceDialog setItemsMultiChoice(List<T> items, OnItemsSelectedListener<T> itemsSelectedListener) {
        return setItemsMultiChoice(items, null, itemsSelectedListener);
    }

    public <T> LovelyChoiceDialog setItemsMultiChoice(List<T> items, boolean[] selectionState, OnItemsSelectedListener<T> itemsSelectedListener) {
        ArrayAdapter<T> adapter = new ArrayAdapter<>(getContext(),
                R.layout.dialog_item_simple_text_multichoice, android.R.id.text1,
                items);
        return setItemsMultiChoice(adapter, selectionState, itemsSelectedListener);
    }

    public <T> LovelyChoiceDialog setItemsMultiChoice(ArrayAdapter<T> adapter, OnItemsSelectedListener<T> itemsSelectedListener) {
        return setItemsMultiChoice(adapter, null, itemsSelectedListener);
    }

    public <T> LovelyChoiceDialog setItemsMultiChoice(ArrayAdapter<T> adapter, boolean[] selectionState, OnItemsSelectedListener<T> itemsSelectedListener) {
        LayoutInflater inflater = LayoutInflater.from(getContext());
        View confirmBtnContainer = inflater.inflate(R.layout.dialog_item_footer_confirm, null);
        confirmButton = (TextView) confirmBtnContainer.findViewById(R.id.ld_btn_confirm);
        confirmButton.setOnClickListener(new ItemsSelectedAdapter<>(itemsSelectedListener));
        choicesList.addFooterView(confirmBtnContainer);

        ListView choicesList = findView(R.id.ld_choices);
        choicesList.setChoiceMode(AbsListView.CHOICE_MODE_MULTIPLE);
        choicesList.setAdapter(adapter);

        if (selectionState != null) {
            for (int i = 0; i < selectionState.length; i++) {
                choicesList.setItemChecked(i, selectionState[i]);
            }
        }

        return this;
    }

    public LovelyChoiceDialog setConfirmButtonText(@StringRes int text) {
        return setConfirmButtonText(string(text));
    }

    public LovelyChoiceDialog setConfirmButtonText(String text) {
        if (confirmButton == null) {
            throw new IllegalStateException(string(R.string.ex_msg_dialog_choice_confirm));
        }
        confirmButton.setText(text);
        return this;
    }

    public LovelyChoiceDialog setConfirmButtonColor(int color) {
        if (confirmButton == null) {
            throw new IllegalStateException(string(R.string.ex_msg_dialog_choice_confirm));
        }
        confirmButton.setTextColor(color);
        return this;
    }

    @Override
    void onSaveInstanceState(Bundle outState) {
        super.onSaveInstanceState(outState);
        if (isMultiChoiceList()) {
            ListAdapter adapter = choicesList.getAdapter();
            boolean[] checkedStates = new boolean[adapter.getCount()];
            SparseBooleanArray checkedPositions = choicesList.getCheckedItemPositions();
            for (int i = 0; i < checkedPositions.size(); i++) {
                if (checkedPositions.valueAt(i)) {
                    checkedStates[checkedPositions.keyAt(i)] = true;
                }
            }
            outState.putBooleanArray(KEY_ITEM_CHECKED_STATES, checkedStates);
        }
    }

    @Override
    void restoreState(Bundle savedState) {
        super.restoreState(savedState);
        if (isMultiChoiceList()) {
            boolean[] checkedStates = savedState.getBooleanArray(KEY_ITEM_CHECKED_STATES);
            if (checkedStates == null) {
                return;
            }
            for (int index = 0; index < checkedStates.length; index++) {
                choicesList.setItemChecked(index, checkedStates[index]);
            }
        }
    }

    @Override
    protected int getLayout() {
        return R.layout.dialog_choice;
    }

    private boolean isMultiChoiceList() {
        return choicesList.getChoiceMode() == AbsListView.CHOICE_MODE_MULTIPLE;
    }

    public interface OnItemSelectedListener<T> {
        void onItemSelected(int position, T item);
    }

    public interface OnItemsSelectedListener<T> {
        void onItemsSelected(List<Integer> positions, List<T> items);
    }

    private class ItemSelectedAdapter<T> implements AdapterView.OnItemClickListener {

        private OnItemSelectedListener<T> adaptee;

        private ItemSelectedAdapter(OnItemSelectedListener<T> adaptee) {
            this.adaptee = adaptee;
        }

        @Override
        @SuppressWarnings("unchecked")
        public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
            if (adaptee != null) {
                adaptee.onItemSelected(position, (T) parent.getItemAtPosition(position));
            }
            dismiss();
        }
    }

    private class ItemsSelectedAdapter<T> implements View.OnClickListener {

        private OnItemsSelectedListener<T> adaptee;

        private ItemsSelectedAdapter(OnItemsSelectedListener<T> adaptee) {
            this.adaptee = adaptee;
        }

        @Override
        @SuppressWarnings("unchecked")
        public void onClick(View v) {
            if (adaptee != null) {
                SparseBooleanArray checkedItemPositions = choicesList.getCheckedItemPositions();
                List<T> selectedItems = new ArrayList<>(checkedItemPositions.size());
                List<Integer> selectedPositions = new ArrayList<>(checkedItemPositions.size());
                ListAdapter adapter = choicesList.getAdapter();
                for (int index = 0; index < adapter.getCount(); index++) {
                    if (checkedItemPositions.get(index)) {
                        selectedPositions.add(index);
                        selectedItems.add((T) adapter.getItem(index));
                    }
                }
                adaptee.onItemsSelected(selectedPositions, selectedItems);
            }
            dismiss();
        }
    }
}

LovelyDialogCompat.java

public class LovelyDialogCompat {

    /**
     * If you don't want to change implemented interfaces when migrating from standard dialogs
     * to LovelyDialogs - use this method.
     */
    public static View.OnClickListener wrap(Dialog.OnClickListener listener) {
        return new DialogOnClickListenerAdapter(listener);
    }

    static class DialogOnClickListenerAdapter implements View.OnClickListener {

        private Dialog.OnClickListener adapted;

        DialogOnClickListenerAdapter(DialogInterface.OnClickListener adapted) {
            this.adapted = adapted;
        }

        public void onClick(DialogInterface dialogInterface, int which) {
            if (adapted != null) {
                adapted.onClick(dialogInterface, which);
            }
        }

        @Override
        public void onClick(View v) {

        }
    }
}

LovelySaveStateHandler.java

public class LovelySaveStateHandler {

    private static final String KEY_DIALOG_ID = "id";

    private SparseArray<WeakReference<AbsLovelyDialog<?>>> handledDialogs;

    public LovelySaveStateHandler() {
        handledDialogs = new SparseArray<>();
    }

    public static boolean wasDialogOnScreen(Bundle savedInstanceState) {
        return savedInstanceState.keySet().contains(KEY_DIALOG_ID);
    }

    public static int getSavedDialogId(Bundle savedInstanceState) {
        return savedInstanceState.getInt(KEY_DIALOG_ID, -1);
    }

    public void saveInstanceState(Bundle outState) {
        for (int index = handledDialogs.size() - 1; index >= 0; index--) {
            WeakReference<AbsLovelyDialog<?>> dialogRef = handledDialogs.valueAt(index);
            if (dialogRef.get() == null) {
                handledDialogs.remove(index);
                continue;
            }
            AbsLovelyDialog<?> dialog = dialogRef.get();
            if (dialog.isShowing()) {
                dialog.onSaveInstanceState(outState);
                outState.putInt(KEY_DIALOG_ID, handledDialogs.keyAt(index));
                return;
            }
        }
    }

    void handleDialogStateSave(int id, AbsLovelyDialog<?> dialog) {
        handledDialogs.put(id, new WeakReference<AbsLovelyDialog<?>>(dialog));
    }
}