ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • 블루아카이브 루트슈터 팬게임 프로젝트(3) - 아이템랜덤 옵션 생성기능
    루트슈터 프로젝트 2023. 12. 30. 00:24

    원본: 디아블로3


    핵앤슬래시, 루트슈터 장르의 꽃은 누가 뭐래도 다양한 옵션, 다양한 등급의 아이템 드랍 시스템일 것입니다. 이를 구현하는 방법에 대해서 고민을 했었습니다만, 이것에 대해 정답은 없는것 같아서 일단 제 생각대로 구현한 방법에 대해 소개하겠습니다. 

     

     

     먼저 제가 한 일은 무기의 기본 베이스 옵션을 DataTable로 만드는 일이었습니다. 제가 고안한 무기 스탯 산출방식은 기본 무기 베이스에 등급별로 추가옵션이 몇줄 붙어서 스탯이 변하는 방식입니다.
    예를 들면 30데미지의 베이스 무기에 20% 무기데미지 증가 옵션이 붙으면 36이 되는 방식인거죠. Name 열은 사실 이름이 아니라 레벨입니다. 상대하는 적의 레벨이 높을수록 높은 데미지의 베이스 아이템이 나와야 하기 때문에 레벨이 높아질수록 베이스 데미지가 높아집니다. 옆의 fireRate(발사속도)와 maxMag(탄창용량)은 레벨이 바뀌면서 변하지 않으니 여기에 있을 필요가 없고 블루프린트단에서 변경해줘도 좋을 것 같습니다. 

     

     

     

     

    다음은 무기 옵션의 데이터 테이블입니다. 지금은 무기 옵션의 종류가 6종류 있고, 옵션마다 정해진 최소 옵션 수치와 최고 옵션 수치가 적혀있습니다. 

     

     

     

    이 코드는 따로 데이터 테이블을 관리하는 헤더파일입니다. 언리얼에서 데이터 테이블을 구조체의 형태로 받아올 수 있으므로 데이터를 받아오기 위해 방금 작성했던 CSV파일의 구조와 똑같이 구조체를 구성해놓아야 합니다. 

     

     

     

    이곳은 게임모드베이스의 헤더파일입니다. 게임모드에서 아이템 옵션관련 기능을 담당하는 이유는 게임모드에서 액터(적)의 죽음을 처리하기 때문에 이곳에서 액터의 죽음과 동시에 아이템의 생성 또한 담당하는것이 자연스럽다고 생각했기 때문입니다. 

     

    itemClass 서브클래스에 대해 설명하자면, 저곳에서 총의 베이스 정보가 담긴 BP, 블루프린트가 담겨집니다. TArray로 구성되었기 때문에 여러개의 블루프린트를 가질 수 있고 저 Array에서 무작위로 하나가 아이템으로 스폰되는 것입니다. 


     

    그리고 게임모드 베이스의 cpp 파일입니다. 먼저 생성자에서 DataTable을 전부 불러옵니다. 아직은 SMG와 AR의 베이스 스탯 테이블 뿐입니다만, 기능 테스트가 끝나면 본격적으로 DataTable을 전부 만들어서 불러오게 해야겠습니다. 

     

    또한 밑의 ActorDied 함수는 플레이어와 적의 죽음을 담당하는 함수입니다. 플레이어의 죽음에 대해서는 아직 처리를 해놓지 않았고, 아이템 드랍 기능을 위해 적 액터의 죽음만 설정해놓았습니다. 이곳에서 아이템 드랍 개수에 대해서 정해놓았습니다. 

     

     

     

     

    EnemyClass.h

     

    아이템 드랍개수는 적 클래스가 가진 itemDropRate 변수에 의해 정해집니다. 만약 등장 확률이 80%라면 80%의 확률로 아이템이 하나 드랍되는 것입니다. 이 값은 100%가 넘게 설정될 수 있는데, 100%를 넘는다면 아이템 하나는 무조건 확정 드랍입니다. 만약 200%라면 2개가 확정드랍이 되는것이죠. 350%라면 3개가 확정드랍되고 50%에 대해서만 확률에 기반하여 아이템을 하나 더 드랍할지 말지 정해지는 것입니다. 

     

     

     

     

    그렇게 아이템을 스폰하는 함수가 실행됩니다. 먼저 랜덤으로 TArray에서 어떤 무기베이스로 드랍될지 정합니다. 그 후 SpawnActor를 호출하여 무기를 스폰하고 return으로 무기의 포인터를 받아옵니다. AGun 액터는기본적으로 피직스가 설정 안돼있으므로 활성화 시켜주고, 적에게서 아이템이 튀어나오는 연출을 주기 위해 impulse를 가합니다. 그리고 본격적으로 무기의 옵션을 붙여주는 GunOptionGenerator함수를 실행시켜줍니다. 

     

     

     

     

    총의 포인터 변수와 적의 레벨, 적의 드랍확률을 받아와서 총의 옵션을 박아줍니다. 먼저 스폰한 총기 BP의 무기 종류에 맞는 데이터 테이블을 참조하여 베이스 옵션을 가져와서 baseStatRow에 저장해둡니다. 그 후 총기의 레벨과 희귀도를 정해주고.. 마지막으로 총기 베이스 스탯과 추가 옵션을 연산하여 총기의 옵션 지정이 전부 끝납니다. 추가옵션을 정하는 함수는 SetItemRarity함수에서 진행됩니다. 

     

     

     

    아이템의 희귀도와 추가옵션을 정해주는 함수입니다. 1부터 100의 숫자중 하나를 랜덤으로 뽑고 비교를 시작합니다.

    만약 전설등장확률이 10%, 레어템확률 20%, 언커먼템 확률이 30%라고 가정하고 
    첫줄에 1~100중 랜덤숫자가 40이 떳다면 전설확률 10보다 크므로 전설이 되지 않고 전설확률 + 레어템확률인 30보다도 더 크니 레어템이 되지 않습니다. 10 + 20 + 30인 60보다는 작으니 언커먼 템이 되겠네요. 만약 60보다 높은 숫자가 나왔다면 일반템이 될겁니다.

    그리고 SetGunOption은 희귀도의 정도만큼 추가 옵션의 개수를 정해줍니다. 전설은 4줄, 레어템은 3줄, 언커먼템은 2줄입니다. 노말템은 추가 옵션이 없습니다.

     

     

     

     

    이렇게 보니까 정말 난잡하기 그지없습니다.. 버그가 발생할 가능성도 농후할거 같고, 나중에 수정이 필요하긴 할거 같은데 정말 난감하네요.. 계속 더 좋은 방법을 찾기위해 생각해봐야겠습니다. 다음 기능에 대한 소개는 인벤토리 기능이 될것 같습니다. 앞으로는 시연을 위해 움짤도 같이 곁들이고 싶네요. 이만 줄이겠습니다 글솜씨가 좋지 않지만 여기까지 읽어주신분들 모두 감사합니다. 

Designed by Tistory.