Controler de jucător RTS și MOBA pentru Unity

În jocurile video, termenul RTS înseamnă strategie în timp real.

Diferența dintre RTS și jocurile convenționale cu împușcături la prima / a treia persoană este că personajele sunt controlate folosind indicatorul mouse-ului, mai degrabă decât butoanele obișnuite W, A, S și D.

Jucătorului i se oferă o vedere de vultur a câmpului de luptă cu capacitatea de a da ordine trupelor, fără a le controla direct. Exemple de jocuri RTS sunt Warcraft, Starcraft, Cassacks etc.

Captură de ecran pentru jocul Warcraft 3

Pe de altă parte, MOBA înseamnă Multiplayer Online Battle Arena, este un subgen oarecum mai nou al jocurilor RTS în care jucătorul controlează doar un personaj în loc de multe.

Exemple de astfel de jocuri sunt League of Legends și Dota 2.

În acest tutorial, voi arăta cum să creez un controler în stil RTS/MOBA în Unity.

Pasul 1: Să creăm scripturile necesare

Acest tutorial este destul de simplu, deoarece necesită un singur script.

RTSPlayerController.cs

//You are free to use this script in Free or Commercial projects
//sharpcoderblog.com @2018

using UnityEngine;
using UnityEngine.AI;

[RequireComponent(typeof(NavMeshAgent))]

public class RTSPlayerController : MonoBehaviour
{
    public Camera playerCamera;
    public Vector3 cameraOffset;
    public GameObject targetIndicatorPrefab;
    NavMeshAgent agent;
    GameObject targetObject;

    // Use this for initialization
    void Start()
    {
        agent = GetComponent<NavMeshAgent>();
        //Instantiate click target prefab
        if (targetIndicatorPrefab)
        {
            targetObject = Instantiate(targetIndicatorPrefab, Vector3.zero, Quaternion.identity) as GameObject;
            targetObject.SetActive(false);
        }
    }

    // Update is called once per frame
    void Update()
    {
#if (UNITY_ANDROID || UNITY_IOS || UNITY_WP8 || UNITY_WP8_1) && !UNITY_EDITOR
            //Handle mobile touch input
            for (var i = 0; i < Input.touchCount; ++i)
            {
                Touch touch = Input.GetTouch(i);

                if (touch.phase == TouchPhase.Began)
                {
                    MoveToTarget(touch.position);
                }
            }
#else
        //Handle mouse input
        if (Input.GetKeyDown(KeyCode.Mouse0))
        {
            MoveToTarget(Input.mousePosition);
        }
#endif

        //Camera follow
        playerCamera.transform.position = Vector3.Lerp(playerCamera.transform.position, transform.position + cameraOffset, Time.deltaTime * 7.4f);
        playerCamera.transform.LookAt(transform);
    }

    void MoveToTarget(Vector2 posOnScreen)
    {
        //print("Move To: " + new Vector2(posOnScreen.x, Screen.height - posOnScreen.y));

        Ray screenRay = playerCamera.ScreenPointToRay(posOnScreen);

        RaycastHit hit;
        if (Physics.Raycast(screenRay, out hit, 75))
        {
            agent.destination = hit.point;

            //Show marker where we clicked
            if (targetObject)
            {
                targetObject.transform.position = agent.destination;
                targetObject.SetActive(true);
            }
        }
    }
}

Pasul 2

Acum să setăm un controler de jucător și un nivel de joc.

  • Creați un nou GameObject și apelați-l 'RTSPlayer'
  • Atașați scriptul RTSPlayerController.cs la acesta (NOTĂ: La atașare, va adăuga automat o altă componentă numită NavMeshAgent, această componentă va fi necesară mai târziu)

  • Adăugați un corp de jucător (în cazul meu voi folosi o capsulă simplă cu un cube, dar puteți adăuga un model de jucător dacă aveți). Reduceți-l până la dimensiunea dorită.
  • Mutați modelul jucătorului în interiorul 'RTSPlayer' GameObject (NOTĂ: înainte de a fi părinte, asigurați-vă că 'RTSPlayer' este plasat în partea de jos a modelului jucătorului)

  • Selectați 'RTSPlayer' și în NavMeshAgent ajustați Raza și Înălțimea până când se potrivesc cu modelul jucătorului

  • Următorul este să creați un Indicator țintă prefab. Acesta este doar un simplu GameObject cu un Quad care va indica unde am făcut clic pe hartă.

Puteți folosi textura de mai jos:

indicator al țintei strategiei în timp real

  • Și, în sfârșit, selectați 'RTSPlayer' și atribuiți toate variabilele necesare în scriptul RTSPlayerController:

Player Camera - se explică de la sine, aceasta poate fi orice cameră

Camera Offset - cât de departe ar trebui să fie camera de player

Target Indicator Prefab - prefabricatul pe care tocmai l-am creat

În modul Play, veți observa că făcând clic pe hartă nu îl face pe jucător să se miște. Asta pentru că avem un ultim lucru de făcut, care este Bake a Navigation Mesh (Navmesh):

  • Selectați toate obiectele care fac parte din hartă și marcați-le statice:

  • Accesați Fereastră -> AI -> Navigare

  • Sub fila Coace, modificați valorile Razei agentului și Înălțimii agentului (acestea ar trebui să se potrivească cu valorile din NavMeshAgent), apoi faceți clic pe Coacere.

  • După ce s-a terminat coacerea, veți observa o plasă conturată albăstruie, care reprezintă zona de mers pe jos.

NOTĂ: Pentru a împiedica jucătorul să treacă peste dealuri, întoarceți-vă la fila Coace și micșorați unghiul Pantă maximă, apoi refaceți rețeaua de navigare.

Mult mai bine!

În cele din urmă, reveniți la modul Play și faceți clic stânga undeva pe hartă.

Jucătorul ar trebui să se deplaseze acum spre țintă evitând obstacolele:

Sharp Coder Video player

Sfat: Modificați valoarea vitezei, vitezei unghiulare și accelerației la NavMeshagent pentru a se potrivi nevoilor dvs.

Articole sugerate
Controler de jucător planetar bazat pe corp rigid pentru Unity
Controler de avion pentru Unity
Player 3D și 2D Wall Jump Tutorial pentru Unity
Tutorial de sus în jos pentru controlerul jucătorului pentru Unity
Controler de elicopter pentru Unity
Adăugarea suportului pentru salt dublu la un controler de caractere 2D platformer în Unity
Controler auto pentru Unity