Unity3D for VR —— 学习VR Gaze Input

在VR中,最“贴切”的输入方式是眼神,即 VR Gaze Input,如盯着某UGUI UI、某GameObject,2s后触发事件– 显示ToolTip或者切换场景等。 因为这不需要蓝牙手柄输入,显得更自然且方便,风靡VR Gear的Lamper VR游戏,就是Gaze Input(陀螺仪)的典范—可顺利完成游戏的全部过程,的确很酷。

UGUI UI Gaze 选择

  1. GazeInputModule(继承自PointerInputModule),挂到EventSystem实现。

  2. 通过输入按钮触发选择事件;或者Gaze 2s,触发选择事件。

    这里使用了raycasting,故要求Canvas是Word坐标系,且要求有raphic Raycaster组件,并挂上Center Eye Camera(其他L、R VR Eye未测试)。

  3. EventSystem上,disable StandaloneInputModule & TouchInputModule。

  4. 会触发IPointEnter事件,通过查看Button的源码知道会触发Button.Hightlight高亮

GameObject Gaze 选择

  1. 在上面UGUI的基础上,给Camera添加PhysicsRaycaster组件

  2. 给GameObject,如Cube添加相应EventTriger:通过添加EventTrigger组件或者一个继承IPointDown**的脚本,来响应对应的Event即可。

备注:在UGUI开源工程中,有很多源码值得解读

如:ExecuteEvents.cs,核心代码片段(IEventSystemHandler):

public static bool Execute<T>(GameObject target, BaseEventData eventData, EventFunction<T> functor) where T : IEventSystemHandler 
        { 
            var internalHandlers = s_HandlerListPool.Get(); 
            GetEventList<T>(target, internalHandlers); 
            //    if (s_InternalHandlers.Count > 0) 
            //        Debug.Log(“Executinng ” + typeof (T) + ” on ” + target);
            for (var i = 0; i < internalHandlers.Count; i++) 
            { 
                T arg; 
                try 
                { 
                    arg = (T)internalHandlers[i]; 
                } 
                catch (Exception e) 
                { 
                    var temp = internalHandlers[i]; 
                    Debug.LogException(new Exception(string.Format(“Type {0} expected {1} received.”, typeof(T).Name, temp.GetType().Name), e)); 
                    continue; 
                }
                try 
                { 
                    functor(arg, eventData); 
                } 
                catch (Exception e) 
                { 
                    Debug.LogException(e); 
                } 
            }
            var handlerCount = internalHandlers.Count; 
            s_HandlerListPool.Release(internalHandlers); 
            return handlerCount > 0; 
        }

如:PhysicsRaycaster.cs ,核心代码片段(Physics.RaycastAll):

public override void Raycast(PointerEventData eventData, List<RaycastResult> resultAppendList) 
        { 
            if (eventCamera == null) 
                return;
            var ray = eventCamera.ScreenPointToRay(eventData.position); 
            float dist = eventCamera.farClipPlane – eventCamera.nearClipPlane;
            var hits = Physics.RaycastAll(ray, dist, finalEventMask);
            if (hits.Length > 1) 
                System.Array.Sort(hits, (r1, r2) => r1.distance.CompareTo(r2.distance));
            if (hits.Length != 0) 
            { 
                for (int b = 0, bmax = hits.Length; b < bmax; ++b) 
                { 
                    var result = new RaycastResult 
                    { 
                        gameObject = hits[b].collider.gameObject, 
                        module = this, 
                        distance = hits[b].distance, 
                        worldPosition = hits[b].point, 
                        worldNormal = hits[b].normal, 
                        screenPosition = eventData.position, 
                        index = resultAppendList.Count, 
                        sortingLayer = 0, 
                        sortingOrder = 0 
                    }; 
                    resultAppendList.Add(result); 
                } 
            } 
        }

源码下载地址:http://pan.baidu.com/s/1hqYX2Ry

【按住Alt + 鼠标。 到Cube上后,2s触发“Selected”事件】


转自赛隆网 http://www.cylonspace.com/

标签: unity, vr, unity3d for vr 学习

?>