package com.cooleshow.base.widgets; import android.app.Dialog; import android.content.res.Configuration; import android.os.Build; import android.os.Bundle; import android.view.Gravity; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.view.Window; import android.view.WindowManager; import androidx.annotation.LayoutRes; import androidx.annotation.NonNull; import androidx.annotation.Nullable; import androidx.annotation.StyleRes; import androidx.fragment.app.DialogFragment; import androidx.fragment.app.FragmentManager; import androidx.fragment.app.FragmentTransaction; import com.cooleshow.base.R; /** * Dialog通用样式 */ public abstract class BaseDialog extends DialogFragment { private static final String MARGIN = "margin"; private static final String WIDTH = "width"; private static final String HEIGHT = "height"; private static final String DIM = "dim_amount"; private static final String GRAVITY = "gravity"; private static final String CANCEL = "out_cancel"; private static final String THEME = "theme"; private static final String ANIM = "anim_style"; private static final String LAYOUT = "layout_id"; private int margin;//左右边距 private int width;//宽度 private int height;//高度 private float dimAmount = 0.5f;//灰度深浅 private int gravity = Gravity.CENTER;//显示的位置 private boolean outCancel = true;//是否点击外部取消 @StyleRes protected int theme = R.style.BaseDialog; // dialog主题 @StyleRes private int animStyle; @LayoutRes protected int layoutId; public abstract int intLayoutId(); public abstract void convertView(ViewHolder holder, BaseDialog dialog); public int initTheme() { return theme; } @Override public void onCreate(@Nullable Bundle savedInstanceState) { super.onCreate(savedInstanceState); setStyle(DialogFragment.STYLE_NO_TITLE, initTheme()); //恢复保存的数据 if (savedInstanceState != null) { margin = savedInstanceState.getInt(MARGIN); width = savedInstanceState.getInt(WIDTH); height = savedInstanceState.getInt(HEIGHT); dimAmount = savedInstanceState.getFloat(DIM); gravity = savedInstanceState.getInt(GRAVITY); outCancel = savedInstanceState.getBoolean(CANCEL); theme = savedInstanceState.getInt(THEME); animStyle = savedInstanceState.getInt(ANIM); layoutId = savedInstanceState.getInt(LAYOUT); } } private void hideNavigationBar(Window window) { int uiOptions = View.SYSTEM_UI_FLAG_HIDE_NAVIGATION | View.SYSTEM_UI_FLAG_LAYOUT_STABLE | View.SYSTEM_UI_FLAG_HIDE_NAVIGATION | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION | View.SYSTEM_UI_FLAG_IMMERSIVE | View.SYSTEM_UI_FLAG_FULLSCREEN; if (window == null) { return; } window.getDecorView().setSystemUiVisibility(uiOptions); } public void adjustFullScreen(Window window) { if (window == null) { return; } if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) { WindowManager.LayoutParams lp = window.getAttributes(); lp.layoutInDisplayCutoutMode = WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES; window.setAttributes(lp); final View decorView = window.getDecorView(); decorView.setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN | View.SYSTEM_UI_FLAG_LAYOUT_STABLE); } } @Nullable @Override public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) { layoutId = intLayoutId(); View view = inflater.inflate(layoutId, container, false); convertView(ViewHolder.create(view), this); return view; } @Override public void onStart() { super.onStart(); initParams(); } /** * 屏幕旋转等导致DialogFragment销毁后重建时保存数据 * * @param outState */ @Override public void onSaveInstanceState(Bundle outState) { super.onSaveInstanceState(outState); outState.putInt(MARGIN, margin); outState.putInt(WIDTH, width); outState.putInt(HEIGHT, height); outState.putFloat(DIM, dimAmount); outState.putInt(GRAVITY, gravity); outState.putBoolean(CANCEL, outCancel); outState.putInt(THEME, theme); outState.putInt(ANIM, animStyle); outState.putInt(LAYOUT, layoutId); } @Override public void onConfigurationChanged(@NonNull Configuration newConfig) { super.onConfigurationChanged(newConfig); initParams(); } @NonNull @Override public Dialog onCreateDialog(@Nullable Bundle savedInstanceState) { Dialog dialog = new Dialog(requireContext(), getTheme()); hideNavigationBar(dialog.getWindow()); adjustFullScreen(dialog.getWindow()); return dialog; } private void initParams() { Window window = getDialog().getWindow(); if (window != null) { WindowManager.LayoutParams lp = window.getAttributes(); //调节灰色背景透明度[0-1],默认0.5f lp.dimAmount = dimAmount; if (gravity != 0) { lp.gravity = gravity; } switch (gravity) { case Gravity.LEFT: case (Gravity.LEFT | Gravity.BOTTOM): case (Gravity.LEFT | Gravity.TOP): if (animStyle == 0) { animStyle = R.style.LeftAnimation; } break; case Gravity.TOP: if (animStyle == 0) { animStyle = R.style.TopAnimation2; } break; case Gravity.RIGHT: case (Gravity.RIGHT | Gravity.BOTTOM): case (Gravity.RIGHT | Gravity.TOP): if (animStyle == 0) { animStyle = R.style.RightAnimation; } break; case Gravity.BOTTOM: if (animStyle == 0) { animStyle = R.style.BottomAnimation; } break; default: break; } //设置dialog宽度 if (width == 0) { lp.width = DensityUtil.getScreenWidth(getContext()) - 2 * DensityUtil.dp2px(getContext(), margin); } else if (width == -1) { lp.width = WindowManager.LayoutParams.WRAP_CONTENT; } else { lp.width = DensityUtil.dp2px(getContext(), width); } //设置dialog高度 if (height == 0) { lp.height = WindowManager.LayoutParams.WRAP_CONTENT; }else if(height == -1){ lp.height = WindowManager.LayoutParams.MATCH_PARENT; } else { lp.height = DensityUtil.dp2px(getContext(), height); } //设置dialog进入、退出的动画 window.setWindowAnimations(animStyle); window.setAttributes(lp); } setCancelable(outCancel); } public BaseDialog setMargin(int margin) { this.margin = margin; return this; } public BaseDialog setWidth(int width) { this.width = width; return this; } public BaseDialog setHeight(int height) { this.height = height; return this; } public BaseDialog setDimAmount(float dimAmount) { this.dimAmount = dimAmount; return this; } public BaseDialog setGravity(int gravity) { this.gravity = gravity; return this; } public BaseDialog setOutCancel(boolean outCancel) { this.outCancel = outCancel; return this; } public BaseDialog setAnimStyle(@StyleRes int animStyle) { this.animStyle = animStyle; return this; } public BaseDialog show(FragmentManager manager) { FragmentTransaction ft = manager.beginTransaction(); if (this.isAdded()) { ft.remove(this).commit(); } ft.add(this, String.valueOf(System.currentTimeMillis())); ft.addToBackStack(null); // 为解决该问题 Can not perform this action after onSaveInstanceState ft.commitAllowingStateLoss(); return this; } }