主要有单指移动3D物体、单指旋转3D物体、双指缩放3D物体。

基类

using UnityEngine;
using System.Collections;
/// <summary>
/// 手势操作父类,并用于互斥三种手势
/// </summary>
public class GestureControl : MonoBehaviour
{
//记录手势状态:
//-1——没有任何手势在操作
//0——移动手势正在操作
//1——旋转手势正在操作
//2——缩放手势正在操作
public static int status = -;
//用于记录触碰物体的时间(区分同为单指时移动与旋转,详见相应代码)
public static float TouchTime = ; protected bool isSelected = false; //判断是否事先选择到了某物体
protected void OnMouseDown() {
isSelected = true;
} //手指抬起,记录归零
protected void OnMouseUp() {
isSelected = false;
status = -;
TouchTime = ;
}
// Update is called once per frame
protected void Update()
{
if (!isSelected)
{
return;
}
else if(status == -)
{
InputCheck();
}
}
/// <summary>
/// 之类相应操作
/// </summary>
protected virtual void InputCheck() { }
}

单指移动3D物体

using UnityEngine;
using System.Collections;
using UnityEngine.EventSystems;
using System; public class MoveControl : GestureControl
{
protected override void InputCheck()
{
//单指移动
if (Input.touchCount == )
{
//触碰按住3D物体不动1秒后物体随手指一起移动
if (Input.GetTouch().phase == TouchPhase.Stationary)
{
TouchTime += Time.deltaTime;
if (TouchTime > )
{
status = ;
}
}
if (status == )
{
StartCoroutine(CustomOnMouseDown());
}
}
}
IEnumerator CustomOnMouseDown()
{
//将物体由世界坐标系转化为屏幕坐标系,由vector3 结构体变量ScreenSpace存储,以用来明确屏幕坐标系Z轴的位置
Vector3 ScreenPoint = Camera.main.WorldToScreenPoint(transform.position); //由于鼠标的坐标系是二维的,需要转化成三维的世界坐标系;
Vector3 WorldPostion = Camera.main.ScreenToWorldPoint(new Vector3(Input.mousePosition.x, Input.mousePosition.y, ScreenPoint.z)); //三维的情况下才能来计算鼠标位置与物体的距离
Vector3 distance = transform.position - WorldPostion; //当鼠标左键按下时
while (Input.GetMouseButton())
{
//得到现在鼠标的二维坐标系位置
Vector3 curScreenSpace = new Vector3(Input.mousePosition.x, Input.mousePosition.y, ScreenPoint.z);
//将当前鼠标的2维位置转化成三维的位置,再加上鼠标的移动距离
Vector3 CurPosition = Camera.main.ScreenToWorldPoint(curScreenSpace) + distance;
//CurPosition就是物体应该的移动向量赋给transform的position属性
transform.position = CurPosition;
//鼠标释放前都起作用
yield return new WaitForFixedUpdate();
}
}
}

单指旋转3D物体

using UnityEngine;
using System.Collections;
using UnityEngine.EventSystems;
using System; public class RotateControl : GestureControl
{ protected override void InputCheck()
{
#region 单点触发旋转(真实模型旋转)
if (Input.touchCount == )
{
//触摸为移动类型
if (Input.GetTouch().phase == TouchPhase.Moved)
{
status = ;
try
{
StartCoroutine(CustomOnMouseDown());
}
catch (Exception e)
{
Debug.Log(e.ToString());
}
} }
#endregion #region 键盘A、D、W、S模拟旋转(真实模型旋转)
if (Input.GetKeyDown(KeyCode.A))
{
transform.Rotate(Vector3.up, * Time.deltaTime, Space.World);
} if (Input.GetKeyDown(KeyCode.D))
{
transform.Rotate(Vector3.up, - * Time.deltaTime, Space.World);
} if (Input.GetKeyDown(KeyCode.W))
{
transform.Rotate(Vector3.left, * Time.deltaTime, Space.World);
} if (Input.GetKeyDown(KeyCode.S))
{
transform.Rotate(Vector3.left, - * Time.deltaTime, Space.World);
}
#endregion
} IEnumerator CustomOnMouseDown()
{
//当检测到一直触碰时,会不断循环运行
while (Input.GetMouseButton())
{
//判断是否点击在UI上
#if UNITY_ANDROID || UNITY_IPHONE
if (EventSystem.current.IsPointerOverGameObject(Input.GetTouch().fingerId))
#else
if (EventSystem.current.IsPointerOverGameObject())
#endif
{
Debug.Log("当前点击在UI上");
}
else
{
float XX = Input.GetAxis("Mouse X");
float YY = Input.GetAxis("Mouse Y");
#region
//判断左右滑动的距离与上下滑动距离大小
if (Mathf.Abs(XX) >= Mathf.Abs(YY))
{
//单指向左滑动情况
if (XX < )
{
transform.Rotate(Vector3.up, * Time.deltaTime, Space.World);
}
//单指向右滑动情况
if (XX > )
{
transform.Rotate(-Vector3.up, * Time.deltaTime, Space.World);
}
}
else
{
//单指向下滑动情况
if (YY < )
{
transform.Rotate(Vector3.left, * Time.deltaTime, Space.World);
}
//单指向上滑动情况
if (YY > )
{
transform.Rotate(-Vector3.left, * Time.deltaTime, Space.World);
}
}
#endregion
}
yield return new WaitForFixedUpdate();
}
}
}

双指缩放3D物体

using UnityEngine;
using System.Collections; public class ZoomControl : GestureControl
{
//记录上一次手机触摸位置判断用户是在左放大还是缩小手势
private Vector2 oldPosition1;
private Vector2 oldPosition2;
//实时大小
Vector3 RealScale = new Vector3(1f, 1f, 1f);
//原始大小
float InitialScale = ;
//缩放速度
public float ScaleSpeed = 0.1f;
//缩放比例
public float MaxScale = 2.5f;
public float MinScale = 0.5f; void Start()
{
//获取物体最原始大小
InitialScale = this.transform.localScale.x;
} protected override void InputCheck()
{
#region 多点触摸缩放(真实模型缩放) if (Input.touchCount > )
{
status = ;
StartCoroutine(CustomOnMouseDown());
}
#endregion
} IEnumerator CustomOnMouseDown()
{
//当检测到一直触碰时,会不断循环运行
while (Input.GetMouseButton())
{
//实时记录模型大小
RealScale = this.transform.localScale;
if (Input.GetTouch().phase == TouchPhase.Moved || Input.GetTouch().phase == TouchPhase.Moved)
{
//触摸位置
Vector3 tempPosition1 = Input.GetTouch().position;
Vector3 tempPosition2 = Input.GetTouch().position; //函数返回真为放大,返回假为缩小
if (isEnlarge(oldPosition1, oldPosition2, tempPosition1, tempPosition2))
{
//判断是否超过边界
if (RealScale.x < InitialScale * MaxScale)
{
this.transform.localScale += this.transform.localScale * ScaleSpeed;
}
}
else
{
//判断是否超过边界
if (RealScale.x > InitialScale * MinScale)
{
this.transform.localScale -= this.transform.localScale * ScaleSpeed;
}
}
//备份上一次的触摸位置
oldPosition1 = tempPosition1;
oldPosition2 = tempPosition2;
} yield return new WaitForFixedUpdate();
}
} //记录手指位置与初始位置是缩小或放大
bool isEnlarge(Vector2 oP1, Vector2 oP2, Vector2 nP1, Vector2 nP2)
{
float leng1 = Mathf.Sqrt((oP1.x - oP2.x) * (oP1.x - oP2.x) + (oP1.y - oP2.y) * (oP1.y - oP2.y));
float leng2 = Mathf.Sqrt((nP1.x - nP2.x) * (nP1.x - nP2.x) + (nP1.y - nP2.y) * (nP1.y - nP2.y));
if (leng1 < leng2)
{
return true;
}
else
{
return false;
}
}
}

Unity手机端手势基本操作的更多相关文章

  1. touch.js 手机端的操作手势

    使用原生的touchstart总是单击.长按有冒泡冲突事件,发现百度在几年开源的touch.js库,放在现在来解决手机端的操作手势,仍然很好用.

  2. bootstrap实现 手机端滑动效果,滑动到下一页,jgestures.js插件

    bootstrap能否实现 手机端滑动效果,滑动到下一页 jgestures.js插件可以解决,只需要引入一个JS文件<script src="js/jgestures.min.js& ...

  3. js仿手机端九宫格登录功能

    js仿手机端九宫格登录功能 最近闲来无事把以前无聊时开发的小东西拿出来和大家分享下,写的不好的请指出,我会及时修改.谢谢. 功能及方法逻辑都注释在代码中.所以麻烦大家直接看代码. 效果如下: 话不多说 ...

  4. web端和手机端测试有什么不同

    面试中经常被问到web端测试和手机端测试有什么相同点和区别呢?现在总结一下这个问题,如有不对敬请指正 web端和手机端测试有什么区别 1.相同点 不管是web测试还是手机App测试,都离不开测试的相关 ...

  5. Unity手游引擎安全解析及实践

    近日,由Unity主办的"Unity技术开放日"在广州成功举办,网易移动安全技术专家卓辉作为特邀嘉宾同现场400名游戏开发者分享了网易在手游安全所积累的经验.当下,很多手游背后都存 ...

  6. 使用localResizeIMG3+WebAPI实现手机端图片上传

    前言 惯例~惯例~昨天发表的使用OWIN作为WebAPI的宿主..嗯..有很多人问..是不是缺少了什么 - - 好吧,如果你要把OWIN寄宿在其他的地方...代码如下: namespace Conso ...

  7. 《JS实现复制内容到剪贴板功能,可兼容所有PC浏览器,不兼容手机端》

    前记:本来原生的JS是有提供一个函数来实现这个功能(window.clipboardData),但是很遗憾,这个函数仅仅支持IE和FF浏览器,所以基本用处不大.下边介绍的是一个第三方插件库(ZeroC ...

  8. 【极品代码】一般人我不告诉他,手机端h5播放时不自动全屏代码

    已测适用于ios,某些安卓手机微信下播放视频会出现播放器控件(这个实在是无力吐槽噢,因为之前还遇到过微信播放完视频后竟然无法退出全屏出现广告的情况,只有播放完后刷新页面并且要放到框架页里才能屏蔽微信视 ...

  9. 判断是pc端还是手机端,并跳转到相应页面

    <!-- 判断浏览器是否为手机端 -->  <script>     // class     ! function(navigator) {         var user ...

随机推荐

  1. axios 跨域请求允许带cookie,则服务器Access-Control-Allow-Origin应设置为具体域名,否则请求无法获得返回数据

    1.通过允许跨域访问实现了跨域请求,但为了使每个请求带上session信息,我设置了withCredentials ,即: axios.defaults.withCredentials = true ...

  2. C++->二进制文件流的输入输出

    C++->文件流的输入输出 1.书本里以“简单事务处理”为例子,解析二进制输入输出文件流的read和write函数的使用,以及输入输出文件流 过程中指针的捕获.定位,文件流位置的判断,二进制文件 ...

  3. Mysql快速入门(三)

    MySQL性能优化之查看执行计划explain 介绍: (1).MySQL 提供了一个 EXPLAIN 命令, 它可以对 SELECT 语句进行分析, 并输出 SELECT 执行的详细信息, 以供开发 ...

  4. 树莓派4B遇到的坑

    由于大创需要用到机器学习这些东西,入手了一个树莓派4B(新手没弄过,直接上手最新版果然是有坑的),大佬勿喷

  5. IntelliJ IDEA Ultimate 6.2 版本免费试用期过期后如何破解

    今天早上一打开IntelliJ IDEA时弹出“InteliJ IDEA License Activation”界面,需要激活新的license才可以使用.下面直接使用Activation code进 ...

  6. 用MyEclipse远程debug

    第一步 编辑 tomcat下的文件startup.sh文件,我的路径是 /root/apache-tomcat-6.0.24/bin/startup.sh 命令:vim startup.sh将decl ...

  7. RN开发-组件View,Text

    1.外联js文件(RN自定义组件)        module.exports=Header; 导出模块         const Header=require('./header'); 导入外部j ...

  8. 解决:java.lang.ClassNotFoundException: org.apache.xmlbeans.XmlObject报错问题。

    利用POI操作PPT一直报如下错误java.lang.ClassNotFoundException: org.apache.xmlbeans.XmlObject 是因为项目中缺少一个包xmlbeans ...

  9. 让Surface Shader不受光照的明暗影响

    直接上码 Shader "Custom/3DVideo" { Properties { _Color (,,,) _MainTex ("Albedo (RGB)" ...

  10. 《Head first设计模式》学习笔记 – 迭代器模式

    <Head first设计模式>学习笔记 – 迭代器模式 代器模式提供一种方法顺序访问一个聚合对象中的各个元素,而又不暴露其内部的表示. 爆炸性新闻:对象村餐厅和对象村煎饼屋合并了!真是个 ...