RPG角色控制

作者:追风剑情 发布于:2020-3-19 14:09 分类:Unity3d

一、在资源商店下载一个场景和一个带动画的角色
333.png

1111.png

二、调整角色动画控制器
222.png

三、编写角色控制器脚本并挂到Player对象上

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.AI;
/// <summary>
/// 玩家角色控制器
/// </summary>
public class PlayerController : MonoBehaviour
{
    private NavMeshAgent agent;
    private Animator animator;
    private Transform mTransform;
    private AnimationState animationState = AnimationState.idle;

    private void Awake()
    {
        mTransform = transform;
        if (agent == null)
            agent = this.GetComponent<NavMeshAgent>();
        if (animator == null)
            animator = this.GetComponent<Animator>();
    }

    void Start()
    {
        animator.CrossFade(animationState.ToString(), 0.5f, 0, 0);
    }

    void Update()
    {
        //导航到鼠标点击位置
        if (Input.GetMouseButtonDown(0))
        {
            Vector3 mousePosition = Input.mousePosition;
            Ray ray = Camera.main.ScreenPointToRay(mousePosition);
            RaycastHit hit;
            if (Physics.Raycast(ray, out hit))
            {
                agent.SetDestination(hit.point);
                if (animationState != AnimationState.walk)
                {
                    animationState = AnimationState.walk;
                    animator.CrossFade(animationState.ToString(), 0.3f, 0, 0);
                }
            }
        }

        //到达终点后切换成空闲状态
        if (animationState == AnimationState.walk &&
            Vector3.Distance(mTransform.position, agent.destination) < 0.01f)
        {
            animationState = AnimationState.idle;
            animator.CrossFade(animationState.ToString(), 0.5f, 0, 0);
        }

        //通过按键切换到其他动作
        if (Input.GetKeyDown(KeyCode.A))
        {
            if (animationState != AnimationState.attack)
            {
                animationState = AnimationState.attack;
                animator.CrossFade(animationState.ToString(), 0.2f, 0, 0);
            }
        }
        else if (Input.GetKeyDown(KeyCode.S))
        {
            if (animationState != AnimationState.active)
            {
                animationState = AnimationState.active;
                animator.CrossFade(animationState.ToString(), 0.2f, 0, 0);
            }
        }
        else if (Input.GetKeyDown(KeyCode.F))
        {
            if (animationState != AnimationState.passive)
            {
                animationState = AnimationState.passive;
                animator.CrossFade(animationState.ToString(), 0.2f, 0, 0);
            }
        }
        else if (Input.GetKeyDown(KeyCode.D))
        {
            if (animationState != AnimationState.dead)
            {
                animationState = AnimationState.dead;
                animator.CrossFade(animationState.ToString(), 0.2f, 0, 0);
            }
        }
    }
}

public enum AnimationState
{
    idle,
    walk,
    attack,
    active,
    passive,
    dead
}


四、编写摄像机跟随脚本并挂到Camera对象上

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.AI;
/// <summary>
/// 摄像机跟随玩家
/// </summary>
public class FollowCamera : MonoBehaviour
{
    public Transform player;
    public bool fixCamera;
    private Transform mTransform;
    private Vector3 originPosition;
    private Vector3 offset;
    private float distance;
    private bool rightMouseDown;
    private Vector3 mouseLastPosition;
    private Vector3 playerHeadPosition;
    private float agentHeight;

    void Awake()
    {
        NavMeshAgent agent = player.GetComponent<NavMeshAgent>();
        agentHeight = agent.height;
        mTransform = transform;
        originPosition = mTransform.position;
        //offset相对于头顶坐标
        playerHeadPosition = player.position;
        playerHeadPosition.y += agentHeight;
        offset = originPosition - playerHeadPosition;
        distance = Vector3.Distance(originPosition, playerHeadPosition);
    }

    void Update()
    {
        if (fixCamera)
        {
            //自动跟随
            playerHeadPosition = player.position;
            playerHeadPosition.y += agentHeight;
            mTransform.position = playerHeadPosition + offset;

            //支持鼠标右键旋转镜头
            if (Input.GetMouseButtonDown(1))
            {
                rightMouseDown = true;
                mouseLastPosition = Input.mousePosition;
            }
            if (Input.GetMouseButtonUp(1))
                rightMouseDown = false;

            if (rightMouseDown)
            {
                Vector3 mousePosition = Input.mousePosition;
                float deltaX = mousePosition.x - mouseLastPosition.x;
                mTransform.RotateAround(player.position, Vector3.up, deltaX);
                mouseLastPosition = mousePosition;
                offset = mTransform.position - playerHeadPosition;
            }

            //支持鼠标滚轮推拉镜头
            Vector2 mouseScrollDelta = Input.mouseScrollDelta;
            if (mouseScrollDelta.y > 0) //镜头拉近
            {
                if (Vector3.Magnitude(offset) > distance * 0.5f)
                    offset *= 0.9f;
            }
            else if (mouseScrollDelta.y < 0) //镜头拉远
            {
                if (Vector3.Magnitude(offset) < distance * 2)
                    offset *= 1.1f;
            }
        }
        else
        {
            //自动跟随&旋转镜头
            Vector3 back = -player.forward;
            Vector3 camPos = player.position + back * distance;
            camPos.y = originPosition.y;
            mTransform.position = camPos;
            mTransform.LookAt(player);
        }
    }
}


运行测试
552.gif

标签: Unity3d

Powered by emlog  蜀ICP备18021003号-1   sitemap

川公网安备 51019002001593号