Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 5 additions & 1 deletion .idea/misc.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

36 changes: 0 additions & 36 deletions .idea/sonarlint/issuestore/index.pb

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Binary file added img/command/img.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added img/command/img2.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added img/command/img3.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
112 changes: 112 additions & 0 deletions src/command/CommandPattern.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,112 @@
package command;

import command.command.impl.*;
import command.invoker.RemoteControl;
import command.invoker.RemoteControlWithUndo;
import command.invoker.SimpleRemoteControl;
import command.receiver.GarageDoor;
import command.receiver.Light;
import command.receiver.Stereo;

/**
* 커맨드 패턴에서 클라이언트에 해당하는 클래스
*/
public class CommandPattern {
public static void main(String[] args) {
// simpleRemoteControl();
// remoteControl();
remoteControlWithUndo();
}

private static void simpleRemoteControl() {
final SimpleRemoteControl remote = new SimpleRemoteControl(); // remote 변수 : 인보커(invoker)

final Light light = new Light(); // light : 리시버
final LightOnCommand lightOnCommand = new LightOnCommand(light); // lightOnCommand : 커맨드 객체

final GarageDoor garageDoor = new GarageDoor(); // 리시버
final GarageDoorUpCommand garageDoorUpCommand = new GarageDoorUpCommand(garageDoor); // 커맨드 객체

remote.setCommand(lightOnCommand); // invoker의 setCommand 메소드로 커맨드 객체를 전달
remote.buttonWasPressed(); // invoker로 커맨드 객체의 execute 메소드를 호출

remote.setCommand(garageDoorUpCommand);
remote.buttonWasPressed();
}

private static void remoteControl() {
RemoteControl remoteControl = new RemoteControl();

Light livingRoomLight = new Light("Living Room");
Light kitchenLight = new Light("Kitchen");
GarageDoor garageDoor = new GarageDoor("Garage");
Stereo livingRoomStereo = new Stereo("Living Room");

LightOnCommand livingRoomLightOnCommand = new LightOnCommand(livingRoomLight);
LightOffCommand livingRoomLightOffCommand = new LightOffCommand(livingRoomLight);
LightOnCommand kitchenLightOnCommand = new LightOnCommand(kitchenLight);
LightOffCommand kitchenLightOffCommand = new LightOffCommand(kitchenLight);
GarageDoorUpCommand garageDoorUpCommand = new GarageDoorUpCommand(garageDoor);
GarageDoorDownCommand garageDoorDownCommand = new GarageDoorDownCommand(garageDoor);
StereoOnWithCDCommand stereoOnWithCDCommand = new StereoOnWithCDCommand(livingRoomStereo);
StereoOffCommand stereoOffCommand = new StereoOffCommand(livingRoomStereo);

remoteControl.setCommand(0, livingRoomLightOnCommand, livingRoomLightOffCommand);
remoteControl.setCommand(1, kitchenLightOnCommand, kitchenLightOffCommand);
remoteControl.setCommand(2, garageDoorUpCommand, garageDoorDownCommand);
remoteControl.setCommand(3, stereoOnWithCDCommand, stereoOffCommand);

System.out.println(remoteControl);

for (int i = 0; i < 4; i++) {
remoteControl.onButtonWasPushed(i);
remoteControl.offButtonWasPushed(i);
}
}

private static void remoteControlWithLambda() {
RemoteControl remoteControl = new RemoteControl();

Light livingRoomLight = new Light("Living Room");
Light kitchenLight = new Light("Kitchen");
GarageDoor garageDoor = new GarageDoor("Garage");
Stereo livingRoomStereo = new Stereo("Living Room");

StereoOnWithCDCommand stereoOnWithCDCommand = new StereoOnWithCDCommand(livingRoomStereo);
StereoOffCommand stereoOffCommand = new StereoOffCommand(livingRoomStereo);

// 람다식은 메소드가 오직 한개일 때에만 사용할 수 있다.
// remoteControl.setCommand(0, livingRoomLight::on, livingRoomLight::off);
// remoteControl.setCommand(1, kitchenLight::on, kitchenLight::off);
// remoteControl.setCommand(2, garageDoor::up, garageDoor::down);
remoteControl.setCommand(3, stereoOnWithCDCommand, stereoOffCommand);

System.out.println(remoteControl);

for (int i = 0; i < 4; i++) {
remoteControl.onButtonWasPushed(i);
remoteControl.offButtonWasPushed(i);
}
}

private static void remoteControlWithUndo() {
RemoteControlWithUndo remoteControl = new RemoteControlWithUndo();

Light livingRoomLight = new Light("Living Room");

LightOnCommand livingRoomLightOnCommand = new LightOnCommand(livingRoomLight);
LightOffCommand livingRoomLightOffCommand = new LightOffCommand(livingRoomLight);

remoteControl.setCommand(0, livingRoomLightOnCommand, livingRoomLightOffCommand);

remoteControl.onButtonWasPushed(0);
remoteControl.offButtonWasPushed(0);
System.out.println(remoteControl);

remoteControl.undoButtonWasPushed();

remoteControl.offButtonWasPushed(0);
remoteControl.onButtonWasPushed(0);
System.out.println(remoteControl);
}
}
11 changes: 11 additions & 0 deletions src/command/command/Command.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
package command.command;

/**
* 커맨드 객체는 모두 같은 인터페이스(Command)를 구현해야 한다.
* 해당 인터페이스는 메소드가 하나뿐이다.
*/
public interface Command {
void execute();

void undo();
}
22 changes: 22 additions & 0 deletions src/command/command/impl/GarageDoorDownCommand.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package command.command.impl;

import command.command.Command;
import command.receiver.GarageDoor;

public class GarageDoorDownCommand implements Command {
private final GarageDoor garageDoor;

public GarageDoorDownCommand(GarageDoor garageDoor) {
this.garageDoor = garageDoor;
}

@Override
public void execute() {
garageDoor.down();
}

@Override
public void undo() {
garageDoor.up();
}
}
22 changes: 22 additions & 0 deletions src/command/command/impl/GarageDoorUpCommand.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package command.command.impl;

import command.command.Command;
import command.receiver.GarageDoor;

public class GarageDoorUpCommand implements Command {
private final GarageDoor garageDoor;

public GarageDoorUpCommand(GarageDoor garageDoor) {
this.garageDoor = garageDoor;
}

@Override
public void execute() {
garageDoor.up();
}

@Override
public void undo() {
garageDoor.down();
}
}
22 changes: 22 additions & 0 deletions src/command/command/impl/LightOffCommand.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package command.command.impl;

import command.command.Command;
import command.receiver.Light;

public class LightOffCommand implements Command {
private final Light light; // 리시버 객체

public LightOffCommand(Light light) {
this.light = light;
}

@Override
public void execute() {
light.off();
}

@Override
public void undo() {
light.on();
}
}
22 changes: 22 additions & 0 deletions src/command/command/impl/LightOnCommand.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package command.command.impl;

import command.command.Command;
import command.receiver.Light;

public class LightOnCommand implements Command {
private final Light light; // 리시버 객체

public LightOnCommand(Light light) {
this.light = light;
}

@Override
public void execute() {
light.on();
}

@Override
public void undo() {
light.off();
}
}
20 changes: 20 additions & 0 deletions src/command/command/impl/NoCommand.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
package command.command.impl;

import command.command.Command;

/**
* 일종의 null object
* null 처리 로직을 줄이고 싶을 때 활용한다.
* null object 를 일종의 디자인 패턴으로 분류하기도 한다.
*/
public class NoCommand implements Command {
@Override
public void execute() {

}

@Override
public void undo() {

}
}
24 changes: 24 additions & 0 deletions src/command/command/impl/StereoOffCommand.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package command.command.impl;

import command.command.Command;
import command.receiver.Stereo;

public class StereoOffCommand implements Command {
private final Stereo stereo;

public StereoOffCommand(Stereo stereo) {
this.stereo = stereo;
}

@Override
public void execute() {
stereo.off();
}

@Override
public void undo() {
stereo.on();
stereo.setCD();
stereo.setVolume(11);
}
}
24 changes: 24 additions & 0 deletions src/command/command/impl/StereoOnWithCDCommand.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package command.command.impl;

import command.command.Command;
import command.receiver.Stereo;

public class StereoOnWithCDCommand implements Command {
private final Stereo stereo;

public StereoOnWithCDCommand(Stereo stereo) {
this.stereo = stereo;
}

@Override
public void execute() {
stereo.on();
stereo.setCD();
stereo.setVolume(11);
}

@Override
public void undo() {
stereo.off();
}
}
49 changes: 49 additions & 0 deletions src/command/invoker/RemoteControl.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
package command.invoker;

import command.command.Command;
import command.command.impl.NoCommand;

public class RemoteControl {
Command[] onCommands;
Command[] offCommands;

public RemoteControl() {
onCommands = new Command[7];
offCommands = new Command[7];

final NoCommand noCommand = new NoCommand(); // 빈 커맨드 객체
for (int i = 0; i < 7; i++) {
onCommands[i] = noCommand;
offCommands[i] = noCommand;
}
}

public void setCommand(int slot, Command onCommand, Command offCommand) {
onCommands[slot] = onCommand;
offCommands[slot] = offCommand;
}

public void onButtonWasPushed(int slot) {
onCommands[slot].execute();
}

public void offButtonWasPushed(int slot) {
offCommands[slot].execute();
}

@Override
public String toString() {
final StringBuilder stringBuilder = new StringBuilder();
stringBuilder.append("\n------- 리모컨 -------\n");
for (int i = 0; i < onCommands.length; i++) {
stringBuilder.append("[slot ")
.append(i)
.append("]")
.append(onCommands[i].getClass().getName())
.append(" ")
.append(offCommands[i].getClass().getName())
.append("\n");
}
return stringBuilder.toString();
}
}
Loading