Menu
CoddyTech

자라기

Coddy의 Unity 게임: 3D 스네이크 코스 레슨. 14개 중 8번째.

먹이를 먹으면 뱀의 몸통이 한 칸 길어집니다. 새 몸통은 이동하기 전에 꼬리 끝이 있던 자리에 생깁니다. 꼬리가 앞으로 이동하고, 새 몸통이 꼬리 끝이 비운 칸을 채우므로 뱀은 뒤쪽부터 자랍니다.

꼬리가 이동하면 그 칸은 비게 되므로, 먼저 그 위치를 기억해 두세요. 그런 다음 머리가 먹이에 도달했을 때 그 자리에 몸통을 인스턴스화하고 목록에 추가하면, 다음 이동부터 몸통이 뱀을 따라갑니다. 만들어졌지만 목록에 추가되지 않은 몸통은 움직이지 않습니다. 기차도 같은 방식으로 뒤쪽에 객차를 추가합니다.

Vector3 back = wagons[wagons.Count - 1].position;
// ... 기차가 계속 움직인다 ...
Transform wagon = Instantiate(wagonPrefab, back, Quaternion.identity);
wagons.Add(wagon);

Eat()를 호출하기 전에 몸통을 늘리세요. Eat()는 먹이를 이동시키며, 다음 강의에서는 새 몸통을 포함해 뱀이 차지하지 않는 칸을 찾도록 먹이 이동 로직을 수정합니다.

challenge icon

챌린지

중급

먹이를 먹을 때마다 꼬리에 세그먼트가 하나 추가됩니다.

  1. Snake에 public Transform segmentPrefab;을 추가하세요(씬에서 연결합니다).
  2. Step()에서 꼬리가 움직이기 전에 Vector3 tailEnd를 저장하세요. 꼬리가 비어 있으면 마지막 세그먼트의 칸을, 비어 있으면 머리의 칸을 저장합니다.
  3. 먹이를 먹으면 Instantiate(segmentPrefab, tailEnd, Quaternion.identity)를 tail에 추가한 다음 Eat()을 호출하세요.

‘플레이’를 누르고 먹이를 몇 개 먹어 보세요. 먹을 때마다 뱀이 큐브 하나만큼 자랍니다. 그런 다음 ‘확인’을 누르세요.

직접 해보기

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

public class Snake : MonoBehaviour
{
    public float tick = 0.15f;   // 두 이동 사이의 시간(초)
    public int edge = 7;         // 보드의 칸은 -edge부터 edge까지 이어진다
    public bool alive = true;
    public List<Transform> tail = new List<Transform>();
    private float timer;
    private Vector3 direction = Vector3.right;       // 머리가 마지막 이동에서 움직인 방향
    private Vector3 nextDirection = Vector3.right;   // 다음 이동을 기다리는 방향 전환

    void Update()
    {
        if (!alive) return;

        Keyboard keyboard = Keyboard.current;
        if (keyboard != null)
        {
            if (keyboard.upArrowKey.wasPressedThisFrame || keyboard.wKey.wasPressedThisFrame) Turn(Vector3.forward);
            if (keyboard.downArrowKey.wasPressedThisFrame || keyboard.sKey.wasPressedThisFrame) Turn(Vector3.back);
            if (keyboard.leftArrowKey.wasPressedThisFrame || keyboard.aKey.wasPressedThisFrame) Turn(Vector3.left);
            if (keyboard.rightArrowKey.wasPressedThisFrame || keyboard.dKey.wasPressedThisFrame) Turn(Vector3.right);
        }

        timer += Time.deltaTime;
        if (timer >= tick)
        {
            timer -= tick;
            Step();
        }
    }

    void Turn(Vector3 newDirection)
    {
        if (newDirection != -direction)
        {
            nextDirection = newDirection;
        }
    }

    void Step()
    {
        direction = nextDirection;
        Vector3 next = transform.position + direction;
        if (Mathf.Abs(next.x) > edge || Mathf.Abs(next.z) > edge)
        {
            Die();
            return;
        }

        for (int i = tail.Count - 1; i > 0; i--)
        {
            tail[i].position = tail[i - 1].position;
        }
        if (tail.Count > 0)
        {
            tail[0].position = transform.position;
        }
        transform.position = next;

        if (GameManager.Instance.IsFood(next))
        {
            GameManager.Instance.Eat();
        }
    }

    void Die()
    {
        alive = false;
    }
}

Unity 게임: 3D 스네이크의 모든 레슨

직접 연습해 보세요: Unity 플레이그라운드