🎯 Unity 技术文档:3D 第一人称任务指示器
📌 功能概述
该脚本用于在 Unity 3D 第一人称视角 中实现任务指示器功能。
当目标在摄像机视野内时,指示器会显示在屏幕对应位置;当目标在视野外时,指示器会移动到屏幕边缘并旋转箭头指向目标方向。
🛠️ 使用说明
- KeyButton:UI 图像,用作指示器(通常是箭头或按钮图标)。
- target:需要跟踪的目标对象。
- mainCamera:场景中的主摄像机。
- indicator:UI 元素的 RectTransform,用于定位和旋转。
📄 完整代码
using UnityEngine;
using UnityEngine.UI;
public class InteractiveIndicator : MonoBehaviour
{
public Image KeyButton;
public Transform target;
Camera mainCamera => Camera.main;
RectTransform indicator => KeyButton.rectTransform;
static Rect rect = new Rect(0, 0, 1, 1);
private void Update()
{
if (target == null || mainCamera == null)
{
return;
}
Vector3 targetViewportPos = mainCamera.WorldToViewportPoint(target.position);
//如果目标在摄像机的视野内
if(targetViewportPos.z>0&&rect.Contains(targetViewportPos))
{
indicator.anchoredPosition=new Vector2((targetViewportPos.x-0.5f)*Screen.width,
(targetViewportPos.y-0.5f)*Screen.height);
indicator.rotation = Quaternion.identity;
}
else
{
Vector3 screenCenter = new Vector3(Screen.width, Screen.height, 0) / 2;
Vector3 targetScreenPos = mainCamera.WorldToScreenPoint(target.position);
//确保目标在摄像机前方
if(targetScreenPos.z<0)
{
targetScreenPos *= -1;
}
Vector3 directionFromCenter = (targetScreenPos - screenCenter).normalized;
//计算与屏幕边缘的交点
float x = screenCenter.x / Mathf.Abs(directionFromCenter.y);
float y = screenCenter.x / Mathf.Abs(directionFromCenter.x);
float d = Mathf.Min(x, y);
Vector3 edgePosition = screenCenter + directionFromCenter * d;
//将z坐标设置为0以保持在UI层
edgePosition.z = 0;
indicator.position = edgePosition;
//计算角度
float angle = Mathf.Atan2(directionFromCenter.y, directionFromCenter.x) * Mathf.Rad2Deg;
//旋转箭头以指向目标
indicator.rotation = Quaternion.Euler(0, 0, angle + 90);
}
}
}
📊 工作流程
-
检测目标是否在摄像机视野内
- 使用
WorldToViewportPoint判断目标是否在rect范围内。 - 若在视野内,则将 UI 指示器定位到屏幕对应位置。
- 使用
-
目标在视野外时
- 计算目标与屏幕中心的方向向量。
- 将指示器移动到屏幕边缘交点。
- 旋转指示器箭头,使其指向目标方向。
链接:【游戏中追踪目标指向箭头怎么做?一个脚本解决2D3D游戏屏幕贴边指向目标的UI指示标记,Unity中快速实现】https://www.bilibili.com/video/BV1uKBXYPE7w?vd_source=256a31ec907fa4985a200f42dceb1035

浙公网安备 33010602011771号