Пример #1
0
        public void Update()
        {
            if (!CommonScriptableObjects.rendererState.Get() || charCamera == null)
            {
                return;
            }

            IWorldState worldState = Environment.i.world.state;

            // We use Physics.Raycast() instead of our raycastHandler.Raycast() as that one is slower, sometimes 2x, because it fetches info we don't need here
            bool   didHit         = Physics.Raycast(GetRayFromCamera(), out hitInfo, Mathf.Infinity, PhysicsLayers.physicsCastLayerMaskWithoutCharacter);
            bool   uiIsBlocking   = false;
            string currentSceneId = worldState.currentSceneId;

            bool validCurrentSceneId = !string.IsNullOrEmpty(currentSceneId);
            bool validCurrentScene   = validCurrentSceneId && worldState.loadedScenes.ContainsKey(currentSceneId);

            // NOTE: in case of a single scene loaded (preview or builder) sceneId is set to null when stepping outside
            if (didHit && validCurrentSceneId && validCurrentScene)
            {
                UIScreenSpace    currentUIScreenSpace = worldState.loadedScenes[currentSceneId].GetSharedComponent <UIScreenSpace>();
                GraphicRaycaster raycaster            = currentUIScreenSpace?.graphicRaycaster;

                if (raycaster)
                {
                    uiGraphicRaycastPointerEventData.position = new Vector2(Screen.width / 2, Screen.height / 2);
                    uiGraphicRaycastResults.Clear();
                    raycaster.Raycast(uiGraphicRaycastPointerEventData, uiGraphicRaycastResults);
                    uiIsBlocking = uiGraphicRaycastResults.Count > 0;
                }
            }

            if (!didHit || uiIsBlocking)
            {
                clickHandler = null;
                UnhoverLastHoveredObject(hoverController);
                return;
            }

            var raycastHandlerTarget = hitInfo.collider.GetComponent <IRaycastPointerHandler>();

            if (raycastHandlerTarget != null)
            {
                ResolveGenericRaycastHandlers(raycastHandlerTarget);
                UnhoverLastHoveredObject(hoverController);
                return;
            }

            if (CollidersManager.i.GetColliderInfo(hitInfo.collider, out ColliderInfo info))
            {
                newHoveredEvent = info.entity.gameObject.GetComponentInChildren <IPointerEvent>();
            }
            else
            {
                newHoveredEvent = hitInfo.collider.GetComponentInChildren <IPointerEvent>();
            }

            clickHandler = null;

            if (!EventObjectCanBeHovered(info, hitInfo.distance))
            {
                UnhoverLastHoveredObject(hoverController);
                return;
            }

            newHoveredGO = newHoveredEvent.GetTransform().gameObject;

            if (newHoveredGO != lastHoveredObject)
            {
                UnhoverLastHoveredObject(hoverController);

                lastHoveredObject    = newHoveredGO;
                lastHoveredEventList = newHoveredGO.GetComponents <IPointerEvent>();
                OnPointerHoverStarts?.Invoke();
            }

            // OnPointerDown/OnClick and OnPointerUp should display their hover feedback at different moments
            if (lastHoveredEventList != null && lastHoveredEventList.Length > 0)
            {
                for (int i = 0; i < lastHoveredEventList.Length; i++)
                {
                    IPointerEvent e = lastHoveredEventList[i];

                    bool eventButtonIsPressed = InputController_Legacy.i.IsPressed(e.GetActionButton());

                    bool isClick = e.GetEventType() == PointerEventType.CLICK;
                    bool isDown  = e.GetEventType() == PointerEventType.DOWN;
                    bool isUp    = e.GetEventType() == PointerEventType.UP;

                    if (isUp && eventButtonIsPressed)
                    {
                        e.SetHoverState(true);
                    }
                    else if ((isDown || isClick) && !eventButtonIsPressed)
                    {
                        e.SetHoverState(true);
                    }
                    else
                    {
                        e.SetHoverState(false);
                    }
                }
            }

            newHoveredGO    = null;
            newHoveredEvent = null;
        }
Пример #2
0
        private void ProcessButtonDown(WebInterface.ACTION_BUTTON buttonId, bool useRaycast, LayerMask pointerEventLayer, int globalLayer)
        {
            IWorldState    worldState = Environment.i.world.state;
            RaycastHitInfo raycastGlobalLayerHitInfo;
            Ray            ray = GetRayFromCamera();

            // Raycast for pointer event components
            RaycastResultInfo raycastInfoPointerEventLayer = raycastHandler.Raycast(ray, charCamera.farClipPlane, pointerEventLayer, worldState.loadedScenes[worldState.currentSceneId]);

            // Raycast for global pointer events
            RaycastResultInfo raycastInfoGlobalLayer = raycastHandler.Raycast(ray, charCamera.farClipPlane, globalLayer, worldState.loadedScenes[worldState.currentSceneId]);

            raycastGlobalLayerHitInfo = raycastInfoGlobalLayer.hitInfo;

            bool isOnClickComponentBlocked = IsBlockingOnClick(raycastInfoPointerEventLayer.hitInfo, raycastGlobalLayerHitInfo);

            if (!isOnClickComponentBlocked && raycastInfoPointerEventLayer.hitInfo.hit.collider)
            {
                Collider collider = raycastInfoPointerEventLayer.hitInfo.hit.collider;

                GameObject hitGameObject;

                if (CollidersManager.i.GetColliderInfo(collider, out ColliderInfo info))
                {
                    hitGameObject = info.entity.gameObject;
                }
                else
                {
                    hitGameObject = collider.gameObject;
                }

                var events = hitGameObject.GetComponentsInChildren <IPointerEvent>();

                for (var i = 0; i < events.Length; i++)
                {
                    IPointerEvent e             = events[i];
                    bool          areSameEntity = AreSameEntity(e, info);

                    switch (e.GetEventType())
                    {
                    case PointerEventType.CLICK:
                        if (areSameEntity)
                        {
                            e.Report(buttonId, ray, raycastInfoPointerEventLayer.hitInfo.hit);
                        }
                        break;

                    case PointerEventType.DOWN:
                        if (areSameEntity)
                        {
                            e.Report(buttonId, ray, raycastInfoPointerEventLayer.hitInfo.hit);
                        }
                        break;

                    case PointerEventType.UP:
                        if (areSameEntity)
                        {
                            pointerUpEvent = e;
                        }
                        else
                        {
                            pointerUpEvent = null;
                        }
                        break;
                    }
                }

                lastPointerDownEventHitInfo = raycastInfoPointerEventLayer.hitInfo;
            }

            ReportGlobalPointerDownEvent(buttonId, useRaycast, raycastGlobalLayerHitInfo, raycastInfoGlobalLayer, worldState.currentSceneId);

            // Raycast for global pointer events (for each PE scene)
            List <string> currentPortableExperienceIds = WorldStateUtils.GetActivePortableExperienceIds();

            for (int i = 0; i < currentPortableExperienceIds.Count; i++)
            {
                raycastInfoGlobalLayer    = raycastHandler.Raycast(ray, charCamera.farClipPlane, globalLayer, worldState.loadedScenes[currentPortableExperienceIds[i]]);
                raycastGlobalLayerHitInfo = raycastInfoGlobalLayer.hitInfo;

                ReportGlobalPointerDownEvent(buttonId, useRaycast, raycastGlobalLayerHitInfo, raycastInfoGlobalLayer, currentPortableExperienceIds[i]);
            }
        }