유니티 기초/복습

챕터 5 고양이 탈출 복습 - [완]

다모아 2023. 8. 4. 00:33

GameDirector

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;

public class GameDirector : MonoBehaviour
{
    private GameObject catGo;
    private GameObject hpGaugeGo;
    public GameObject txtGameOverGo;
    public Text txtScoreGo;

    private int score;
    private bool isGameOver = false;

    // Start is called before the first frame update
    void Start()
    {
        this.catGo = GameObject.Find("cat");
        this.hpGaugeGo = GameObject.Find("hpGauge");
        this.txtGameOverGo = GameObject.Find("txtGameOver");
        this.txtScoreGo = GameObject.Find("txtScore").GetComponent<Text>();

        Debug.LogFormat("{0}, {1}", this.catGo, this.hpGaugeGo);
    }

    public void DecreaseHp()
    {
        Image hpGauge = this.hpGaugeGo.GetComponent<Image>();
        hpGauge.fillAmount -= 0.1f;

        if (hpGauge.fillAmount == 0f)
        {
            Text text = txtGameOverGo.GetComponent<Text>();
            text.text = string.Format("GameOver");
            this.GameOver();
            GameObject arrowGeneratorGo = GameObject.Find("ArrowGenerator");
            ArrowGenerator arrowGenerator = arrowGeneratorGo.GetComponent<ArrowGenerator>();
            arrowGenerator.StopArrow();
        }
    }

    public void IncreaseScore(int score)
    {
        if (this.isGameOver == true) return;

        //this.txtScoreGo = GameObject.Find("txtScoreGo");
        this.score += score;

        Debug.LogFormat("score: {0}", this.score);
        this.txtScoreGo.text = this.score.ToString();
    }

    public void GameOver()
    {
        this.isGameOver = true;

        CatController catController = this.catGo.GetComponent<CatController>();
        if(catController != null)
        {
            catController.StopMoving();
        }

    }
}

 

ArrowGenerator

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class ArrowGenerator : MonoBehaviour
{
    public GameObject arrowPrefab;  //프리팹 원본 파일 
    private float elapsedTime; //경과 시간 

    private bool isStopArrow = false;
    private void Awake()
    {

    }
    // Start is called before the first frame update
    void Start()
    {

    }

    // Update is called once per frame
    void Update()
    {
        if (isStopArrow) return;
            //매프레임마다 Time.deltaTime을 경과시간에 더해준다 
            this.elapsedTime += Time.deltaTime;

            //경과시간이 1초를 지나갔다면 
            if (this.elapsedTime > 1f)
            {
                //화살을 만든다 
                this.CreateArrow();
                //경과시간 초기화 
                this.elapsedTime = 0;   //0초부터 1초까지를 셀수 있도록 
            }
    }

    private void CreateArrow()
    {
        //arrowGo : 프리팹 복제본 (인스턴스)
        GameObject arrowGo = Instantiate(this.arrowPrefab);
        //Random.Range(-7.5f, -7.5f)
        arrowGo.transform.position = new Vector3(Random.Range(-7, 8), 6f, 0);
    }

    public void StopArrow()
    {
        isStopArrow = true;
    }
}

 

ArrowController

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class ArrowController : MonoBehaviour
{
    public float speed;
    public float radius = 1;
    private GameObject catGo;
    private GameDirector gameDirector;

    private bool isGameOver;
    // Start is called before the first frame update
    void Start()
    {
        this.catGo = GameObject.Find("cat");
        GameObject gameDirectorGo = GameObject.Find("GameDirector");
        this.gameDirector = gameDirectorGo.GetComponent<GameDirector>();
        Debug.Log("catGo : {0}", catGo);
    }

    private bool IsCollide()
    {
        //두 원사이의 거리
        var dis = Vector3.Distance(this.transform.position, this.catGo.transform.position);

        //반지름의 합
        CatController catController = this.catGo.GetComponent<CatController>();
        float sumRadius = this.radius + catController.radius;

        //두 원 사이의 거리가 두 원의 반지름의 합보다 크면 false (부딪히지 않았다)

        //두 원의 반지름의 합이 두 원 사이의 거리보다 크다면 부딪혔다. true

        return dis < sumRadius;
    }

    //이벤트 함수
    private void OnDrawGizmos()
    {
        Gizmos.color = Color.red;
        Gizmos.DrawWireSphere(this.transform.position, this.radius);
    }

    // Update is called once per frame
    void Update()
    {
        this.transform.Translate(this.speed * Vector3.down * Time.deltaTime);

        if(this.transform.position.y <= -4.562)
        {
            this.gameDirector.IncreaseScore(100);
            Destroy(this.gameObject);
        }

        if(this.IsCollide())
        {
            Debug.LogFormat("충돌했다.");
            gameDirector.DecreaseHp();
            Destroy(this.gameObject);
        }
        else
        {
            Debug.LogFormat("충돌하지 않았다.");
        }
    }
}

 

CatController

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class CatController : MonoBehaviour
{
    private bool isMoving = true;
    // Start is called before the first frame update
    void Start()
    {
        
    }

    public float radius = 1;
    //이벤트 함수
    private void OnDrawGizmos()
    {
        Gizmos.color = Color.red;
        Gizmos.DrawWireSphere(this.transform.position, this.radius);
    }
    // Update is called once per frame
    void Update()
    {
        if (isMoving)
        {
            //왼쪽 키를 누르면
            if (Input.GetKeyDown(KeyCode.LeftArrow))
            {
                this.MoveLeft();
            }

            else if (Input.GetKeyDown(KeyCode.RightArrow))
            {
                this.MoveRight();
            }
        }
    }

    public void MoveLeft()
    {
        this.transform.Translate(-2, 0, 0);
    }

    public void MoveRight()
    {
        this.transform.Translate(2, 0, 0);
    }

    public void StopMoving()
    {
        isMoving = false;
    }
}

 

GameOver가 되면 안움직이고 Arrow들이 내리지 않는다.


그동안 score가 무한 증식하고 그래서 상당히 골치아팠다.

그동안 Console 창에 score를 찍어놓고 점수를 봤는데 무한으로 증식하고 text에는 나오지 않아서 엄청 골치아팠는데

이곳에 txtScore를 지정해주지 않아서 생긴 문제 같았다.

아무리 생각해도 코딩에는 문제가 없다고 생각하고 강사님 코드도 보고 찍어보고 하는데 차이가

나는 private로 찍어놨었고 강사님꺼는 public으로 찍어놨어서 하니까 해결되었다.

 

그리고 중간에 GameOver 후 움직이지 않는 것도 강사님은 .SetActive로 오브젝트를 완전 종료해버리셨지만

뭔가 내가 글로 써놓은

이걸 변경하기 귀찮아서 찾아보니까

CatController에다가 isMoving bool 변수를 지정해서 true로 해놓고 GameOver가 되면 false로 해서 이동하는 코드들을 막아버리면 되는 문제였다.