前言
使用DialogFragment来管理对话框,当旋转屏幕和按下后退键时可以更好的管理其声明周期,它和Fragment有着基本一致的声明周期。且DialogFragment也允许开发者把Dialog作为内嵌的组件进行重用。(结合大佬们的博客总结的,如有侵权,麻烦联系我删除此文章)
使用DialogFragment至少需要实现onCreateView或者onCreateDIalog方法。onCreateView即使用定义的xml布局文件展示Dialog。onCreateDialog即利用AlertDialog或者Dialog创建出Dialog。
用法
onCreateView的实现
继承DialogFragment
public class EditNameDialogFragment extends DialogFragment {
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState)
{
View view = inflater.inflate(R.layout.fragment_setname, container);
Button button = view.findViewById(R.id.id_sure_edit_name);
button.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
dismiss();
}
});
return view;
}
}
fragment_setname.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="wrap_content" >
<TextView
android:id="@+id/id_label_your_name"
android:layout_width="wrap_content"
android:layout_height="32dp"
android:gravity="center_vertical"
android:text="Your name:" />
<EditText
android:id="@+id/id_txt_your_name"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_toRightOf="@id/id_label_your_name"
android:imeOptions="actionDone"
android:inputType="text" />
<Button
android:id="@+id/id_sure_edit_name"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_below="@id/id_txt_your_name"
android:text="ok" />
</RelativeLayout>
调用
EditNameDialogFragment editNameDialog = new EditNameDialogFragment();
editNameDialog.show(getFragmentManager(), "EditNameDialog");
运行截图
![](https://img.haomeiwen.com/i9956726/55c7a9662e420cac.jpg)
onCreateDialog的实现
继承DialogFragment
public class LoginDialogFragment extends DialogFragment {
private EditText t_username;
private EditText t_password;
public interface LoginListener {
void login(String username,String psw);
}
@Override
public Dialog onCreateDialog(Bundle savedInstanceState)
{
AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
// Get the layout inflater
LayoutInflater inflater = getActivity().getLayoutInflater();
View view = inflater.inflate(R.layout.dialog_login, null);
t_username = view.findViewById(R.id.id_txt_username);
t_password = view.findViewById(R.id.id_txt_password);
builder.setView(view)
// Add action buttons
.setPositiveButton("Sign in",
new DialogInterface.OnClickListener()
{
@Override
public void onClick(DialogInterface dialog, int id)
{
((LoginListener)getActivity()).login(t_username.getText().toString(),t_password.getText().toString());
}
}).setNegativeButton("Cancel", null);
return builder.create();
}
}
dialog_login.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical" >
<ImageView
android:layout_width="match_parent"
android:layout_height="64dp"
android:background="#FFFFBB33"
android:contentDescription="@string/app_name"
android:scaleType="center"
android:src="@drawable/ic_launcher_background" />
<EditText
android:id="@+id/id_txt_username"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginBottom="4dp"
android:layout_marginLeft="4dp"
android:layout_marginRight="4dp"
android:layout_marginTop="16dp"
android:hint="input username"
android:inputType="textEmailAddress" />
<EditText
android:id="@+id/id_txt_password"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginBottom="16dp"
android:layout_marginLeft="4dp"
android:layout_marginRight="4dp"
android:layout_marginTop="4dp"
android:fontFamily="sans-serif"
android:hint="input password"
android:inputType="textPassword" />
</LinearLayout>
调用及数据回传
LoginDialogFragment dialog = new LoginDialogFragment();
dialog.show(getFragmentManager(), "loginDialog");
@Override
public void login(String username, String psw) {
LogUtil.log("Get Data : username = " + username + " , password = " + psw);
}
运行截图:
![](https://img.haomeiwen.com/i9956726/95ef0916e212599e.png)
2019-06-29 12:23:49.922 28355-28355/sayhallo.cn.ilikeandroid E/LOG_: Get Data : username = hhhh , password = hhhhh
附加说明
1、屏蔽返回键和外部点击
只需要在onCreate方法中加入
@Override
public void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setCancelable(false);
}
2、去掉,弹窗的黑色棱角
在onViewCreated方法中加入
getDialog().getWindow().setBackgroundDrawable(new BitmapDrawable());
3、设置软键盘监听,在DialogFragment中含有EditText时,点击EditText以外的部分,关闭软键盘
在onViewCreate()方法中加入如下代码
/**
* 点击非输入框区域时,自动收起键盘
*/
private void initSoftInputListener() {
getDialog().getWindow().getDecorView()
.setOnTouchListener(new View.OnTouchListener() {
@Override
public boolean onTouch(View view, MotionEvent event) {
InputMethodManager manager = (InputMethodManager)getActivity()
.getSystemService(Context.INPUT_METHOD_SERVICE);
if (event.getAction() == MotionEvent.ACTION_DOWN) {
if (getDialog().getCurrentFocus() != null
&& getDialog().getCurrentFocus().getWindowToken() != null) {
manager.hideSoftInputFromWindow(
getDialog().getCurrentFocus().getWindowToken(),
InputMethodManager.HIDE_NOT_ALWAYS);
}
}
return false;
}
});
}
在工作中,遇到了适配平板的问题,于是找了很多文章和资料去控制窗口的大小,终于找到一种方式可以控制,于是,我把它封装成了一个基类
public abstract class BaseFragmentDialog extends DialogFragment {
@Nullable
@Override
public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
View view = inflater.inflate(initLayoutId(), container);
ButterKnife.bind(this,view);
initView();
initListener();
return view;
}
protected abstract void initListener();
protected abstract void initView();
/**
* 设置窗体大小的方法
*/
@Override
public void onStart() {
super.onStart();
Window window = getDialog().getWindow();
window.setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
WindowManager.LayoutParams windowParams = window.getAttributes();
int height = windowParams.height;
int width = windowParams.width;
// windowParams.dimAmount = 0.0f;
// windowParams.y = 100;
// window.setAttributes(windowParams);
Dialog dialog = getDialog();
if (dialog != null) {
DisplayMetrics dm = new DisplayMetrics();
getActivity().getWindowManager().getDefaultDisplay().getMetrics(dm);
dialog.getWindow().setLayout(PxdUtils.Dp2Px(getContext(),getWidth()), height);
// dialog.getWindow().setLayout((int) (dm.widthPixels * 0.6), (int) (dm.heightPixels * 0.5));
}
}
protected float getWidth() {
return 400.0f;
}
protected abstract int initLayoutId();
}
待我抽空研究下Dialog和它的窗口大小的控制方法
网友评论