建造者模式的定义
将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示。
这里給大家分析一下:
定义的前半句说,构造与表示分离,其实就是继承(或实现)。
两种工厂模式也都是为某个对象提供一个接口,而且无需指定它们的具体类。
所以建造者模式的重点是后半句:同样的构建过程可以创建不同的结果。
但是我仔细想了一下,这句话说的也是太含糊了,并且和工厂模式也是类似的,工厂模式的接口也是定义了产品的过程,子类去实现,然后生产出不同的产品。
虽然是有点纠结但是还是应该先看完,在慢慢来深入理解这个建造者模式。
建造者模式中,有如下四种角色:
1.抽象建造者(Builder):该绝是用于规范产品的各个组成部分,并进行抽象,一般独立于应用程序的逻辑。
2.具体建造者(Concrete Builder):该角色实现抽象建造者中定义的所有方法,并且返回一个组件好的产品实例。
3.产品(Product):该角色是建造者中的复杂对象,一个系统中会有多个产品类,这些产品类不一定有共同的接口,可以是完成不相关的。
4.导演者(Director):该角色负责安排已有模块的顺序,然后告诉Builder开始建造
建造者模式的类图:
下面以自定义Dialog 为例
public class CursorDialog extends Dialog {
public CursorDialog(@NonNull Context context) {
super(context);
}
public CursorDialog(@NonNull Context context, int themeResId) {
super(context, themeResId);
}
}
需要在方法里创建一个内部类
public class CursorDialog extends Dialog {
private CursorDialog(@NonNull Context context) {
super(context);
}
private CursorDialog(@NonNull Context context, int themeResId) {
super(context, themeResId);
}
//内部类 能在下面返回 上面的方法就私有化了
public static class Builder {
private final Context mContext;
//参数 在這寫一些Dialog的參數 不全屏
public Builder(Context context) {
mContext = context;
}
public CursorDialog builder() {
return new CursorDialog(mContext);
}
}
}
最后成型:
public class CursorDialog extends Dialog {
private CursorDialog(Context context) {
super(context);
}
private CursorDialog(Context context, int themeResId) {
super(context, themeResId);
}
public static class Builder {
private final Context mContext;
//参数
//是否全屏 默认不全屏
private boolean isFloating = true;//浮动 窗口化
private String title;//flase
private boolean isFull;
private View layout;
//设置布局
public Builder setLayout(int res) {
layout = View.inflate(mContext, res, null);
return this;
}
public Builder setViewClick(int id, View.OnClickListener listener) {
View view = layout.findViewById(id);
view.setOnClickListener(listener);
return this;
}
public Builder setViewClick(int id, AdapterView.OnItemClickListener listener) {
View view = layout.findViewById(id);
if (view instanceof AdapterView) {
AdapterView v = (AdapterView) view;
v.setOnItemClickListener(listener);
}
return this;
}
public Builder setView(View v) {
layout = v;
return this;
}
public Builder notFloating() {
isFloating = false;
return this;
}
public Builder setTitle(String title) {
this.title = title;
return this;
}
public Builder full() {
isFull = true;
isFloating = false;
return this;
}
public Builder(Context context) {
this.mContext = context;
}
public CursorDialog builder() {
CursorDialog dialog;
if (isFloating) {
//浮动的
if (TextUtils.isEmpty(title)) {
dialog = new CursorDialog(mContext, R.style.CursorDialogThemeNotTitle);
} else {
dialog = new CursorDialog(mContext);
}
}
if (layout == null)
throw new IllegalArgumentException("view不能为空");
dialog.setContentView(layout);
return dialog;
}
}
}
调用
Dialog dialog = new CursorDialog.Builder(this).setLayout(R.layout.dialog_updata).notFloating().builder();
//此外需要自己写对应的style