- 플레이어의 이름을 묻기
- 게임 시작(전투시작)
- 몬스터의 공격
- 플레이어 데미지 입음
- 플레이어의 공격
- 몬스터 데미지 입음
- 만약 플레이어의 Health가 0이 된다면
- 게임 종료
- 몬스터의 Health가 0이 된다면
- 남은 몬스터가 있는지 체크
- 남은 몬스터가 있다면
- 보상 아이템을 선택할 수 있게됨
- 체력 포션을 받는다면
- 체력 올려줌
- 공격력 포션을 받는다면
- 공격력 올려줌
- 보상을 선택한 뒤 다음 몬스터와 전투 시작
- 남은 몬스터가 없다면
- 게임 종료
Appeared 메서드
//몬스터
public void Appeared()
{
Console.WriteLine($"적이 등장했습니다!\n");
Console.WriteLine($"이름: {Name}");
Console.WriteLine($"체력: {Health}");
Console.WriteLine($"공격력: {Attack}\n");
Thread.Sleep(1000);
}
//플레이어
public void Appeared()
{
Console.WriteLine($"현재 {Name}의 체력: {Health}");
Console.WriteLine($"현재 {Name}의 공격력: {Attack}\n");
Thread.Sleep(1000);
}
TakeDamage 메서드
public void TakeDamage(int damage)
{
Console.WriteLine($"{Name}(이)가 {damage}의 데미지를 입었습니다.");
Health -= damage;
Console.WriteLine($"현재 {Name}의 체력: {Health}\n");
Thread.Sleep(1000);
if (Health <= 0)
{
IsDead = true;
Die();
}
}
GiveDamage 메서드
public void GiveDamage()
{
Console.WriteLine($"{Name}의 공격!\n");
Thread.Sleep(1000);
OnAttack?.Invoke(Attack);
}
Die 메서드
public void Die()
{
Console.WriteLine($"{Name}(이)가 사망했습니다.\n");
Thread.Sleep(1000);
}
모두가 체력 0이 될 때까지 전투가 계속되는 버그 :
while(!player.IsDead || !goblin.IsDead)
{
player.GiveDamage();
goblin.GiveDamage();
}
player.IsDead || goblin.IsDead
로 바꿔주었다.적이 죽은 뒤에도 플레이어를 때리는 버그 발생 :
{}
안쪽의 코드를 모두 실행한 뒤에 확인하는 구조라 죽은 고블린이 플레이어를 한 대 더 때리고 나서야 게임이 끝나는 버그가 발생했다.while (true)
{
player.GiveDamage();
if (goblin.IsDead) break;
goblin.GiveDamage();
if (player.IsDead) break;
}
Thread.Sleep
을 사용하여 1초의 대기시간을 추가해주세요” 라는 부분이 있었기에 메서드 안 출력문 아래마다 Thread.Sleep(1000)
를 붙여 1초의 딜레이를 주었다.메모리 오버헤드
를 “프로그램의 실행 흐름 도중에 동떨어진 위치의 코드를 실행시켜야 할 때, 추가적으로 시간, 메모리, 사원이 사용되는 현상”이라고 정리해 두었는데, 아무리 event를 사용했다지만 같은 클래스에서 필드를 참조하는 문구와 이렇게까지 차이가 날 필요가 있나? 싶은 생각이 드는 것이다.player.OnAttack += goblin.TakeDamage;
같이 메서드를 붙여주는 코드 사이에서도 공격 메서드와 같은 딜레이가 일어나지 않는 게 조금 이상하다는 생각이 들었다.Thread.Sleep
이 두 번 실행되는 게 아닌가 의심하며 코드를 다시 한번 살펴보았는데… 아니나 다를까, 붙여준 OnAttack 뒤에서 Thread.Sleep
을 실행시켜주고 있었다.public void TakeDamage(int damage)
{
Console.WriteLine($"{Name}(이)가 {damage}의 데미지를 입었습니다.");
Health -= damage;
Console.WriteLine($"현재 {Name}의 체력: {Health}\n");
Thread.Sleep(1000);
if (Health <= 0)
{
IsDead = true;
Die();
}
}
public void GiveDamage()
{
Console.WriteLine($"{Name}의 공격!");
OnAttack?.Invoke(Attack); //TakeDamage가 실행된 뒤 Thread.Sleep이 또 실행됨
Thread.Sleep(1000);
}
Thread.Sleep
의 위치를 OnAttack(델리게이트) 앞으로 바꾸니 딜레이 없이 잘 돌아갔다…isAttack
이라는 bool 변수를 만들어서 메서드 간에 신호를 주고받을 수 있도록 손수 구현해야 했을 텐데, 델리게이트를 통해 메서드를 연결해 두면 [몬스터 공격 - 플레이어 공격받음]이 자동으로 실행되는 점이 정말, 진짜, 진심, 너무!!! 편리하고 신기했음. (덕분에 구현 시간도 생각보다 오래 걸리지 않았다!!)