1. 程式人生 > >android 自定義dialog的實現方法

android 自定義dialog的實現方法

listener params .get animator miss nim style wrap 參數

最近一直在做 java 相關的東西, 雖然一直在看 Android 但感覺有點留於理論,總這樣畢竟不行,寫的多不一定懂得多,但要想懂得多就一
定要寫的多,於是今天動手寫了一下 Dialog 有關的東西,算是對 Dialog 的一個整理吧。

AlertDialog 的使用就不說了,隨便百度一下就能找到,這裏要說的,主要就是自定義的 Dialog。

然後還是先上代碼吧:

public class CustomDialog extends AlertDialog {

protected CustomDialog(Context context) {
super(context);
}

protected CustomDialog(Context context, boolean cancelable, OnCancelListener cancelListener) {
super(context, cancelable, cancelListener);
}

protected CustomDialog(Context context, @StyleRes int themeResId) {
super(context, themeResId);
}

public static class Builder {

private Context mContext;
private CustomDialog dialog;
private View layout;
private int mIcon = -1;
private String mText;
private String mContent;
private String mPoiBtn;
private View.OnClickListener mPoiListener;
private String mNegBtn;
private View.OnClickListener mNegListener;
private int animateType = -1;
public static final int LOW_DISAPPEAR_ANIMATION = 1;
public static final int ROTATE_DISAPPEAR_ANIMATION = 2;

public Builder(Context context) {
mContext = context;
dialog = new CustomDialog(context, R.style.Theme_AppCompat_Dialog_Alert);
layout = View.inflate(mContext, R.layout.custom_dialog1, null);

}

public Builder setTitleIcon(int iconRes) {
mIcon = iconRes;
return this;
}

public Builder setTitle(CharSequence text) {
mText = (String) text;
return this;
}

public Builder setContent(CharSequence text) {
mContent = (String) text;
return this;
}

public Builder setPositiveButton(CharSequence text, @NonNull View.OnClickListener
clickListener) {
mPoiBtn = (String) text;
mPoiListener = clickListener;
return this;
}

public Builder setNegativeButton(CharSequence text, @NonNull View.OnClickListener
clickListener) {
mNegBtn = (String) text;
mNegListener = clickListener;
return this;
}

public Builder create() {
ImageView titleIcon = (ImageView) layout.findViewById(R.id.title_icon);
TextView contentView = (TextView) layout.findViewById(R.id.custom_content);
TextView titleView = (TextView) layout.findViewById(R.id.title);
TextView poiBtn = (TextView) layout.findViewById(R.id.custom_confirm);
TextView negBtn = (TextView) layout.findViewById(R.id.custom_cancel);
poiBtn.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
dialog.dismiss();
}
});
if (mIcon != -1) {
titleIcon.setImageBitmap(BitmapFactory.decodeResource(mContext.getResources(),
mIcon));
}

if (!TextUtils.isEmpty(mText)) {
titleView.setText(mText);
}

if (!TextUtils.isEmpty(mContent)) {
contentView.setText(mContent);
}

if (!TextUtils.isEmpty(mPoiBtn)) {
poiBtn.setText(mPoiBtn);
poiBtn.setOnClickListener(mPoiListener);
} else {
poiBtn.setVisibility(View.GONE);
}

if (!TextUtils.isEmpty(mNegBtn)) {
negBtn.setText(mNegBtn);
negBtn.setOnClickListener(mNegListener);
} else {
negBtn.setVisibility(View.GONE);
}

dialog.setCancelable(true);
dialog.setCanceledOnTouchOutside(true);
return this;
}
int i = 0;
public CustomDialog show(){
Window mWin = dialog.getWindow();
dialog.show();
dialog.setContentView(layout, new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ActionBar.LayoutParams.WRAP_CONTENT));
switch (animateType){
case LOW_DISAPPEAR_ANIMATION:
mWin.setWindowAnimations(R.style.dialog_Low_appear_animation);
break;
case ROTATE_DISAPPEAR_ANIMATION:
mWin.setWindowAnimations(R.style.dialog_rotate_appear_animation);
break;
}

return dialog;
}

public Builder setDisappearAnimator(int animateType){
this.animateType = animateType;
return this;
}

}
}

代碼算不上多,做個分類的話,主要是有 3 部分: Builder 的構建,內容的設置,Dilalog的顯示

首先說一下 Builder 的構建, 構建方法主要完成了 2 個功能, CustomDialog 的實例化 和 布局的填充,這裏需要註意的有一點,不要急著吧
填充的布局添加到 dialog 實例中去, 在 dialog 的 show 方法之前調用 setContentView 或是 addContentView ,這樣都會導致報錯 RequestFeature must be called before adding content;

內容設置的代碼,主要就是采用了一種鏈式的設計方法,每個方法都可以返回 Builder 類本身, 這樣就可以一條直線的調用方法了,這樣寫起來 比較簡潔;

最後,就是 dialog 的顯示了, 記住在 show 之後調用 setContentView 或是 addContentView 就可以了, 置於 setCancelable() 和 setCancelableOnTouchOutside() 這個是對 dialog 消失時的設置,主要就兩個 boolean 值,可以自己看一下;

下面是 R.layout.custom_dialog1 的布局

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@drawable/shape_custom_bg_grey">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="40dp"
android:gravity="center">
<ImageView
android:id="@+id/title_icon"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
/>
<TextView
android:id="@+id/title"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="這裏放置默認的標題"
android:textSize="20sp"/>
</LinearLayout>
<TextView
android:id="@+id/custom_content"
android:layout_width="match_parent"
android:layout_height="120dp"
android:padding="10dp"
android:text="這裏可以放置正文內容"
android:textAlignment="center"
android:textSize="16sp"/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="40dp">
<TextView
android:id="@+id/custom_cancel"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1"
android:text="取消"
android:textSize="18sp"
android:gravity="center"
android:background="@color/cancelBtn"
/>
<TextView
android:id="@+id/custom_confirm"
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1"
android:text="確定"
android:textSize="18sp"
android:gravity="center"
android:background="@color/confirmBtn"
/>
</LinearLayout>

</LinearLayout>

最最後, 補充一下 Dialog 的入場動畫和出場動畫的定義方法

Dialog 主要是依附於一個 Window 對象來進行顯示隱藏的,Window 對象的獲取可以通過 dialog.getWindow 獲得, 所以,dialog的出入場 動畫其實就是 Window 的出入場動畫,那麽就簡單了,通過 xml 來定義;

首先是 res/values/style.xml 文件

<style name="dialog_Low_appear_animation" parent="android:Animation">
<item name="android:windowEnterAnimation">@anim/dialog_low_enter_animation</item>
<item name="android:windowExitAnimation">@anim/dialog_low_exit_animation</item>
</style>

然後,顯然後是 res/anim 下新建 dialog_low_enter_animation 和 dialog_low_exit_animation 的 Resource 文件;

<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<translate android:fromXDelta="0" android:toXDelta="0" android:fromYDelta="100%" android:toYDelta="0"
android:duration="500"/>
<alpha android:fromAlpha="0" android:toAlpha="1" android:duration="500"/>

</set>

入場和出場的參數自己看著怎麽定義合適,也就不多說了。

附上使用方法

CustomDialog dialog = new CustomDialog.Builer().setTitle("").setContent("")
.setPositiveButton("確定", new View.OnclickListerner(){
@override
public void onClick(View view){
dialog.dismiss();
}
})
.setNegativeButton("取消", new View.OnClickListener(){
@override
public void onClick(View view){
dialog.dismiss();
}
})
.setDisappearAnimation(CustomDialog.Builder.LOW_DISAPPEAR_ANIMATION)
.creat().show();

寫到這裏,好吧,dialog 的用法基本就寫完了,關於原理方面的東西現在還沒有涉及,以後涉獵了再來接著補充。

android 自定義dialog的實現方法