在王者荣耀这款游戏中,玩家可以根据自己的喜好来调整页面布局,比如有的玩家觉得左侧出装顺手,而有的玩家则觉得右侧出装顺手;再比如说玩家在局内想要通过展开地图向队友发送信号时,有些玩家觉得地图左侧展开操作顺畅,而另外一些玩家觉得右侧展开操作顺畅。这些组件的页面布局亦可通过自定义来完成。所有的这些功能,达到了王者荣耀设计者让玩家能更好地体验游戏的初衷。 在本实例中,包含有地图左侧展开右侧出装、地图右侧展开左侧出装、地图/出装同左/右侧等多种组件,玩家对于不同组件的组合(布局)有着不同的要求。很显然,在编写代码时无法在构造方法中进行硬编码来满足所有玩家对组件组合(布局)的要求,而是将布局结果对象的构造过程分成若干个步骤,即根据当前组件个数,在一个接口中定义若干个方法,每个方法负责创建布局结果对象的一个组件,而实现该接口的类将负责创建布局结果对象,也就是说,将布局结果对象的创建过程封装在另一个类中(像这种封装一个对象的创建过程的类称作生成器),从而实现满足所有玩家对于出装、地图展开不同布局需求的目的。
生成器模式理解: 高度概括:将一个复杂对象的构建与它的表示分离,使同样的构建过程可以创建不同的表示。 当系统准备为用户提供一个内部结构复杂的对象时,就可以使用生成器模式,使用该模式可以逐步的构造对象,使对象的创建更具弹性,生成器模式的关键是将一个含有多个组件对象的创建分成若干个步骤,并将这些步骤封装在一个称作生成器的接口中。 生成器模式又被称为建造者模式/生产者模式,属于创建型模式。
生成器模式结构中的四种角色: ①产品(Product):具体生成器要构造的复杂对象; ②抽象生成器(Builder):抽象生成器是一个接口,该接口除了为创建一个Product对象的各个组件定义了若干个方法外,还要定义返回Product对象的方法; ③具体生成器(ConcreteBuilder):实现builder接口的类,具体生成器将实现builder接口所定义的方法; ④指挥者(Director):指挥者是一个类,该类需含有builder接口声明的变量。指挥者的职责是负责向用户提供具体生成器,即指挥者将请求具体生成器来构造用户所需要的product对象,如果所请求的具体生成器成功的构造出product对象,指挥者就可以让该具体生成器返回所构造的product对象。
生成器式的UML类图:
生成器模式的优缺点: 优点: ①生成器模式将对象的构造过程封装在具体生成器中,用户使用不同的具体生成器就可以得到该对象的不同表示; ②生成器模式将对象的构造过程从创建该对象的类中分离出来,使用户无需了解该对象的具体组件; ③可以更加精细有效地控制对象的构造过程,生成器将对象的构造过程分解成若干步骤,这就使程序可以更加精细有效地控制整个对象的构造; ④生成器模式将对象的构造过程与创建该对象类解耦,使对象的创建更加灵活有弹性; ⑤当增加新的具体生成器时,不必修改指挥者的代码,即该模式满足开闭原则; 缺点: ①创建者模式所创建的产品一般具有较多的共同点,其组成部分相似。如果产品之间的差异很大,则不适合使用建造者模式,因此其适用范围受到一定的限制; ②如果产品的内部变化复杂,可能会导致需要定义更多具体建造者类来实现这种变化,导致系统变得很庞大。
生成器模式的适用情景: ①当系统准备为用户提供一个内部结构复杂的对象,而且在构造方法中编写创建该对象的代码无法满足用户需求时,就可以使用生成器模式来构造这样的对象; ②当某些系统要求对象的构造过程必须独立于创建该对象的类时。
eclipse结构图
主函数【应用(Application)】 Application.java
package angle_builderPattern;
import angle_builderPattern.Builder;
import angle_builderPattern.ConcreteBuilderOne;
import angle_builderPattern.ConcreteBuilderTwo;
import angle_builderPattern.Director;
import javax.swing.JFrame;
import javax.swing.JPanel;
public class Application{
public static void main(String args[]){
Builder builder=new ConcreteBuilderOne();
Director director=new Director(builder);
JPanel panel=director.constructProduct();
JFrame frameOne=new JFrame();
frameOne.add(panel);
frameOne.setBounds(1600,300,200,120);
frameOne.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
frameOne.setVisible(true);
builder=new ConcreteBuilderTwo();
director=new Director(builder);
panel=director.constructProduct();
JFrame frameTwo=new JFrame();
frameTwo.add(panel);
frameTwo.setBounds(1600,450,200,120);
frameTwo.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
frameTwo.setVisible(true);
builder=(Builder) new ConcreteBuilderThree();
}
}
12345678910111213141516171819202122232425262728293031323334
产品(Product) Product.java
package angle_builderPattern;
import javax.swing.JButton;
import javax.swing.JLabel;
import javax.swing.JPanel;
public class Product extends JPanel{
JButton button;
JLabel label;
}
1234567891011
抽象生成器(Builder) Builder.java
package angle_builderPattern;
import javax.swing.JPanel;
public interface Builder{
public abstract void buildButton();
public abstract void buildLabel();
public abstract JPanel getPanel();
}
123456789
具体生成器(ConcreteBuilder) ConcreteBuilderOne.java
package angle_builderPattern;
import angle_builderPattern.Builder;
import angle_builderPattern.Product;
import javax.swing.JButton;
import javax.swing.JLabel;
import javax.swing.JPanel;
public class ConcreteBuilderOne implements Builder{
private Product panel;
ConcreteBuilderOne(){
panel=new Product();
}
public void buildButton(){
panel.button=new JButton("地图左侧展开");
}
public void buildLabel(){
panel.label=new JLabel("右侧出装");
}
public JPanel getPanel(){
panel.add(panel.button);
panel.add(panel.label);
return panel;
}
}
1234567891011121314151617181920212223242526
ConcreteBuilderTwo.java
package angle_builderPattern;
import angle_builderPattern.Builder;
import angle_builderPattern.Product;
import javax.swing.JButton;
import javax.swing.JLabel;
import javax.swing.JPanel;
public class ConcreteBuilderTwo implements Builder{
private Product panel; //需要创建的容器
ConcreteBuilderTwo(){
panel=new Product();
}
public void buildButton(){
panel.button=new JButton("地图右侧展开");
}
public void buildLabel(){
panel.label=new JLabel("左侧出装");
}
public JPanel getPanel(){
panel.add(panel.label);
panel.add(panel.button);
return panel;
}
}
1234567891011121314151617181920212223242526
ConcreteBuilderThree.java
package angle_builderPattern;
import javax.swing.*;
import java.awt.*;
public class ConcreteBuilderThree extends JFrame{
JButton jb1,jb2,jb3;
JPanel jp1,jp2,jp3;
public ConcreteBuilderThree(){
jb1=new JButton("同左/右侧展开地图");
jb2=new JButton("同左/右侧出装");
jb3=new JButton("");
JLabel label = new JLabel("同左/右侧出装");
JLabel label1 = new JLabel(" ");
jp1=new JPanel();
jp2=new JPanel();
jp3=new JPanel();
jp1.add(jb1);
jp2.add(label);
jp3.add(label1);
this.add(jp1,BorderLayout.NORTH);
this.add(jp3);
this.add(jp2,BorderLayout.SOUTH);
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
this.setVisible(true);
}
}
123456789101112131415161718192021222324252627282930
指挥者(Director) Director.java
package angle_builderPattern;
import angle_builderPattern.Builder;
import javax.swing.JPanel;
public class Director{
private Builder builder;
Director(Builder builder){
this.builder=builder;
}
public JPanel constructProduct(){
builder.buildButton();
builder.buildLabel();
JPanel product=builder.getPanel();
return product;
}
}
1234567891011121314151617
运行结果截图
更多设计模式在王者荣耀中的应用请点击我的→设计模式在王者荣耀中的应用
感谢阅读
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。