2023. 1. 23. 20:54ㆍDIY/[개발 중][MSW] 모험가 키우기
핵심은 공격자가 공격을 명중시키면 데미지를 계산해 피격자에게 전달한다.
피격자는 공격을 회피하지 못할 시, 데미지에 자신의 방어력을 적용시킨 후 그 값만큼 피해를 입는다.
일단, 공격 함수는 Native단에 AttackComponent란 곳에 있으므로,
AttackComponent를 Extend시켜 사용할 것이다.
AttackComponent에는 attack함수를 호출했을 때 내부적으로 호출되어 동작하는 함수들이 있다.
바로 아래에 나온 함수들인데, 아래와 같은 순서로 호출된다는 걸 알아두자.
isAttackTarget은 2번 호출되는데,
호출되는 횟수는 공격 범위에 위치한 hitComponent를 가진 엔티티의 개수와 같다.
(플레이어도 hitComponent를 가지므로 일단 2번 호출되는 것.
플레이어는 공격 대상에서 제외되도록 isAttackTarget함수에서 내부적으로 처리됨)
※Attack함수를 이용하면서, 타겟 수를 제한하기 위해서는
내부 동작 함수를 어떻게 사용해야 하는가?
스킬의 타겟 수는 어떻게 알려줄 것이며, 어떻게 그 타겟 수만큼만 공격을 할 것인가?
->
Attack함수는 공격 범위에 들어온 적들 모두에게 판정 심사를 진행한다.
원치 않는 대상에겐 isAttackTarget에서 false를 반환해 공격 처리를 하지 않을 수 있다.
즉, isAttackTarget 함수는 스킬의 타겟 수를 알아야 하고,
isAttackTarget에서 true를 반환한 횟수가 스킬의 타겟 수보다 작거나 같아야 한다.
이 조건문을 거친 다음에 명중률 연산을 한다.
attack함수를 호출할때 데미지를 계산하는데 쓰일 파라미터를 넘겨야 하는데,
string 형식으로 넘겨야 한다.
어떻게 해야 이 string 타입을 통해 내가 원하는 데미지를 계산하는데 필요한 파라미터들을
넘겨줄 수 있을까?
내가 생각한 방법은
Attack컴포넌트의 attack함수가 호출되면 그 함수의 인자를 통해
any타입으로 스킬정보가 담긴 데이터셋의 행을 받아 프라퍼티에 저장하는 것이다.
스킬정보중에는 attackInfo라는 정보가 있는데 이는 피격되는 개체에게 전달되는 정보로,
방어력 무시 수치와 어떤 속성의 공격인지에 대한 정보가 담겨있다.
이 두개의 정보를 나는 아래와 같은 방법으로 string.match함수를 사용해 전달하였다.
위의 방법을 통해 hitComponent가 피격데미지를 계산하는데 쓰일 attackInfo를 전달할 수 있다.
몬스터에게 방어력을 부여하고 데미지 연산에 적용하는 과정은 건너뛰고
몬스터가 피격을 당하는 것까지 구현했으니
이제 데미지를 받으면 체력이 닳고,
체력게이지ui에 표시하는 것까지 해보고 이 포스팅을 마무리하겠다.
첫번째로 플레이어가 몬스터를 공격하는 경우이다.
일단 몬스터의 HitComponent가 HitEvent를 발생시키면
몬스터의 StatusComponent(이하 상태컴포넌트)가 그 이벤트를 받아
피격 데미지를 자신의 hpChange함수로 전달한다.
이 함수는 자신의 hp를 깎고, 깎인 비율만큼 몬스터의 hpGauge를 변화시키는 기능을 한다.
hpGauge를 변화시키는 방법은
해당 몬스터의 hp바를 담당하는 슬라이더컴포넌트의 value를 바꾸는 것인데,
몬스터 모델을 만들때마다 일일이 슬라이더 컴포넌트를 참조시키긴 번거로우므로
슬라이더 컴포넌트에게 이벤트를 보내서 커플링 없이 해결했다.
몬스터의 hp바슬라이더 컴포넌트가 있는 엔티티는 UI엔티티로,
몬스터와 별개의 엔티티로 존재하기 때문에
몬스터엔티티:GetChildByName으로 hp바엔티티를 찾아서
그 엔티티로 이벤트를 보내주어야 한다.
그리고 상태컴포넌트에서 hp를 깎다가 0보다 작거나 같아지면 OnDie함수를 실행하여
자신의 엔티티, 몬스터를 Destroy시키도록 하였는데 몬스터 엔티티가 소멸되지 않았다.
이는 Destroy할 대상이 서버에 배치되어 있는데
OnDie함수의 실행공간은 클라이언트라서 발생된 문제였다.
아마도 Preset List에서 곧바로 뽑아온 몬스터 모델의 엔티티는 서버 공간에 생성되는 것 같다.
클라이언트 공간에서 생성시킨 몬스터 엔티티의 OnDie함수를 실행시키자,
정상적으로 몬스터가 소멸되었다.
두번째로, 플레이어가 피격되는 경우이다.
플레이어는 몬스터와 달리 항상 동일하게 존재한다.
따라서 다양한 몬스터들의 동적할당을 고려해서
몬스터 전용 HP바 컴포넌트, 상태 컴포넌트를 만들었던 것과는 다르게,
플레이어의 경우는 컴포넌트가 아닌 로직으로 구현할 것이다.
로직은 static과 비슷하게 월드 내에 항상 존재하고,
엔티티에 포함시켜야만 동작하는 컴포넌트와 달리
_SpawnService처럼 언제 어디서든 접근할 수 있다.
그래서 나는 이 로직을 이용해
플레이어의 Status 컴포넌트와 UIManager를 구현할 것이다.
왜냐하면 플레이어의 상태는 언제 어디서든 접근이 쉬워야 한다.
참조하는 컴포넌트가 많기 때문이다.
UIManager는 그냥 로직으로 하면 편할 것 같았다.
UI를 변화시킬 경우가 많을 것 같기 때문이다.
플레이어의 HitComponent의 OnHit이 호출되면,
OnHit 함수에서 플레이어 상태 로직의 HpChange 함수를 호출한다.
(인자로 받은 데미지가 들어감)
플레이어 상태 로직은 HpChange함수에서 받은 데미지만큼
수치 상의 hp를 감소시키고, UIManager 로직의 HpChangeUI 함수를 호출한다.
(인자로 현재 hp와 최대 hp가 들어감)
UIManager 로직은 HpChangeUI 함수에서 받은 인자를 가지고
hp바 슬라이더의 value를 결정하고, hp 텍스트의 text값을 할당한다.
이렇게 프로토타입을 위한 대략적인 공격과 피격 구현은 완료 되었다.
'DIY > [개발 중][MSW] 모험가 키우기' 카테고리의 다른 글
[MSW] 모험가 키우기 - 7 (수치 설정, 스킬시스템 개편) (0) | 2023.02.17 |
---|---|
[MSW] 모험가 키우기 - 6 (프로토타입을 위한 전투씬 연출) (0) | 2023.02.11 |
[MSW] 모험가 키우기 - 4 (스킬시스템 구조 설계) (1) | 2023.01.05 |
[MSW] 모험가 키우기 - 3 (프로토타입을 위한 기본 환경 구성) (0) | 2022.12.26 |
[MSW] 모험가 키우기 - 2 (프로토타입을 위한 기본 플레이어 제어) (0) | 2022.12.24 |