您的位置:首页 > 其它

DialogFragment使用总结

2016-11-25 13:41 351 查看
        最近使用dialog的情况比较多,谷歌现在开始建议使用Dialogfragment 来代替传统的dialog,至于dialogfragment 的好处大家可以百度一下,于是乎要转变思路开始使用最新的dialogfragment,不过使用过程不是很顺利,各种坑,所以今天索性把基本上所有情况都整理了一下,上代码吧还是

       1.最基本的一个普通的dialog

public static class NormalFragmentDialog extends DialogFragment {
public static NormalFragmentDialog getInstance() {
NormalFragmentDialog normalFragmentDialog = new NormalFragmentDialog();
return normalFragmentDialog;
}

@Override
public Dialog onCreateDialog(Bundle savedInstanceState) {
AlertDialog alertDialog = new AlertDialog.Builder(getActivity())
.setTitle("普通的DIALOG")
.setMessage("这是一个普通的dialog")
.setNegativeButton(R.string.cancle, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
}
})
.setPositiveButton(R.string.ok, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
}
})
.create();
alertDialog.setCancelable(true);
alertDialog.setCanceledOnTouchOutside(true);
//和普通的dialog没什么区别了,想干什么就干什么了
return alertDialog;
}
}是不是很简单,没有什么技术含量吧,不过实际中往往需求多多啊,那就要开始自定义了。
        2.自定义view,还是一个title一个确定一个取消(布局就不贴出来了,太简单了)

         public static class CustomViewDialg extends DialogFragment implements View.OnClickListener {
private static final String NO_TITLE = "no_title";
private boolean mNoTitle;

/**
* @param noTitle 是否含有title
* @return
*/
public static CustomViewDialg getInstance(boolean noTitle) {
CustomViewDialg customViewDialg = new CustomViewDialg();
Bundle bundle = new Bundle();
bundle.putBoolean(NO_TITLE, noTitle);
customViewDialg.setArguments(bundle);
return customViewDialg;
}

@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mNoTitle = getArguments().getBoolean(NO_TITLE);
}

@Nullable
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
if (mNoTitle) {
getDialog().requestWindowFeature(Window.FEATURE_NO_TITLE);//设置dialog没有title
}
return inflater.inflate(R.layout.layout_custom_dialog, container, false);
//这里需要说明一下,这个view的高度,由布局的所有控件高度与padding和margin的高度和
}

@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
view.findViewById(R.id.tv_cancle).setOnClickListener(this);
view.findViewById(R.id.tv_ok).setOnClickListener(this);
}

@Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
getDialog().setCancelable(false);
getDialog().setCanceledOnTouchOutside(false);
}

@Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.tv_cancle:
this.dismiss();
break;
case R.id.tv_ok:
this.dismiss();
break;
}
}
}这里需要注意,第一设置有没有title的代码位置,第二系统默认是都有title的,所以如果不加去掉title的代码,会很难看的。
        3.好了,现在我们需要自定义view的dialog的大小,显示的位置,怎么办?注意点都在代码的注释里了,不多说

public static class CustomViewAnyPositionDialog extends DialogFragment {
public static CustomViewAnyPositionDialog getInstance() {
CustomViewAnyPositionDialog customViewAnyPositionDialog = new CustomViewAnyPositionDialog();
return customViewAnyPositionDialog;
}

@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//1 通过样式定义,DialogFragment.STYLE_NORMAL这个很关键的
setStyle(DialogFragment.STYLE_NORMAL, R.style.MyDialog1);

//2代码设置 无标题 无边框 这个就很坑爹,这么设置很多系统效果就都没有了
//setStyle(DialogFragment.STYLE_NO_TITLE|DialogFragment.STYLE_NO_FRAME,0);

}

@Nullable
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
//3 在此处设置 无标题 对话框背景色
//getDialog().getWindow().requestFeature(Window.FEATURE_NO_TITLE);
// dialog的背景色
//getDialog().getWindow().setBackgroundDrawable(new ColorDrawable(Color.RED));
//getDialog().getWindow().setDimAmount(0.8f);//背景黑暗度
return inflater.inflate(R.layout.layout_custom_dialog1, container, false);
}

@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
}

@Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
//注意下面这个方法会将布局的根部局忽略掉,所以需要嵌套一个布局
Window dialogWindow = getDialog().getWindow();
WindowManager.LayoutParams lp = dialogWindow.getAttributes();
lp.gravity = Gravity.LEFT | Gravity.TOP;//改变在屏幕中的位置,如果需要改变上下左右具体的位置,比如100dp,则需要对布局设置margin
// Display defaultDisplay = getActivity().getWindowManager().getDefaultDisplay();
// lp.width = defaultDisplay.getWidth() - 200; //改变宽度
// lp.height=300;// 改变高度
dialogWindow.setAttributes(lp);

getDialog().setCancelable(false);
getDialog().setCanceledOnTouchOutside(false);
getDialog().setOnKeyListener(new DialogInterface.OnKeyListener() {
@Override
public boolean onKey(DialogInterface dialog, int keyCode, KeyEvent event) {//可以在这拦截返回键啊home键啊事件
dialog.dismiss();
return false;
}
});
}
}这里有一个很关键的stytle,所以必须要贴出来,否则会很坑爹,各种问题
<style name="MyDialog1" parent="Base.AlertDialog.AppCompat.Light">
<!-- 背景颜色及透明程度 -->
<item name="android:windowBackground">@android:color/transparent</item>
<!-- 是否半透明 -->
<item name="android:windowIsTranslucent">false</item>
<!-- 是否没有标题 -->
<item name="android:windowNoTitle">true</item>
<!-- 是否浮现在activity之上 -->
<item name="android:windowIsFloating">true</item>
<!-- 是否背景模糊 -->
<item name="android:backgroundDimEnabled">false</item>
<!-- 设置背景模糊的透明度-->
<item name="android:backgroundDimAmount">0.0</item>
</style>         4.好了,最后需要一个进出带动画效果的dialog,这里实现了一个从页面底部进入退出的效果,代码如下:
public static class CustomAnimationDialg extends DialogFragment {
public static CustomAnimationDialg getInstance() {
return new CustomAnimationDialg();
}

@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setStyle(DialogFragment.STYLE_NORMAL, R.style.CustomDatePickerDialog);
}

@Nullable
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
return inflater.inflate(R.layout.layout_custom_dialog2, container, false);
}

@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
}

@Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
Window dialogWindow = getDialog().getWindow();
WindowManager.LayoutParams lp = dialogWindow.getAttributes();
lp.width = ViewGroup.LayoutParams.MATCH_PARENT;
lp.gravity = Gravity.BOTTOM;
dialogWindow.setAttributes(lp);
}
}  同样道理有个最关键的stytle必须贴出来,否则坑爹啊!
<style name="CustomDatePickerDialog" parent="@style/AppTheme">
<item name="android:layout_width">match_parent</item>
<item name="android:layout_height">wrap_content</item>
<item name="android:windowIsFloating">true</item>
<item name="android:background">#00000000</item>
<item name="android:windowBackground">@android:color/transparent</item>
<item name="android:colorBackgroundCacheHint">@null</item>
<item name="android:backgroundDimEnabled">false</item>
<item name="android:windowAnimationStyle">@style/dialog_animation</item>
</style>
<!-- 对话框显示和退出动画 -->
<style name="dialog_animation">
<item name="android:windowEnterAnimation">@anim/dialog_enter</item>
<item name="android:windowExitAnimation">@anim/dialog_exit</item>
</style>      最后贴出来进入的动画,退出的自己写吧
<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">
<translate
android:duration="1000"
android:fillAfter="true"
android:fromYDelta="100%"
android:toYDelta="0%"/>
</set>最后就是一定要注意各个属性要在生命周期的哪个方法中设置,否则无效果或者崩溃,还有就是一定要注意stytle样式的重要性,很多问题都出在样式那了。

最后demo 下载地址   http://download.csdn.net/detail/zhq217217/9693368
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: