即使目标丢失,也可以将对象/ 3D模型保留在屏幕上(UNITY + Vuforia)

时间:2017-05-22 17:53:09

标签: c# unity3d vuforia

我想将对象/ 3D模型保持在移动屏幕的中心,即使目标丢失(跟踪丢失())以及目标找到的最后一个跟踪图像模型应该消失。我正在使用团结。

我试图关注cloudreco样本,但不能正确。

用于我正在使用的屏幕居中:

GameObject lost = GameObject.Find ("IT"+mTrackableBehaviour.TrackableName);

lost.transform.position=Camera.main.ScreenToWorldPoint(new Vector3(Screen.width/2, Screen.height/2, Camera.main.nearClipPlane) );


我有大约10个图像目标,最大同时图像跟踪设置为1。
寻找解决方案。
谢谢!

编辑:

using UnityEngine;
using UnityEngine.UI;
using System.Collections;
using System.Collections.Generic;
namespace Vuforia
{
    /// <summary>
    /// A custom handler that implements the ITrackableEventHandler interface.
    /// </summary>
    public class dtehedit : MonoBehaviour,
    ITrackableEventHandler
    {

        #region PRIVATE_MEMBER_VARIABLES

        private TrackableBehaviour mTrackableBehaviour;
        private bool firsttime=false;
        //private bool secondtime=false;
        GameObject lost, lostclone;
        #endregion // PRIVATE_MEMBER_VARIABLES



        #region UNTIY_MONOBEHAVIOUR_METHODS

        void Start()
        {
            Debug.Log ("start method before registring");
            mTrackableBehaviour = GetComponent<TrackableBehaviour>();
            if (mTrackableBehaviour)
            {
                mTrackableBehaviour.RegisterTrackableEventHandler(this);
            }
            Debug.Log ("start method after registring");
        }

        #endregion // UNTIY_MONOBEHAVIOUR_METHODS



        #region PUBLIC_METHODS

        /// <summary>
        /// Implementation of the ITrackableEventHandler function called when the
        /// tracking state changes.
        /// </summary>
        public void OnTrackableStateChanged(
            TrackableBehaviour.Status previousStatus,
            TrackableBehaviour.Status newStatus)
        {
            if (newStatus == TrackableBehaviour.Status.DETECTED ||
                newStatus == TrackableBehaviour.Status.TRACKED ||
                newStatus == TrackableBehaviour.Status.EXTENDED_TRACKED)
            {
                OnTrackingFound();
            }
            else
            {
                OnTrackingLost();
            }
        }

        #endregion // PUBLIC_METHODS



        #region PRIVATE_METHODS


        private void OnTrackingFound()
        {
            firsttime = true;
            if (lostclone != null) {
                Debug.Log ("LOST CLONE otf ::" + lostclone.name);
                DestroyObject (lostclone); // (1) if new object is scanned gameobject lostclone is not destroyed
            }

            Renderer[] rendererComponents = GetComponentsInChildren<Renderer>(true);
            Collider[] colliderComponents = GetComponentsInChildren<Collider>(true);

            // Enable rendering:
            foreach (Renderer component in rendererComponents)
            {
                component.enabled = true;
            }

            // Enable colliders:
            foreach (Collider component in colliderComponents)
            {
                component.enabled = true;
            }

            Debug.Log("Trackable " + mTrackableBehaviour.TrackableName + " found");
        }


        private void OnTrackingLost()
        {
//          Debug.Log (firsttime);
//          if (!firsttime) {
//              Renderer[] rendererComponents = GetComponentsInChildren<Renderer> (true);
//              Collider[] colliderComponents = GetComponentsInChildren<Collider> (true);
//
//              // Disable rendering:
//              foreach (Renderer component in rendererComponents) {
//                  component.enabled = false;
//              }
//
//              // Disable colliders:
//              foreach (Collider component in colliderComponents) {
//                  component.enabled = false;
//              }
//
//          } else {
//              string itname = mTrackableBehaviour.TrackableName;
//              Debug.Log ("lost trackable name " + itname);
//              GameObject lost = GameObject.Find ("IT" + itname);
// (2) WOrking but dont know how to reposition gameobject after next tracker is found 
//              lost.transform.GetChild(0).transform.position=Camera.main.ScreenToWorldPoint(new Vector3(Screen.width/2, Screen.height/2, Camera.main.nearClipPlane+20) ); 
// (3) workinh but dont know how to reset camera position when next tracker is found
////                Camera.main.transform.position = lost.transform.GetChild(0).transform.position + lost.transform.GetChild(0).transform.forward * 25;
////                Camera.main.transform.LookAt (lost.transform.GetChild(0).transform);
//          }


                            Renderer[] rendererComponents = GetComponentsInChildren<Renderer> (true);
                            Collider[] colliderComponents = GetComponentsInChildren<Collider> (true);

                            // Disable rendering:
                            foreach (Renderer component in rendererComponents) {
                                component.enabled = false;
                            }

                            // Disable colliders:
                            foreach (Collider component in colliderComponents) {
                                component.enabled = false;
                            }
            if (firsttime) {
                string itname = mTrackableBehaviour.TrackableName;
                Debug.Log ("lost trackable name " + itname);
                lost = GameObject.Find ("IT" + itname).transform.GetChild (0).gameObject;
                lostclone = Instantiate (lost) as GameObject; //decoupling
                Debug.Log ("LOST CLONE ::"+lostclone.name);
            }
            Debug.Log("Trackable " + mTrackableBehaviour.TrackableName + " lost");
        }

        #endregion // PRIVATE_METHODS
    }
}

对于上面的代码,我尝试了三种方法/方法,在跟踪丢失后在屏幕上显示我的3D模型,但似乎没有一个完美或按照需要工作

  

我通过实例化方法解耦/克隆我的3d对象但是当我再次找到跟踪器时,最后一个没有被销毁(1)以及如何让它来到相机前面   
  我将3dobject移动到了跟踪丢失的相机上,但是当再次跟踪发现如何将我的3d模型再次移动到原始位置时(2)

  我在跟踪丢失后将相机移动到我的3dobject但是再次跟踪发现如何将相机带到原始位置(3)
  请看一下代码,请帮帮我..不知道我错过了什么......?

1 个答案:

答案 0 :(得分:0)

我看了你的代码,修了一下,我相信这可以解决你的问题。

using UnityEngine;
using UnityEngine.UI;
using System.Collections;
using System.Collections.Generic;
namespace Vuforia
{
    /// <summary>
    /// A custom handler that implements the ITrackableEventHandler interface.
    /// </summary>
    public class dtehedit : MonoBehaviour,
    ITrackableEventHandler
    {

        #region PRIVATE_MEMBER_VARIABLES

        private TrackableBehaviour mTrackableBehaviour;
        private bool firsttime = false;
        string itname = "";
        //private bool secondtime=false;
        GameObject lost, lostclone;
        #endregion // PRIVATE_MEMBER_VARIABLES



        #region UNTIY_MONOBEHAVIOUR_METHODS

        void Start()
        {
            Debug.Log("start method before registring");
            mTrackableBehaviour = GetComponent<TrackableBehaviour>();
            if (mTrackableBehaviour)
            {
                mTrackableBehaviour.RegisterTrackableEventHandler(this);
            }
            Debug.Log("start method after registring");
        }

        #endregion // UNTIY_MONOBEHAVIOUR_METHODS



        #region PUBLIC_METHODS

        /// <summary>
        /// Implementation of the ITrackableEventHandler function called when the
        /// tracking state changes.
        /// </summary>
        public void OnTrackableStateChanged(
            TrackableBehaviour.Status previousStatus,
            TrackableBehaviour.Status newStatus)
        {
            if (newStatus == TrackableBehaviour.Status.DETECTED ||
                newStatus == TrackableBehaviour.Status.TRACKED ||
                newStatus == TrackableBehaviour.Status.EXTENDED_TRACKED)
            {
                OnTrackingFound();
            }
            else
            {
                OnTrackingLost();
            }
        }

        #endregion // PUBLIC_METHODS



        #region PRIVATE_METHODS


        private void OnTrackingFound()
        {
            // This is wrong because you never set it to false. Every time a tracker(image) is found it will be the first time - wrong.
            //      firsttime = true;      


            if (lostclone != null)
            {
                Debug.Log("LOST CLONE otf ::" + lostclone.name);
                // DestroyObject(lostclone); // (1) if new object is scanned gameobject lostclone is not destroyed
            }

            //Here you can reset the position of the GameObject back to the parent(tracker)'s position. 
            this.transform.GetChild(0).transform.position = new Vector3(0, 0, 0);

            Renderer[] rendererComponents = GetComponentsInChildren<Renderer>(true);
            Collider[] colliderComponents = GetComponentsInChildren<Collider>(true);

            // Enable rendering:
            foreach (Renderer component in rendererComponents)
            {
                component.enabled = true;
            }

            // Enable colliders:
            foreach (Collider component in colliderComponents)
            {
                component.enabled = true;
            }

            Debug.Log("Trackable " + mTrackableBehaviour.TrackableName + " found");
        }


        private void OnTrackingLost()
        {
            Renderer[] rendererComponents = GetComponentsInChildren<Renderer>(true);
            Collider[] colliderComponents = GetComponentsInChildren<Collider>(true);

            // What you can do is not disable this
            //foreach (Renderer component in rendererComponents)
            //{
            //    component.enabled = false;
            //}

            // Disable colliders: Disable this if you need it diabled only
            foreach (Collider component in colliderComponents)
            {
                component.enabled = false;
            }

            string itname = mTrackableBehaviour.TrackableName;
            Debug.Log("lost trackable name " + itname);
            GameObject lost = GameObject.Find("IT" + itname);
            //(2) WOrking but dont know how to reposition gameobject after next tracker is found

            // This is not decoupling but it should work ( you dont need to find the gameobject you can use [this] instead)
            this.transform.GetChild(0).transform.position = Camera.main.ScreenToWorldPoint(new Vector3(Screen.width / 2, Screen.height / 2, Camera.main.nearClipPlane + 20));
            // Disable rendering:

            itname = mTrackableBehaviour.TrackableName;
            Debug.Log("lost trackable name " + itname);
            lost = GameObject.Find("IT" + itname).transform.GetChild(0).gameObject;
            // this is not I ment by decoupling sory, I ment de parenting -> (gameObject.parent = null)
            //lostclone = Instantiate(lost) as GameObject; //decoupling
        }

        #endregion // PRIVATE_METHODS
    }
}