1. 개념
1) 의미
공동작업시 공유된 자원을 조정하는 조정자 역할을 하는 패턴
상호간에 통신이 필요할때 꼭 조정자로 지정한 객체를 통해서
통신하도록 정보를 집중하는 패턴
GUI 에서 많이 사용함
2. 소스
1) Mediattor 인터페이스
해당 인터페이스는 조정자 역할을 담당할 클래스의
interface를 정의합니다.
이를 구현한 구현체는 LoginFrame이라는 클래스로 구현합니다.
public interface Mediator {
public abstract void createColleagues();
public abstract void colleagueChanged(Colleague colleague);
}
import java.awt.Frame;
import java.awt.Label;
import java.awt.Color;
import java.awt.CheckboxGroup;
import java.awt.GridLayout;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;
public class LoginFrame extends Frame implements ActionListener, Mediator {
private ColleagueCheckbox checkGuest;
private ColleagueCheckbox checkLogin;
private ColleagueTextField textUser;
private ColleagueTextField textPass;
private ColleagueButton buttonOk;
private ColleagueButton buttonCancel;
// 생성자
// Colleague들을 생성해서 배치한 후에 표시를 실행한다.
public LoginFrame(String title) {
super(title);
setBackground(Color.lightGray);
// 레이아웃 매니저를 사용해서 4*2의 그리드를 만든다.
setLayout(new GridLayout(4, 2));
// Colleague들의 생성
createColleagues();
// 배치
add(checkGuest);
add(checkLogin);
add(new Label("Username:"));
add(textUser);
add(new Label("Password:"));
add(textPass);
add(buttonOk);
add(buttonCancel);
// 유효/무효의 초기지정
colleagueChanged(checkGuest);
// 표시
pack();
show();
}
// Colleague들을 생성한다.
public void createColleagues() {
// 생성
CheckboxGroup g = new CheckboxGroup();
checkGuest = new ColleagueCheckbox("Guest", g, true);
checkLogin = new ColleagueCheckbox("Login", g, false);
textUser = new ColleagueTextField("", 10);
textPass = new ColleagueTextField("", 10);
textPass.setEchoChar('*');
buttonOk = new ColleagueButton("OK");
buttonCancel = new ColleagueButton("Cancel");
// Mediator의 세트
checkGuest.setMediator(this);
checkLogin.setMediator(this);
textUser.setMediator(this);
textPass.setMediator(this);
buttonOk.setMediator(this);
buttonCancel.setMediator(this);
// Listener의 세트
checkGuest.addItemListener(checkGuest);
checkLogin.addItemListener(checkLogin);
textUser.addTextListener(textUser);
textPass.addTextListener(textPass);
buttonOk.addActionListener(this);
buttonCancel.addActionListener(this);
}
// Colleague로부터의 통지로 각 Colleague의 유효/무효를 판정한다.
public void colleagueChanged(Colleague c) {
if (c == checkGuest || c == checkLogin) {
if (checkGuest.getState()) { // Guest 모드
textUser.setColleagueEnabled(false);
textPass.setColleagueEnabled(false);
buttonOk.setColleagueEnabled(true);
} else { // Login 모드
textUser.setColleagueEnabled(true);
userpassChanged();
}
} else if (c == textUser || c == textPass) {
userpassChanged();
} else {
System.out.println("colleagueChanged:unknown colleague = " + c);
}
}
// textUser 또는 textPass의 변경이 있었다.
// 각 Colleague의 유효/무효를 판정한다.
private void userpassChanged() {
if (textUser.getText().length() > 0) {
textPass.setColleagueEnabled(true);
if (textPass.getText().length() > 0) {
buttonOk.setColleagueEnabled(true);
} else {
buttonOk.setColleagueEnabled(false);
}
} else {
textPass.setColleagueEnabled(false);
buttonOk.setColleagueEnabled(false);
}
}
public void actionPerformed(ActionEvent e) {
System.out.println("" + e);
System.exit(0);
}
}
2) Colleague 인터페이스 및 구현체들
해당 구현체는 Mediator에게 뭔가 정보를 요구하거나
정보를 요청하는 사용자들입니다.
public interface Colleague {
public abstract void setMediator(Mediator mediator);
public abstract void setColleagueEnabled(boolean enabled);
}
import java.awt.Button;
public class ColleagueButton extends Button implements Colleague {
private Mediator mediator;
public ColleagueButton(String caption) {
super(caption);
}
public void setMediator(Mediator mediator) { // Mediator를 보관
this.mediator = mediator;
}
public void setColleagueEnabled(boolean enabled) { // Mediator가 유효/무효를 지시한다.
setEnabled(enabled);
}
}
import java.awt.Checkbox;
import java.awt.CheckboxGroup;
import java.awt.event.ItemListener;
import java.awt.event.ItemEvent;
public class ColleagueCheckbox extends Checkbox implements ItemListener, Colleague {
private Mediator mediator;
public ColleagueCheckbox(String caption, CheckboxGroup group, boolean state) { // 생성자
super(caption, group, state);
}
public void setMediator(Mediator mediator) { // Mediator를 보관
this.mediator = mediator;
}
public void setColleagueEnabled(boolean enabled) { // Mediator가 유효/무효를 지시한다.
setEnabled(enabled);
}
public void itemStateChanged(ItemEvent e) { // 상태가 변하면 Mediator에게 통지
mediator.colleagueChanged(this);
}
}
import java.awt.TextField;
import java.awt.Color;
import java.awt.event.TextListener;
import java.awt.event.TextEvent;
public class ColleagueTextField extends TextField implements TextListener, Colleague {
private Mediator mediator;
public ColleagueTextField(String text, int columns) {
// 생성자
super(text, columns);
}
public void setMediator(Mediator mediator) {
// Mediator를 보관
this.mediator = mediator;
}
public void setColleagueEnabled(boolean enabled) {
// Mediator가 유효/무효를 지시한다.
setEnabled(enabled);
setBackground(enabled ? Color.white : Color.lightGray);
}
public void textValueChanged(TextEvent e) {
// 문자열이 변하면 Mediator에게 통지
mediator.colleagueChanged(this);
}
}
3) 테스트 메인소스를 작성합니다.
public class Main {
static public void main(String args[]) {
new LoginFrame("Mediator Sample");
}
}
3. 다이어그램
https://en.wikipedia.org/wiki/Mediator_pattern
http://copynull.tistory.com/145
4. 관련패턴
1) Facade 패턴
Mediatro 가 양방향 중재자로서 인터페이스를 제공했다면
Facade는 단방향으로 정보를 제공합니다.
2) Observer 패턴
통신 자체는 Observer 패턴을 이용해서 수행되는 경우가 있습니다.