【Unity3DRPG入门学习笔记第六卷】SetCursor 设置鼠标指针

在上一卷使用了 UnityEvent,还用了序列化,在编辑器界面拖拽绑定事件对象,不太好维护,本卷换一种方式实现,先看 MouseManager.cs 中的更改

using System;
public event Action<Vector3> m_OnMouseClicked;  // 鼠标点击事件

MouseManager.cs

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

public class MouseManager : MonoBehaviour
{
    [Header("鼠标控制移动参数")]
    private RaycastHit m_HitInfo;                   // 射线击中信息
    private static MouseManager m_Instance;         // 单例对象

    public event Action<Vector3> m_OnMouseClicked;  // 鼠标点击事件
    public Texture2D m_Point, m_Doorway, m_Attack, m_Target, m_Arrow;   // 鼠标指针纹理

    // --- private -------------------------------------
    private MouseManager() { }

    private void Awake()
    {
        m_Instance = this;  // 初始化单例
    }

    private void Update()
    {
        SetCursorTexture(); // 切换鼠标贴图
        MouseControl();     // 鼠标控制
    }

    // --- public --------------------------------------
    public static MouseManager GetInstance()
    {
        if (m_Instance == null)
            m_Instance = new MouseManager();
        return m_Instance;
    }


    // --- private -------------------------------------
    /// <summary>
    /// @brief 切换鼠标贴图
    /// </summary>
    private void SetCursorTexture()
    {
        // 获取相机到鼠标点击点的射线
        Ray ray = Camera.main.ScreenPointToRay(Input.mousePosition);

        if (Physics.Raycast(ray, out m_HitInfo))
        {
            // 更换鼠标纹理
            switch (m_HitInfo.collider.gameObject.tag)
            {
                case "Ground":
                    Cursor.SetCursor(m_Target, new Vector2(16, 16), CursorMode.Auto);
                    break;
            }
        }
    }

    /// <summary>
    /// @brief 鼠标控制
    /// </summary>
    private void MouseControl()
    {
        // 如果在边界内点击了左键
        if (Input.GetMouseButtonDown(0) && m_HitInfo.collider != null)
        {
            if (m_HitInfo.collider.gameObject.CompareTag("Ground")) // 如果是地面
                m_OnMouseClicked?.Invoke(m_HitInfo.point);          // 如果对象不为空,则调用所有已注册的回调
        }
    }
}

PlayerController.cs

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

public class PlayerController : MonoBehaviour
{
    private NavMeshAgent m_Agent;   // 导航网格动力源

    private void Awake()
    {
        m_Agent = GetComponent<NavMeshAgent>();
    }

    private void Start()
    {
        // 添加事件调用的方法
        MouseManager.GetInstance().m_OnMouseClicked += MoveToTarget;
    }

    private void Update()
    {
        
    }

    /// <summary>
    /// @brief 移动到目标点
    /// </summary>
    /// <param name="target"></param>
    public void MoveToTarget(Vector3 target)
    {
        m_Agent.destination = target;
    }
}

本卷演示



The End.

posted @ 2022-12-16 13:41  AnnihilateSword  阅读(52)  评论(0编辑  收藏  举报