Unity3D使用鼠标旋转缩放平移视角

Unity使用鼠标旋转缩放平移视角,供大家参考,具体内容如下

用代码在Game界面完美实现Scene界面的操作方法。

使用方法:把脚本挂在相机上,把跟踪的target拖到脚本上。

视角跟踪的是一个空物体,当然如果你是做RPG游戏需要跟踪某一角色的视角,那就不需要中键平移功能,把空物体换成角色就行。

代码主要是分三部分功能进行实现。

1.右键拖动控制视角的旋转;
2.滚轮旋转控制视角的缩放;
3.中键拖动控制视角的平移。

右键拖动控制旋转主要是用GetAxis获得鼠标在x方向与y方向平移的距离,相机的旋转是通过旋转相机本体坐标系的x轴与y轴实现的,重要的是在旋转相机的同时,要控制相机和target物体的相对距离,即同时控制相机绕target物体的旋转。这个网上多数实现都相同,不赘述

中键滚轮控制视角的缩放,定义Distance变量控制相机与target的距离(相机z轴方向的距离),用GetAxis获得滚轮旋转的程度,控制Distance的变动。这里和网上已有的方法也没什么区别。

中键拖动控制视角的平移,之前在网上查找相关的实现,结果实际效果都比较差,所以自己实现了一下。视角的平移是通过获取中键在屏幕坐标系下的平移的方向向量,然后转换为世界坐标系下的target坐标的平移,然后调整相机的位置进行相应的平移以保证旋转和缩放不受影响。

屏幕坐标系的平移转换到世界坐标系下的平移,本质上就是世界坐标系下沿着相机的本体坐标系的x与y轴进行相应的平移。所以只需要求出屏幕坐标系x与y方向的平移,分别乘以相机x与y轴的方向向量,然后与target原来的坐标相加,就可以获得target平移后的位置,再将相机的位置平移过去即实现了视角的平移,这种平移保证了相机平面和target之间的相对距离保持不变。具体代码如下:

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

public class MouseLookTest : MonoBehaviour {

 //相机跟随的目标物体,一般是一个空物体
 public Transform target;
 private int MouseWheelSensitivity = 1; //滚轮灵敏度设置
 private int MouseZoomMin = 1; //相机距离最小值
 private int MouseZoomMax = 20; //相机距离最大值

 private float moveSpeed = 10; //相机跟随速度(中键平移时),采用平滑模式时起作用,越大则运动越平滑

 private float xSpeed = 250.0f; //旋转视角时相机x轴转速
 private float ySpeed = 120.0f; //旋转视角时相机y轴转速

 private int yMinLimit = -360;
 private int yMaxLimit = 360;

 private float x = 0.0f; //存储相机的euler角
 private float y = 0.0f; //存储相机的euler角

 private float Distance = 5; //相机和target之间的距离,因为相机的Z轴总是指向target,也就是相机z轴方向上的距离
 private Vector3 targetOnScreenPosition; //目标的屏幕坐标,第三个值为z轴距离
 private Quaternion storeRotation; //存储相机的姿态四元数
 private Vector3 CameraTargetPosition; //target的位置
 private Vector3 initPosition; //平移时用于存储平移的起点位置
 private Vector3 cameraX; //相机的x轴方向向量
 private Vector3 cameraY; //相机的y轴方向向量
 private Vector3 cameraZ; //相机的z轴方向向量

 private Vector3 initScreenPos; //中键刚按下时鼠标的屏幕坐标(第三个值其实没什么用)
 private Vector3 curScreenPos; //当前鼠标的屏幕坐标(第三个值其实没什么用)
 void Start () {
 //这里就是设置一下初始的相机视角以及一些其他变量,这里的x和y。。。是和下面getAxis的mouse x与mouse y对应
 var angles = transform.eulerAngles;
 x = angles.y;
 y = angles.x;
 CameraTargetPosition = target.position;
 storeRotation = Quaternion.Euler (y + 60, x, 0);
 transform.rotation = storeRotation; //设置相机姿态
 Vector3 position = storeRotation * new Vector3 (0.0F, 0.0F, -Distance) + CameraTargetPosition; //四元数表示一个旋转,四元数乘以向量相当于把向量旋转对应角度,然后加上目标物体的位置就是相机位置了
 transform.position = storeRotation * new Vector3 (0, 0, -Distance) + CameraTargetPosition; //设置相机位置

 // Debug.Log("Camera x: "+transform.right);
 // Debug.Log("Camera y: "+transform.up);
 // Debug.Log("Camera z: "+transform.forward);

 // //-------------TEST-----------------
 // testScreenToWorldPoint();

 }

 void Update () {
 //鼠标右键旋转功能
 if (Input.GetMouseButton (1)) {
 x += Input.GetAxis ("Mouse X") * xSpeed * 0.02f;
 y -= Input.GetAxis ("Mouse Y") * ySpeed * 0.02f;

 y = ClampAngle (y, yMinLimit, yMaxLimit);

 storeRotation = Quaternion.Euler (y + 60, x, 0);
 var position = storeRotation * new Vector3 (0.0f, 0.0f, -Distance) + CameraTargetPosition;

 transform.rotation = storeRotation;
 transform.position = position;
 } else if (Input.GetAxis ("Mouse ScrollWheel") != 0) //鼠标滚轮缩放功能
 {
 if (Distance >= MouseZoomMin && Distance <= MouseZoomMax) {
 Distance -= Input.GetAxis ("Mouse ScrollWheel") * MouseWheelSensitivity;
 }
 if (Distance < MouseZoomMin) {
 Distance = MouseZoomMin;
 }
 if (Distance > MouseZoomMax) {
 Distance = MouseZoomMax;
 }
 var rotation = transform.rotation;

 transform.position = storeRotation * new Vector3 (0.0F, 0.0F, -Distance) + CameraTargetPosition;
 }

 //鼠标中键平移
 if (Input.GetMouseButtonDown (2)) {
 cameraX = transform.right;
 cameraY = transform.up;
 cameraZ = transform.forward;

 initScreenPos = new Vector3 (Input.mousePosition.x, Input.mousePosition.y, targetOnScreenPosition.z);
 Debug.Log ("downOnce");

 //targetOnScreenPosition.z为目标物体到相机xmidbuttonDownPositiony平面的法线距离
 targetOnScreenPosition = Camera.main.WorldToScreenPoint (CameraTargetPosition);
 initPosition = CameraTargetPosition;
 }

 if (Input.GetMouseButton (2)) {
 curScreenPos = new Vector3 (Input.mousePosition.x, Input.mousePosition.y, targetOnScreenPosition.z);
 //0.01这个系数是控制平移的速度,要根据相机和目标物体的distance来灵活选择
 target.position = initPosition - 0.01f * ((curScreenPos.x - initScreenPos.x) * cameraX + (curScreenPos.y - initScreenPos.y) * cameraY);

 //重新计算位置
 Vector3 mPosition = storeRotation * new Vector3 (0.0F, 0.0F, -Distance) + target.position;
 transform.position = mPosition;

 // //用这个会让相机的平移变得更平滑,但是可能在你buttonup时未使相机移动到应到的位置,导致再进行旋转与缩放操作时出现短暂抖动
 //transform.position=Vector3.Lerp(transform.position,mPosition,Time.deltaTime*moveSpeed);

 }
 if (Input.GetMouseButtonUp (2)) {
 Debug.Log ("upOnce");
 //平移结束把cameraTargetPosition的位置更新一下,不然会影响缩放与旋转功能
 CameraTargetPosition = target.position;
 }

 }

 //将angle限制在min~max之间
 static float ClampAngle (float angle, float min, float max) {
 if (angle < -360)
 angle += 360;
 if (angle > 360)
 angle -= 360;
 return Mathf.Clamp (angle, min, max);
 }

 void testScreenToWorldPoint () {
 //第三个坐标指的是在相机z轴指向方向上的距离
 Vector3 screenPoint = Camera.main.WorldToScreenPoint (CameraTargetPosition);
 Debug.Log ("ScreenPoint: " + screenPoint);

 // var worldPosition = Camera.main.ScreenToWorldPoint(new Vector3(1,1,10));
 // Debug.Log("worldPosition: "+worldPosition);
 }
}

实现的效果如下图:

demo工程在此下载:MouseLookDemoWithUnity3D

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持我们。

(0)

相关推荐

  • Unity3D实现鼠标控制旋转转盘

    在培训模拟考试软件中,我们经常会遇到类似用鼠标旋转转盘打开开关的需求.让用户更加真实的操作设备仪器.接下来说下我的解决方案. 因为鼠标操作是在UI平面上,所以我们要先将被操作的模型的世界坐标转换到屏幕坐标上.代码如下: ModelScreenPos = camera.WorldToScreenPoint(Model.transform.position); 这里有个声明,这个模型代表的是转盘,而且要保证模型的中心点在转盘中心.然后我们就要计算鼠标以模型在屏幕坐标为中心点的旋转偏移量.我们开始以鼠

  • Unity3D使用鼠标旋转缩放平移视角

    Unity使用鼠标旋转缩放平移视角,供大家参考,具体内容如下 用代码在Game界面完美实现Scene界面的操作方法. 使用方法:把脚本挂在相机上,把跟踪的target拖到脚本上. 视角跟踪的是一个空物体,当然如果你是做RPG游戏需要跟踪某一角色的视角,那就不需要中键平移功能,把空物体换成角色就行. 代码主要是分三部分功能进行实现. 1.右键拖动控制视角的旋转: 2.滚轮旋转控制视角的缩放: 3.中键拖动控制视角的平移. 右键拖动控制旋转主要是用GetAxis获得鼠标在x方向与y方向平移的距离,相

  • Unity3D实现物体旋转缩放移动效果

    本文实例为大家分享了Unity3D实现物体旋转缩放移动的具体代码,供大家参考,具体内容如下 由于项目运行在安卓上,运用到了插件,比较麻烦.你们可以在触发条件上进行修改,不用插件也可以. 1.下载FingerGestures 插件 下载地址 点击打开链接 2.导入插件,创建场景 将预设Finger Gestures Initializer 拖拽到 Hierarchy 视图中 3.添加脚本,拖拽到摄像机上.创建一个方块拖拽到脚本target 属性上. using UnityEngine; using

  • 图片旋转、鼠标滚轮缩放、镜像、切换图片js代码

    本文实例为大家展示了图片旋转.鼠标滚轮缩放.镜像.切换图片多重效果,提供了详细的代码,分享给大家供大家参考,具体内容如下 具体代码: <!DOCTYPE html> <html lang="zh-cn"> <head> <title>图片旋转,鼠标滚轮缩放,镜像,切换图片</title> <meta charset="utf-8" /> <!--<script type="

  • Android旋转、平移、缩放和透明度渐变的补间动画

    android实现旋转.平移.缩放和透明度渐变的补间动画,具体实现如下: 1.在新建项目的res目录中,创建一个名为anim的目录,并在该目录中创建实现旋转.平移.缩放和透明度渐变的动画资源文件. 透明度渐变的动画资源文件anim_alpha.xml(完全不透明->完全透明->完全不透明) <?xml version="1.0" encoding="utf-8"?> <set xmlns:android="http://sch

  • OpenCV 图像旋转、平移、缩放操作代码

    目录 1 缩放图片 2 翻转图片 2.1 垂直翻转 2.2 水平翻转 2.3 水平垂直翻转 3 平移图片 本文是 OpenCV图像视觉入门之路的第7篇文章,本文详细的进行了图像的缩放 cv2.resize().旋转 cv2.flip().平移 cv2.warpAffine()等操作. 1 缩放图片 缩放就是调整图片的大小,使用cv2.resize()函数实现缩放,可以按照比例缩放,也可以按照指定的大小缩放:也可以指定缩放方法为线性插值INTER_LINEAR. 放过程中有五种插值方式: cv2.

  • Qt图形图像开发曲线图表模块QChart库缩放/平移详细方法与实例

    1.使用QChartView来缩放 (1)用鼠标框选一个矩形,把图放大到这个矩形 QChartView::setRubberBand(QChartView::RectangleRubberBand);//XY方向同时放大到鼠标画出的矩形大小(也可以设置为只放大X轴或Y轴) (2)setRubberBand函数同时也能使鼠标右键,具备缩小图的功能. 2.使用Qchart来平移和缩放 QChart::scroll(-10, 5);//整体平移(-10, 5),两个参数分别为Δx和Δy QChart:

  • Android实现手势滑动多点触摸缩放平移图片效果(二)

    上一篇已经带大家实现了自由的放大缩小图片,简单介绍了下Matrix:具体请参考:Android实现手势滑动多点触摸缩放平移图片效果,本篇继续完善我们的ImageView. 首先加入放大后的移动. 1.自由的进行移动 我们在onTouchEvent里面,加上移动的代码,当然了,必须长或宽大于屏幕才可以移动~~~ @Override public boolean onTouch(View v, MotionEvent event) { mScaleGestureDetector.onTouchEve

  • JS实现禁止用户使用Ctrl+鼠标滚轮缩放网页的方法

    本文实例讲述了JS实现禁止用户使用Ctrl+鼠标滚轮缩放网页的方法.分享给大家供大家参考,具体如下: 为什么会有人会使用ctrl+鼠标滚轮缩放网页?坚决禁止! <html> <head> <title>测试</title> <script language="javascript"> var scrollFunc=function(e){ e=e || window.event; if(e.wheelDelta &&a

  • 跟随鼠标旋转的文字

    if (document.all) { yourLogo = "我们欢迎您的光临"; logoFont = "宋体"; logoColor = "000000"; yourLogo = yourLogo.split(''); L = yourLogo.length; TrigSplit = 360 / L; Sz = new Array() logoWidth = 100; logoHeight = -30; ypos = 0; xpos = 0

随机推荐