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.结语

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

  • 相关阅读:
    Oracle EBS R12 (12.1.3) Installation Linux(64 bit)
    LINUX的磁盘管理du命令详解
    Solution for Error FRM-92095: Oracle Jnitiator version too low
    EBS learning history (to know about the environment)
    MD5 Checksums for R12.1.1 Rapid Install Media (文档 ID 802195.1)
    adpatch options=hotpatch
    B树和B+树
    Elasticsearch倒排索引
    mysql主从复制
    Found option without preceding group in config file /etc/mysql/my.cnf
  • 原文地址:https://www.cnblogs.com/llstart-new0201/p/12684131.html
Copyright © 2011-2022 走看看