zoukankan      html  css  js  c++  java
  • (十一)自定义VrInputModule

    1.前言

    本文基于InputModule的逻辑,根据VR的操作特点,写一个VrInputModule。

    2.Input

    虚拟一个Input类,来获取最基本的信息,如下代码所示(示意代码):

    using UnityEngine;
    using System.Collections;
    
    public class GazeInput : MonoBehaviour
    {
        public Vector2 GetGazePosition()
        {
            return new Vector2(Screen.width/2, Screen.height/2);
        }
    
        public Vector2 GetGazeDelta()
        {
            //TODO:Get position delta or rotation delta;
            return new Vector2(0, 0);
        }
    }
    
    

    3.自定义InputModule

    using System.Collections;
    using System.Collections.Generic;
    using UnityEngine;
    using UnityEngine.EventSystems;
    
    public class GazeInputModule : BaseInputModule
    {
        [SerializeField]
        private float dragThreshold = 10;
    
        private PointerEventData pointer;
    
        private GazeInput gaze;
    
        private GazeInput gazeInput
        {
            get
            {
                if (gaze == null)
                {
                    gaze = GetComponent<GazeInput>();
                }
    
                return gaze;
            }
        }
    
        private PointerEventData GetGazePointerEventData(out bool pressed,out bool released)
        {
            if (pointer == null)
            {
                pointer = new PointerEventData(eventSystem);
                pointer.dragging = false;
            }
    
            pressed = PressedThisFrame();
            released = ReleasedThisFrame();
    
            pointer.position = gazeInput.GetGazePosition();
            pointer.delta = gazeInput.GetGazeDelta();
    
            eventSystem.RaycastAll(pointer, m_RaycastResultCache);
            pointer.pointerCurrentRaycast = FindFirstRaycast(m_RaycastResultCache);
            m_RaycastResultCache.Clear();
    
            return pointer;
        }
    
        private void ProcessGazePress(PointerEventData pointerData, bool pressed, bool released)
        {
            GameObject currentOverGo = pointerData.pointerCurrentRaycast.gameObject;
    
            if (pressed)
            {
                pointerData.eligibleForClick = true;
                pointer.dragging = false;
                pointerData.pressPosition = pointerData.position;
                pointerData.pointerPressRaycast = pointerData.pointerCurrentRaycast;
    
                //Selected and deselected event are neglected
    
                GameObject newPressed = ExecuteEvents.ExecuteHierarchy(currentOverGo, pointerData, ExecuteEvents.pointerDownHandler);
    
                if (newPressed == null)
                {
                    newPressed = ExecuteEvents.GetEventHandler<IPointerClickHandler>(currentOverGo);
                }
    
                pointerData.pointerPress = newPressed;
                pointerData.rawPointerPress = currentOverGo;
    
                pointerData.pointerDrag = ExecuteEvents.GetEventHandler<IDragHandler>(currentOverGo);
    
                if (pointerData.pointerDrag != null)
                {
                    ExecuteEvents.Execute(pointerData.pointerDrag, pointerData, ExecuteEvents.initializePotentialDrag);
                }
            }
    
            if (released)
            {
                ExecuteEvents.Execute(pointerData.pointerPress, pointerData, ExecuteEvents.pointerUpHandler);
    
                GameObject pointerClickHandler = ExecuteEvents.GetEventHandler<IPointerClickHandler>(currentOverGo);
    
                if (pointerData.pointerPress == pointerClickHandler && pointerData.eligibleForClick)
                {
                    ExecuteEvents.Execute(pointerData.pointerPress, pointerData, ExecuteEvents.pointerClickHandler);
                }
                else if(pointerData.pointerDrag != null && pointerData.dragging)
                {
                    ExecuteEvents.ExecuteHierarchy(currentOverGo, pointerData, ExecuteEvents.dropHandler);
                }
    
                pointerData.eligibleForClick = false;
                pointerData.pointerPress = null;
                pointerData.rawPointerPress = null;
    
                if (pointerData.pointerDrag != null && pointerData.dragging)
                    ExecuteEvents.Execute(pointerData.pointerDrag, pointerData, ExecuteEvents.endDragHandler);
    
                pointerData.dragging = false;
                pointerData.pointerDrag = null;
    
                if (currentOverGo != pointerData.pointerEnter)
                {
                    HandlePointerExitAndEnter(pointerData, null);
                    HandlePointerExitAndEnter(pointerData, currentOverGo);
                }
            }
        }
    
        private void ProcessMove(PointerEventData pointerData)
        {
            HandlePointerExitAndEnter(pointerData, pointerData.pointerCurrentRaycast.gameObject);
        }
    
        private void ProcessDrag(PointerEventData pointerData)
        {
            if (!ShoundProcessDrag(pointerData))
                return;
    
            if (!pointerData.dragging)
            {
                ExecuteEvents.Execute(pointerData.pointerDrag, pointerData, ExecuteEvents.beginDragHandler);
                pointerData.dragging = true;
            }
    
            if (pointerData.dragging)
            {
                if (pointerData.pointerPress != pointerData.pointerDrag)
                {
                    ExecuteEvents.Execute(pointerData.pointerPress, pointerData, ExecuteEvents.pointerUpHandler);
                    pointerData.eligibleForClick = false;
                    pointerData.pointerPress = null;
                    pointerData.rawPointerPress = null;
                }
    
                ExecuteEvents.Execute(pointerData.pointerDrag, pointerData, ExecuteEvents.dragHandler);
            }
        }
    
        public override void Process()
        {
            bool pressed, released;
            PointerEventData eventData = GetGazePointerEventData(out pressed, out released);
    
            ProcessGazePress(eventData, pressed, released);
    
            if (!eventData.dragging)
            {
                ProcessMove(eventData);
            }
    
            if (!released)
            {
                ProcessDrag(eventData);
            }
        }
    
        private bool PressedThisFrame()
        {
            return Input.GetKeyDown(KeyCode.KeypadEnter);
        }
    
        private bool ReleasedThisFrame()
        {
            return Input.GetKeyUp(KeyCode.KeypadEnter); ;
        }
    
        private bool ShoundProcessDrag(PointerEventData pointerData)
        {
            return Mathf.Abs(pointerData.delta.x) > dragThreshold || Mathf.Abs(pointerData.delta.y) > dragThreshold;
        }
    }
    
    

    4.结语

    强迫症晚期,没有结语。。。。。。。。

  • 相关阅读:
    HDU3910(数学期望题,题目难懂)
    HDU2389(二分图匹配Hopcroft-Carp算法)
    二分图详解
    巴什博弈、威佐夫博弈、尼姆博弈
    HDU2819(二分图匹配,记录过程)
    查找外键未创建索引
    acl使用示例
    oracle数据库备份任务
    集中备份相关
    集中备份项目实施方案
  • 原文地址:https://www.cnblogs.com/llstart-new0201/p/12684131.html
Copyright © 2011-2022 走看看