CatEscape

dev bourgeois·2023년 11월 21일

Unity VR/AR

목록 보기
4/8
post-thumbnail

CatEscape 단계별 게임 리소스

1단계: 화면에 놓일 오브젝트를 모두 나열

2단계: 오브젝트를 움직일 수 있는 컨트롤러 스크립트 정함
플레이어, 화살

3단계: 오브젝트를 자동으로 생성할 수 있는 제너레이터 스크립트 정함
화살 (1초마다 1개씩 생성)

4단계: UI 갱신할 수 있도록 감독 스크립트 준비
HP 게이지

5단계: 스크립트를 만드는 흐름 생각



씬에 오브젝트 배치-배경 이미지 넣기 (레이어 설정)

-플레이어와 배경 이미지를 배치할 때 화면에 놓이는 앞뒤 위치가 결정되는데,
이때 플레이어가 배경 이미지 뒤에 놓이면 화면에는 플레이어가 보이지 않는다.

-유니티 2D 게임에서 각 게임 오브젝트는 레이어 번호를 갖고 있고, 이 번호에 따라 화면에 놓일 앞뒤 위치가 결정된다.

-레이어 번호가 클수록 화면 앞쪽(겉)에 표시되고 작을수록 화면 뒤쪽(속)에 표시된다.

-Sprite Renderer - Order in Layer 값을 변화시키면 된다.


플레이어 스크립트 (컨트롤러)

using System.Collections;
using Sytem.Collectons.Generic;
using UnityEngine;

public class PlayerController : MonoBehaviour
{
  

void Start() 
{
  Application.targetFrameRate = 60;
}

void Update() 
{   
  // 왼쪽 화살표 눌렸을 때
  // Input 클래스의 GetKeyDown 메소드 사용 
  // 매개변수로 전달한 키가 눌리는 순간 true 한 번 반
  if (Input.GetKeyDown(KeyCode.LeftArrow))
  {
    transform.Translate(-3, 0, 0) 
  }

  // 오른쪽 화살표 눌렸을 때
  if (Input.GetKeyDown(KeyCode.RightArrow))
  {
    transform.Translate(3, 0, 0) 
  }

}

}


화살 스크립트 (컨트롤러)

*Physics 없이 화살 떨어뜨리기

-유니티에 내장된 Physics 기능을 사용하면 유니티가 중력을 계산해주므로 스크립트를 쓰지 않고도 화살을 떨어뜨릴 수 있다.

✅단, Physics를 사용하면 직접적인 움직임을 처리하기 어렵다.


*움직이는 오브젝트 만드는 방법
1) Scene 뷰에 오브젝트 배치
2) 오브젝트를 움직이는 방법을 쓴 스크립트 작성
3) 작성한 스크립트를 오브젝트에 적용


*충돌 판정

-플레이어가 화살에 맞았는지 감지
-게임에서 오브젝트끼리 충돌한 것을 감지하는 구조
-게임을 만들 때 아무것도 설정하지 않으면 오브젝트끼리 충돌해도 그냥 통과한다.
-충돌 판정 대상 → 화살과 플레이어


*충돌 판정 알고리즘

-오브젝트끼리 닿았는지 감지 → 오브젝트 형상을 원형이라고 가정
-원형은 오브젝트의 윤곽을 확인하지 않아도 원의 중심 좌표와 반경을 알면 충돌 판정을 간단히 할 수 있다.

using System.Collections;
using Sytem.Collectons.Generic;
using UnityEngine;

public class ArrowController : MonoBehaviour
{
   GameObject player;  

void Start() 
{
   this.player = GameObject.Find("player"); // 플레이어의 좌표를 알기 위해 플레이어 검색
}

void Update() 
{   
   // 오브젝트(화살)를 프레임마다 등속으로 낙하
   transform.Translate(0, -0.1f, 0);

   if (transform.position.y < -5.0f)
   {
      // 자신(화살 오브젝트)을 소멸시킴 
      // Destroy 메소드 : 매개변수로 전달한 오브젝트 삭제 
      Destroy(gameObject);
   }

   // 충돌 판정
   Vector2 p1 = transform.position; // 화살의 중심좌표
   Vector2 p2 = this.player.transform.position; // 플레이어의 중심좌표

   Vector2 dir = p1 - p2; // p2에서 p1으로 향햐는 벡터
   float d = dir.magnitude; // 벡터의 길이 -> magnitude 사용해서 계산

   float r1 = 0.5f; // 화살의 반경
   float r2 = 1.0f; // 플레이어의 반경

   if (d < r1 + r2)
   {
     // Destroy(gameObject);
        GameObject director = GameObject.Find("GameDirector");
        director.GetComponent<GameDirector>().DecreaseHp();

        Destroy(gameObject);
   }

}

}



프리팹과 공장 만들기 / 화살 제너레이터 스크립트

*공장의 구성
-화살 오브젝트를 1초에 한 개씩 만드는 공장(화살 제너레이터)
-화살 공장은 양산 기계가 설계도대로 제품을 생산하는 구조
-설계도 → 프리팹

즉, 설계도(프리팹)을 양산 기계(제너레이터 스크립트)로 넘기면 설계도대로 제품 (인스턴스)을 생산한다.

*프리팹
-같은 오브젝트를 많이 만들고 싶을 때 사용한다.
-단순 복사랑 다르다.

*공장 만드는 방법

  1. 이미 있는 오브젝트를 사용해 프리펩을 만단다.
  2. 제너레이터 스크립트를 만단다.
  3. 빈 오브젝트에 제너레이터 스크립트를 적용한다.
  4. 제너레이터 스크립트에 프리팹을 전달한다.

-프리팹을 만들면 씬에 배치한 화살 오브젝트는 필요없다.

*this.delta += Time.deltaTime;
-Update 메소드는 프레임마다 실행되고 앞 프레임과 현재 프레임 사이의 시간 차이는 Time.deltaTime에 대입한다.
-프레임과 프레임 사이의 시간 차이를 delta 변수에 모으고 1초 이상이 되면 화살이 생성된다.

*Instantiate 메소드
-화살 인스턴스 생성

*Random 클래스의 Range 메소드
(-6, 7) → `6 ~ 6

-감독 스크립트와 마찬가지로 빈 오브젝트에 제너레이트 스크립트를 적용해야된다.

*아웃렛 접속
-Project 창에 있는 프리팹 실체를 스크립트 변수에 대입(연결)한다. / public

  • 아웃렛을 '콘센트에서 플러그를 꽂는 구멍'을 의미한다.
  • 아웃렛 접속에서는 스크립트 쪽에 플러그를 꽂을 수 있는 콘센트 구멍을 준비한다.
  • 다음으로 Inspector 창에서 해당하는 플러그를 만들고 스크립트의 콘센트 구멍에 끼워 오브젝트를 대입한다.

*제너레이터 스크립트에 프리팹 전달하기

*아울렛 접속
1. 스크립트 쪽에 콘센트 구멍을 만들어야 하므로 스크립트 변수 앞에 public 접근 수식자를 붙인다.
2. public 접근 수식자를 붙인 변수가 Inspector 창에 보인다.
3. Inspector 창의 콘센트 구멍에 대입할 오브젝트를 끼운다. (drag&drop)


*콘센트 구멍 만들기
1단계로 콘센트 구멍을 만들어야 하는데, 이미 ArrowGenerator 스크립트에서 설계도를 나타내는 변수 arrowPrefab에 public 접근 수식자를 붙여 선언했다.

using System.Collections;
using Sytem.Collectons.Generic;
using UnityEngine;

public class ArrowGeneratorer : MonoBehaviour
{
   public GameObject arrowPrefab; // 스크립트 쪽에 콘센트 구멍
   float span = 1.0f;
   float delta = 0;

void Start() 
{
   
}

void Update() 
{   
   this.delta += Time.deltaTime;
   if (this.delta > this.span)
   {
      this.delta = 0;
      GameObject go = Instantiate(arrowPrefab); // 화살 인스턴스 생성
      int px = Random.Range(-6, 7); // 화살의 X 좌표 불규칙
      go.transform.position = new Vector3(px, 7, 0);
}

}

UI / hp 게이지

*UI를 만드는 방법

  1. UI 부품을 Scene 뷰에 배치한다.
  2. UI를 갱신하는 감독 스크립트를 작성한다.
  3. 빈 오브젝트를 만들고 작성한 스크립트를 적용한다.

*HP 게이지 배치
-UI 오브젝트인 Image를 사용해 HP 게이지를 만든다.

*앵커 포인트 설정
-화면 크기가 바껴도 화면 오른 쪽 위에 게이지 표시되도록
-UI 오브젝트 위치 앵커 포인트를 원점(0, 0)으로 하는 값으로 지정 → X

-UI 오브젝트 위치 앵커 포인트를 화면 오른쪽 위 → 실행 기기 화면 크기에 의존X → O

*HP 게이지 줄여나가기
-UI 오브젝트의 Image에서 제공하는 Fill 기능을 사용한다.
-Fill Amout 변수값 바꾸면 이미지 표시 영역을 줄이거나 늘릴 수 있다.

▪ 게이지를 표시하는 방법에는 원형으로 이미지를 잘라 내는 방법 말고도 상하 방향(Horizontal), 좌우 방향(Vertical), 선형(Radial)으로 게이지를 만드는 방법 등 여러 방법이 가능하다.
▪ Fill Method를 바꾸면서 여러 가지 방법을 확인해 보자


UI 갱신 감독 스크립트

  1. 화살 컨트롤러는 감독에게 HP가 감소되었다고 알린다.
  2. 감독은 HP 게이지의 UI를 갱신한다.

감독 스크립트 작성 ➡️ 빈 오브젝트 만들기 ➡️ 빈 오브젝트에 감독 스크립트 적용


*UI를 갱신하는 감독 만들기

▪ using UnityEngine.UI는 UI 오브젝트를 스크립트에서 조작할 때 필요하다.
▪ Start 메서드에서는 Find 메서드를 사용해 씬 중에서 HP 게이지의 오브젝트를 찾고
hpGauge 변수에 대입한다.
▪ 나중에 화살 컨트롤러에서 HP 게이지 표시를 줄이는 처리를 호출할 것을 고려해
HP 게이지의 처리는 public 메서드로 작성한다.
▪ 화살과 플레이어가 충돌했을 때 화살 컨트롤러가 호출하는 메서드로 Image 오브젝트
(hpGauge)의 fillAmount를 줄여 HP 게이지를 표시하는 비율을 낮춘다.

*빈 오브젝트 만들기
▪ UI 감독 스크립트를 작성했다면 빈 오브젝트를 만든 후 적용한다.
▪ 이렇게 하면 빈 오브젝트가 감독 오브젝트로 동작한다.

*HP가 줄었다고 감독에게 알리기

▪ 플레이어가 화살에 맞으면 화살 컨트롤러에서 감독 스크립트의 DecreaseHp 메서드를
호출하는 부분을 만든다.
▪ 화살과 플레이어의 충돌 판정은 화살 컨트롤러에 구현한다.
▪ 플레이어가 화살에 맞은 시점에 HP가 줄도록 DecreaseHp 메서드를 호출하는 처리를 화살컨트롤러의 충돌 판정 처리에 추가한다.
▪ Project 창의 ArrowController를 더블클릭해 파일을 열고 스크립트 추가한다.

▪ ArrowController에서 GameDirector 오브젝트에 있는 DecreaseHp 메서드를 호출하기 때문에 Find 메서드를 사용해 GameDirector 오브젝트를 찾는다.
▪ 다음에 GetComponent 메서드를 사용해 GameDirector 오브젝트의 GameDirector 스크립트를 구하고 DecreaseHp 메서드를 호출한다.

0개의 댓글