내일배움캠프 11일차 TIL : 유니티 입문, 델리게이트 실습

woollim·2024년 10월 7일
0

내일배움캠프TIL

목록 보기
10/20
post-thumbnail

■ 학습 개요

오늘 계획

  • 유니티 강의 1~5강 듣기
  • 강의 내용 정리
  • 실습내용 깃허브 올리기
  • C# 4주차 내용 복습
  • 델리게이트 & 리스트로 스킬 리스트 구현 실습 해보기

학습 회고

  • 유니티랑 언리얼이 생각보다 많이 달라서 학습하는데 꽤 오래걸릴 것 같다.
  • 학습 정리내용에 유니티와 언리얼 비교점을 분석하여 추가하는 것도 좋을 듯하다.
  • 팀프로젝트 과제 기간에는 안되었던게 오늘 개인 공부 시간에 구현하니 성공했다. (스킬 리스트 상속관련)내일 튜터님께 그 이유를 자세히 여쭤보아야 할 것같다.
    과제기간 당시 이슈 링크


■ 학습 내용

○ 질문 내용 정리

Q1. 유니티는 컴파일 버튼이나 단축키 없나요
= 코드 작성 후 저장하면 자동으로 컴파일이 이루어짐
= 코드의 변화를 감지하고, 저장된 코드가 있을 때 자동으로 빌드 및 컴파일을 실행해줌

Q2. GetComponent옆은 제네릭 표시인가요
= 맞음. F12 눌러서 정의 볼 수 있음

  public unsafe T GetComponent<T>()
  {
      CastHelper<T> castHelper = default(CastHelper<T>);
      GetComponentFastPath(typeof(T), new IntPtr(&castHelper.onePointerFurtherThanT));
      return castHelper.t;
  }

Q3. Random 클래스는 static인가요?
= 유니티에서 사용 가능한 static Random 클래스
(마찬가지로 F12를 눌러 정의를 볼 수 있음)
= 일반C#의 using System에서 쓰이던 것은 static이 아님

○ 유니티 학습내용 정리 링크

○ 스킬 리스트 상속 구현 실습

  • 목표 : 직업 클래스 별로 스킬리스트에 각 개성에 맞는 직업 스킬을 추가하고 싶다.

  • 아이디어 : 부모 클래스에 스킬리스트 선언 후 각 직업클래스(자식클래스)에서 AddSkill 함수를 통해 스킬을 리스트에 추가한다.

  • 문제점 : 부모 클래스인 User로 선언 후 자식 클래스인 Warrior로 객체를 생성하면, User 클래스의 프로퍼티와 메소드는 이용 할 수있지만, 자식 클래스에만 있는 메소드에 접근 할 수없다. 고로 AddSkill은 이용 불가.

  • 해결책 : 자식 클래스로 객체를 생성할때 생성자는 반드시 호출 된다. 자식클래스 내부에서는 자식클래스의 메소드를 이용할 수 있다. 자식 클래스의 생성자에서 AddSkill 함수를 호출한다.

○ 델리게이트를 이용해 스킬 실행 실습

  • 목표 : 스킬리스트에 스킬 정보는 넣었으니 이제 스킬을 실행하는 메소드를 추가해보자.

  • 아이디어 : 리스트에 스킬 메소드를 추가하자.

  • 문제점 : C#은 리스트에 메소드를 추가할 수 없다.(C++은 됐는데!!)😥

  • 해결책1 : User 클래스를 추상 클래스로 만든 후 가상 함수로 스킬실행 메소드 UseSkill을 만들고, 자식클래스인 Warrior 클래스에서 override한다.

  • 해결책2 : 스킬 클래스에 SkillHandler 델리게이트를 추가하고, 델리게이트 변수를 만든다. 스킬 클래스의 생성자에서 User 객체를 매개변수로 받고, User 클래스의 UseSkill 메소드를 델리게이트 변수에 대입하여 델리게이트와 메소드를 연결한다. (근데 델리게이트 변수 위치가 저게 맞나. 이것도 여쭤봐야겠다.)

  • 결론 : 메인에서 user 객체의 스킬리스트 인덱스0번에 저장된 델리게이트를 호출하면 자식 클래스 고유의 스킬 메소드가 실행 된다. 성공!👍

  • 깃허브 링크

  • 추가 의문점 : 스킬을 많이 넣고 싶을땐 어떡하지.

  • Skill 클래스

public class Skill
{
    public string SkillName { get; set; }
    public int UsingMP { get; set; }
    public delegate void SkillHandler();
    public SkillHandler skillHandler;

    public Skill(string SkillName, int UsingMP, User user)
    {
        this.SkillName = SkillName;
        this.UsingMP = UsingMP;
        skillHandler = user.UseSkill;
    }
}
  • User 클래스(부모)
public abstract class User
{
    public string Name { get; set; }
    public string UserClass { get; set; }
    public int Level { get; set; }
    public int HP { get; set; }
    public int MaxHP { get; set; }
    public int MP { get; set; }
    public int MaxMP { get; set; }

    public List<Skill> SkillList { get; set; }

    public virtual void UseSkill()
    {
        if (MP > 10)
        {
            MP -= 10;
            Console.WriteLine("스킬사용");
        }
        else
        {
            Console.WriteLine("마나가 부족합니다.");
        }
    }

    public User()
    {
        Name = "없음";
        UserClass = "없음";
        Level = 0;
        MaxHP = 10;
        HP = MaxHP;
        MaxMP = 10;
        MP = MaxMP;
        SkillList = new List<Skill>();
    }

    public void InputUserName(string name)
    {
        Name = name;
    }

}
  • Warrior 클래스(자식)
public class Warrior : User
{
    public Warrior()
    {
        UserClass = "전사";
        Level = 1;
        MaxHP = 100;
        HP = MaxHP;
        MaxMP = 50;
        MP = MaxMP;
        AddSkill();
    }

    public void AddSkill()
    {
        SkillList.Add(new Skill("스매시", 10, this));
    }

    public override void UseSkill()
    {
        if (MP > 10)
        {
            MP -= 10;
            Console.WriteLine("스매시!!");
        }
        else
        {
            Console.WriteLine("마나가 부족합니다.");
        }
    }
}
  • Main 문
static void Main(string[] args)
{
    User user;
    user = new Warrior();

    Console.WriteLine(user.HP);
    Console.WriteLine(user.UserClass);
    Console.WriteLine(user.Level);

    Console.WriteLine(user.SkillList[0].SkillName);

    user.SkillList[0].skillHandler();
}
  • 출력

0개의 댓글