这是老版本的教程,为了不耽误大家的时间,请直接看原文,本文仅供参考哦!原文链接:https://developer.microsoft.com/EN-US/WINDOWS/HOLOGRAPHIC/holograms_210

Hololens的使用如果类比到计算机的使用,在输入操作方面,Hololens了解用户的操作意图的第一个步骤是凝视,用户的凝视射线呈现在场景中的点为凝视点,就好像是电脑中的鼠标光标点,凝视是第一步,是人与hololens操作的开始。

涉及凝视相关的知识点如下:

1 当用户看着一个全息图时,光标点会有反馈表现—表明用户看到了全息图,当用户凝视视线离开全息图时,光标点也要有反馈-表明用户没有在看全息图。

2 当用户注视到全息图时,给于用户更多反馈,例如声音,全息图当变化等。

3 使用定位技术使得用户可以选中更小的全息图。

4 添加方向指示图标指引用户找到全息图

5全息指示面板追随用户移动,一直保持在用户可见视角之内。

前提条件:

1 一台已经安装好开发工具的windows10 pc

2 一些C#编程能力

3 已经完成了教程 Holograms-101

4 一个开发者模式的Hololens 设备

项目文件:

下载该教程所需文件files

章节1-Unity 设置

步骤:

  • 开启 Unity.
  • 选择 New Project.
  • 给项目命名为 ModelExplorer.
  • 保存地址到你下载的项目文件下的 Gaze 文件夹下
  • 选择为 3D项目.
  • 点击 Create Project.

发布到Hololens设备前的一些Unity必要设置

  • 到Unity中选择 Edit > Project Settings > Player.
  • 在右侧的Inspector Panel 面板中, 选择 Windows Store 图标.
  • 展开 Other Settings 组.
  • Rendering 部分, 勾选 Virtual Reality Supported 选框 以添加一个新的 Virtual Reality SDKs 列表.
  • 验证 Windows Holographic 是否在列表中. 如果不在,选择 + 按钮将 Windows Holographic添加进列表.
  • 在主工具栏中选择Edit > Project Settings > Quality.
  • 依然是右侧的Inspector面板,在 Windows Store 图标下点击Default 下拉箭头.
  • 选择 Fastest for Windows Store Apps.

导入美术资源

  • 右击Project 面板下Assets 文件夹.
  • 点击 Import Package > Custom Package.
  • 定位到你下载的项目文件,然后选择 ModelExplorer.unitypackage.
  • 点击 Open.
  • 在出现的小窗口中,选择 Import button.

场景设置

  • 删除 Hierarchy面板中的 Main Camera.
  • 在Project面板下,找到 HoloToolkit 文件夹, 打开 Utilities folder, 然后打开 Prefabs folder.
  • 拖拽Prefabs文件夹下的 Main CameraHierarchy 面板中.
  • 右击Hierarchy中的Directional Light 然后选择 Delete.
  • 在Project面板下的 Holograms 文件夹下, 拖拽以下资源到 Hierarchy面板中:
    • AstroMan
    • Lights
    • SpaceAudioSource
    • SpaceBackground
    • Fitbox
  • 选择Hierarchy 面板下的Fitbox
  • 拖拽场景中的 AstroMan 到右侧Fitbox的Inspector 面板中的Hologram Collection 属性

发布项目

  • 保存当前场景: File > Save Scene As.
  • 点击 New Folder 命名新文件夹为 Scenes.
  • 将当前场景命名为 “ModelExplorer” 然后保存在刚新建的 Scenes 文件夹下.
  • 返回Unity,选择 File > Build Settings.
  • 点击 Add Open Scenes 添加ModelExplorer场景.
  • 选择 Windows Store然后点击Switch Platform.
  • 设置 SDKUniversal 10Build TypeD3D.
  • 勾选 Unity C# Projects.
  • 点击 Build.
  • 创建一个新的文件夹命名为  "App".
  • 单击App文件夹
  • 选择 Select Folder.
  • 当Unity Build完成后, 一个新的文件窗口会出现.
  • 打开其 App Folder.
  • 打开 ModelExplorer Visual Studio Solution.
  • 在 Visual Studio中, 右击 Package.appxmanifest 文件选择查看代码
  • 定位代码中的 TargetDeviceFamily 然后将名称改掉, Name="Windows.Universal" 变为Name="Windows.Holographic".
  • 点击保存 Package.appxmanifest.
  • 在 Visual Studio顶部工具栏中, 将 Debug 改为 Release ,将 ARM 改为 x86.
  • 点击Device 按钮的下拉箭头, 然后选择远程设备 Remote Machine.
  • 输入你设备的IP地址, 然后将认证模式设为 Universal (Unencrypted Protocol). 点击 Select. 如果你不知道你设备的IP地址, 打开你的设备,在 Settings > Network & Internet > Advanced Options中可以查看到.
  • 在VS的顶部工具栏, 点击 Debug -> Start Without debugging 或者 Ctrl + F5. 如果这是你第一次部署到你的设备, 你需要进行配对 pair it with Visual Studio.
  • 部署完成后,  可以使用选择手势关闭Fixbox.

章节2 光标点与目标反馈

光标设计遵循以下原则:

1 光标要一直出现在视角中

2 光标不能太小也不能太大

3 光标不能遮挡内容

步骤:

  • Hierarchy 面板的顶部点击Create 按钮.
  • 选择 Create Empty.
  • 点击新创建的 GameObject 然后将它名称改为为 "Managers".
  • Hierarchy 面板下, 选择 Managers 对象.
  • Inspector 面板下, 点击 Add Component 按钮.
  • 在搜索框输入 Gaze Manager. 选择此结果.
  • Inspector 面板下, 选择 RaycastLayerMask 下拉单 将勾选的 TransparentFX 去掉.
  • 在project面板下,找到HoloToolkit\Input\Prefabs 文件夹, 找到 Cursor 对象.
  • 拖拽此对象 CursorHierarchy.
  • Hierarchy 面板下, 选择Cursor 对象.
  • Inspector 面板下, 点击Add Component 按钮.
  • 在搜索框输入Cursor Manager. 选择此结果.
  • 展开Hierarchy 面板下的Cursor 对象.
  • 拖拽 CursorOnHolograms 对象到右侧Inspector 面板下的Cursor On Holograms 属性中。
  • 同理拖拽 CursorOffHolograms 对象到右侧Inspector 面板下的  Cursor Off Holograms 属性中。

接下来你需要编辑GazeManager.cs 代码,实现以下几点:

1 执行一个物理射线physics raycast,

2 存储射线交叉点的位置和法线position and normal

3 如果射线没有击中任何对象,将位置与法线设为默认值

GazeManager.cs

using HoloToolkit;
using UnityEngine; /// <summary>
/// GazeManager determines the location of the user's gaze, hit position and normals.
/// </summary>
public class GazeManager : Singleton<GazeManager>
{
[Tooltip("Maximum gaze distance for calculating a hit.")]
public float MaxGazeDistance = 5.0f; [Tooltip("Select the layers raycast should target.")]
public LayerMask RaycastLayerMask = Physics.DefaultRaycastLayers; /// <summary>
/// Physics.Raycast result is true if it hits a Hologram.
/// </summary>
public bool Hit { get; private set; } /// <summary>
/// HitInfo property gives access
/// to RaycastHit public members.
/// </summary>
public RaycastHit HitInfo { get; private set; } /// <summary>
/// Position of the user's gaze.
/// </summary>
public Vector3 Position { get; private set; } /// <summary>
/// RaycastHit Normal direction.
/// </summary>
public Vector3 Normal { get; private set; } private GazeStabilizer gazeStabilizer;
private Vector3 gazeOrigin;
private Vector3 gazeDirection; void Awake()
{
/* TODO: DEVELOPER CODING EXERCISE 3.a */ // 3.a: GetComponent GazeStabilizer and assign it to gazeStabilizer. } private void Update()
{
// 2.a: Assign Camera's main transform position to gazeOrigin.
gazeOrigin = Camera.main.transform.position; // 2.a: Assign Camera's main transform forward to gazeDirection.
gazeDirection = Camera.main.transform.forward; // 3.a: Using gazeStabilizer, call function UpdateHeadStability.
// Pass in gazeOrigin and Camera's main transform rotation. // 3.a: Using gazeStabilizer, get the StableHeadPosition and
// assign it to gazeOrigin. UpdateRaycast();
} /// <summary>
/// Calculates the Raycast hit position and normal.
/// </summary>
private void UpdateRaycast()
{
/* TODO: DEVELOPER CODING EXERCISE 2.a */ // 2.a: Create a variable hitInfo of type RaycastHit.
RaycastHit hitInfo; // 2.a: Perform a Unity Physics Raycast.
// Collect return value in public property Hit.
// Pass in origin as gazeOrigin and direction as gazeDirection.
// Collect the information in hitInfo.
// Pass in MaxGazeDistance and RaycastLayerMask.
Hit = Physics.Raycast(gazeOrigin,
gazeDirection,
out hitInfo,
MaxGazeDistance,
RaycastLayerMask); // 2.a: Assign hitInfo variable to the HitInfo public property
// so other classes can access it.
HitInfo = hitInfo; if (Hit)
{
// If raycast hit a hologram... // 2.a: Assign property Position to be the hitInfo point.
Position = hitInfo.point;
// 2.a: Assign property Normal to be the hitInfo normal.
Normal = hitInfo.normal;
}
else
{
// If raycast did not hit a hologram... // Save defaults ... // 2.a: Assign Position to be gazeOrigin plus MaxGazeDistance times gazeDirection.
Position = gazeOrigin + (gazeDirection * MaxGazeDistance);
// 2.a: Assign Normal to be the user's gazeDirection.
Normal = gazeDirection;
}
}
}

GazeManager

接下来你要编辑 CusorManager.cs 代码实现以下目标:

1 判断哪个光标状态应该被激活,
2 根据光标是否在全息图上来不断更新光标状态
3 始终将光标放在用户正在注视的位置。

CursorManager.cs

using HoloToolkit;
using UnityEngine; /// <summary>
/// CursorManager class takes Cursor GameObjects.
/// One that is on Holograms and another off Holograms.
/// Shows the appropriate Cursor when a Hologram is hit.
/// Places the appropriate Cursor at the hit position.
/// Matches the Cursor normal to the hit surface.
/// </summary>
public class CursorManager : Singleton<CursorManager>
{
[Tooltip("Drag the Cursor object to show when it hits a hologram.")]
public GameObject CursorOnHolograms; [Tooltip("Drag the Cursor object to show when it does not hit a hologram.")]
public GameObject CursorOffHolograms; void Awake()
{
if (CursorOnHolograms == null || CursorOffHolograms == null)
{
return;
} // Hide the Cursors to begin with.
CursorOnHolograms.SetActive(false);
CursorOffHolograms.SetActive(false);
} void Update()
{
/* TODO: DEVELOPER CODING EXERCISE 2.b */ if (GazeManager.Instance == null || CursorOnHolograms == null || CursorOffHolograms == null)
{
return;
} if (GazeManager.Instance.Hit)
{
// 2.b: SetActive true the CursorOnHolograms to show cursor.
CursorOnHolograms.SetActive(true);
// 2.b: SetActive false the CursorOffHolograms hide cursor.
CursorOffHolograms.SetActive(false);
}
else
{
// 2.b: SetActive true CursorOffHolograms to show cursor.
CursorOffHolograms.SetActive(true);
// 2.b: SetActive false CursorOnHolograms to hide cursor.
CursorOnHolograms.SetActive(false);
} // 2.b: Assign gameObject's transform position equals GazeManager's instance Position.
gameObject.transform.position = GazeManager.Instance.Position; // 2.b: Assign gameObject's transform up vector equals GazeManager's instance Normal.
gameObject.transform.up = GazeManager.Instance.Normal;
}
}

CursorManager

接下来可以再次发布部署一次APP,看一下当光标移动到全息图上时光标的变化。

全息图的凝视反馈:

步骤:

  • Hierarchy 面板中, 选择 Managers 对象.
  • 在右侧 Inspector 面板中, 点击 Add Component 按钮.
  • 在搜索框中输入 Interactible Manager. 选择此结果.
  • Hierarchy 面板中, 选择AstroMan 对象.
  • 在右侧 Inspector 面板中, 点击 Add Component 按钮.
  • 在搜索框中输入 Interactible . 选择此结果.

接下来你需要编辑 InteractibleManager.csInteractible.cs 两个代码文件来实现以下功能 :

  1. InteractibleManager.cs 脚本中,获取凝视射线击中的点和保存碰撞对象 collided GameObject.
  2. 当凝视交点在你可以交互的全息对象上时发送 GazeEntered message
  3. 当凝视交点离开你可以交互的全息对象上时发送 GazeExited message
  4. 在Interactible.cs 代码中处理GazeEntered和GazeExited回调。
using HoloToolkit;
using UnityEngine; /// <summary>
/// InteractibleManager keeps tracks of which GameObject
/// is currently in focus.
/// </summary>
public class InteractibleManager : Singleton<InteractibleManager>
{
public GameObject FocusedGameObject { get; private set; } private GameObject oldFocusedGameObject = null; void Start()
{
FocusedGameObject = null;
} void Update()
{
/* TODO: DEVELOPER CODING EXERCISE 2.c */ oldFocusedGameObject = FocusedGameObject; if (GazeManager.Instance.Hit)
{
RaycastHit hitInfo = GazeManager.Instance.HitInfo;
if (hitInfo.collider != null)
{
// 2.c: Assign the hitInfo's collider gameObject to the FocusedGameObject.
FocusedGameObject = hitInfo.collider.gameObject;
}
else
{
FocusedGameObject = null;
}
}
else
{
FocusedGameObject = null;
} if (FocusedGameObject != oldFocusedGameObject)
{
ResetFocusedInteractible(); if (FocusedGameObject != null)
{
if (FocusedGameObject.GetComponent<Interactible>() != null)
{
// 2.c: Send a GazeEntered message to the FocusedGameObject.
FocusedGameObject.SendMessage("GazeEntered");
}
}
}
} private void ResetFocusedInteractible()
{
if (oldFocusedGameObject != null)
{
if (oldFocusedGameObject.GetComponent<Interactible>() != null)
{
// 2.c: Send a GazeExited message to the oldFocusedGameObject.
oldFocusedGameObject.SendMessage("GazeExited");
}
}
}
}

InteractibleManager

using UnityEngine;

/// <summary>
/// The Interactible class flags a Game Object as being "Interactible".
/// Determines what happens when an Interactible is being gazed at.
/// </summary>
public class Interactible : MonoBehaviour
{
[Tooltip("Audio clip to play when interacting with this hologram.")]
public AudioClip TargetFeedbackSound;
private AudioSource audioSource; private Material[] defaultMaterials; void Start()
{
defaultMaterials = GetComponent<Renderer>().materials; // Add a BoxCollider if the interactible does not contain one.
Collider collider = GetComponentInChildren<Collider>();
if (collider == null)
{
gameObject.AddComponent<BoxCollider>();
} EnableAudioHapticFeedback();
} private void EnableAudioHapticFeedback()
{
// If this hologram has an audio clip, add an AudioSource with this clip.
if (TargetFeedbackSound != null)
{
audioSource = GetComponent<AudioSource>();
if (audioSource == null)
{
audioSource = gameObject.AddComponent<AudioSource>();
} audioSource.clip = TargetFeedbackSound;
audioSource.playOnAwake = false;
audioSource.spatialBlend = ;
audioSource.dopplerLevel = ;
}
} /* TODO: DEVELOPER CODING EXERCISE 2.d */ void GazeEntered()
{
for (int i = ; i < defaultMaterials.Length; i++)
{
// 2.d: Uncomment the below line to highlight the material when gaze enters.
defaultMaterials[i].SetFloat("_Highlight", .25f);
}
} void GazeExited()
{
for (int i = ; i < defaultMaterials.Length; i++)
{
// 2.d: Uncomment the below line to remove highlight on material when gaze exits.
defaultMaterials[i].SetFloat("_Highlight", 0f);
}
} void OnSelect()
{
for (int i = ; i < defaultMaterials.Length; i++)
{
defaultMaterials[i].SetFloat("_Highlight", .5f);
} // Play the audioSource feedback when we gaze and select a hologram.
if (audioSource != null && !audioSource.isPlaying)
{
audioSource.Play();
} /* TODO: DEVELOPER CODING EXERCISE 6.a */
// 6.a: Handle the OnSelect by sending a PerformTagAlong message. }
}

Interactible

接下来你可以再一次发布部署到Hololens上查看当凝视点击中全息图时,全息图的反馈状态。

章节3 定位技术

目标:更容易定位到全息对象,稳定且自然到头部移动

步骤:

  1. Hierarchy 面板中, 选择 Managers 对象.
  2. 在右侧 Inspector 面板中, 点击 Add Component 按钮.
  3. 在搜索框中输入 Gaze Stabilizer. 选择此结果.

接下来需要更新GazeManager 脚本

  1. 用VS打开GazeManager脚本 .
  2. 粘贴以下代码到GazeManager.cs
using HoloToolkit;
using UnityEngine; /// <summary>
/// GazeManager determines the location of the user's gaze, hit position and normals.
/// </summary>
public class GazeManager : Singleton<GazeManager>
{
[Tooltip("Maximum gaze distance for calculating a hit.")]
public float MaxGazeDistance = 5.0f; [Tooltip("Select the layers raycast should target.")]
public LayerMask RaycastLayerMask = Physics.DefaultRaycastLayers; /// <summary>
/// Physics.Raycast result is true if it hits a Hologram.
/// </summary>
public bool Hit { get; private set; } /// <summary>
/// HitInfo property gives access
/// to RaycastHit public members.
/// </summary>
public RaycastHit HitInfo { get; private set; } /// <summary>
/// Position of the user's gaze.
/// </summary>
public Vector3 Position { get; private set; } /// <summary>
/// RaycastHit Normal direction.
/// </summary>
public Vector3 Normal { get; private set; } private GazeStabilizer gazeStabilizer;
private Vector3 gazeOrigin;
private Vector3 gazeDirection; void Awake()
{
/* TODO: DEVELOPER CODING EXERCISE 3.a */ // 3.a: GetComponent GazeStabilizer and assign it to gazeStabilizer.
gazeStabilizer = GetComponent<GazeStabilizer>();
} private void Update()
{
// 2.a: Assign Camera's main transform position to gazeOrigin.
gazeOrigin = Camera.main.transform.position; // 2.a: Assign Camera's main transform forward to gazeDirection.
gazeDirection = Camera.main.transform.forward; // 3.a: Using gazeStabilizer, call function UpdateHeadStability.
// Pass in gazeOrigin and Camera's main transform rotation.
gazeStabilizer.UpdateHeadStability(gazeOrigin, Camera.main.transform.rotation); // 3.a: Using gazeStabilizer, get the StableHeadPosition and
// assign it to gazeOrigin.
gazeOrigin = gazeStabilizer.StableHeadPosition; UpdateRaycast();
} /// <summary>
/// Calculates the Raycast hit position and normal.
/// </summary>
private void UpdateRaycast()
{
/* TODO: DEVELOPER CODING EXERCISE 2.a */ // 2.a: Create a variable hitInfo of type RaycastHit.
RaycastHit hitInfo; // 2.a: Perform a Unity Physics Raycast.
// Collect return value in public property Hit.
// Pass in origin as gazeOrigin and direction as gazeDirection.
// Collect the information in hitInfo.
// Pass in MaxGazeDistance and RaycastLayerMask.
Hit = Physics.Raycast(gazeOrigin,
gazeDirection,
out hitInfo,
MaxGazeDistance,
RaycastLayerMask); // 2.a: Assign hitInfo variable to the HitInfo public property
// so other classes can access it.
HitInfo = hitInfo; if (Hit)
{
// If raycast hit a hologram... // 2.a: Assign property Position to be the hitInfo point.
Position = hitInfo.point;
// 2.a: Assign property Normal to be the hitInfo normal.
Normal = hitInfo.normal;
}
else
{
// If raycast did not hit a hologram...
// Save defaults ... // 2.a: Assign Position to be gazeOrigin plus MaxGazeDistance times gazeDirection.
Position = gazeOrigin + (gazeDirection * MaxGazeDistance);
// 2.a: Assign Normal to be the user's gazeDirection.
Normal = gazeDirection;
}
}
}

GazeManager

章节4 方向指示器

给光标添加一个方向箭头使得用户更容易找到全息对象。

步骤:

  • 点击Hierarchy 面板下的AstroMan 对象然后点击小箭头展开它
  • 选中AstroMan下的DirectionalIndicator.
  • 在右侧的 Inspector面板中点击Add Component 按钮.
  • 在搜索框输入Direction Indicator. 选择此结果.
  • 此时拖拽Hierarchy面板下的Cursor 对象 到右侧Inspector面板下Cursor属性中.
  • Project 面板下, 拖拽 Holograms 文件夹下的 DirectionalIndicator 资源到右侧Inspector中的Directional Indicator 属性里
  • 部署发布项目
  • 看方向指示器如何帮助你找到宇航员

章节5 广告牌

我们使用一个广告牌来使得全息对象始终面向用户

  • Hierarchy 面板中, 选择 AstroMan 对象.
  • 在右侧的 Inspector面板中点击Add Component 按钮.
  • 在搜索框输入Billboard. 选择此结果.
  • Inspector面板中Pivot Axis属性设置为Y.
  • 现在可以发布到Hololens上看看效果
  • 看看全息图是不是一直都面向你,无论你怎么转换视角

在做接下来的教程时先把 AstroMan 中的Billboard 脚本删掉

章节6 追随标签

使用追随标签可以使得我们的全息对象追随我们到房间的任何位置。

追随全息对象的设计应遵循以下原则:

1 全息内容应该在视角范围内一眼就可以看到

2全息内容不能显示在用户前进路上

3 头部锁定内容是不舒服的

我们可以想象这个Tag-along全息对象一直保持在我们视角的边缘,无论我们走到哪里,我们都可以一眼就看到它。

步骤:

  1. Hierarchy 面板中, 选择 Managers 对象.
  2. 在右侧 Inspector 面板中, 点击 Add Component 按钮.
  3. 在搜索框中输入  Gesture Manager. 选择此结果.

接下来将使用SimpleTagalong.cs 文件,它会做到:

  1. 确定 Tag-Along 对象是否在摄像机边界内.
  2. 如果不在视椎体内, 定位 Tag-Along 对象部分到摄像机到视椎体内.
  3. 否则, 定位 Tag-Along 对象到离用户固定距离的位置上。

接下来要做:

  • Holograms 文件夹下找到 Tagalong asset并点击.
  • 在右侧 Inspector面板中,  上方有个Tag 下拉列表,点击 Add Tag ….
  • 点击+ ,然后将 Tag 0 命名为 TagAlong.
  • Holograms 文件夹下点击 Tagalong asset然后点击右侧Inspector面板中Tag dropdown.
  • 选择 TagAlong 标签.
  • 我们必须编辑 Interactible.cs 脚本 发送信息到 InteractibleAction.
using UnityEngine;

/// <summary>
/// The Interactible class flags a Game Object as being "Interactible".
/// Determines what happens when an Interactible is being gazed at.
/// </summary>
public class Interactible : MonoBehaviour
{
[Tooltip("Audio clip to play when interacting with this hologram.")]
public AudioClip TargetFeedbackSound;
private AudioSource audioSource; private Material[] defaultMaterials; void Start()
{
defaultMaterials = GetComponent<Renderer>().materials; // Add a BoxCollider if the interactible does not contain one.
Collider collider = GetComponentInChildren<Collider>();
if (collider == null)
{
gameObject.AddComponent<BoxCollider>();
} EnableAudioHapticFeedback();
} private void EnableAudioHapticFeedback()
{
// If this hologram has an audio clip, add an AudioSource with this clip.
if (TargetFeedbackSound != null)
{
audioSource = GetComponent<AudioSource>();
if (audioSource == null)
{
audioSource = gameObject.AddComponent<AudioSource>();
} audioSource.clip = TargetFeedbackSound;
audioSource.playOnAwake = false;
audioSource.spatialBlend = ;
audioSource.dopplerLevel = ;
}
} /* TODO: DEVELOPER CODING EXERCISE 2.d */ void GazeEntered()
{
for (int i = ; i < defaultMaterials.Length; i++)
{
// 2.d: Uncomment the below line to highlight the material when gaze enters.
defaultMaterials[i].SetFloat("_Highlight", .25f);
}
} void GazeExited()
{
for (int i = ; i < defaultMaterials.Length; i++)
{
// 2.d: Uncomment the below line to remove highlight on material when gaze exits.
defaultMaterials[i].SetFloat("_Highlight", 0f);
}
} void OnSelect()
{
for (int i = ; i < defaultMaterials.Length; i++)
{
defaultMaterials[i].SetFloat("_Highlight", .5f);
} // Play the audioSource feedback when we gaze and select a hologram.
if (audioSource != null && !audioSource.isPlaying)
{
audioSource.Play();
} /* TODO: DEVELOPER CODING EXERCISE 6.a */
// 6.a: Handle the OnSelect by sending a PerformTagAlong message.
SendMessage("PerformTagAlong");
}
}

Interactible

InteractibleAction.cs脚本在您注视全息图时执行自定义操作。 让我们更新它与标签一起使用。

  • Complete the coding exercise or change it to this:

    • Hierarchy 面板的顶部的搜索框内输入ChestButton_Center 然后选择它.
    • 在右侧Inspector 面板下点击 Add Component 按钮.
    • 在搜索框内输入 Interactible Action. 并选择
    • 在project面板下 Holograms 文件夹中找到 Tagalong asset.
    • 选中Hierarchy面板下的 ChestButton_Center 对象. 拖拽 TagAlong 对象从 Project 面板到右侧 Inspector 面板中到 Object to TagAlong property.
    • Double click the InteractibleAction script to open it in Visual Studio.
using HoloToolkit;
using UnityEngine; /// <summary>
/// InteractibleAction performs custom actions when you gaze at the holograms.
/// </summary>
public class InteractibleAction : MonoBehaviour
{
[Tooltip("Drag the Tagalong prefab asset you want to display.")]
public GameObject ObjectToTagAlong; void PerformTagAlong()
{
if (ObjectToTagAlong == null)
{
return;
} // Recommend having only one tagalong.
GameObject existingTagAlong = GameObject.FindGameObjectWithTag("TagAlong");
if (existingTagAlong != null)
{
return;
} GameObject instantiatedObjectToTagAlong = GameObject.Instantiate(ObjectToTagAlong); instantiatedObjectToTagAlong.SetActive(true); /* TODO: DEVELOPER CODING EXERCISE 6.b */ // 6.b: AddComponent Billboard to instantiatedObjectToTagAlong.
// So it's always facing the user as they move.
instantiatedObjectToTagAlong.AddComponent<Billboard>(); // 6.b: AddComponent SimpleTagalong to instantiatedObjectToTagAlong.
// So it's always following the user as they move.
instantiatedObjectToTagAlong.AddComponent<SimpleTagalong>(); // 6.b: Set any public properties you wish to experiment with.
}
}

InteractibleAction

发布部署到设备上查看

原文链接https://developer.microsoft.com/en-us/windows/holographic/holograms_210

如有翻译上的错误请指正。谢谢

微软Hololens学院教程-Hologram 210 Gaze(凝视)【微软教程已经更新,本文是老版本】的更多相关文章

  1. 微软Hololens学院教程-Hologram 230-空间场景建模(Spatial mapping )【微软教程已经更新,本文是老版本】

    这是老版本的教程,为了不耽误大家的时间,请直接看原文,本文仅供参考哦!原文链接:https://developer.microsoft.com/EN-US/WINDOWS/HOLOGRAPHIC/ho ...

  2. 微软Hololens学院教程-Hologram 211-Gestures(手势)【微软教程已经更新,本文是老版本】

    这是老版本的教程,为了不耽误大家的时间,请直接看原文,本文仅供参考哦!原文链接:https://developer.microsoft.com/EN-US/WINDOWS/HOLOGRAPHIC/ho ...

  3. 微软Hololens学院教程-Hologram 212-Voice(语音)【微软教程已经更新,本文是老版本】

    这是老版本的教程,为了不耽误大家的时间,请直接看原文,本文仅供参考哦!原文链接:https://developer.microsoft.com/EN-US/WINDOWS/HOLOGRAPHIC/ho ...

  4. 微软Hololens学院教程-Hologram 220-空间声音(Spatial sound )【本文是老版本,与最新的微软教程有出入】

    这是老版本的教程,为了不耽误大家的时间,请直接看原文,本文仅供参考哦! 原文链接https://developer.microsoft.com/EN-US/WINDOWS/HOLOGRAPHIC/ho ...

  5. 微软Hololens学院教程- Holograms 101: Introduction with Device【微软教程已经更新,本文是老版本】

    这是老版本的教程,为了不耽误大家的时间,请直接看原文,本文仅供参考哦!原文链接:https://developer.microsoft.com/EN-US/WINDOWS/HOLOGRAPHIC/ho ...

  6. 微软Hololens学院教程- Holograms 100: Getting Started with Unity【微软教程已经更新,本文是老版本】

    这是老版本的教程,为了不耽误大家的时间,请直接看原文,本文仅供参考哦!原文链接:https://developer.microsoft.com/EN-US/WINDOWS/HOLOGRAPHIC/ho ...

  7. HoloLens开发手记 - Unity之Gaze凝视射线

    凝视是HoloLens首要输入方式,形式功能类似于桌面系统的光标,用于选择操作全息对象.然而在Unity中并没有明确的Gaze API或者组件. 实现Gaze Implementing Gaze 概念 ...

  8. Microsoft HoloLens 开发(3): 全息图交互方式 - Gaze

    Gaze(凝视) 是 HoloLens 交互输入的第一种形式,告诉你 用户 在世界上的位置,并让你确定他们的意图. 1.Gaze的用途 作为一个 Mixed Reality 开发者,Gaze 可以做很 ...

  9. 微软Hololens设备 浅分析

    微软Hololens的定位是一款MR 设备(Mixed reality).MR与AR的不同我认为是MR能够将真实环境的场景信息与虚拟对象进行完美的融合,它是基于SLAM(SimultaneousLoc ...

随机推荐

  1. c++内联函数与静态函数

    不能是虚函数的成员函数有:静态成员函数,内联成员函数,构造函数.没有什么函数需要硬性规定为虚函数,一般析构函数会被定义为虚函数其他就是在继承类中可能需要override的类成员函数应该定义为虚函数 h ...

  2. docker no permmition problem

    resolved by: sudo docker run --privileged ....

  3. mysql的数据导入导出

    1.Navicat for Mysql XML导出导入格式支持二进制数据:虽然同步数据人眼看不出区别,但是java尝试读取数据时,报datetime字段取出的值为“0000-00-00 00:00:0 ...

  4. mkfs.xfs命令没找到

    yum install xfsprogs xfsdump

  5. Echarts基于动态数据初步使用 及问题 代码记录.

    ECHARTS 插件 基本的动态数据展示(横向图) 下载 echarts.commn.min.js文件 在页面中进行引用, 并为Echarts图形准备一个div盒子 <!-- 引入插件 --&g ...

  6. 다음에 적용될 Auto_increment 값 알아 내기 (计算下一个Auto_increment的值)

    Mysql 4.X <------ SHOW TABLE STATUS FROM [DB_NAME] LIKE '[TABLE_NAME]';     Mysql 5.X ----------- ...

  7. OpenWebFlow0.9用户手册与设计说明

    1.    OpenWebFlow概述 OpenWebFlow是基于Activiti扩展的工作流引擎.Activiti (官方网站http://activiti.org/,代码托管在https://g ...

  8. Android Studio如何显示行号

    Android Studio默认没有显示行号,很多同学在使用中很不习惯.本经验介绍怎样让Android Studio显示行号. 首先我们打开我们下载安装好的Android Studio 然后右击工具按 ...

  9. Mysql - 解决Access denied for user ''@'localhost' to database 'mysql'问题

    http://361324767.blog.163.com/blog/static/11490252520124454042468/ 首先我想说一句话: 我极度鄙视国内搞IT的人,简直无语,同样是解决 ...

  10. 3D Touch ? 木有6s,也阔以玩!!!

    3D Touch 之 Peek & Pop 3D Touch 是iOS9之后专为 iPhone6s 机型加入的新特性,这一新技术移植于 Mac Book 上的 ForceTouch 更准确地说 ...