设置场景中的多个标志,通过跟踪这些标志,实现操控虚拟物体的目的。虚拟物体自选,要求:
- 标志物至少有3个;
- 操控虚拟物体的平移和旋转;
- 文档给出代码及实现思路。
创建5个脚本,Cube、Doll、Sphere、Move、Rotate
Cube,Doll,Sphere对应三个标志物
这三个脚本侦测标志物是否被找到,若标志物被找到
则脚本里面的静态bool变量为TRUE
Cube脚本的代码,其他两个一样概念
(这其实是项目里的内建脚本,只是多加个静态变量)
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.Events;
using Vuforia;
public class Cube : MonoBehaviour
{
//要设个静态变量,被侦测到时为True
public static bool cube = false;
public enum TrackingStatusFilter
{
Tracked,
Tracked_ExtendedTracked,
Tracked_ExtendedTracked_Limited
}
/// <summary>
/// A filter that can be set to either:
/// - Only consider a target if it's in view (TRACKED)
/// - Also consider the target if's outside of the view, but the environment is tracked (EXTENDED_TRACKED)
/// - Even consider the target if tracking is in LIMITED mode, e.g. the environment is just 3dof tracked.
/// </summary>
public TrackingStatusFilter StatusFilter = TrackingStatusFilter.Tracked_ExtendedTracked_Limited;
public UnityEvent OnTargetFound;
public UnityEvent OnTargetLost;
protected TrackableBehaviour mTrackableBehaviour;
protected TrackableBehaviour.Status m_PreviousStatus;
protected TrackableBehaviour.Status m_NewStatus;
protected TrackableBehaviour.StatusInfo m_PreviousStatusInfo;
protected TrackableBehaviour.StatusInfo m_NewStatusInfo;
protected bool m_CallbackReceivedOnce = false;
protected virtual void Start()
{
mTrackableBehaviour = GetComponent<TrackableBehaviour>();
if (mTrackableBehaviour)
{
mTrackableBehaviour.RegisterOnTrackableStatusChanged(OnTrackableStatusChanged);
mTrackableBehaviour.RegisterOnTrackableStatusInfoChanged(OnTrackableStatusInfoChanged);
}
}
protected virtual void OnDestroy()
{
if (mTrackableBehaviour)
{
mTrackableBehaviour.UnregisterOnTrackableStatusInfoChanged(OnTrackableStatusInfoChanged);
mTrackableBehaviour.UnregisterOnTrackableStatusChanged(OnTrackableStatusChanged);
}
}
void OnTrackableStatusChanged(TrackableBehaviour.StatusChangeResult statusChangeResult)
{
m_PreviousStatus = statusChangeResult.PreviousStatus;
m_NewStatus = statusChangeResult.NewStatus;
Debug.LogFormat("Trackable {0} {1} -- {2}",
mTrackableBehaviour.TrackableName,
mTrackableBehaviour.CurrentStatus,
mTrackableBehaviour.CurrentStatusInfo);
HandleTrackableStatusChanged();
}
void OnTrackableStatusInfoChanged(TrackableBehaviour.StatusInfoChangeResult statusInfoChangeResult)
{
m_PreviousStatusInfo = statusInfoChangeResult.PreviousStatusInfo;
m_NewStatusInfo = statusInfoChangeResult.NewStatusInfo;
HandleTrackableStatusInfoChanged();
}
protected virtual void HandleTrackableStatusChanged()
{
if (!ShouldBeRendered(m_PreviousStatus) &&
ShouldBeRendered(m_NewStatus))
{
OnTrackingFound();
}
else if (ShouldBeRendered(m_PreviousStatus) &&
!ShouldBeRendered(m_NewStatus))
{
OnTrackingLost();
}
else
{
if (!m_CallbackReceivedOnce && !ShouldBeRendered(m_NewStatus))
{
// This is the first time we are receiving this callback, and the target is not visible yet.
// --> Hide the augmentation.
OnTrackingLost();
}
}
m_CallbackReceivedOnce = true;
}
protected virtual void HandleTrackableStatusInfoChanged()
{
if (m_NewStatusInfo == TrackableBehaviour.StatusInfo.WRONG_SCALE)
{
Debug.LogErrorFormat("The target {0} appears to be scaled incorrectly. " +
"This might result in tracking issues. " +
"Please make sure that the target size corresponds to the size of the " +
"physical object in meters and regenerate the target or set the correct " +
"size in the target's inspector.", mTrackableBehaviour.TrackableName);
}
}
protected bool ShouldBeRendered(TrackableBehaviour.Status status)
{
if (status == TrackableBehaviour.Status.DETECTED ||
status == TrackableBehaviour.Status.TRACKED)
{
// always render the augmentation when status is DETECTED or TRACKED, regardless of filter
return true;
}
if (StatusFilter == TrackingStatusFilter.Tracked_ExtendedTracked)
{
if (status == TrackableBehaviour.Status.EXTENDED_TRACKED)
{
// also return true if the target is extended tracked
return true;
}
}
if (StatusFilter == TrackingStatusFilter.Tracked_ExtendedTracked_Limited)
{
if (status == TrackableBehaviour.Status.EXTENDED_TRACKED ||
status == TrackableBehaviour.Status.LIMITED)
{
// in this mode, render the augmentation even if the target's tracking status is LIMITED.
// this is mainly recommended for Anchors.
return true;
}
}
return false;
}
protected virtual void OnTrackingFound()
{
if (mTrackableBehaviour)
{
var rendererComponents = mTrackableBehaviour.GetComponentsInChildren<Renderer>(true);
var colliderComponents = mTrackableBehaviour.GetComponentsInChildren<Collider>(true);
var canvasComponents = mTrackableBehaviour.GetComponentsInChildren<Canvas>(true);
// Enable rendering:
foreach (var component in rendererComponents)
component.enabled = true;
// Enable colliders:
foreach (var component in colliderComponents)
component.enabled = true;
// Enable canvas':
foreach (var component in canvasComponents)
component.enabled = true;
}
if (OnTargetFound != null)
OnTargetFound.Invoke();
//被侦测到时cube为True
cube = true;
}
protected virtual void OnTrackingLost()
{
if (mTrackableBehaviour)
{
var rendererComponents = mTrackableBehaviour.GetComponentsInChildren<Renderer>(true);
var colliderComponents = mTrackableBehaviour.GetComponentsInChildren<Collider>(true);
var canvasComponents = mTrackableBehaviour.GetComponentsInChildren<Canvas>(true);
// Disable rendering:
foreach (var component in rendererComponents)
component.enabled = false;
// Disable colliders:
foreach (var component in colliderComponents)
component.enabled = false;
// Disable canvas':
foreach (var component in canvasComponents)
component.enabled = false;
}
if (OnTargetLost != null)
OnTargetLost.Invoke();
}
}
Move和Rotate 对应球形和方块.分别控制移动和旋转
public class Move : MonoBehaviour
{
public GameObject g;
Vector3 position_o,position,position_s;
int n =0;
// Start is called before the first frame update
void Start()
{
}
// Update is called once per frame
void Update()
{
g = GameObject.Find("unitychan");
if (!Doll.doll || !Sphere.sphere) //其中一个找不到
{
n = 0;
}
else //两个都找到
{
if (n == 0)
n = 1;
else
n = 2;
if (n == 1)
{ }
else//改变位置
g.transform.localPosition = position_o + (transform.position - position_s);
position_o = g.transform.localPosition;
}
position_s = transform.position;
}
}
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Rotate : MonoBehaviour
{
public GameObject g;
// Start is called before the first frame update
void Start()
{
}
// Update is called once per frame
void Update()
{
g = GameObject.Find("unitychan");
if (Doll.doll == true || Cube.cube == true)
g.transform.localEulerAngles = transform.eulerAngles;
}
}