在 Unity 中使游戏对象可触摸 - 增强现实
Make GameObjects Touchable in Unity - Augmented Reality
我正在尝试使用 Vuforia SDK 在 Unity 中开发增强现实 iOS 应用程序。我正在努力尝试让我的游戏对象可触摸。
目前,我能够让我的游戏对象按预期悬停在我的标记上。但是,点击它们时,没有任何反应。
这是我的层次结构。
现在,我一直在浏览论坛和在线教程以了解如何执行此操作,这是我目前拥有的代码。
我有两个 C# 脚本:touchableManager(附加到 ARCamera)和 touchableGameobject(附加到 Cube 和 Cube)
touchableManager:
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
public class touchableManager : MonoBehaviour
{
public LayerMask touchInputMask;
private List<GameObject> touchList = new List<GameObject>();
private GameObject[] touchesOld;
private RaycastHit hit;
void Update ()
{
if (Input.touchCount > 0)
{
touchesOld = new GameObject[touchList.Count];
touchList.CopyTo(touchesOld);
touchList.Clear();
foreach (Touch touch in Input.touches)
{
Ray ray = GetComponent<Camera>().ScreenPointToRay (touch.position); //attached the main camera
if (Physics.Raycast(ray, out hit, 100f, touchInputMask.value))
{
GameObject recipient = hit.transform.gameObject;
touchList.Add(recipient);
if (touch.phase == TouchPhase.Began) {
recipient.SendMessage ("onTouchDown", hit.point, SendMessageOptions.DontRequireReceiver);
}
if (touch.phase == TouchPhase.Ended) {
recipient.SendMessage ("onTouchUp", hit.point, SendMessageOptions.DontRequireReceiver);
}
if (touch.phase == TouchPhase.Stationary || touch.phase == TouchPhase.Moved) {
recipient.SendMessage ("onTouchStay", hit.point, SendMessageOptions.DontRequireReceiver);
}
if (touch.phase == TouchPhase.Canceled) {
recipient.SendMessage ("onTouchExit", hit.point, SendMessageOptions.DontRequireReceiver);
}
}
}
foreach (GameObject g in touchesOld)
{
if (!touchList.Contains(g))
{
g.SendMessage("onTouchExit", hit.point, SendMessageOptions.DontRequireReceiver);
}
}
}
}
}
可触摸游戏对象:
using UnityEngine;
using System.Collections;
public class touchableGameobject : MonoBehaviour
{
public Color defaultColor;
public Color selectedColor;
private Material mat;
void Start()
{
mat = GetComponent<Renderer>().material;
}
void onTouchDown()
{
mat.color = selectedColor;
}
void onTouchUp()
{
mat.color = defaultColor;
}
void onTouchStay()
{
mat.color = selectedColor;
}
void onTouchExit()
{
mat.color = defaultColor;
}
}
到目前为止,我的应用程序所做的只是显示两个游戏对象。当我点击它们时,没有任何反应。代码应在点击时更改立方体的颜色。
请提供任何帮助,我们将不胜感激。请引导我走正确的道路。
编辑:添加了 Box Collider。见截图。
尝试改变调用方法:
recipient.SendMessage ("onTouchExit")
我明白了"optional"的参数,但是突然...
更多 我建议进入调试器来检查变量的值。也许某处为空。无论如何,这样你就可以理解哪个方法没有被调用。
我使用 Unity 方法简单地让它工作
void OnMouseDown(){
//...在这里写你的东西,点击时会执行
}
好吧,折腾了半天,终于弄明白了。如果某些可怜的未来灵魂可以从中获得一些价值,我会在这里发布对我有用的东西。
我会回答我自己的问题,希望对我之后的任何人有所帮助。
以下代码对我有用。将 touchableGameObject.cs
附加到游戏对象并将 touchableManager.cs
附加到 ARCamera。
touchableGameObject.cs:
using UnityEngine;
using System.Collections;
public class touchableGameobject : MonoBehaviour
{
public Color defaultColor;
public Color selectedColor;
private Material mat;
void Start()
{
mat = GetComponent<Renderer>().material;
}
void onTouchDown()
{
mat.color = selectedColor;
}
void onTouchUp()
{
mat.color = defaultColor;
}
void onTouchStay()
{
mat.color = selectedColor;
}
void onTouchExit()
{
mat.color = defaultColor;
}
}
touchableManager.cs
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
public class touchableManager : MonoBehaviour
{
public LayerMask touchInputMask;
private List<GameObject> touchList = new List<GameObject>();
private GameObject[] touchesOld;
private RaycastHit hit;
void Update ()
{
if (Input.touchCount > 0)
{
touchesOld = new GameObject[touchList.Count];
touchList.CopyTo(touchesOld);
touchList.Clear();
foreach (Touch touch in Input.touches)
{
Ray ray = Camera.main.ScreenPointToRay(touch.position); //attached the main camera
if (Physics.Raycast(ray, out hit, Mathf.Infinity, touchInputMask.value))
{
GameObject recipient = hit.transform.gameObject;
touchList.Add(recipient);
if (touch.phase == TouchPhase.Began) {
Debug.Log("Touched: " + recipient.name);
recipient.SendMessage ("onTouchDown", hit.point, SendMessageOptions.DontRequireReceiver);
}
if (touch.phase == TouchPhase.Ended) {
recipient.SendMessage ("onTouchUp", hit.point, SendMessageOptions.DontRequireReceiver);
}
if (touch.phase == TouchPhase.Stationary || touch.phase == TouchPhase.Moved) {
recipient.SendMessage ("onTouchStay", hit.point, SendMessageOptions.DontRequireReceiver);
}
if (touch.phase == TouchPhase.Canceled) {
recipient.SendMessage ("onTouchExit", hit.point, SendMessageOptions.DontRequireReceiver);
}
}
}
foreach (GameObject g in touchesOld)
{
if (!touchList.Contains(g))
{
g.SendMessage("onTouchExit", hit.point, SendMessageOptions.DontRequireReceiver);
}
}
}
}
}
此外,在 Unity 编辑器中,单击右上角的 "Layers" 下拉菜单。编辑图层。我只是在一个字段中输入 "Touch Input"(例如,用户第 8 层,或任何可用的字段)。然后,select ARCamera 并在 Inspector 选项卡中,select 在 "Layer" 下拉列表中新命名的层。对每个游戏对象执行相同的操作。此外,在 ARCamera 中,在 "touchableManager" 组件下,您还必须在 "Touch Input Mask" 下拉列表中 select 新命名的图层。
希望这对某人有所帮助。
我正在尝试使用 Vuforia SDK 在 Unity 中开发增强现实 iOS 应用程序。我正在努力尝试让我的游戏对象可触摸。
目前,我能够让我的游戏对象按预期悬停在我的标记上。但是,点击它们时,没有任何反应。
这是我的层次结构。
现在,我一直在浏览论坛和在线教程以了解如何执行此操作,这是我目前拥有的代码。
我有两个 C# 脚本:touchableManager(附加到 ARCamera)和 touchableGameobject(附加到 Cube 和 Cube)
touchableManager:
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
public class touchableManager : MonoBehaviour
{
public LayerMask touchInputMask;
private List<GameObject> touchList = new List<GameObject>();
private GameObject[] touchesOld;
private RaycastHit hit;
void Update ()
{
if (Input.touchCount > 0)
{
touchesOld = new GameObject[touchList.Count];
touchList.CopyTo(touchesOld);
touchList.Clear();
foreach (Touch touch in Input.touches)
{
Ray ray = GetComponent<Camera>().ScreenPointToRay (touch.position); //attached the main camera
if (Physics.Raycast(ray, out hit, 100f, touchInputMask.value))
{
GameObject recipient = hit.transform.gameObject;
touchList.Add(recipient);
if (touch.phase == TouchPhase.Began) {
recipient.SendMessage ("onTouchDown", hit.point, SendMessageOptions.DontRequireReceiver);
}
if (touch.phase == TouchPhase.Ended) {
recipient.SendMessage ("onTouchUp", hit.point, SendMessageOptions.DontRequireReceiver);
}
if (touch.phase == TouchPhase.Stationary || touch.phase == TouchPhase.Moved) {
recipient.SendMessage ("onTouchStay", hit.point, SendMessageOptions.DontRequireReceiver);
}
if (touch.phase == TouchPhase.Canceled) {
recipient.SendMessage ("onTouchExit", hit.point, SendMessageOptions.DontRequireReceiver);
}
}
}
foreach (GameObject g in touchesOld)
{
if (!touchList.Contains(g))
{
g.SendMessage("onTouchExit", hit.point, SendMessageOptions.DontRequireReceiver);
}
}
}
}
}
可触摸游戏对象:
using UnityEngine;
using System.Collections;
public class touchableGameobject : MonoBehaviour
{
public Color defaultColor;
public Color selectedColor;
private Material mat;
void Start()
{
mat = GetComponent<Renderer>().material;
}
void onTouchDown()
{
mat.color = selectedColor;
}
void onTouchUp()
{
mat.color = defaultColor;
}
void onTouchStay()
{
mat.color = selectedColor;
}
void onTouchExit()
{
mat.color = defaultColor;
}
}
到目前为止,我的应用程序所做的只是显示两个游戏对象。当我点击它们时,没有任何反应。代码应在点击时更改立方体的颜色。
请提供任何帮助,我们将不胜感激。请引导我走正确的道路。
编辑:添加了 Box Collider。见截图。
尝试改变调用方法:
recipient.SendMessage ("onTouchExit")
我明白了"optional"的参数,但是突然...
更多 我建议进入调试器来检查变量的值。也许某处为空。无论如何,这样你就可以理解哪个方法没有被调用。
我使用 Unity 方法简单地让它工作
void OnMouseDown(){
//...在这里写你的东西,点击时会执行
}
好吧,折腾了半天,终于弄明白了。如果某些可怜的未来灵魂可以从中获得一些价值,我会在这里发布对我有用的东西。
我会回答我自己的问题,希望对我之后的任何人有所帮助。
以下代码对我有用。将 touchableGameObject.cs
附加到游戏对象并将 touchableManager.cs
附加到 ARCamera。
touchableGameObject.cs:
using UnityEngine;
using System.Collections;
public class touchableGameobject : MonoBehaviour
{
public Color defaultColor;
public Color selectedColor;
private Material mat;
void Start()
{
mat = GetComponent<Renderer>().material;
}
void onTouchDown()
{
mat.color = selectedColor;
}
void onTouchUp()
{
mat.color = defaultColor;
}
void onTouchStay()
{
mat.color = selectedColor;
}
void onTouchExit()
{
mat.color = defaultColor;
}
}
touchableManager.cs
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
public class touchableManager : MonoBehaviour
{
public LayerMask touchInputMask;
private List<GameObject> touchList = new List<GameObject>();
private GameObject[] touchesOld;
private RaycastHit hit;
void Update ()
{
if (Input.touchCount > 0)
{
touchesOld = new GameObject[touchList.Count];
touchList.CopyTo(touchesOld);
touchList.Clear();
foreach (Touch touch in Input.touches)
{
Ray ray = Camera.main.ScreenPointToRay(touch.position); //attached the main camera
if (Physics.Raycast(ray, out hit, Mathf.Infinity, touchInputMask.value))
{
GameObject recipient = hit.transform.gameObject;
touchList.Add(recipient);
if (touch.phase == TouchPhase.Began) {
Debug.Log("Touched: " + recipient.name);
recipient.SendMessage ("onTouchDown", hit.point, SendMessageOptions.DontRequireReceiver);
}
if (touch.phase == TouchPhase.Ended) {
recipient.SendMessage ("onTouchUp", hit.point, SendMessageOptions.DontRequireReceiver);
}
if (touch.phase == TouchPhase.Stationary || touch.phase == TouchPhase.Moved) {
recipient.SendMessage ("onTouchStay", hit.point, SendMessageOptions.DontRequireReceiver);
}
if (touch.phase == TouchPhase.Canceled) {
recipient.SendMessage ("onTouchExit", hit.point, SendMessageOptions.DontRequireReceiver);
}
}
}
foreach (GameObject g in touchesOld)
{
if (!touchList.Contains(g))
{
g.SendMessage("onTouchExit", hit.point, SendMessageOptions.DontRequireReceiver);
}
}
}
}
}
此外,在 Unity 编辑器中,单击右上角的 "Layers" 下拉菜单。编辑图层。我只是在一个字段中输入 "Touch Input"(例如,用户第 8 层,或任何可用的字段)。然后,select ARCamera 并在 Inspector 选项卡中,select 在 "Layer" 下拉列表中新命名的层。对每个游戏对象执行相同的操作。此外,在 ARCamera 中,在 "touchableManager" 组件下,您还必须在 "Touch Input Mask" 下拉列表中 select 新命名的图层。
希望这对某人有所帮助。