用户登录
用户注册

分享至

Android Dialog 封装及常用动画

  • 作者: 达?矢抾哆拉?
  • 来源: 51数据库
  • 2021-08-29

项目开发中我们经常用到 dialog 来弹窗,为了不重复写,封装一个简单的基类 dialog。

直接上代码:

?

/**
 * @desciption: Dialog 基类
 */
public class BaseDialog extends AppCompatDialog {

    private static BaseDialog mBaseDialog;
    private Builder mBuilder;

    private BaseDialog(Builder builder) {
        this(builder, R.style.BaseDialogStyle);
    }

    private BaseDialog(Builder builder, int theme) {
        super(builder.mContext, theme);
        mBuilder = builder;
    }

    /**
     * 取消Dialog
     */
    public void dismissDialog() {
        mBaseDialog.dismiss();
        mBaseDialog = null;
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(mBuilder.mView);
        setCanceledOnTouchOutside(mBuilder.cancelTouchout);
        Window window = getWindow();
        if (window != null) {
            WindowManager.LayoutParams params = window.getAttributes();
            if (mBuilder.width > 0) {
                params.width = mBuilder.width;
            }
            if (mBuilder.height > 0) {
                params.height = mBuilder.height;
            }
            params.gravity = mBuilder.gravity;
            window.setAttributes(params);
        }
    }

    @Override
    public void show() {
        if (!mBaseDialog.isShowing()) {
            super.show();
        }
    }

    public static final class Builder {
        private Context mContext;
        private boolean cancelTouchout = false;
        private int width, height;
        private int gravity;
        private View mView;
        private int resStyle = -1;

        public Builder(Context context) {
            mContext = context;
        }

        public Builder setView(int layoutId) {
            mView = LayoutInflater.from(mContext).inflate(layoutId, null);
            return this;
        }

        public Builder setView(View view) {
            mView = view;
            return this;
        }

        public Builder setGravity(int gravity) {
            this.gravity = gravity;
            return this;
        }

        public Builder setWidthdp(int val) {
            width = UiUtils.getInstance().dip2px(val);
            return this;
        }

        public Builder setHeightdp(int val) {
            height = UiUtils.getInstance().dip2px(val);
            return this;
        }

        public Builder setWidthDimenRes(int dimenRes) {
            width = UiUtils.getInstance().getDimens(dimenRes);
            return this;
        }

        public Builder setHeightDimenRes(int dimenRes) {
            height = UiUtils.getInstance().getDimens(dimenRes);
            return this;
        }

        public Builder setStyle(int resStyle) {
            this.resStyle = resStyle;
            return this;
        }

        public Builder setCancelTouchout(boolean val) {
            cancelTouchout = val;
            return this;
        }

        public Builder addViewOnClick(int viewRes, View.OnClickListener listener) {
            mView.findViewById(viewRes).setOnClickListener(listener);
            return this;
        }

        public <T extends View> T findViewById(int id) {
            return mView.findViewById(id);
        }

        /**
         * 防止Dialog show两次
         */
        public BaseDialog build() {
            if (mBaseDialog == null) {
                if (resStyle != -1) {
                    mBaseDialog = new BaseDialog(this, resStyle);
                } else {
                    mBaseDialog = new BaseDialog(this);
                }
            }
            return mBaseDialog;
        }
    }
}

工具类 UiUtils 常用工具类

使用方式:

?

/**
 * @desciption:
 */
public class DialogUtils {
    private static BaseDialog dialog;

    public static void showTipsSingleDialog(Context context, String content, final View.OnClickListener listener) {
        BaseDialog.Builder builder = new BaseDialog.Builder(context);
        dialog = builder
                .setView(R.layout.dialog_common_tips)
                .addViewOnClick(R.id.btn_positive, new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        dialog.dismissDialog();
                        listener.onClick(v);
                    }
                })
                .build();
        builder.findViewById(R.id.btn_negative).setVisibility(View.GONE);
        AppCompatTextView txtContent = builder.findViewById(R.id.txt_content);
        txtContent.setText(content);
        dialog.show();
    }

    public static void showTipsTwoDialog(Context context, String content, String negative, String positive, final View.OnClickListener listener) {
        BaseDialog.Builder builder = new BaseDialog.Builder(context);
        dialog = builder
                .setView(R.layout.dialog_common_tips)
                .addViewOnClick(R.id.btn_positive, new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        dialog.dismissDialog();
                        listener.onClick(v);
                    }
                })
                .addViewOnClick(R.id.btn_negative, new View.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        dialog.dismissDialog();

                    }
                })
                .build();
        AppCompatTextView txtContent = builder.findViewById(R.id.txt_content);
        AppCompatTextView btnNegative = builder.findViewById(R.id.btn_negative);
        AppCompatTextView btnPositive = builder.findViewById(R.id.btn_positive);
        txtContent.setText(content);
        btnNegative.setText(negative);
        btnPositive.setText(positive);
        dialog.show();
    }
}

下面是dialog 常用动画:

在styles.xml文件中写入如下style

?

<style name="BaseDialogStyle" parent="Theme.AppCompat.DayNight.Dialog.Alert">
        <!--无边框-->
        <item name="android:windowFrame">@null</item>
        <!--浮在Activity之上-->
        <item name="android:windowIsFloating">true</item>
        <!--半透明-->
        <item name="android:windowIsTranslucent">true</item>
        <!--背景透明-->
        <item name="android:windowBackground">@android:color/transparent</item>
        <!--遮盖层-->
        <item name="android:backgroundDimEnabled">true</item>
        <!--动画效果-->
        <item name="android:windowEnterAnimation">@anim/push_scale_in</item>
        <item name="android:windowExitAnimation">@anim/push_scale_out</item>
        <!-- Base.Theme.AppCompat.Light.Dialog.Alert 特有的属性,用于指定默认宽度,这里需要禁用 -->
        <item name="android:windowMinWidthMajor">0dp</item>
        <item name="android:windowMinWidthMinor">0dp</item>
        <!-- 解决 ActionBar 占位导致 Dialog 无法全屏显示的问题 -->
        <item name="windowActionBar">false</item>
        <!--无标题-->
        <item name="windowNoTitle">true</item>
        <!-- ActionMode覆盖Actionbar,不顶下来 -->
        <item name="windowActionModeOverlay">true</item>
        <item name="android:windowContentOverlay">@null</item>
    </style>
    <!-- 缩放动画 -->
    <style name="DialogScaleAnim" parent="android:Animation">
        <item name="android:windowEnterAnimation">@anim/push_scale_in</item>
        <item name="android:windowExitAnimation">@anim/push_scale_out</item>
    </style>

    <!-- ios 动画 -->
    <style name="DialogIOSAnim" parent="android:Animation">
        <item name="android:windowEnterAnimation">@anim/push_ios_in</item>
        <item name="android:windowExitAnimation">@anim/push_ios_out</item>
    </style>

    <!-- 顶部弹出动画 -->
    <style name="DialogTopAnim" parent="android:Animation">
        <item name="android:windowEnterAnimation">@anim/push_top_in</item>
        <item name="android:windowExitAnimation">@anim/push_top_out</item>
    </style>

    <!-- 底部弹出动画 -->
    <style name="DialogBottomAnim" parent="android:Animation">
        <item name="android:windowEnterAnimation">@anim/push_bottom_in</item>
        <item name="android:windowExitAnimation">@anim/push_bottom_out</item>
    </style>

    <!-- 左边弹出动画 -->
    <style name="DialogLeftAnim" parent="android:Animation">
        <item name="android:windowEnterAnimation">@anim/push_left_in</item>
        <item name="android:windowExitAnimation">@anim/push_left_out</item>
    </style>

    <!-- 右边弹出动画 -->
    <style name="DialogRightAnim" parent="android:Animation">
        <item name="android:windowEnterAnimation">@anim/push_right_in</item>
        <item name="android:windowExitAnimation">@anim/push_right_out</item>
    </style>

缩放动画

?

//push_scale_in.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">

    <scale
        android:duration="135"
        android:fromXScale="0.8"
        android:fromYScale="0.8"
        android:pivotX="50%"
        android:pivotY="50%"
        android:toXScale="1.05"
        android:toYScale="1.05"/>
    <scale
        android:duration="105"
        android:fromXScale="1.05"
        android:fromYScale="1.05"
        android:pivotX="50%"
        android:pivotY="50%"
        android:startOffset="135"
        android:toXScale="0.95"
        android:toYScale="0.95"/>
    <scale
        android:duration="60"
        android:fromXScale="0.95"
        android:fromYScale="0.95"
        android:pivotX="50%"
        android:pivotY="50%"
        android:startOffset="240"
        android:toXScale="1.0"
        android:toYScale="1.0"/>

    <alpha
        android:duration="90"
        android:fromAlpha="0.0"
        android:interpolator="@android:anim/accelerate_interpolator"
        android:toAlpha="1.0"/>
</set>

//push_scale_out.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
    <scale
        android:duration="150"
        android:fromXScale="1.0"
        android:fromYScale="1.0"
        android:pivotX="50%"
        android:pivotY="50%"
        android:toXScale="0.6"
        android:toYScale="0.6"/>

    <alpha
        android:duration="150"
        android:fromAlpha="1.0"
        android:interpolator="@android:anim/accelerate_interpolator"
        android:toAlpha="0.0"/>
</set>

ios 动画

?

//push_ios_in.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
    <scale
        android:duration="300"
        android:fromXScale="1.1"
        android:fromYScale="1.1"
        android:pivotX="50%"
        android:pivotY="50%"
        android:toXScale="1.0"
        android:toYScale="1.0"/>
    <alpha
        android:duration="300"
        android:fromAlpha="0.0"
        android:toAlpha="1.0"/>
</set>

//push_ios_out.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
    <scale
        android:duration="300"
        android:fromXScale="1.0"
        android:fromYScale="1.0"
        android:pivotX="50%"
        android:pivotY="50%"
        android:toXScale="1.1"
        android:toYScale="1.1"/>
    <alpha
        android:duration="300"
        android:fromAlpha="1.0"
        android:toAlpha="0.0"/>
</set>

顶部弹出动画

?

//push_top_in.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
    <translate
        android:duration="400"
        android:fromYDelta="-100%p"
        android:toYDelta="0"/>
</set>

//push_top_out.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
    <translate
        android:duration="400"
        android:fromYDelta="0"
        android:toYDelta="-100%p"/>
</set>

底部弹出动画

?

//push_bottom_in.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
    <translate
        android:duration="400"
        android:fromYDelta="100%p"
        android:toYDelta="0"/>
</set>

//push_bottom_out.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
    <translate
        android:duration="400"
        android:fromYDelta="0"
        android:toYDelta="100%p"/>
</set>

左边弹出动画

?

//push_left_in.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
    <!--100%p表示父层View的100%,是以它父层View为参照的。
    表示自身的100%,也就是从View自己的位置开始。-->
    <translate
        android:duration="@android:integer/config_mediumAnimTime"
        android:fromXDelta="-100%p"
        android:toXDelta="0%"/>
    <!-- 0.0表示完全不透明 1.0表示完全透明-->
    <alpha
        android:duration="@android:integer/config_mediumAnimTime"
        android:fromAlpha="0.0"
        android:toAlpha="1.0"/>
</set>

//push_left_out.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
    <!--100%p表示父层View的100%,是以它父层View为参照的。
    表示自身的100%,也就是从View自己的位置开始。-->
    <translate
        android:duration="@android:integer/config_mediumAnimTime"
        android:fromXDelta="0%p"
        android:toXDelta="-100%"/>
    <!-- 0.0表示完全不透明 1.0表示完全透明-->
    <alpha
        android:duration="@android:integer/config_mediumAnimTime"
        android:fromAlpha="1.0"
        android:toAlpha="0.0"/>
</set>

右边弹出动画

?

//push_right_in.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
    <!--100%p表示父层View的100%,是以它父层View为参照的。
    表示自身的100%,也就是从View自己的位置开始。-->
    <translate
        android:duration="@android:integer/config_mediumAnimTime"
        android:fromXDelta="100%p"
        android:toXDelta="0%"/>
    <!-- 0.0表示完全不透明 1.0表示完全透明-->
    <alpha
        android:duration="@android:integer/config_mediumAnimTime"
        android:fromAlpha="0.0"
        android:toAlpha="1.0"/>
</set>

//push_right_out.xml
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
    <!--100%p表示父层View的100%,是以它父层View为参照的。
    表示自身的100%,也就是从View自己的位置开始。-->
    <translate
        android:duration="@android:integer/config_mediumAnimTime"
        android:fromXDelta="0%p"
        android:toXDelta="100%"/>
    <!-- 0.0表示完全不透明 1.0表示完全透明-->
    <alpha
        android:duration="@android:integer/config_mediumAnimTime"
        android:fromAlpha="1.0"
        android:toAlpha="0.0"/>
</set>


?

软件
前端设计
程序设计
Java相关