Unity3D-场景中3D物体添加点击事件
鼠标点击3D物体触发,Unity从本质上来说有两种:一种是通过事件(event)触发,一种是通过射线(ray)判断穿过的物体触发。这两种触发的原理是不同的,不论哪种触发都必须满足触发的要求才可以,既然原理不同,触发的要求也不一样,下面详细说明一下3种不同的方式。
Unity版本 5.6.2f Unity API版本 2019.1
参考 Unity API:
一、通过事件,实现接口
先了解下接口,这个接树关系是 ...,下面看下它还有哪些可以实现的接口
这里用举例(api中这样解释):
也就是在我们的被点击的类中实现了接口后,在实现方法,在这个方法里操作点击后的处理。
既然是事件,首先满足事件触发的要求:
给场景中的添加脚本
在场景中添加事件系统,如图操作:
点击 Add … 后出现如图:
重点来了,设置被点击物体(3D)物体,一定要带触发器(),然后把点击后处理的脚本挂在被点击的物体上
到这里,需要我们开发的只有一个脚本,Demo里的.cs
using UnityEngine;
using UnityEngine.EventSystems;public class EventClick : MonoBehaviour,IPointerClickHandler
{public void OnPointerClick(PointerEventData eventData){print("点击了::"+this.name);}
}
运行点击cube:
二、通过事件,附加脚本
这里也是同过事件来实现的,也要按照 一 里满足事件触发的要求(不懂!往上翻看下):
给场景中的添加脚本。在场景中添加事件系统;
完成以上两步后,注意也要带触发器(),3就和一里的不一样了。
这里有两种做法,分别是4 和 5 ,只是在用法上不同,原理是一样的。 首先给被点击的物体添加脚本。
是静态添加事件触发
给添加事件类型,根据需要选择
Demo里选择点击事件
给添加触发后执行函数
这里的执行函数,是下面我们开发的类.cs,把这个脚本添加到被点击的物体上即可。
using UnityEngine;
using UnityEngine.Events;
using UnityEngine.EventSystems;public class ClickEventTrigger : MonoBehaviour
{
public void OnClick(){print("MyOnClick 点击了::"+this.name);}
}
到这里,静态添加事件就完成了,运行效果:
是动态添加事件触发
动态触发,在Unity编辑器中操作就方便多了,只需要在被点击物体上添加就可以了,然后再把我们的脚本.cs添加到被点击物体上,剩下的都在代码中完成。
using UnityEngine;
using UnityEngine.Events;
using UnityEngine.EventSystems;public class ClickEventTrigger : MonoBehaviour {// Use this for initialization
void Start () {//获取或添加EventTrigger组件EventTrigger trigger = transform.GetComponent();if (trigger == null){trigger = transform.gameObject.AddComponent();}//初始化EventTrigger.Entry的数组 如果这里初始化了事件触发数组,那么在ide静态添加的事件会丢失//trigger.triggers = new List();//创建各种 EventTrigger.Entry的类型EventTrigger.Entry entry = new EventTrigger.Entry();entry.eventID = EventTriggerType.PointerEnter;//设置Entry的eventID类型 即EventTriggerType的各种枚举(比如鼠标点击,滑动,拖动等)UnityAction callback = new UnityAction(OnPointerEnter); //注册代理entry.callback.AddListener(callback);//添加代理事件到EventTrigger.EntryEventTrigger.Entry entry2 = new EventTrigger.Entry();entry2.eventID = EventTriggerType.PointerDown;UnityAction callback1 = new UnityAction(OnPointerDown);entry2.callback.AddListener(callback1);//在EventTrigger.Entry的数组添加EventTrigger.Entrytrigger.triggers.Add(entry);trigger.triggers.Add(entry2);}private void OnPointerDown(BaseEventData arg0){Debug.Log("OnPointerDown");}private void OnPointerEnter(BaseEventData arg0){Debug.Log("OnPointerEnter");}
}
运行结果:
三、通过射线,
这个方法主要是通过,射线发射,判断射线穿过的物体,根据特定的标志来判断是否点击到了该物体(比如:物体的标签Tag,还有物体的名称)
这里只需要3d物体,并且有明确的唯一标识,再加上我们开发的ol.cs就可以。
在场景中创建一个物体(Cube),然后点击面板下Tag - …- 在Tags列表中,点击+,输入你要添加的Tag名称就可以。创建Tag完成后,回到场景给这个Cube选择刚才创建的Tag。
在创建一个Cube,demo中起名(),这个名字就是射线穿过判断的标识,这个物体就创建完成了。
创建单独层,挂载我们开发的脚本即可。
运行结果:
完整代码:
using UnityEngine;public class ClickRayCastHitControl : MonoBehaviour {Ray ray;RaycastHit hit;GameObject obj;// Use this for initializationvoid Start () {
}// Update is called once per framevoid Update(){if (Input.GetMouseButtonDown(0)){Debug.Log("点击鼠标左键");ray = Camera.main.ScreenPointToRay(Input.mousePosition);if (Physics.Raycast(ray, out hit)){Debug.Log(hit.collider.gameObject.name);obj = hit.collider.gameObject;//通过名字if (obj.name.Equals("BeiJiChuan")){Debug.Log("点中" + obj.name);}//通过标签if (obj.tag == "ClicObj"){Debug.Log("点中" + obj.name);}}}}
}