前言
在安卓开发中经常会遇到一个需求,确定按钮需要等待用户全部输入完之后才能点击
OK!很简单我们只需要用户在每个EditText都去监听就可以判断了。但是这个工作量特别巨大。所以我们需要对该类问题进行封装。
思路
PlanA:使用代理模式写一个BindHelper。由代理统一处理。
PlanB:使用模版模式父类处理核心逻辑,子类被动调用方法。
对比两个方法,PlanA更加解耦,PlanB更加方便调用;这里书写PlanB方法,因为对我项目本身更加契合。因为太多地方调用了。所以写入基类是比较方便的方法。
直接上代码
/**
* 调用基类
*/
public abstract class BaseFragment extends Fragment {
//...
private View[] mViews;
private JwkillButton btSure;
/**
* 调用bindValid(绑定严重)其控件直接既可以主要调用,这里只举例TextView,CheckBox
* 和其继承类的使用 其他由需要请自行扩展
*/
public void bindValid(JwkillButton btSure, View... views) {
this.mViews = views;
this.btSure = btSure;
if (views == null && views.length == 0) {
return;
}
for (int i = 0; i < views.length; i++) {
if (views[i] instanceof TextView) {
((TextView) views[i]).addTextChangedListener(new JwkillTextWatch() {
@Override
protected void onTextChanged(String s) {
valid();
}
});
}
if (views[i] instanceof CheckBox) {
((CheckBox) views[i]).setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
@Override
public void onCheckedChanged(CompoundButton compoundButton, boolean b) {
valid();
}
});
}
}
valid();
}
/**
* 验证
* setJwkillEnabled 这里方法不用管 你可以当成是setEnabled
* @return
*/
final public void valid() {
btSure.setJwkillEnabled(customerValid() && systemValid());
}
/**
* 系统认证
* 这个意思呢,就是不可修改的。只要绑定完按钮系统(其实是基类)就可以直接帮你处理完
* @return
*/
private boolean systemValid() {
if (mViews == null || mViews.length == 0) {
return true;
}
for (int i = 0; i < mViews.length; i++) {
//只有可见的 才验证
if (mViews[i].getVisibility() == View.VISIBLE) {
if (mViews[i] instanceof TextView && !(mViews[i] instanceof CheckBox)) {
String text = ((TextView) mViews[i]).getText().toString().trim();
if (TextUtils.isEmpty(text)) {
return false;
}
}
if (mViews[i] instanceof CheckBox) {
boolean checked = ((CheckBox) mViews[i]).isChecked();
if (!checked) {
return false;
}
}
}
}
return true;
}
/**
* 用户补充认证
*
* @return
*/
protected boolean customerValid() {
return true;
}
//...
}
基类搞定 接下来调用。没有特殊要求只需要如下即可
/**
*
*/
public class ChildFragment extends BaseFragment {
@Override
protected void onInitView(View view) {
super.onInitView(view);
//...
bindValid(mBinding.btnSure, mBinding.etNickname);
//...
}
}
> 还有其他需求,我们重写customerValid。使用模版模式最大的好处在于重写了,代理模式这里相对来说没这么方便。 言归正传,我们这里需要验证一下 “昵称不为空” “并且昵称是2-14之内的字符”
```java
/**
*
*/
public class ChildFragment extends BaseFragment {
@Override
protected void onInitView(View view) {
super.onInitView(view);
//...
bindValid(mBinding.btnSure, mBinding.etNickname);
//...
}
@Override
protected boolean customerValid() {
/** 通过customerValid 我们还可以附加我自己一些需要 在错误的情况下 显示啥,做一些
* 什么事情
*/
String nickName = mBinding.etNickname.getText().toString().trim();
//昵称不为空
if (JwkillUtils.isStringEmpty(nickName)) {
//我们还可以顺带显示自己的错误信息 请输入昵称
mBinding.nicknameError.setText(R.string.set_nick_name);
//这里返回false 按钮就不能点击了
return false;
}
if (nickName.length() < 2 || nickName.length() > 14) {
//我们还可以顺带显示自己的错误信息 昵称必须是2-14之内的字符
mBinding.nicknameError.setText(R.string.nick_name_long);
//这里返回false 按钮就不能点击了
return false;
}
//关闭内容显示内容
mBinding.nicknameError.setText("");
return true;
}
}
总结
通过模板模式,父类调用子类可以减少很多工作。