DialogFragment 其實就是繼承fragment,用Fragment的事物進行管理
首先在onCreate中指定DialogFragment 所對應的樣式
setStyle(DialogFragment.STYLE_NO_FRAME, R.style.DialogStyle);
<style name="DialogStyle" parent="@android:style/Theme.Dialog">
<item name="android:windowFrame">@null</item>
<item name="android:windowIsFloating">true</item>
<item name="android:windowIsTranslucent">true</item>
<item name="android:windowNoTitle">true</item>
<item name="android:windowBackground">@color/white</item>
</style>
然後在onCreateView 中返回的是我們將要展示的佈局
rootView = View.inflate(getContext(), R.layout.dialog_fragment,null);
final ViewTreeObserver viewTreeObserver = rootView.getViewTreeObserver();
boolean alive = viewTreeObserver.isAlive();
// 當一個視圖樹將要繪製時,所要調用的回調函數的接口類
// 增加監聽是爲了,加入DialogFragment的出場動畫
viewTreeObserver.addOnPreDrawListener(new ViewTreeObserver.OnPreDrawListener() {
@Override
public boolean onPreDraw() {
// this 就表示的這個接口的匿名實現類
rootView.getViewTreeObserver().removeOnPreDrawListener(this);
System.out.println("MyDialogFragment onPreDraw 33333333333");
if (circleAnimal != null){
circleAnimal.show(rootView);
}
return true;
}
});
在onstart方法中設置DialogFragment的寬高,然後設置初始化動畫對象
@Override
public void onStart() {
super.onStart();
System.out.println("MyDialogFragment onStart 44444444444444");
ViewGroup.LayoutParams params = getDialog().getWindow().getAttributes();
params.width = WindowManager.LayoutParams.MATCH_PARENT;
params.height = WindowManager.LayoutParams.MATCH_PARENT;
getDialog().getWindow().setAttributes((WindowManager.LayoutParams) params);
//取消過渡動畫 , 使DialogSearch的出現更加平滑
// getDialog().getWindow().setWindowAnimations(R.style.DialogEmptyAnimation);
// 初始化動畫對象,並且設置回調監聽
circleAnimal = new CircleAnimal();
circleAnimal.setAnimListener(this);
}
動畫類
public class CircleAnimal {
//duration 運行時間
private static final long DURATION = 200;
//動畫監聽
private AnimListener mListener = null;
private Animator anim;
public interface AnimListener {
//退出動畫完成
void onHideAnimationEnd();
//出場動畫完成
void onShowAnimationEnd();
}
private void actionOtherVisible(boolean isShow,final View animView){
int[] location = new int[2];
// 獲取view在當前窗口內的絕對座標
animView.getLocationInWindow(location);
System.out.println("location :" + location[0]);// X 0
System.out.println("location :" + location[1]);// y 0
//計算中心位置
int avX = location[0] + animView.getWidth() / 2;
int avY = location[1] + animView.getHeight() / 2;
System.out.println("location avX" + avX +" avY " +avY);
//這個是獲取view在當前屏幕的高度,包含通知欄的高度也就是狀態欄的高度
// int[] locaton2 = new int[2];
// animView.getLocationOnScreen(locaton2);
// System.out.println("locaton2 :" + locaton2[0]);// x 0
// System.out.println("locaton2 :" + locaton2[1]);// y 90
float startRadius;
float endRadius;
// Math.sqrt 這個函數是用來計算平方根的
float maxRadius = (float) Math.sqrt((double) (avX * avX + avY * avY));
System.out.println("maxRadius :" + maxRadius);
if (isShow) {
startRadius = 0f;
endRadius = maxRadius;
} else {
startRadius = maxRadius;
endRadius = 0f;
}
// 快速實現圓形動畫縮放的api,5.0之後才引入 Reveal 顯示,展示的意思
anim = ViewAnimationUtils.createCircularReveal(animView,0,0,startRadius, 2160f);
animView.setVisibility(View.VISIBLE);
anim.setDuration(500);
anim.setInterpolator(new DecelerateInterpolator());
anim.start();
anim.addListener(new AnimatorListenerAdapter() {
@Override
public void onAnimationEnd(Animator animation) {
// animView.setVisibility(View.VISIBLE);
}
});
}
public void show(View rootView){
actionOtherVisible(true,rootView);
}
public void hide(View rootView) {
actionOtherVisible(false,rootView);
}
// 設置對動畫的監聽
public void setAnimListener(AnimListener listener) {
mListener = listener;
}
}
下面這個是玩Android 的動畫類
public class CircularRevealAnim {
//duration 運行時間
private static final long DURATION = 200;
//動畫監聽
private AnimListener mListener = null;
private Animator anim;
public interface AnimListener {
void onHideAnimationEnd();
//動畫展示完成
void onShowAnimationEnd();
}
@SuppressLint("NewApi")
private void actionOtherVisible(Boolean isShow, View triggerView, View animView) {
// triggerView 是所要獲取焦點的EditTextView
// Lollipop是21
if (android.os.Build.VERSION.SDK_INT < android.os.Build.VERSION_CODES.LOLLIPOP) {
if (isShow) {
// animView 是整個rootView,
animView.setVisibility(View.VISIBLE);
if (mListener != null) {
anim.cancel();
anim = null;
mListener.onShowAnimationEnd();
}
} else {
animView.setVisibility(View.GONE);
if (mListener != null) {
anim.cancel();
anim = null;
mListener.onHideAnimationEnd();
}
}
return;
}
/**
* 計算 triggerView 的中心位置
*/
int[] tvLocation = {0, 0};
triggerView.getLocationInWindow(tvLocation);
//156--------12
System.out.println("tvLocation :" + tvLocation[0] +"--------" +tvLocation[1]);
// 屏幕寬度的的0.8 倍
int tvX = (int) (tvLocation[0] + animView.getWidth() * 0.8);
// edittext 高度的一般
int tvY = tvLocation[1] + triggerView.getHeight() / 2;
// 1002-----tvY84
System.out.println("tvX :" + tvX +"-----tvY" +tvY);
/**
* 計算 animView 的中心位置
*/
int[] avLocation = {0, 0};
animView.getLocationInWindow(avLocation);
// 0--------0
System.out.println("avLocation :" + avLocation[0] +"--------" +avLocation[1]);
int avX = avLocation[0] + animView.getWidth() / 2;
int avY = avLocation[1] + animView.getHeight() / 2;
// : avX :529 avY :987
System.out.println("avX :"+ avX + " avY :"+ avY);
int rippleW;
if (tvX < avX) { //1002 < 529
rippleW = animView.getWidth() - tvX;
} else {
// 1002 - 0
rippleW = tvX - avLocation[0];
}
// 84
int rippleH;
if (tvY < avY) {//84 < 987
rippleH = animView.getHeight() - tvY;
} else {
rippleH = tvY - avLocation[1];//84 -
}
// Math.sqrt(9) 返回一個正值的平方根 爲3 1002*1002 +
float maxRadius = (float) Math.sqrt((double) (rippleW * rippleW + rippleH * rippleH));
float startRadius;
float endRadius;
if (isShow) {
startRadius = 0f;
endRadius = maxRadius;
} else {
startRadius = maxRadius;
endRadius = 0f;
}
// tvX :1002 ;tvY :84 endRadius :2139.183
System.out.println("tvX :" + tvX +" ;tvY :" +tvY + " endRadius :" + endRadius);
anim = ViewAnimationUtils.createCircularReveal(animView, tvX, tvY, startRadius, endRadius);
animView.setVisibility(View.VISIBLE);
anim.setDuration(DURATION);
anim.setInterpolator(new DecelerateInterpolator());
anim.addListener(new Animator.AnimatorListener() {
@Override
public void onAnimationStart(Animator animation) {
}
@Override
public void onAnimationEnd(Animator animation) {
if (isShow) {
animView.setVisibility(View.VISIBLE);
if (mListener != null) {
mListener.onShowAnimationEnd();
}
} else {
animView.setVisibility(View.GONE);
if (mListener != null) {
mListener.onHideAnimationEnd();
}
}
}
@Override
public void onAnimationCancel(Animator animation) {
}
@Override
public void onAnimationRepeat(Animator animation) {
}
});
anim.start();
}
public void show(View triggerView, View showView) {
actionOtherVisible(true, triggerView, showView);
}
public void hide(View triggerView, View hideView) {
actionOtherVisible(false, triggerView, hideView);
}
public void setAnimListener(AnimListener listener) {
mListener = listener;
}
}