/*
* ==================================================================================================================
*
* UnityVersion : 2021.3.6f1
* Description : 眼部交互基类
* Author:
* CreateTime : 2023-10-11 09:43:20
* Version : V1.0.0
*
* ==================================================================================================================
*/
using System.Collections.Generic;
using Microsoft.MixedReality.Toolkit.Input;
using UnityEngine;
namespace MRTKExtend.EyeTracking
{
[RequireComponent(typeof(Collider))]
public abstract class BaseFocus : MonoBehaviour, IMixedRealityFocusHandler, IMixedRealityFocusChangedHandler
{
[SerializeField] [Tooltip("是否启用焦点?")] private bool focusEnabled = true;
/// <summary>
/// 是否为启用了焦点
/// </summary>
public virtual bool FocusEnabled
{
get => focusEnabled;
set => focusEnabled = value;
}
/// <summary>
/// 此对象当前是否有焦点
/// </summary>
public virtual bool HasFocus => FocusEnabled && Focusers.Count > 0;
/// <summary>
/// 当前聚焦此对象的列表
/// </summary>
public List<IMixedRealityPointer> Focusers { get; } = new(0);
/// <summary>
/// 焦点进入
/// </summary>
public virtual void OnFocusEnter(FocusEventData eventData)
{
}
/// <summary>
/// 焦点退出
/// </summary>
public virtual void OnFocusExit(FocusEventData eventData)
{
}
public virtual void OnBeforeFocusChange(FocusEventData eventData)
{
//如果是新的目标对象,将指针添加到焦点列表。
if (eventData.NewFocusedObject == gameObject)
{
eventData.Pointer.FocusTarget = this;
Focusers.Add(eventData.Pointer);
}
//如果是旧的聚焦目标对象,从列表中删除指针。
else if (eventData.OldFocusedObject == gameObject)
{
Focusers.Remove(eventData.Pointer);
//如果没有新的焦点目标,从指针中清除焦点目标。
if (eventData.NewFocusedObject == null)
{
eventData.Pointer.FocusTarget = null;
}
}
}
public virtual void OnFocusChanged(FocusEventData eventData)
{
}
}
}
/*
* ==================================================================================================================
*
* UnityVersion : 2021.3.6f1
* Description : 眼部交互
* Author:
* CreateTime : 2023-10-11 09:21:40
* Version : V1.0.0
*
* ==================================================================================================================
*/
using System;
using Microsoft.MixedReality.Toolkit.Input;
using UnityEngine;
namespace MRTKExtend.EyeTracking
{
public abstract class BaseEyeFocus : BaseFocus
{
[Tooltip("可配置的持续时间,用于在用户查注释目标的时间超过此持续时间时触发事件。")] [SerializeField] [Range(0, 20)]
private float timeToTriggerDwellInSec = 5;
/// <summary>
/// 停留时间
/// </summary>
private DateTime _dwellTimer;
/// <summary>
/// 是否持续注视
/// </summary>
private bool _isDwelling = false;
/// <summary>
/// 是否注视
/// </summary>
private bool _hadFocus = false;
/// <summary>
/// 处理光标进入目标时的突出显示目标。
/// </summary>
protected virtual void Update()
{
if (!HasFocus && _hadFocus)
{
OnEyeFocusStop();
_isDwelling = false;
_hadFocus = false;
}
else if (HasFocus)
{
if (!_hadFocus)
{
OnEyeFocusStart();
_dwellTimer = DateTime.UtcNow;
_hadFocus = true;
}
else
{
OnEyeFocusStay();
if (!_isDwelling && (DateTime.UtcNow - _dwellTimer).TotalSeconds > timeToTriggerDwellInSec)
{
OnEyeFocusDwell();
_isDwelling = true;
}
}
}
}
/// <inheritdoc />
public override void OnBeforeFocusChange(FocusEventData eventData)
{
//如果注视新的目标对象,将指针添加到焦点列表。
if (eventData.NewFocusedObject == gameObject &&
eventData.Pointer.InputSourceParent.SourceType == InputSourceType.Eyes)
{
eventData.Pointer.FocusTarget = this;
Focusers.Add(eventData.Pointer);
}
//如果注视是旧的聚焦目标对象,从列表中删除指针。
else if (eventData.OldFocusedObject == gameObject)
{
Focusers.Remove(eventData.Pointer);
// 如果没有新目标,从指针中清除焦点目标
if (eventData.NewFocusedObject == null)
{
eventData.Pointer.FocusTarget = null;
}
}
}
/// <summary>
///一旦眼睛凝视射线开始与该目标的碰撞体接触,就会触发。
/// </summary>
protected virtual void OnEyeFocusStart()
{
}
/// <summary>
/// 在眼睛凝视射线与该目标的碰撞体持续接触时触发。
/// </summary>
protected virtual void OnEyeFocusStay()
{
}
/// <summary>
///一旦眼睛凝视射线停止与该目标的碰撞体,就会触发。
/// </summary>
protected virtual void OnEyeFocusStop()
{
}
/// <summary>
/// 一旦眼睛凝视射线与该目标的碰撞体接触指定时间后触发。
/// </summary>
protected virtual void OnEyeFocusDwell()
{
}
}
}
/*
* ==================================================================================================================
*
* UnityVersion : 2021.3.6f1
* Description : 功能描述
* Author:
* CreateTime : 2023-10-10 16:09:27
* Version : V1.0.0
*
* ==================================================================================================================
*/
using MRTKExtend.EyeTracking;
using UnityEngine;
public class EyeTrackingTest : BaseEyeFocus
{
protected override void OnEyeFocusStay()
{
Debug.Log("OnEyeFocusStay");
//todo something
RotateHitTarget();
}
protected override void OnEyeFocusStart()
{
Debug.Log("OnEyeFocusStart");
//todo something
}
protected override void OnEyeFocusStop()
{
Debug.Log("OnEyeFocusStop");
//todo something
}
protected override void OnEyeFocusDwell()
{
Debug.Log("OnEyeFocusDwell");
//todo something
}
private void RotateHitTarget()
{
transform.localEulerAngles += new Vector3(0, 0.1f, 0);
}
}
在场景中新建一个物体,将EyeTrackingTest组件挂载到新建的物体上就可以了
文章来源地址https://www.toymoban.com/news/detail-721757.html
文章来源:https://www.toymoban.com/news/detail-721757.html
到了这里,关于Unity MRTK Hololens2眼动交互的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!