3D 简易制作福运来源码出售摄像机围绕物体随鼠标旋转效果

梗概:
一. 摄像机围绕福运来源码出售QQ2952777280【话仙源码论坛】hxforum.com【木瓜源码论坛】papayabbs.com 目标物体旋转, 即摄像机离目标物体有一定的距离且旋转轴心为该物体的位置.

二. 当目标物体被障碍物挡住后, 需要将摄像机移动到障碍物前方能看见目标物体的位置.

思路:
一. 摄像机绕轴心旋转, 可以在轴心处创建一个空物体, 将摄像机设为该轴心的子物体. 如图:

这样便可以简单地实现摄像机旋转轴心 (注意: 旋转时应旋转轴心而不是单独旋转摄像机) . 还应注意, 如果摄像机的目标物体可以移动的话, 就应每帧将轴心的坐标设为目标物体的坐标 (尽量不要直接将轴心设为目标物体的子物体! 除非有特别需要) .

二. 当目标物体被障碍物挡住后, 可以在目标物体处发射一条射线, 射线原点就是目标物体的坐标 (也就是轴心) , 射线方向就是从原点到摄像机的方向. 此时射线的碰撞点就是将要把摄像机调整到的位置.

三. 当将摄像机移动到后方没有障碍物的位置时, 就应将摄像机移回至原距离.

过程:
创建任意目标物体;

创建一个空物体并命名, 这个空物体就是轴心, 并将其 Tag 设为 "3rdCameraAxle":

或者将其 Tag 设为你喜欢的一个都可以;

创建摄像机, 将其 Tag 设为 "MainCamera", 并设为刚创建的轴心的子物体;

创建任意障碍物.

代码:
一. 此时绕物体旋转摄像机便可简化为直接旋转轴心, 代码也简化了许多:

定义鼠标灵敏度:

public float mouseSensitivity = 2;
定义目标物体的 Transform :

public Transform targetTrans;
定义轴心 Transform 与轴心旋转角度:

Transform thirdPCamAxle;
Vector3 thirdPCamEuler;
在 void Start() 下对其赋值:

void Start () {
thirdPCamAxle = GameObject.FindGameObjectWithTag("3rdCameraAxle").transform; //括号里的引号中也可以写上你自己对轴心设的 Tag.
thirdPCamEuler = thirdPCamAxle.localEulerAngles; //推荐写 localEulerAngles, 要不之后处理起来会比较麻烦.
}
定义摄像机:

Camera thirdPCam;
在 void Start() 下对其赋值:

void Start () {
thirdPCam = Camera.main;
}
定义并赋值摄像机离物体的最大距离, 摄像机离物体的当前距离:

float camForwardMaxDistance = 9;
float camForwardDistance;
float camBackDistance;
在 void Update() 下写:

复制代码
thirdPCamAxle.position = targetTrans.position; //将摄像机旋转轴心位置设为目标物体位置
//定义旋转量
float mouseX = Input.GetAxis("Mouse X") mouseSensitivity;
float mouseY = Input.GetAxis("Mouse Y")
mouseSensitivity;
thirdPCamEuler.y += mouseX; //控制摄像机左右旋转
//控制摄像机上下旋转, 并且上下旋转范围不能超过90°或-90°, 此方法适用于 localEulerAngles.
if (thirdPCamEuler.z < 90 && mouseY > 0) { thirdPCamEuler.z += mouseY; }
if (thirdPCamEuler.z > -90 && mouseY < 0) { thirdPCamEuler.z += mouseY; }
thirdPCamAxle.localEulerAngles = thirdPCamEuler; //将旋转量应用到摄像机上.
复制代码
至此, 控制摄像机旋转完成. 此部分代码如下:

复制代码
1 using System.Collections;
2 using System.Collections.Generic;
3 using UnityEngine;
4 ​
5 public class ThirdPCamC : MonoBehaviour {
6 public float mouseSensitivity = 2;
7 public Transform targetTrans;
8 ​
9 Transform thirdPCamAxle;
10 Vector3 thirdPCamEuler;
11 ​
12 Camera thirdPCam;
13 float camForwardMaxDistance = 9;
14 float camForwardDistance;
15 float camBackDistance;
16 ​
17 void Start () {
18 thirdPCamAxle = GameObject.FindGameObjectWithTag("3rdCameraAxle").transform;
19 thirdPCamEuler = thirdPCamAxle.localEulerAngles;
20 ​
21 thirdPCam = Camera.main;
22 }
23
24 void Update () {
25 thirdPCamAxle.position = targetTrans.position;
26 ​
27 float mouseX = Input.GetAxis("Mouse X") mouseSensitivity;
28 float mouseY = Input.GetAxis("Mouse Y")
mouseSensitivity;
29 thirdPCamEuler.y += mouseX;
30 if (thirdPCamEuler.z < 90 && mouseY > 0) { thirdPCamEuler.z += mouseY; }
31 if (thirdPCamEuler.z > -90 && mouseY < 0) { thirdPCamEuler.z += mouseY; }
32 thirdPCamAxle.localEulerAngles = thirdPCamEuler;
33 }
34 }
复制代码
二. 摄像机避开障碍物, 并在后方没有障碍物时移回原距离 (原距离可通过设置对 camForwardMaxDistance 的赋值来改变):

在 void Update() 下写:

复制代码
Ray camForwardRay = new Ray(thirdPCam.transform.position, thirdPCam.transform.forward); //在摄像机处发射一条向前的射线, 用来检测摄像机当前离目标的距离 (此处不必担心射线碰撞处是障碍物的情况).
RaycastHit forwardRayHit; //定义射线碰撞.
if (Physics.Raycast(camForwardRay, out forwardRayHit)) //当射线有碰撞物时 (也就是目标物体),
{
camForwardDistance = Vector3.Distance(thirdPCam.transform.position, forwardRayHit.point); //计算从摄像机到碰撞点的距离 (碰撞点也可以改为目标物体的位置).
}

Vector3 dir = thirdPCam.transform.position - targetTrans.position; //定义从目标物体到摄像机的方向.
dir = dir.normalized; //将方向单位化.
Ray ray = new Ray(targetTrans.position, dir); //在目标物体处发射一条射线, 方向即为刚刚定义的向量.
RaycastHit hit; //定义射线碰撞.
if (Physics.Raycast(ray, out hit)) //当该射线有碰撞, 即目标物体被障碍物挡住时,
{
thirdPCam.transform.position = hit.point; //将摄像机位置设为碰撞点位置.
}
else //如果没有碰撞, 即目标物体没有被障碍物挡住,
{
if (camForwardDistance < camForwardMaxDistance) //并且当前距离没有超过最大距离时,
{
thirdPCam.transform.Translate(Vector3.back Time.deltaTime 5); //将摄像机缓慢后移至最大距离.
}
}
复制代码
全部代码如下:

复制代码
1 using System.Collections;
2 using System.Collections.Generic;
3 using UnityEngine;
4 ​
5 public class ThirdPCamC : MonoBehaviour {
6 public float mouseSensitivity = 2;
7 public Transform targetTrans;
8 ​
9 Transform thirdPCamAxle;
10 Vector3 thirdPCamEuler;
11 ​
12 Camera thirdPCam;
13 float camForwardMaxDistance = 9;
14 float camForwardDistance;
15 float camBackDistance;
16 ​
17 void Start () {
18 thirdPCamAxle = GameObject.FindGameObjectWithTag("3rdCameraAxle").transform;
19 thirdPCamEuler = thirdPCamAxle.localEulerAngles;
20 ​
21 thirdPCam = Camera.main;
22 }
23
24 void Update () {
25 thirdPCamAxle.position = targetTrans.position;
26 ​
27 float mouseX = Input.GetAxis("Mouse X") mouseSensitivity;
28 float mouseY = Input.GetAxis("Mouse Y")
mouseSensitivity;
29 thirdPCamEuler.y += mouseX;
30 if (thirdPCamEuler.z < 90 && mouseY > 0) { thirdPCamEuler.z += mouseY; }
31 if (thirdPCamEuler.z > -90 && mouseY < 0) { thirdPCamEuler.z += mouseY; }
32 thirdPCamAxle.localEulerAngles = thirdPCamEuler;
33 ​
34 Ray camForwardRay = new Ray(thirdPCam.transform.position, thirdPCam.transform.forward);
35 RaycastHit forwardRayHit;
36 if (Physics.Raycast(camForwardRay, out forwardRayHit))
37 {
38 camForwardDistance = Vector3.Distance(thirdPCam.transform.position, forwardRayHit.point);
39 }
40 ​
41 Vector3 dir = thirdPCam.transform.position - targetTrans.position;;
42 dir = dir.normalized;
43 Ray ray = new Ray(targetTrans.position, dir);
44 RaycastHit hit;
45 if (Physics.Raycast(ray, out hit))
46 {
47 Debug.DrawLine(ray.origin, hit.point, Color.green);
48 thirdPCam.transform.position = hit.point;
49 }
50 else
51 {
52 if (camForwardDistance < camForwardMaxDistance)
53 {
54 thirdPCam.transform.Translate(Vector3.back Time.deltaTime 5);
55 }
56 }
57 }
58 }

猜你喜欢

转载自blog.51cto.com/13902713/2152776