我的光线投射没有正确检测到物体
My raycast is not detecting objects properly
我正在尝试为 2.5d 游戏创建一个 CameraFollow 脚本,其中相机以 60 度倾斜角跟随玩家,但当玩家隐藏在墙后时,相机使用 90 度的鹰眼视角。为此,我从相机到播放器进行光线投射,从相机到播放器的确切距离。如果发生碰撞,则采用鹰视图,否则使用普通视图。这是我的代码:
using UnityEngine;
public class CameraFollow : MonoBehaviour
{
private float distance = 10;
private Vector3 offset;
private Vector3 eagle_offset;
public Transform target;
public float smoothSpeed = 5.0f;
void Start() {
offset = new Vector3(0.0f, 1.5f, -1.0f).normalized * distance;
eagle_offset = new Vector3(0.0f, 1.0f, 0.0f).normalized * distance;
}
void LateUpdate()
{
Vector3 desiredPosition = target.position + offset;
Vector3 smoothedPosition;
RaycastHit hit;
Vector3 direction = (desiredPosition - target.position).normalized;
if (Physics.Raycast(desiredPosition, direction, out hit, distance)) {
smoothedPosition = Vector3.Lerp(transform.position, target.position + eagle_offset, Time.deltaTime * smoothSpeed );
}
else {
smoothedPosition = Vector3.Lerp(transform.position, desiredPosition, Time.deltaTime * smoothSpeed);
}
transform.position = smoothedPosition;
transform.LookAt(target);
}
}
首先,我最讨厌的是 lerp。 Lerp 是线性插值,从第一个参数到第二个参数,第三个参数是 0 到 1 之间的值,它确定第一个参数 (0) 和第二个参数 (1) 之间的“混合”。
如果您遇到相机抖动,那么您可能正在使用物理学,而问题是 FixedUpdate 上的物理学更新,而 put 应该很少与 Update 重合。
对于你的问题,如果我们看下面的定义:
Vector3 desiredPosition = target.position + offset;
然后看下面的:
Vector3 direction = (desiredPosition - target.position).normalized;
那么你可以看到方向是(目标位置+偏移量)-目标位置,也就是说你的“方向”正好等于偏移量。
所以,这里有几点说明。
- 如果您尝试从相机向目标投射光线,我建议您首先使用
transform.LookAt(target);
,然后您可以只使用 transform.forward
作为方向。 transform.position
将是光线投射命令中的原点或“来自”。
- 我建议将此脚本放在一台摄像机上,并将第二台摄像机作为“鹰”视图。考虑存在障碍物的情况 - 你的光线投射检测到命中并翻转到鹰视图,那里没有障碍物,所以你翻转回正常视图,它仍然被阻挡,所以它翻转回来,等等。如果你有两个摄像头,那么你可以每帧从主摄像头进行光线投射,如果它被遮挡,你只需禁用主摄像头并启用鹰摄像头,如果它没有被遮挡,那么你做相反的事情。
我正在尝试为 2.5d 游戏创建一个 CameraFollow 脚本,其中相机以 60 度倾斜角跟随玩家,但当玩家隐藏在墙后时,相机使用 90 度的鹰眼视角。为此,我从相机到播放器进行光线投射,从相机到播放器的确切距离。如果发生碰撞,则采用鹰视图,否则使用普通视图。这是我的代码:
using UnityEngine;
public class CameraFollow : MonoBehaviour
{
private float distance = 10;
private Vector3 offset;
private Vector3 eagle_offset;
public Transform target;
public float smoothSpeed = 5.0f;
void Start() {
offset = new Vector3(0.0f, 1.5f, -1.0f).normalized * distance;
eagle_offset = new Vector3(0.0f, 1.0f, 0.0f).normalized * distance;
}
void LateUpdate()
{
Vector3 desiredPosition = target.position + offset;
Vector3 smoothedPosition;
RaycastHit hit;
Vector3 direction = (desiredPosition - target.position).normalized;
if (Physics.Raycast(desiredPosition, direction, out hit, distance)) {
smoothedPosition = Vector3.Lerp(transform.position, target.position + eagle_offset, Time.deltaTime * smoothSpeed );
}
else {
smoothedPosition = Vector3.Lerp(transform.position, desiredPosition, Time.deltaTime * smoothSpeed);
}
transform.position = smoothedPosition;
transform.LookAt(target);
}
}
首先,我最讨厌的是 lerp。 Lerp 是线性插值,从第一个参数到第二个参数,第三个参数是 0 到 1 之间的值,它确定第一个参数 (0) 和第二个参数 (1) 之间的“混合”。
如果您遇到相机抖动,那么您可能正在使用物理学,而问题是 FixedUpdate 上的物理学更新,而 put 应该很少与 Update 重合。
对于你的问题,如果我们看下面的定义:
Vector3 desiredPosition = target.position + offset;
然后看下面的:
Vector3 direction = (desiredPosition - target.position).normalized;
那么你可以看到方向是(目标位置+偏移量)-目标位置,也就是说你的“方向”正好等于偏移量。
所以,这里有几点说明。
- 如果您尝试从相机向目标投射光线,我建议您首先使用
transform.LookAt(target);
,然后您可以只使用transform.forward
作为方向。transform.position
将是光线投射命令中的原点或“来自”。 - 我建议将此脚本放在一台摄像机上,并将第二台摄像机作为“鹰”视图。考虑存在障碍物的情况 - 你的光线投射检测到命中并翻转到鹰视图,那里没有障碍物,所以你翻转回正常视图,它仍然被阻挡,所以它翻转回来,等等。如果你有两个摄像头,那么你可以每帧从主摄像头进行光线投射,如果它被遮挡,你只需禁用主摄像头并启用鹰摄像头,如果它没有被遮挡,那么你做相反的事情。