+TypeScript 예제
Dialog가 테마 선택과 각 부품의 그리기까지 맡으면 새 테마를 넣을 때 화면 코드도 바뀐다. IWidgetFactory는 함께 쓸 부품을 고르고, Dialog는 그 부품을 사용하는 일만 맡는다.
interface IButton { draw(): string; }
interface ICheckbox { draw(): string; }
// 테마 선택을 화면에서 떼어 내고 관련 제품의 생성 약속으로 모은다.
interface IWidgetFactory {
button(): IButton;
checkbox(): ICheckbox;
}
class LightButton implements IButton { draw(): string { return "light button"; } }
class LightCheckbox implements ICheckbox { draw(): string { return "light checkbox"; } }
class DarkButton implements IButton { draw(): string { return "dark button"; } }
class DarkCheckbox implements ICheckbox { draw(): string { return "dark checkbox"; } }
class LightFactory implements IWidgetFactory {
button(): IButton { return new LightButton(); }
checkbox(): ICheckbox { return new LightCheckbox(); }
}
class DarkFactory implements IWidgetFactory {
button(): IButton { return new DarkButton(); }
checkbox(): ICheckbox { return new DarkCheckbox(); }
}
// 화면은 선택된 제품을 사용할 뿐 구체 테마 클래스를 만들지 않는다.
class Dialog {
constructor(private readonly factory: IWidgetFactory) {}
render(): string {
return this.factory.button().draw() + " + " + this.factory.checkbox().draw();
}
}
for (const factory of [new LightFactory(), new DarkFactory()]) {
console.log(new Dialog(factory).render());
}
light button + light checkbox
dark button + dark checkbox
같은 역할의 C# 인터페이스를 TypeScript 인터페이스로 옮겼다. 테마가 섞이지 않게 제품을 돌려주는 책임은 각 팩토리 구현에 있다.