Builder design pattern is one of the creational design Patterns. This pattern separates a complex object from its building process. When building various complex objects, the process of building remains same, but the way of building may vary.
This complex object may have lots of optional configurations.
Key Components of Builder Design Pattern:
Product
The Complex object is the product. this might contain other optional configurations like Shape with Color, dimension etc. In our Example, the Complex object we try to create are: CirclePanel and RectanglePanel.
Builder
The builder is an interface class which has the list of steps to create the complex object. There is a separate method for each step in this builder interface. In our example, ShapeBuilder is the builder interface.
Concrete Builder
Concrete Builder is the implementation of builder interface, it provides implementation to actual steps to create a complex object. For each type of the complex object there will be separate concrete builder class. In our example, RectangleShapeBuilder and CircleShapeBuilder are the concrete builders.
Director
Director class manages and organizes the process of creating the complex object with the help of builder object. In our example, ShapeBuilderDirector is the director class which manages the creation of CirclePanel and RectanglePanel.
Advantages:
- Builder pattern paves the way to create complex object with optional and customizable features.
- Builder pattern clearly separates a complex object’s representation from its building process.
- This pattern gives the flexibility of controlling each step of the building process.
Example:
Consider a scenario where, a ShapeBuilder has to build two different shapes Rectangle and Circle.
Creating ShapeBuilder Interface
Here the ShapeBuilder interface is the builder interface.
package com.learningupskills.designpattern.builder;
import java.awt.Color;
import java.awt.Font;
import javax.swing.JPanel;
public interface ShapeBuilder<T> {
void setColor(Color color);
void setDimension(T dimension);
void setFont(Font font);
JPanel buildShapePanel();
}
Creating RectangleShapeBuilder Class
RectangleShapeBuilder class is a concrete builder class.
package com.learningupskills.designpattern.builder;
import java.awt.Color;
import java.awt.Font;
import javax.swing.JPanel;
public class RectangleShapeBuilder implements ShapeBuilder<RectangleDimension> {
private RectanglePanel rectanglePanel = new RectanglePanel();
@Override
public void setColor(Color color) {
rectanglePanel.setColor(color);
}
@Override
public JPanel buildShapePanel() {
return rectanglePanel;
}
@Override
public void setDimension(RectangleDimension dimension) {
rectanglePanel.setDimension(dimension);
}
@Override
public void setFont(Font font) {
rectanglePanel.setFont(font);
}
}
Creating CircleShapeBuilder class
CircleShapeBuilder class is also a concrete builder class.
package com.learningupskills.designpattern.builder;
import java.awt.Color;
import java.awt.Font;
import javax.swing.JPanel;
public class CircleShapeBuilder implements ShapeBuilder<CircleDimension>{
private CirclePanel circlePanel = new CirclePanel();
@Override
public void setColor(Color color) {
circlePanel.setColor(color);
}
@Override
public JPanel buildShapePanel() {
return circlePanel;
}
@Override
public void setDimension(CircleDimension dimension) {
circlePanel.setDimension(dimension);
}
@Override
public void setFont(Font font) {
circlePanel.setFont(font);
}
}
Creating RectanglePanel class
RectanglePanel class is a product class which is the complex object creating the rectangle shape.
package com.learningupskills.designpattern.builder;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Graphics2D;
import javax.swing.JPanel;
public class RectanglePanel extends JPanel{
/**
*
*/
private static final long serialVersionUID = 1L;
private Color color;
private RectangleDimension dimension;
private Font font;
public void setFont(Font font) {
this.font = font;
}
public void setColor(Color color) {
this.color = color;
}
public void setDimension(RectangleDimension dimension) {
this.dimension = dimension;
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g;
g2d.setColor(color);
g2d.fillRect(dimension.getX(), dimension.getY(), dimension.getLength(), dimension.getBreadth());
g2d.setFont(font);
// Draw a string
g2d.drawString("Rectangle Shape", 200, 50);
}
@Override
public String toString() {
return "RectanglePanel [color=" + color + ", dimension=" + dimension + ", font=" + font + "]";
}
}
Creating RectangleDimension Class
RectangleDimension class provides dimension to the RectanglePanel class.
package com.learningupskills.designpattern.builder;
public class RectangleDimension {
private int x;
private int y;
private int length;
private int breadth;
public RectangleDimension(int x, int y , int length, int breadth)
{
this.x = x;
this.y = y;
this.length = length;
this.breadth = breadth;
}
public int getX() {
return x;
}
public int getY() {
return y;
}
public int getLength() {
return length;
}
public int getBreadth() {
return breadth;
}
}
Creating CirclePanel Class
CirclePanel class is a product class which is the complex object creating the circle shape.
package com.learningupskills.designpattern.builder;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Graphics2D;
import javax.swing.JPanel;
public class CirclePanel extends JPanel{
/**
*
*/
private static final long serialVersionUID = 1L;
private Color color;
private CircleDimension dimension;
private Font font;
public void setFont(Font font) {
this.font = font;
}
public void setColor(Color color) {
this.color = color;
}
public void setDimension(CircleDimension dimension) {
this.dimension = dimension;
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
int x = dimension.getX()-(dimension.getRadius()/2);
int y = dimension.getY()-(dimension.getRadius()/2);
Graphics2D g2d = (Graphics2D) g;
g2d.setColor(color);
g.fillOval(x,y,dimension.getRadius(),dimension.getRadius());
g2d.setFont(font);
// Draw a string
g2d.drawString("Circle Shape", 200, 50);
}
@Override
public String toString() {
return "CirclePanel [color=" + color + ", dimension=" + dimension + ", font=" + font + "]";
}
}
Creating CircleDimension Class
CircleDimension class provides dimension to the CirclePanel class.
package com.learningupskills.designpattern.builder;
public class CircleDimension {
private int x;
private int y;
private int radius;
public CircleDimension(int x, int y , int radius)
{
this.x = x;
this.y = y;
this.radius = radius;
}
public int getX() {
return x;
}
public int getY() {
return y;
}
public int getRadius() {
return radius;
}
}
Creating ShapeBuilderDirector Class
ShapeBuilderDirector class is the director class which manages and organizes the creation of RectanglePanel and CirclePanel classes.
package com.learningupskills.designpattern.builder;
import java.awt.Color;
import java.awt.Font;
import javax.swing.JPanel;
public class ShapeBuilderDirector {
public static JPanel constructRectangleShape(ShapeBuilder<RectangleDimension> builder) {
builder.setColor(Color.RED);
builder.setDimension(new RectangleDimension(200, 100, 100, 200));
builder.setFont(new Font(Font.SERIF, Font.BOLD, 20));
return builder.buildShapePanel();
}
public static JPanel constructCirceShape(ShapeBuilder<CircleDimension> builder) {
builder.setColor(Color.DARK_GRAY);
builder.setDimension(new CircleDimension(250, 150, 100));
builder.setFont(new Font(Font.DIALOG, Font.BOLD, 20));
return builder.buildShapePanel();
}
}
Creating BuilderClient Class
BuilderClient class is the main class which starts the program.
package com.learningupskills.designpattern.builder;
import java.awt.GridLayout;
import javax.swing.JFrame;
public class BuilderClient extends JFrame{
/**
*
*/
private static final long serialVersionUID = 1L;
public BuilderClient()
{
setTitle("Builder Pattern");
setLayout(new GridLayout(2,1));
add(ShapeBuilderDirector.constructRectangleShape(new RectangleShapeBuilder()));
add(ShapeBuilderDirector.constructCirceShape(new CircleShapeBuilder()));
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setSize(500, 700);
setVisible(true);
}
public static void main(String[] args) {
new BuilderClient();
}
}